You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
docs(adr): anchor the multi-org entitlement to ADR-0105 D12 (#8531 claim D) (#9069)
"Multi-organization operation is a commercial ENTITLEMENT" was cited in 15
places as "ADR-0081 D2". ADR-0081 in this repo is the trusted `kind:'react'`
page tier; its Decision section is numbered 1-4, so "D2" names nothing in it.
The label is inherited from a pre-repo decision record whose number now
collides -- the same collision ADR-0093 D9 named for the "ADR-0081 D1" half.
ADR-0105 D12 (Edition split, as amended 2026-07-27 by the founder ruling in
#3570) already IS this decision: posture activation is entitled, both walled
postures probe `@objectstack/organizations` to activate, and without it the
tenancy service resolves to single + degraded. No anchor is invented here.
The repo had already converged on that anchor everywhere else -- auth-plugin.ts,
harness.posture-only.test.ts, harness.host-resolution.test.ts, the serve e2e
test and content/docs/deployment/tenancy-modes.mdx all cite ADR-0105 D12 for
this exact claim. These 15 were the stragglers.
Re-points 13 sites to ADR-0105 D12. The 2 sites inside ADR-0105 itself cannot
cite ADR-0105 D12 -- they ARE D12 -- and both sentences refer to the inherited
prior line D12 affirms, so they are de-numbered descriptively instead, matching
the language ADR-0093 already uses for the same pre-repo record. D12 gains a
citation note (hygiene, explicitly not a decision) warning that the anchor is
D12, not this ADR's own D2 (`accessible_org_ids`).
Claims B and C of #8531 (`ensureDefaultOrganization` bootstrap, the org
capability gate) are untouched -- all 22 `ADR-0081 D1` sites remain as they are,
including those in files edited here. Both need a new owning record, which is a
maintainer act.
Behaviour unchanged: 10 comments, 3 documentation strings, no logic.
Part of #8531
Claude-Session: https://claude.ai/code/session_011RB4waLuNbdruCo6X9oobm
Co-authored-by: Claude <noreply@anthropic.com>
// unit-proven at the plugin-security layer, like the #2937 row above. ──
98
98
{id: 'tenancy-posture-spectrum',summary: 'three tenancy postures — single | group | isolated (ADR-0105 D1/D2)',state: 'enforced',
99
99
enforcement: 'plugin-auth/tenancy-service.ts resolves the posture in force; plugin-security/tenant-layer.ts computeTenantLayer0Filter switches the Layer 0 predicate on it — inert (single), `organization_id IN accessible_org_ids` (group, MOAC union), `organization_id = activeOrganizationId` (isolated); empty/absent scope → RLS_DENY_FILTER',
100
-
note: 'Only the PREDICATE widens; composition is untouched — Layer 0 is still computed independently of the RLS compiler, AND-composed outermost, and crossable only by a true PLATFORM_ADMIN on a posture-permitting object, so ADR-0095 W1/W2 hold in every posture. BOTH walled postures require the enterprise @objectstack/organizations runtime to ACTIVATE and can resolve degraded without it (ADR-0081 D2): the wall\'s IMPLEMENTATION is open, but enabling multi-organization operation is an entitlement, and the runtime may narrow it further via `supportedPostures`. Cloud ADR-0016\'s 铁律 is satisfied by REFUSING to run an unwalled multi-org deployment (ADR-0093 D5), not by giving the posture away. Unit-proven in plugin-security/tenant-layer.test.ts and plugin-auth/tenancy-service.test.ts.'},
100
+
note: 'Only the PREDICATE widens; composition is untouched — Layer 0 is still computed independently of the RLS compiler, AND-composed outermost, and crossable only by a true PLATFORM_ADMIN on a posture-permitting object, so ADR-0095 W1/W2 hold in every posture. BOTH walled postures require the enterprise @objectstack/organizations runtime to ACTIVATE and can resolve degraded without it (ADR-0105 D12): the wall\'s IMPLEMENTATION is open, but enabling multi-organization operation is an entitlement, and the runtime may narrow it further via `supportedPostures`. Cloud ADR-0016\'s 铁律 is satisfied by REFUSING to run an unwalled multi-org deployment (ADR-0093 D5), not by giving the posture away. Unit-proven in plugin-security/tenant-layer.test.ts and plugin-auth/tenancy-service.test.ts.'},
enforcement: 'core/security/resolve-authz-context.ts resolveUserAuthzGrants reads every sys_member row for the user under ADR-0091 validity windows; carried on ExecutionContext by every transport (rest-server, runtime resolve-execution-context, mcp, hono) and read directly by the Layer 0 group wall',
103
103
note: 'ONE read serves both the active-org position projection and the full membership set, so the two facts cannot disagree. A transport that fails to carry the set denies under `group` rather than falling back to the active org — the wall must not depend on which surface the request arrived through. Delegated (on-behalf-of) reads resolve the DELEGATOR\'s own set (explain-engine buildContextForUser), never inherit the live principal\'s.'},
0 commit comments