Skip to content

test(qa): record the ADR-0091 grant validity-window primitive in the authz conformance matrix - #9376

Merged
os-zhuang merged 1 commit into
mainfrom
claude/issue-8811-adr-0091-validity-window-row
Aug 17, 2026
Merged

os-zhuang merged 1 commit into
mainfrom
claude/issue-8811-adr-0091-validity-window-row

Conversation

@os-zhuang

Copy link
Copy Markdown
Contributor

Fixes #8811

The ADR-0056 D10 matrix states "one row per authorization primitive, each in EXACTLY ONE honest state", but carried no row for the ADR-0091 grant validity windows. This adds it, mirroring the ADR-0049/#8613 active-flag disposition: an enforced row with no covers, documented as a statement about the ratchet's reach rather than an assertion the ratchet checks.

The row's enforced claim was verified at the call sites, not taken from the filing

The card named isGrantActive at "three call sites" in resolve-authz-context.ts. Measured on the branch point, the raw count of 5 there decomposes as 1 import + 1 comment + 3 real call sites — so the count is right, but two of the card's other premises are not:

1. The primitive's enforcement is much broader than one file. isGrantActive is applied at every seam that turns a window-carrying row into authority — 7 non-test files: resolve-authz-context.ts (steps 4 and 6), explain-engine.ts, position-graph.ts, delegated-admin-gate.ts, last-admin-guard.ts, approval-service.ts, and runtime/domains/keys.ts. The row names all of them.

2. The card's description of call site 1 is wrong, and it matters. The card says the sys_member call happens "before the membership role projection". It does not: the predicate gates the accessible_org_ids accumulation, while the role projection beside it iterates the unfiltered array. That is exactly #8802.

Why the honest state is still enforced rather than partial

The window columns are declared on exactly three objects — sys_user_position, sys_user_permission_set, sys_approval_delegation — and on all three, every authorization-resolution seam applies the predicate. sys_member carries no window columns at all, so both the filtered call and the unfiltered projection beside it are no-ops today; the asymmetry is latent, not live. That reading is corroborated in-repo by last-admin-guard.ts, which already records that "ADR-0091 windows are not columns on sys_member today" and that the resolver "is where the two halves have to be reconciled first" if they ever land.

The second unfiltered read, plugin-approvals' own expandPositionUsers, is a ruled-intentional divergence (#8710) because approval routing is not grant resolution — its own note explicitly forbids "fixing" it with a filter.

Both carve-outs are stated in the row's note, since stating what is and is not mechanically checked is this file's own convention for honesty. #8802 is not addressed here and remains open: it is a defect in the enforcement, not in the ledger, and closing it leaves this row exactly as owed.

Header counts refreshed

The header's measured numbers move with the new row and were recomputed rather than incremented: 43 of 50 becomes 44 of 51 rows with no covers (7 rows / 9 keys unchanged), and 37 of 43 becomes 38 of 44 enforced rows in the in-resolver shape.

No interaction with #9083

checkTransportWiredAdmission iterates covers entries only. This row declares none, so the TRANSPORT-WIRED admission rule is untouched — confirmed by reading the function and by the "the real matrix declares no TRANSPORT-WIRED key today" non-vacuity test staying green.

Verification — all at 08f4bd5

Reverse-verified rather than assumed green: removing the enforcement string from the new row turns the gate red across 6 tests, naming the row by id (grant-validity-window: enforced but names no enforcement site). Restored from the commit, byte-identical.

Gate CI job Result
authz-conformance.test.ts (targeted) Test 21/21 pass
full @objectstack/dogfood suite Test 110 files, 786 pass, 3 skipped
@objectstack/dogfood typecheck TypeScript Type Check pass
check:empty-state, check:liveness, check:strictness-ledger, check:variant-docs spec-liveness-check pass
check:test-source-alias, check:type-source-resolution ESLint pass
check-affected-docs.mjs docs-drift-check pass
check:nul-bytes ESLint pass

Gate set derived by re-running node scripts/pm/dispatch-gates.mjs against the actual changed path; the derivation named 7 families and all were run.

No changeset — skip-changeset

The diff is one test-only file inside @objectstack/dogfood, which is private: true. It publishes nothing and changes no runtime behaviour, so there is no user-visible change to describe.


Generated by Claude Code

…authz conformance matrix (#8811)

The ADR-0056 D10 matrix states one row per authorization primitive in exactly
one honest state, but carried no row for the ADR-0091 grant validity windows —
the only mentions were incidental. Adds the `grant-validity-window` row as
`enforced` with no `covers`, mirroring the ADR-0049/#8613 `active`-flag
disposition, and refreshes the header counts the new row moves.

Co-Authored-By: Claude <noreply@anthropic.com>
@os-zhuang os-zhuang added the skip-changeset PR has no user-facing published change; bypasses the changeset gate label Aug 17, 2026 — with Claude
@github-actions

Copy link
Copy Markdown
Contributor

📓 Docs Drift Check

1 anchor(s) derived from 1 changed package(s); no hand-written page names any of them. ✅

What this run could not see
  • 2 name(s) were too generic to anchor anything (single lowercase words)

Coarse fallback — 2 page(s) merely mention a changed package (the pre-#9192 predicate, kept for the deliberately-wide backstop): node scripts/docs-audit/affected-docs.mjs --json origin/main → packageMentionDocs.

@os-zhuang
os-zhuang marked this pull request as ready for review August 17, 2026 20:05
@os-zhuang
os-zhuang added this pull request to the merge queue Aug 17, 2026
Merged via the queue into main with commit d6e7935 Aug 17, 2026
30 checks passed
@os-zhuang
os-zhuang deleted the claude/issue-8811-adr-0091-validity-window-row branch August 17, 2026 20:26
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

size/s skip-changeset PR has no user-facing published change; bypasses the changeset gate

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants