V1 Web PWA · Surface walkthrough

Aja Data Retention

A per-surface walkthrough of the V1 Web PWA studio surface: layout, states, interactions, data, and cross-references.

walked
8sections3 minread

On this page

Context. surface studio · domain aja · route /studio/aja/data-retention · auth signed-in + studio entitlement · source apps/oshun/web/src/app/studio/aja/data-retention/page.tsx

Last walked. 2026-07-26 authority-boundary runtime coverage — unbound deploy authority, disabled mutations, responsive layout, and automated WCAG 2.1 AA scan

Purpose#

Admin lane console for data-retention governance. The taxonomy catalog is always available, but policies and evaluations are authoritative only when the BFF is explicitly bound to an owning deploy service used by storage lifecycle and deletion executors. The default deployment is currently unbound: it reports aja_data_retention_authority_not_configured, disables both forms, and returns 503 for direct mutation/evaluation requests. AjaDataRetentionStore is retained only as an explicitly injected process-local test/development adapter.

Entry points#

  • Direct URL/studio/aja/data-retention (signed-in + studio entitlement)
  • Breadcrumb — Studio / Aja Content Security / Data Retention
  • Sibling quick-actions from this page — Content Security, Content Moderation, Content Watermarking, Privacy Protection, Back to Studio

Layout regions#

page.tsx mounts ShellLayout with active="studio" and renders four panels.

  • Breadcrumb panel (data-aja-data-retention-breadcrumbs): nav aria-label="Aja Data Retention breadcrumbs" — Studio (link) / Aja Content Security (link) / Data Retention (aria-current="page")
  • Workspace panel (data-aja-data-retention-workspace):
    • <h1> "Aja Data Retention Workspace" (via WorkspaceHeading)
    • <p data-aja-data-retention-summary> — inspect the retention taxonomy and, when its owning authority is connected, create policies or evaluate records
    • The retention-policies section (<h2> "Retention policies (N)" + list + create form) and the "Evaluate a record" section (<h2> + evaluate form)
  • Route Map panel (data-aja-data-retention-route-map): <h2> "Route Map" + one <article> per STUDIO_AJA_DATA_RETENTION_ROUTE_MAP entry (6 entries)
  • Quick actions panel: .quickAction <Link>s — see Interactions

States#

  • Loadingdata-aja-dr-loading "Loading retention policies…"
  • Unauthorized — on 401/403, data-aja-dr-unauthorized ("Access restricted." + reason, default "Aja workspace scope required to view data retention.")
  • Error — non-OK / malformed / unreachable → data-aja-dr-error
  • Ready (forms) — catalog present: policy list (data-aja-dr-policy per category), create-policy form, evaluate form
  • Authority unavailabledata-aja-authority-status="data-retention" names the boundary; both forms are disabled and emit no request
  • Resultdata-aja-dr-evaluation (with data-aja-dr-expired attribute) shows data-aja-dr-applicable (applicable policy name or "none"), expires, expired

Interactions#

Create-policy form (data-aja-dr-policy-form)#

This form is enabled only when authority.configured is true.

  • Nameinput data-aja-dr-field-name
  • Categoryselect data-aja-dr-field-category (from catalog.categories)
  • Retention valueinput data-aja-dr-field-value (number)
  • Unitselect data-aja-dr-field-unit (from catalog.units)
  • Basisselect data-aja-dr-field-basis (from catalog.bases)
  • Create policybutton data-aja-dr-policy-submit; POST /v1/admin/aja/data-retention/policies with { name, category, retention: { value, unit }, retentionBasis, priority }, then reloads the catalog

Evaluate form (data-aja-dr-evaluate-form)#

This form is enabled only when authority.configured is true.

  • Categoryselect data-aja-dr-eval-category (from catalog.categories)
  • Created-at ISOinput data-aja-dr-eval-created
  • Legal holdinput data-aja-dr-eval-legal-hold (checkbox)
  • Evaluatebutton data-aja-dr-evaluate-submit; POST /v1/admin/aja/data-retention/evaluate with { category, createdAtIso, hasLegalHold }

Route Map panel (data-aja-data-retention-route-map)#

Non-interactive <article> blocks from STUDIO_AJA_DATA_RETENTION_ROUTE_MAP (6 entries): /studio/aja/data-retention plus …/scenes/[sceneId], …/exports/[exportId], …/revisions/[revisionId], …/parity/[parityId], …/governance/[policyId].

Quick actions panel#

  • Open Aja Content Security workspace/studio/aja/content-security
  • Open Aja Content Moderation workspace/studio/aja/content-moderation
  • Open Aja Content Watermarking workspace/studio/aja/content-watermarking
  • Open Aja Privacy Protection workspace/studio/aja/privacy-protection
  • Back to Studio workspace index/studio

Data & contracts#

  • Reads: GET /v1/admin/aja/data-retention (catalog: authority, policies, categories, units, bases) on mount via buildBffAuthHeaders(), cache: 'no-store'
  • Writes: POST …/policies (creates a policy, then re-reads the catalog); POST …/evaluate{ applicablePolicy, expired, expiresAtIso }; valid requests return 503 while the deploy authority is unbound
  • Realtime: none
  • Caching: client fetch on mount (no-store); SSR shell only
  • Auth: BFF endpoints admin-scoped + fail-closed (401/403 → unauthorized render); the route is signed-in + studio (proxy gate)

Cross-references#

  • Parent: ../../studio-overview.md
  • Component sources:
    • apps/oshun/web/src/components/studio/StudioAjaDataRetentionWorkspace.tsx
    • apps/oshun/web/src/components/studio/StudioAjaDataRetentionRouteMap.ts
  • Siblings from quick-actions: /studio/aja/content-security, /studio/aja/content-moderation, /studio/aja/content-watermarking, /studio/aja/privacy-protection

Open questions / known gaps#

  • Bind an owning durable retention service that the real storage lifecycle and deletion executors consume, including legal-hold and subject deletion/export semantics, before enabling production decisions
  • Route-map sub-routes (scenes/exports/revisions/parity/governance) are descriptive only; confirm implementation status
  • Document the exact studio entitlement / proxy gate governing /studio/aja/*