---
id: ATS-PFM-CSH-013
scope: CAP-PFM-CSH-013
product_area: platform
module: console-shell
revision: 3
status: proposed
approved_by: null
approved_at: null
source_sha:
  react-console: baf6dae382d6f41dce976c7f848667ccc37e076f
  services-platform: ad3f6a6582843008ed0f5a17b131878d15829af1
  rhythm-v2-docs: 25e253cb434aac6603ee294e3ca197ab6c4bfd0b
scenarios:
  - id: ATS-PFM-CSH-013-01
    title: Staff root landing retains memory without selecting it
    level: browser
    proves:
      - BR-CAP-PFM-CSH-013-06
    preconditions: Staff memory names a workspace covered by a standing grant.
    steps: Open the bare root after storing that choice.
    expected: >-
      HQ links appear without a workspace selector or access banner; browser
      memory still holds the reachable choice.
    negative: false
    data_needs: >-
      An isolated browser context with the stated identity, workspace and
      response fixtures.
    bound_to:
      - TST-PFM-CSH-013
    provenance: test
    source: >-
      react-console:e2e/mock/staff-landing.mock.spec.ts#a staff member with a
      remembered tenant and a standing grant lands on /hq in HQ context
    category: transition
    test_sources:
      - >-
        react-console:e2e/mock/staff-landing.mock.spec.ts#a staff member with a
        remembered tenant and a standing grant lands on /hq in HQ context
    action_evidence:
      provenance: test
      source: >-
        react-console:e2e/mock/staff-landing.mock.spec.ts#a staff member with a
        remembered tenant and a standing grant lands on /hq in HQ context
    assertion_evidence:
      provenance: test
      source: >-
        react-console:e2e/mock/staff-landing.mock.spec.ts#a staff member with a
        remembered tenant and a standing grant lands on /hq in HQ context
  - id: ATS-PFM-CSH-013-02
    title: A cleared bookmark enters its workspace from both starts
    level: browser
    proves:
      - BR-CAP-PFM-CSH-013-07
    preconditions: A standing staff grant covers the bookmarked workspace.
    steps: >-
      Open its bookmark through sign-in and separately from an existing HQ
      session.
    expected: >-
      Both starts reach the requested workspace destination with its query
      retained.
    negative: false
    data_needs: >-
      An isolated browser context with the stated identity, workspace and
      response fixtures.
    bound_to:
      - TST-PFM-CSH-014
      - TST-PFM-CSH-009
    provenance: test
    source: >-
      react-console:e2e/mock/url-architecture.mock.spec.ts#a staff member's
      bookmark into a standing-grant tenant opens that page and query, from
      Rhythm HQ too
    category: interaction
    test_sources:
      - >-
        react-console:e2e/mock/url-architecture.mock.spec.ts#a staff member's
        bookmark into a standing-grant tenant opens that page and query, from
        Rhythm HQ too
      - >-
        react-console:e2e/mock/url-architecture.mock.spec.ts#a staff member with
        a grant goes straight into the tenant
      - >-
        react-console:e2e/dev/url-architecture.dev.spec.ts#signed out: sign-in
        comes back to that page and query in that tenant
      - >-
        react-console:e2e/dev/url-architecture.dev.spec.ts#signed in on Rhythm
        HQ: opening it goes straight into the tenant
    action_evidence:
      provenance: test
      source: >-
        react-console:e2e/mock/url-architecture.mock.spec.ts#a staff member's
        bookmark into a standing-grant tenant opens that page and query, from
        Rhythm HQ too
    assertion_evidence:
      provenance: test
      source: >-
        react-console:e2e/mock/url-architecture.mock.spec.ts#a staff member's
        bookmark into a standing-grant tenant opens that page and query, from
        Rhythm HQ too
  - id: ATS-PFM-CSH-013-03
    title: The working mode determines frame and personal navigation
    level: browser
    proves:
      - BR-CAP-PFM-CSH-013-02
      - BR-CAP-PFM-CSH-013-05
    preconditions: A staff fixture can use both HQ and a customer workspace.
    steps: 'Inspect header, main navigation and personal actions in both contexts.'
    expected: >-
      HQ presents staff navigation and its label; workspace mode presents
      customer work, selection and the return to HQ.
    negative: false
    data_needs: >-
      An isolated browser context with the stated identity, workspace and
      response fixtures.
    bound_to: []
    provenance: proposed
    source: 'react-console:components/console/app-sidebar.tsx:MainNavigation'
    category: invariant
    test_sources: []
    action_evidence:
      provenance: proposed
      source: 'react-console:components/console/app-sidebar.tsx:MainNavigation'
    assertion_evidence:
      provenance: proposed
      source: 'react-console:components/console/app-sidebar.tsx:MainNavigation'
  - id: ATS-PFM-CSH-013-04
    title: Refused staff entry returns to HQ without emergency access
    category: interaction
    level: browser
    proves:
      - BR-CAP-PFM-CSH-013-01
      - INV-DOM-PFM-CSH-003-01
    preconditions: A staff account lacks clearance for the requested workspace.
    steps: Open that workspace bookmark through sign-in with a controlled refusal.
    expected: >-
      HQ opens with a notice naming the refused workspace; neither an
      emergency-access dialog nor a workspace access banner appears.
    negative: false
    data_needs: >-
      A fresh browser context, isolated account fixtures and controlled
      responses for the listed transitions.
    bound_to:
      - TST-PFM-CSH-005
    provenance: test
    source: >-
      react-console:e2e/controlled/staff-deep-link.controlled.spec.ts#an
      uncleared staff member's deep link goes to Rhythm HQ with a notice, not
      the emergency-access dialog
    test_sources:
      - >-
        react-console:e2e/controlled/staff-deep-link.controlled.spec.ts#an
        uncleared staff member's deep link goes to Rhythm HQ with a notice, not
        the emergency-access dialog
    action_evidence:
      provenance: test
      source: >-
        react-console:e2e/controlled/staff-deep-link.controlled.spec.ts#an
        uncleared staff member's deep link goes to Rhythm HQ with a notice, not
        the emergency-access dialog
    assertion_evidence:
      provenance: test
      source: >-
        react-console:e2e/controlled/staff-deep-link.controlled.spec.ts#an
        uncleared staff member's deep link goes to Rhythm HQ with a notice, not
        the emergency-access dialog
evidence:
  - >-
    react-console at baf6dae:
    components/console/{use-shell-mode.ts,app-sidebar.tsx,site-header.tsx,nav-config.ts},
    components/console/hq/{staff-landing-gate,staff-context-gate}.tsx,
    lib/security-context/boot.ts, docs/url-architecture.md §6, §11 item 24,
    e2e/mock/{staff-landing,url-architecture}.mock.spec.ts,
    e2e/dev/url-architecture.dev.spec.ts,
    e2e/controlled/staff-deep-link.controlled.spec.ts.
  - >-
    services-platform at ad3f6a6: modules/security/aws/api/access.routes.ts
    (getMySecurityContext with tenant_id and preferred_tenant_id,
    getMySecurityContextInTenant; MOD-PFM-SEC).
  - >-
    rhythm-v2-docs at 25e253cb434aac6603ee294e3ca197ab6c4bfd0b: capability,
    related capabilities, domain objects, client lifecycles, workflows and prior
    OpenAI examinations; continuation coverage limitations are recorded in
    FND-PFM-CSH-063.
coverage:
  rule: 'gap: FND-PFM-CSH-063'
  transition: 'gap: FND-PFM-CSH-063'
  validation: 'gap: FND-PFM-CSH-063'
  permission: 'gap: FND-PFM-CSH-063'
  edge: 'gap: FND-PFM-CSH-063'
  failure: 'gap: FND-PFM-CSH-063'
  boundary: 'gap: FND-PFM-CSH-063'
  concurrency: 'gap: FND-PFM-CSH-063'
  invariant: 'gap: FND-PFM-CSH-063'
  interaction: 'gap: FND-PFM-CSH-063'
coverage_notes:
  rule:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: >-
      No dedicated scenario establishes this category; applicability and the
      required fixtures need review.
  transition:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: >-
      The associated lifecycle has additional transitions beyond the specified
      cases.
  validation:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: >-
      No dedicated scenario establishes this category; applicability and the
      required fixtures need review.
  permission:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: >-
      The named permission keys still need a complete allowed, denied and scope
      matrix across their enforcement boundaries.
  edge:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: >-
      No dedicated scenario establishes this category; applicability and the
      required fixtures need review.
  failure:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: >-
      No dedicated scenario establishes this category; applicability and the
      required fixtures need review.
  boundary:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: >-
      No dedicated scenario establishes this category; applicability and the
      required fixtures need review.
  concurrency:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: >-
      No complete scenario matrix covers repeated events, overlapping reads or
      superseded answers for this capability.
  invariant:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: Associated object invariants remain without explicit proving scenarios.
  interaction:
    provenance: unknown
    source: FND-PFM-CSH-063
    reason: >-
      Related-capability combinations remain unspecified beyond the interactions
      listed.
design_obligations:
  - artifact: STATE-PFM-CSH-001
    provenance: documented
    source: >-
      rhythm-v2-docs:specs/platform/console-shell/design/state-models/STATE-PFM-CSH-001-console-start-up-and-working-context.md
    transitions:
      - ordinal: 1
        from: loading
        to: unconfigured
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:boot
          (missingConfiguration)
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 2
        from: loading
        to: signing-in
        provenance: test
        source: >-
          react-console:e2e/dev/url-architecture.dev.spec.ts#a signed-out deep
          link goes through sign-in and comes back to the same page and query
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 3
        from: loading
        to: no-access
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:boot
          (PermissionDeniedError)
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 4
        from: loading
        to: failed
        provenance: observed
        source: 'react-console:lib/security-context/provider.tsx:boot'
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 5
        from: loading
        to: ready
        provenance: test
        source: >-
          react-console:lib/security-context/boot.test.ts;
          e2e/controlled/tenant-unavailable.controlled.spec.ts#falls back to the
          default tenant, with a word of explanation, rather than refusing
          access
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 6
        from: failed
        to: failed
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:SecurityContextProvider
          (attempt)
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 7
        from: ready
        to: changing-workspace
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:openTenantId,
          leaveTenant
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 8
        from: changing-workspace
        to: ready
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:openTenantId (ticket),
          leaveTenant
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 9
        from: changing-workspace
        to: failed
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:switchTenant (no
          screen calls it at the pinned commit)
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 10
        from: ready
        to: ended
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:signOut,
          onSessionEnded listener
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 11
        from: no-access
        to: ended
        provenance: observed
        source: >-
          react-console:components/console/console-boot-screens.tsx:consoleBootScreens
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 12
        from: failed
        to: ended
        provenance: observed
        source: >-
          react-console:components/console/console-boot-screens.tsx:consoleBootScreens
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 13
        from: ready
        to: ready
        provenance: observed
        source: 'react-console:lib/security-context/provider.tsx:leaveTenant'
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 14
        from: failed
        to: ready
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:SecurityContextProvider
          (boot)
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 15
        from: failed
        to: no-access
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:SecurityContextProvider
          (boot)
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 16
        from: failed
        to: unconfigured
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:SecurityContextProvider
          (boot)
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 17
        from: failed
        to: signing-in
        provenance: observed
        source: >-
          react-console:lib/security-context/provider.tsx:SecurityContextProvider
          (boot)
        disposition: 'gap: FND-PFM-CSH-063'
    note: >-
      The finding carries exhaustive transition execution coverage; overlapping
      scenario examples do not close the remaining lifecycle matrix.
  - artifact: STATE-PFM-CSH-002
    provenance: documented
    source: >-
      rhythm-v2-docs:specs/platform/console-shell/design/state-models/STATE-PFM-CSH-002-workspace-entry-from-an-address.md
    transitions:
      - ordinal: 1
        from: resolving
        to: entered
        provenance: test
        source: >-
          react-console:e2e/mock/url-architecture.mock.spec.ts#a record deep
          link survives a reload
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 2
        from: resolving
        to: waiting-after-leave
        provenance: observed
        source: >-
          react-console:components/console/tenant-id-gate.tsx:TenantIdGate
          (wasJustLeft, JUST_LEFT_RETRY_MS)
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 3
        from: waiting-after-leave
        to: resolving
        provenance: observed
        source: 'react-console:components/console/tenant-id-gate.tsx:TenantIdGate'
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 4
        from: resolving
        to: not-found
        provenance: test
        source: >-
          react-console:e2e/mock/url-architecture.mock.spec.ts#an id no tenant
          has shows not found
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 5
        from: resolving
        to: denied
        provenance: test
        source: >-
          react-console:components/console/__tests__/tenant-id-gate.test.tsx#leaves
          anyone else on the access-denied page
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 6
        from: denied
        to: sent-to-hq
        provenance: observed
        source: >-
          react-console:components/console/tenant-id-gate.tsx:deniedDestination,
          TenantIdGate
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 7
        from: resolving
        to: unavailable
        provenance: test
        source: >-
          react-console:components/console/__tests__/tenant-id-gate.test.tsx#says
          the workspace is unavailable, never no access, with the way back for
          staff
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 8
        from: resolving
        to: failed
        provenance: observed
        source: >-
          react-console:lib/security-context/tenant-id.ts:TenantIdUnconfirmedError;
          components/console/tenant-id-gate.tsx
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 9
        from: not-found
        to: resolving
        provenance: observed
        source: 'react-console:components/console/tenant-id-gate.tsx:rememberedRefusal'
        disposition: 'gap: FND-PFM-CSH-063'
      - ordinal: 10
        from: denied
        to: resolving
        provenance: observed
        source: 'react-console:components/console/tenant-id-gate.tsx:rememberedRefusal'
        disposition: 'gap: FND-PFM-CSH-063'
    note: >-
      The finding carries exhaustive transition execution coverage; overlapping
      scenario examples do not close the remaining lifecycle matrix.
interactions:
  - capability: CAP-PFM-CSH-010
    provenance: unknown
    source: FND-PFM-CSH-063
  - capability: CAP-PFM-CSH-012
    provenance: unknown
    source: FND-PFM-CSH-063
  - capability: CAP-PFM-CSH-005
    provenance: unknown
    source: FND-PFM-CSH-063
  - capability: CAP-PFM-CSH-006
    provenance: unknown
    source: FND-PFM-CSH-063
workflow_obligations:
  - artifact: WF-PFM-CSH-001
    provenance: documented
    source: >-
      rhythm-v2-docs:specs/platform/console-shell/design/workflows/WF-PFM-CSH-001-start-the-console-and-settle-the-working-context.md
    disposition: 'gap: FND-PFM-CSH-063'
    note: >-
      Review every hop, branch, failure and race with the cited capability
      scenarios; unexecuted combinations remain in the coverage finding.
  - artifact: WF-PFM-CSH-002
    provenance: documented
    source: >-
      rhythm-v2-docs:specs/platform/console-shell/design/workflows/WF-PFM-CSH-002-enter-the-workspace-an-address-names.md
    disposition: 'gap: FND-PFM-CSH-063'
    note: >-
      Review every hop, branch, failure and race with the cited capability
      scenarios; unexecuted combinations remain in the coverage finding.
  - artifact: WF-PFM-CSH-004
    provenance: documented
    source: >-
      rhythm-v2-docs:specs/platform/console-shell/design/workflows/WF-PFM-CSH-004-leave-a-workspace-for-rhythm-hq.md
    disposition: 'gap: FND-PFM-CSH-063'
    note: >-
      Review every hop, branch, failure and race with the cited capability
      scenarios; unexecuted combinations remain in the coverage finding.
  - artifact: WF-PFM-CSH-006
    provenance: documented
    source: >-
      rhythm-v2-docs:specs/platform/console-shell/design/workflows/WF-PFM-CSH-006-resolve-an-older-console-address.md
    disposition: 'gap: FND-PFM-CSH-063'
    note: >-
      Review every hop, branch, failure and race with the cited capability
      scenarios; unexecuted combinations remain in the coverage finding.
  - artifact: WF-PFM-CSH-007
    provenance: documented
    source: >-
      rhythm-v2-docs:specs/platform/console-shell/design/workflows/WF-PFM-CSH-007-assemble-the-navigation-menu.md
    disposition: 'gap: FND-PFM-CSH-063'
    note: >-
      Review every hop, branch, failure and race with the cited capability
      scenarios; unexecuted combinations remain in the coverage finding.
---

# Keep staff work and workspace work in distinct contexts: Capability Test Specification

## Coverage

The coverage map describes specified proof, not a passing run. Each mandatory rule below has a scenario or an explicit finding; a proposed scenario remains an execution obligation even when its expected outcome follows the pinned implementation.

| Mandatory Rule | Scenarios or Finding |
|---|---|
| `BR-CAP-PFM-CSH-013-01` | `ATS-PFM-CSH-013-04` |
| `BR-CAP-PFM-CSH-013-02` | `ATS-PFM-CSH-013-03` |
| `BR-CAP-PFM-CSH-013-05` | `ATS-PFM-CSH-005-05`, `ATS-PFM-CSH-013-03` |
| `BR-CAP-PFM-CSH-013-06` | `ATS-PFM-CSH-012-05`, `ATS-PFM-CSH-013-01` |
| `BR-CAP-PFM-CSH-013-07` | `ATS-PFM-CSH-013-02` |

HQ departure needs cache clearing before local removal, failed cleanup, retained context after a failed refresh and immediate re-entry races. Staff identity controls menu mode; the listed permission keys do not themselves prove every menu action is gated.

## Interactions With Related Capabilities

HQ opens with a notice naming the refused workspace; neither an emergency-access dialog nor a workspace access banner appears.

The interaction rows cite the contracts they exercise. Related combinations without a complete case remain in the coverage finding, together with cross-capability workflows and permission boundaries. A helper assertion is bound only for its stated outcome; the full browser handoff remains proposed until a suite checks it.


Pinned source and exact test anchors are recorded in frontmatter. Test bindings record static assertion review and use the executable-suite register; no product test result is inferred from that review. The prior planning and design examinations supply context, while this continuation records the remaining proof obligations explicitly.
