This is an internal working record, not an everyday instruction. It was written while the system was being rebuilt, for whoever maintains it. If you are here to do today's work, use the everyday documents instead: Procedures · Processes · Runbooks · The working day, step by step
Platform Authorization And Access — Policy And Sequence Catalog¶
- Status:
SOURCE-RECONCILED PLATFORM POLICY/DIAGRAM INPUT / NO RUNTIME CHANGE - Current source baseline:
qa/master@3c084671c034f8f5136b02dce990ecff6c66d107 - Source authority:
PLATFORM_AUTHORIZATION_ACCESS_SOURCE_AUTHORITY.md - Rebuild packet:
PLATFORM_AUTHORIZATION_ACCESS_REBUILD_PACKET.md - Phase implementation:
USER HOLD
1. Core Boundary¶
Menu
-> helps users discover work
Page guard
-> controls one page entry
API route guard
-> controls one transport entry
Action policy
-> controls one semantic command/query
Record predicate
-> controls one tenant/relationship record
State policy
-> controls whether the command is valid now
These layers cooperate but do not replace one another.
2. Current Page Request Sequence¶
sequenceDiagram
actor User
participant Shell as index.php
participant Role as Menu/Page Role Helper
participant Module as Module Guard
participant Page as PHP Page
participant API
User->>Shell: /?page=route
Shell->>Shell: normalize route + file exists
alt physical super-admin
Shell->>Role: super-admin/impersonation page decision
else tenant user
Shell->>Role: getPageRoleAccessDecision
end
Role-->>Shell: known/allowed
Shell->>Module: moduleGuardPageDecision
Module-->>Shell: allowed/known/reason
alt denied or unavailable
Shell-->>User: Access Denied / Feature Not Available
else allowed
Shell->>Page: include page
Page->>API: initial queries/actions
Note over API: API performs its own guards
end
Page entry does not pre-authorize the page's APIs.
3. Current Menu/Page Fail-Open Paths¶
flowchart TD
Req[Page/Menu decision] --> DB{Menu/Module source available?}
DB -->|yes| Found{Matching explicit row?}
Found -->|yes| Role{Role/module/config allow?}
Role -->|yes| Allow[Allow]
Role -->|no| Deny[Deny]
Found -->|no page menu| Admin{Role 1 compatibility?}
Admin -->|yes| CompatAdmin[Allow / known=false]
Admin -->|no| Deny
DB -->|menu DB error| CompatOpen[Allow / known=false]
DB -->|missing tenant module| ModuleCompat[Module default allow]
DB -->|module DB error| ModuleCompat
This diagram records current compatibility. It is not target policy.
4. Current API v2 Sequence¶
sequenceDiagram
actor Client
participant Router as API v2 Router
participant Auth
participant Tenant as Optional Strict Principal
participant Module
participant Menu
participant Role
participant Handler
participant Repo
Client->>Router: method + route
Router->>Auth: authenticated?
opt strictTenantPrincipal
Router->>Tenant: build strict actor/subject/tenant context
end
Router->>Module: moduleKey
Router->>Menu: requiredMenuRoutes
Router->>Role: requiredRoleIds
Router->>Handler: request context/body
Handler->>Repo: tenant/record/state-specific query or mutation
Repo-->>Handler: result
Handler-->>Client: response
The router does not prove record ownership/state by itself.
5. Current Legacy TYPE/ACTION Sequence¶
sequenceDiagram
actor Client
participant Endpoint as Legacy post/query endpoint
participant Auth
participant Module
participant Menu
participant Handler as TYPE/ACTION Handler
participant DB
Client->>Endpoint: TYPE + ACTION + DATA
Endpoint->>Auth: session login check
Endpoint->>Module: TYPE/ACTION module mapping
opt selected endpoint/caller
Endpoint->>Menu: owning menu route
end
Endpoint->>Handler: effective scalar user/client/advancedOperations
Handler->>DB: handler-owned role/tenant/state logic
DB-->>Handler: result
Handler-->>Client: legacy response envelope
API v2 and legacy endpoint evidence must be tested separately until caller-zero.
6. UI Visibility Versus Backend Authorization¶
sequenceDiagram
actor User
participant ReactOrPHP as UI
participant Access as Visibility Query
participant API as Backend Command
participant Policy
ReactOrPHP->>Access: GetVisibleActions
Access-->>ReactOrPHP: show/hide/disabled hints
User->>API: direct or UI command request
API->>Policy: AuthorizeCommand again
alt denied
API-->>User: stable denial
else allowed
API-->>User: command result
end
Required rule:
UI hidden is not a security boundary.
7. Record Authorization¶
sequenceDiagram
participant Adapter as Page/API Adapter
participant Access as Access Policy
participant Repo as Owning Repository
participant App as Application Command
Adapter->>Access: actor/subject/tenant + action + record ref
Access->>Repo: minimal tenant/relation projection
alt missing/foreign/wrong relation
Repo-->>Access: denied/not-found disposition
Access-->>Adapter: stable safe denial
else record belongs to context
Repo-->>Access: authorized record projection + state/version
Access->>App: permission context
App->>App: validate domain state transition
App-->>Adapter: result or record-state denial
end
Authorization does not duplicate the application's transition rules.
8. Physical Super-Admin And Impersonation¶
flowchart TD
Actor[Physical Super Admin?] -->|no| Normal[Normal role/action policy]
Actor -->|yes| Mode{Access mode}
Mode -->|Admin diagnostic override| Allowlist[Require allowlisted resource + authorization ref]
Mode -->|User impersonation| Subject[Evaluate target subject role/action + actor restrictions]
Mode -->|Tenant-only impersonation| Support[Evaluate explicit support/diagnostic capabilities]
Mode -->|No tenant target| Console[Platform admin surfaces only]
Target rule:
Original super-admin status remains audit lineage.
It is not an automatic permit for every impersonated business action.
9. Target Access Decision Sequence¶
sequenceDiagram
actor User
participant UI as React UI
participant Next as Next.js Adapter
participant Identity
participant Platform as Module/Capability/Config
participant Access
participant Repo
participant App
participant Audit
User->>UI: open/act
UI->>Next: request
Next->>Identity: actor/subject/tenant
Identity-->>Next: strict context
Next->>Platform: resolve availability/prerequisites
Platform-->>Next: module/capability/config/credential results
Next->>Access: evaluate action + record reference
Access->>Repo: tenant/relation projection
Repo-->>Access: minimal record/state/version
Access-->>Next: ALLOW/DENY/UNAVAILABLE/UNKNOWN
alt ALLOW
Next->>App: execute owning command/query
App->>Audit: transition/result evidence
App-->>UI: exact result/readback
else not allowed
Next->>Audit: safe decision evidence
Next-->>UI: stable safe reason/recovery
end
10. Target Access Decision State¶
stateDiagram-v2
[*] --> Unknown
Unknown --> Allow: every required check PASS
Unknown --> Deny: actor/action/record not permitted
Unknown --> Unavailable: module/capability/config/credential unavailable
Allow --> Deny: policy/role/record changes before command
Allow --> Unavailable: prerequisite changes before command
Allow --> Unknown: policy/source cannot be reread
note right of Unknown
Consequential writes do not execute.
Existing compatibility migrates by cohort.
end note
11. Selected Strict-Rollout Sequence¶
sequenceDiagram
participant Current as Current Decision
participant Target as Target Read Shadow
participant Matrix as Role/API/Record Matrix
participant Release
Current->>Target: same request inputs
Target-->>Matrix: shadow decision + reasons
Current-->>Matrix: current observed decision
Matrix->>Matrix: compare allow/deny/unavailable and negative cases
alt accepted parity
Matrix->>Release: select one route/action cohort
Release->>Target: target authoritative
else mismatch
Matrix->>Current: keep current authority
end
No global switch.
12. Rollback Sequence¶
sequenceDiagram
participant Operator
participant Router
participant Current as Previous Decision Owner
participant Target as New Decision Owner
participant Audit
Operator->>Router: rollback selected cohort
Router->>Target: stop authoritative decisions
Router->>Current: restore previous accepted decision
Router->>Audit: record rollback version/reason
Operator->>Router: run allow/deny/foreign/state smoke
Router-->>Operator: exact parity readback
Rollback does not reopen unrelated access.
13. Policy Decisions¶
| ID | Decision | Status |
|---|---|---|
ACC-POL-010 |
unknown consequential write | TARGET DENY / CURRENT MIGRATION REQUIRED |
ACC-POL-020 |
unknown read | CALLER-SPECIFIC OPEN |
ACC-POL-030 |
missing tenant-module row | PARITY SEED BEFORE STRICT |
ACC-POL-040 |
module source error | OPEN |
ACC-POL-050 |
unmapped page | INVENTORY REQUIRED |
ACC-POL-060 |
unregistered role-1 page access | OPEN |
ACC-POL-070 |
super-admin bypass categories | OPEN |
ACC-POL-080 |
impersonation action policy | REQUIRED |
ACC-POL-090 |
tenant-only support mode actions | OPEN / DIAGNOSTIC PREFERRED |
ACC-POL-100 |
record 403/404 disclosure | OPEN |
ACC-POL-110 |
menu prerequisite in target | COMPATIBILITY INPUT ONLY |
ACC-POL-120 |
numeric roles to semantic capabilities | REQUIRED FOR TARGET |
ACC-POL-130 |
virtual menu policies | OPEN OWNER MIGRATION |
ACC-POL-140 |
UI visible actions | SAME INPUTS / BACKEND RECHECK |
ACC-POL-150 |
print/direct page aliases | OPEN |
ACC-POL-160 |
legacy TYPE/ACTION retirement | REQUIRED BY CALLER-ZERO |
ACC-POL-170 |
redacted access diagnostics | RECOMMENDED |
ACC-POL-180 |
Client 1 broad guard rollout | PROHIBITED WITHOUT FULL EVIDENCE |
14. Stable Decision Reasons¶
Suggested target reason families:
authentication_required
session_invalid
tenant_context_required
tenant_forbidden
module_disabled
module_unknown
capability_disabled
capability_unavailable
config_unavailable
credential_unavailable
menu_required
page_forbidden
api_forbidden
role_denied
action_denied
record_not_found_or_denied
record_relation_denied
record_state_denied
override_forbidden
impersonation_restricted
policy_stale
policy_source_error
unknown
Current reasons are mapped, not silently replaced, during read shadow.
15. Support Decision Tree¶
flowchart TD
Start[User cannot see/use action] --> Auth{Authenticated?}
Auth -->|no| Login[Resolve session/login]
Auth -->|yes| Tenant{Correct tenant/subject?}
Tenant -->|no| Context[End/fix impersonation or target]
Tenant -->|yes| Module{Module/capability/config available?}
Module -->|no| Owner[Escalate to platform/config owner]
Module -->|yes| Page{Menu/page/API allowed?}
Page -->|no| Role[Review role/action policy]
Page -->|yes| Record{Record belongs and relation valid?}
Record -->|no| Deny[Safe denied/not-found]
Record -->|yes| State{Record state valid?}
State -->|no| Process[Escalate to process owner]
State -->|yes| Unknown[Collect request ID and decision trace]
16. Update Triggers¶
Update this catalog when any accepted change affects:
- authentication/session/tenant inputs;
- menu/role/page helpers;
- module/config availability;
- API route metadata;
- legacy endpoint guard;
- semantic action capability;
- record tenant/relation predicate;
- state-transition owner;
- super-admin/impersonation behavior;
- direct page/print aliases;
- UI action visibility;
- stable access errors/reasons;
- read-shadow/cutover/rollback;
- Client 1/Client 2 role matrix.
Diagrams explain contracts; they do not activate access-policy changes.
---¶
Source:
docs/processes/PLATFORM_AUTHORIZATION_ACCESS_POLICY_AND_SEQUENCE.md— ctc repository · This page is an English translation of the source document. Identifiers, file paths and code symbols are unchanged.