Repository navigation
Commit be318db
<!-- claude-projects-attribution: {"github_login":"os-sales"} -->
_Requested by **Sales** · [project
thread](https://claude.ai/code/project/chan_01D5bWFY3rFzgJcytD5gD4Uu?thread=cmsg_01D5bWFY3rFzgJcytD5gD4UuMYdF2uchcinMphEKW4sYxd)_
Part of #25223
Clause-②: no
Metadata-protocol: none
Ruling-ref: 6353073966
Cut 5 of the `security-plugin.ts` split: step 3.7's Layer 0 tenant write
wall. The claim is 6357083478. The body of one async method,
`composeWriteTenantWall`, moves unedited to the new module
`packages/plugins/plugin-security/src/security-plugin-write-tenant-wall.ts`.
It composes the wall once for one write:
- the ADR-0123 D2 scope pre-test, which refuses a write when the context
has no active organization, ordered ahead of the forge guard;
- the parts every row is held to: the caller's Layer 0 (ADR-0095 D1)
and, on an on-behalf-of write, the delegator's (ADR-0090 D10);
- the judgements that read those parts: the payload half, and the
stored-image seam with its landing refusals (#24784, #24821) and
`judgesOrganization` (#24822).
Nothing in it logs or throws. The middleware's step 3.7 logs and throws
each refusal through `raiseWriteWallRefusal`, and the write preview
`writeWallVerdict` answers it as a row's verdict. Both stay in the class
and still call the method.
It is move-only, and the card stays open for the later cuts. Branch:
`claude/project-thread-3fzya4`, the harness-pinned branch for this
session, restarted from `origin/main` at `4d7e2b1f38` (cut 4's merge).
It names no issue, so the claim comment is the identity record.
**Why now.** Ruling 6353073966 item 4 held this body with the two read
bodies until the Tier H docs PR for #25314 landed. That PR, #25316,
merged as `97967a9a06`, and cut 4 moved the two read bodies. On this
base, ADR-0123:4 anchors `security-plugin.ts#composeWriteTenantWall`, a
method name. The method stays as a shell, so that anchor still resolves
on its declaration.
**What stays in `security-plugin.ts`.**
- No module-level declaration moves. The `WriteTenantWall` and
`WriteWallRefusal` interfaces keep their one declaration, because the
method's signature and `raiseWriteWallRefusal` read them. The module
names both through the class's own signature, as cuts 2 to 4 name
`CbpRelation`.
- `carriesActiveOrganization` stays, because
`callerHasOrganizationScope` reads it too. It gains `export`, and the
module imports it by value, as cut 3's module imports its five values.
It is read only inside the function body, at call time, never while
either module evaluates. `index.ts` still exports only `SecurityPlugin`,
so the published surface does not move (measured below).
- The `matchesFilterCondition` name leaves the `@objectstack/formula`
import of `security-plugin.ts`, because no code left there reads it. The
module imports it from the same package. The module also imports
`postureUsesUnionScope` from `@objectstack/spec/security` and
`PermissionDeniedError` from `errors.js`, as `security-plugin.ts` does.
**One reader outside the package moves with the body.**
`docs/qa/platform-checklist/areas/access-security.json` cites
`packages/plugins/plugin-security/src/security-plugin.ts#denyTenantPlacement`
twice, in the `fixtures.requires` prose of items
`access-security.activation-write-operator-gate` and
`access-security.walled-environment-metadata-operator-only`.
`denyTenantPlacement` is a local `const` inside the moved body. With the
body moved and that citation unchanged, `check-platform-checklist` exits
1 with ABSENT SYMBOL, measured on a trial before the commit. Both
citations now name
`security-plugin-write-tenant-wall.ts#denyTenantPlacement`. Only the
path changed: the symbol, the quoted 403 text and the rest of both
strings are as they were. The gate exits 0 at head.
## The published `.d.ts` does not change
Under the series bar (ruling 6348891160 item 1), measured on base
`4d7e2b1f38` and on the head (the tree of this PR's commit):
- Raw sha256 of `dist/index.d.ts` and `dist/index.d.mts`, base and head,
all four the same:
`ea54b6c9538b135fee36e1309fddc763113443c0dddd174950cbd96c290536a2`. The
raw diff is 0 lines, so no union order moved either.
- Normalised sha256, all four the same:
`652f26b24f41bf031d428f708685abb7517d4247a765246d153d2bbeac13e444`.
- The hashes differ from cut 4's report because `origin/main` moved
between cut 4's head and its merge. The only lines that differ from cut
4's head `.d.ts` are six inlined `requiresFeature` unions from
`@objectstack/spec`, which gained `"cloudManaged"`. Base and head here
are both built against `4d7e2b1f38`'s dependencies.
- The normaliser, run from `packages/plugins/plugin-security` (it sorts
the members of each string-literal union and changes nothing else):
```sh
node -e 'const s=require("fs").readFileSync(process.argv[1],"utf8");process.stdout.write(s.replace(/"[^"\n]*"(?:\s*\|\s*"[^"\n]*")+/g,r=>r.split(/\s*\|\s*/).sort().join(" | ")))' dist/index.d.ts | sha256sum
```
- Positive controls on a copy of the head `dist/index.d.ts`, line 1794
(`private composeWriteTenantWall;`):
- Made public (`composeWriteTenantWall;`): raw
`5c1fa0e3230960f533466bb151a1e1769cdcc855d3227f776a9832d6f0fb7195`,
normalised
`4defa680f3cf4b2ed2b0c60696d8bea7031a82edd43bcabc4ad4b2e346727c80`.
- Renamed (`private composeWriteTenantWallRenamed;`): raw
`82704c4f85cb5d28cb672046ef7e2b05da8348c6cb4efccd4e0e5fe7e58eb0dc`,
normalised
`614cf491f999aa7a4fde4a3317cec1b1ee9e95306e29dab7c5f1c452b9982870`.
- Both differ from the real hashes, so the comparison does see a
visibility change and a rename.
- Export tables: the ESM and CJS bundles each export the same 63 names
at base and head. The lists were loaded at runtime (`require` and
`import()` of the built bundles), not parsed. The sorted name list
hashes
`f607fd765d6b277e08b3b46ccb16d1e2d133ec55658ffe40155aef25e1bf54f0` on
all four, the same as at cuts 2 to 4. The new
`carriesActiveOrganization` export of `security-plugin.ts` does not
reach the entry.
- The bundle JS bytes differ (`index.js` `53af1376` to `a0e03516`,
`index.mjs` `7beda6f7` to `a75436eb`), because code moved within them.
No changeset: `skip-changeset`, per ruling 6348891160 item 4.
## What moved
The base line numbers are the method's signature and closing brace at
`4d7e2b1f38`. The last column lists the members the body reads, which is
exactly what its host carries.
| method | base lines | host members |
|---|---|---|
| `composeWriteTenantWall` (async) | `:8408`-`:8746` |
`computeWriteTenantCheckFilter`, `computeWriteTenantWall`,
`orgScopingEnabled`, `organizationWallRefusal`, `tenancyPosture` |
The stub drops `async` and returns the moved function's promise, as cuts
1 and 3 did for their async methods (6 and 5 of them). The `.d.ts` emits
a private member without modifiers, so this does not reach it.
## The shape (#23050 shape B, as cuts 1 to 4 applied it)
- The class keeps the private method with its name, signature, docblock
and position, because tsup emits private members with their JSDoc into
the `.d.ts`. The body is now one host literal plus
`composeWriteTenantWall.call(host, …)`, marked `[#25223 cut 5]`.
- `WriteTenantWallHost` types every member as the class member itself
(`SecurityPlugin['m']`). The moved function types its `this` as the
`Pick` of the host over exactly the members its body reads, and the stub
annotates its literal with the same `Pick`. There is no cast, and no
member becomes public or protected.
- The module imports `SecurityPlugin` type-only. It names
`WriteTenantWall` as the awaited return type of
`SecurityPlugin['composeWriteTenantWall']`, and `WriteWallRefusal` as
the non-null type of that wall's `preTest`.
- Methods go in as late-bound closures that call `this.m(...a)` on the
plugin at call time. A spy or test double set on the plugin is still the
one the body reaches. The pre-test is still `organizationWallRefusal`,
the one verdict `canWriteObject` asks too. The caller's and the
delegator's Layer 0 still come from the read side's
`computeLayeredRlsFilter`, through `computeWriteTenantWall` and
`computeWriteTenantCheckFilter`. No moved body calls a function-valued
field, so no receiver changes.
- Fields go as getters. `tenancyPosture` is not declared `readonly`,
because `start()` resolves it after construction. `orgScopingEnabled` is
the class's own getter over it, handed over as cut 1 handed it. The host
declares both `readonly`, so the moved body cannot assign a member
through it; the typecheck passes, so it does not.
- Some reads of `this.tenancyPosture` happen when a returned judgement
is called, not when the wall is composed: the developer message of
`denyOrganizationRemoval`, which `judgePayload` and `judgeRow` reach,
and the developer messages of `judgeLanding`'s two refusals. `this`
inside those arrow functions is the host, and the host's getter reads
the plugin's field at that call, which is the read the method made
before.
- Nothing re-exports the module, so the package entry does not move.
## Proof of move-only
- **Body, by AST token**: the moved function's body has the same
TypeScript token sequence as the base method body, and each of its 329
lines is the base line with two leading spaces removed. Parameters, the
return type and `async` match. A negative control,
`rows.some(emptiesOrganization)` changed to
`!rows.some(emptiesOrganization)` in the payload half, fails the check.
- **Class side**: the method keeps its docblock and signature, less
`async`. Every other class member, 124 named members plus the
constructor, is byte-identical to base, `organizationWallRefusal`,
`computeWriteTenantWall`, `computeWriteTenantCheckFilter`,
`raiseWriteWallRefusal`, `writeWallVerdict` and `start()` included. The
class has 126 members at base and at head.
- **Top level**: 100 of the 102 top-level statements other than the
class are byte-identical to base, `WriteTenantWall` and
`WriteWallRefusal` included. The two that differ are the
`@objectstack/formula` import, which loses `matchesFilterCondition`, and
`carriesActiveOrganization`, which is the base text with `export `
before `function`. The one new statement is the import of the new
module.
- **git's own view** (`git diff --color-moved=plain
--color-moved-ws=allow-indentation-change 4d7e2b1 HEAD` over the two
source files): 328 of 331 deleted lines and 337 of 453 added lines are
detected as moved.
- Deleted, not moved (3): the `matchesFilterCondition,` import line, the
`function carriesActiveOrganization(` line, which comes back with
`export`, and the method's signature line, which comes back without
`async`.
- Added, not moved: those two lines' replacements, the stub body, and
the import of the new module with its comment. In the module: the
license header, the module docblock, the imports, the two type aliases,
`WriteTenantWallHost`, the pointer docblock and the rewritten signature
head. The rest are lines git does not pair with a moved block, such as
blanks and closing braces.
- **Size**: 795 changed lines (+462 / -333, 4 files), under the
3000-line human-merge threshold. `security-plugin.ts` goes from 10,205
to 9,890 lines.
## ADR anchors (ruling 6353073966 item 2)
- `node scripts/check-adr-symbol-anchors.mjs`: exit 0 at base
`4d7e2b1f38` and exit 0 at head, both with `2383 anchors across 142
records resolve — 466 symbol (440 declaration, 26 literal), 1889
file-level, 28 cross-repo, 6 exempt, 18 continuation`, the same counts
as cut 4. CI runs this gate (`lint.yml`), but `dispatch-gates
--commands` does not derive it for this change set (#21697), so it is
run by hand here.
- `pnpm check:adr-anchors`: exit 0, 79 anchored files (78 at base, plus
the new entry). The new entry is
`scripts/adr-anchors/packages__plugins__plugin-security__src__security-plugin-write-tenant-wall.ts.json`.
It carries ADR-0123 and the ADR-0123 D2 paragraph of the
`security-plugin.ts` entry, verbatim: the no-active-organization refusal
is this body's pre-test, and the paragraph's rule that it stays ordered
ahead of the forge guard is about code that now lives in this module.
The moved comments also cite ADR-0090, ADR-0095, ADR-0105, ADR-0112 and
ADR-0131. Like the `security-plugin.ts` entry, the new entry does not
list every ADR its file cites, and the gate passes. The
`security-plugin.ts` entry is unchanged: the middleware's step 3.7,
which throws that refusal, stays there. `docs/adr/**` is not touched.
- The anchor map covers every ADR symbol anchor naming
`security-plugin.ts`: 27 anchors, 18 symbols, 10 ADRs on this base. It
was measured with `extractAnchors` and `symbolSegmentResolution` from
`scripts/symbol-anchors.mjs`, which is measurement, not a new gate. It
was read on `4d7e2b1f38` BEFORE the cut, with the body blanked: no
anchor changed class. Every anchor resolves at head in
`security-plugin.ts` with its base class.
The table gives each anchor's class at base and head, the line it
resolves on, and the member that line sits in. Every anchor stays in
`security-plugin.ts`.
| anchor | cited at | base class · line (member) | head class · line |
|---|---|---|---|
| `#CBP_MAX_CHAIN_DEPTH` | ADR-0055:135 | declaration · `:657`
(top-level) | declaration · `:660` |
| `#SecurityPlugin` | ADR-0049:49, ADR-0138:248, ADR-0138:265 |
declaration · `:1334` (class) | declaration · `:1337` |
| `#SecurityPlugin.getMetadataReadableFields` | ADR-0138:153 |
declaration · `:2483` (`start`), `:6102` (method) | declaration ·
`:2486`, `:6105` |
| `#SecurityPlugin.resolvePermissionSetsForContextUnmemoized` |
ADR-0138:427 | declaration · `:7013` (method) | declaration · `:7016` |
| `#assertControlledByParentWrite` | ADR-0055:58, ADR-0055:125 |
declaration · `:9462` (method shell) | declaration · `:9147` |
| `#assertMasterRowEditable` | ADR-0055:125 | declaration · `:9588`
(method shell) | declaration · `:9273` |
| `#collectRLSPolicies` | ADR-0105:93 | declaration · `:9642` (method) |
declaration · `:9327` |
| `#composeWriteTenantWall` | ADR-0123:4 | declaration · `:8408`
(method) | declaration · `:8411` (method shell) |
| `#computeControlledByParentFilter` | ADR-0055:5, ADR-0055:123,
ADR-0139:246 | declaration · `:9054` (method shell) | declaration ·
`:8739` |
| `#computeDelegatedReadFilter` | ADR-0139:223 | declaration · `:5980`
(method) | declaration · `:5983` |
| `#computeRlsFilter` | ADR-0055:24 | declaration · `:5232`
(`explainAccessForCaller`), `:7635` (method) | declaration · `:5235`,
`:7638` |
| `#getReadFilter` | ADR-0096:181, :182, :183, :199, ADR-0139:222 |
declaration · `:2246` (`start`), `:5858` (method) | declaration ·
`:2249`, `:5861` |
| `#hasPlatformAdminPosture` | ADR-0099:317 | declaration · `:7662`
(method) | declaration · `:7665` |
| `#isPrincipalLessContext` | ADR-0138:152 | declaration · `:511`
(top-level) | declaration · `:514` |
| `#manage_metadata` | ADR-0099:68 | literal · `:260`
(`PLATFORM_ADMIN_ONLY_CAPABILITIES`) | literal · `:263` |
| `#nav_permission_sets` | ADR-0126:363 | literal · `:1739` (`init`) |
literal · `:1742` |
| `#rlsFilter` | ADR-0055:24 | declaration · `:4309` (local in `start`)
| declaration · `:4312` |
| `#writeCheckPolicies` | ADR-0066:112 | declaration · `:1229`
(top-level) | declaration · `:1232` |
No resolving site moves. ADR-0123:4 resolves on the
`composeWriteTenantWall` declaration, which stays as a shell. The new
module also declares a function of that name, but the anchor names
`security-plugin.ts`, so it is judged there. This cut adds no
host-literal key line for an anchored name.
## Readers
One reader of the moved lines exists outside this package, the platform
checklist above, and it is re-pointed in this PR. No test, script, gate,
baseline or other docs anchor reads the moved lines by path.
- **The platform checklist.** `check-platform-checklist` exits 0 at base
and at head. Both print `symbol anchors: 986/996 resolved … 10 on the
named #16898 residual, 18 file floors held`. The cited-source count goes
from 435 to 436, because the new module is now a cited source. The
scoped run `--changed-from origin/main` judged 7 anchors in 3 anchored
files of the change set, and lost 0. Before the re-point, on a trial of
the same move, the full gate exited 1 with ABSENT SYMBOL for both
citations.
- **The census pages.** The body holds no `isSystem` read. One comment
names `isSystem`, which the census does not count. So
`check-system-context-census` has no row to move, and
`content/docs/permissions/system-context.mdx` is not touched. `node
scripts/isystem-census.mjs --json` gives the same 148 sites at base and
head (12 in `security-plugin*.ts`), compared without line numbers. Only
the corpus and scanned file counts move, by one. The body holds no
engine write, so `node scripts/tenant-audit-census.mjs --json` gives the
same 237 write call sites at base and head, compared the same way. Only
`scannedSources` moves, 712 to 713, plus the measured-at ref.
- The other symbol-anchor gates all exit 0:
`check-scripts-symbol-anchors`, `check-spec-docblock-symbol-anchors` and
`pnpm --filter @objectstack/spec check:liveness`.
- **Source scans by path.** Two tests read package sources by path.
`packages/core/src/security/row-serving-door-exposure.pin.test.ts`
classifies every caller of the read admission, and the body calls no
admission, so the new file needs no row. Run on its own: 3 of 3 pass.
`delegated-organization-membership.test.ts` counts
`resolveDelegatorContext(` per source file, and the body has none, so
the two counted files are still `explain-engine.ts` and
`security-plugin.ts`. It is part of the plugin-security suite, which
passes.
- Readers by name, not by path. These were read and none needs a change:
- Docblocks in `security-plugin.ts` itself name `{@link
SecurityPlugin.composeWriteTenantWall}` (on `WriteWallRefusal` and
`WriteTenantWall`, and in step 3.7 and `writeWallVerdict`). The method
still exists under that name.
- Test files name the wall's refusal sentences and its `[#24784]`,
`[#24821]` and `[#24822]` arms, and assert behaviour, not location. The
suite passes at head with the same counts as base.
- Line citations: no `security-plugin.ts:N` citation in the repo points
into the moved range, base `:8417`-`:8745`.
- Head line numbers shift by +4 for base `:146`-`:186` (the new import),
by +3 for base `:188`-`:8416`, and by -315 after `:8745`. Lines
`:1`-`:145` do not move. The moved range becomes the 11-line stub at
head `:8420`-`:8430`.
- The citations `:132`, `:303`, `:309`, `:1614`, `:1690`, `:1736`,
`:3215`, `:3281`, `:3519` and `:4344` are the same list cuts 2 to 4
read. Each lands in an unmoved or shifted range, and each already
pointed at an unrelated line before cut 2, so this cut does not make any
of them wrong.
- Docs Drift Check, re-derived with `node
scripts/docs-audit/affected-docs.mjs --json 4d7e2b1` (advisory): 0
pages. Its 17 anchors are the moved names and literals, and the one
broad literal, `organization_id` (37 pages), is dropped as over-broad.
- Census gates, run on base `4d7e2b1f38` and head and compared:
- Identical output: `check-platform-object-tenancy-census`,
`check-registry-log-declared`, `check-rest-log-spy-declared`,
`check-system-context-census`, `check-tenant-audit-census`,
`check-adr-symbol-anchors`, `check:cross-package-test-inputs`,
`check:driver-memory-census` and `check:query-options-erasure`. The last
reports the same counts at both, and `security-plugin.ts` is not a
baseline key.
- Only scanned counts move:
- `check-undeclared-dep-imports`: 3298 to 3299 files, and 2837 to 2840
specifiers. The three are the new module's `@objectstack/spec/security`
(type and value) and `@objectstack/formula` imports, both declared
dependencies.
- `check:doc-authoring`: 1417 to 1418 sources.
- `check:org-identifier`: 3640 to 3641 files.
- `check:logger-receiver-detach`: 3614 to 3616 files.
- `check-position-name-fold-loaders`: 12316 to 12321 files, with the
same 8 references (6 test, 2 declared instrument, 0 loader). It walks
the working tree. Two of the five are this PR's new files. The other
three are gitignored local build outputs that exist only in the head
worktree (`packages/spec/json-schema/data/QueryPageWindow.json`,
`QueryPageWindowParam.json` and `apps/docs/next-env.d.ts`), which CI's
checkout does not have. The second extra file of
`check:logger-receiver-detach` is the same kind of local output, as at
cuts 2 to 4.
- `check-issue-citations` judges a change set, so it has nothing to read
at base. At head it judged 19 citations across 2 files, and all resolve.
## Acceptance notes
- Nothing outside this cut is touched: no other section of the class, no
behaviour, no `docs/adr/**`. The one file outside the package is the
checklist, and only its two path strings change.
- Serial check, also in the claim. #25355 touches `security-plugin.ts`
with one import after `:47` and one block at `:1720`. #25323 (draft)
touches `access-security.json` at `:2919`-`:3063` and adds no
`#denyTenantPlacement` citation. This cut has no hunk near either.
- Since the local runs, `origin/main` gained only #25362 (plugin-auth).
It touches none of this cut's files and no reader of them, so the merge
with this head is clean.
- What is left of the tenant wall in `security-plugin.ts` after this
cut: `computeWriteTenantCheckFilter`, `computeWriteTenantWall`,
`organizationWallRefusal`, `raiseWriteWallRefusal`, `writeWallVerdict`,
the two interfaces and the middleware's step 3.7 that calls the method.
## Gates
All gates ran at the head, the tree of `765326ddf5`, on base
`4d7e2b1f38`.
- `pnpm --filter @objectstack/plugin-security test` (`vitest run
--maxWorkers=3`, under the verify lock): Test Files 212 passed (212),
Tests 4442 passed, 45 skipped (4487). Base `4d7e2b1f38` gives the same
counts. VERDICT command-exit 0 on both.
- `pnpm --filter @objectstack/plugin-security typecheck`: exit 0. It
runs `tsc --noEmit`, the scripts tsconfig, and `check:test-typecheck`.
- `eslint --no-inline-config` over the two touched source files: exit 0.
- `pnpm --filter @objectstack/plugin-security build`: exit 0. It
produced the `.d.ts` and bundles measured above. The package's
dependencies were rebuilt on `4d7e2b1f38` first: on the dependency
outputs of the previous base, the typecheck and build failed on two
`@objectstack/core` exports that `bootstrap-platform-admin.ts` imports
on `origin/main` and that the old core build lacked, not on this cut.
- `packages/core/src/security/row-serving-door-exposure.pin.test.ts`: 3
of 3 pass.
- `node scripts/check-adr-symbol-anchors.mjs` exit 0, `pnpm
check:query-options-erasure` exit 0, and the symbol-anchor gates under
Readers. None of these is derived for this change set; each was run by
hand.
- `dispatch-gates --commands`: 64 commands. They are cut 4's 62, plus
`pnpm check:platform-checklist` and `pnpm --filter @objectstack/lint run
check:doc-formula-expressions`, which the checklist file adds. The
`--ran` reconciliation shows 64 derived, 64 run, 0 NOT-MEASURED, 0
UNRUN. The zero is derived: all 64 recorded an exit code and none is 3.
Per command (exit code):
- `node scripts/check-ci-filter-parity.mjs` exit 0
- `node scripts/check-closing-keyword-parity.mjs` exit 0
- `node scripts/check-closing-keyword-parity.mjs --self-test` exit 0
- `node scripts/check-comment-mask-adoption.mjs` exit 0
- `node scripts/check-comment-mask-adoption.mjs --self-test` exit 0
- `node scripts/check-comment-mask-corpus.mjs` exit 0
- `node scripts/check-dts-emitted.mjs --self-test` exit 0
- `node scripts/check-issue-citations.mjs` exit 0
- `node scripts/check-keyed-text-bounds.mjs` exit 0
- `node scripts/check-keyed-text-bounds.mjs --self-test` exit 0
- `node scripts/check-platform-object-tenancy-census.mjs` exit 0
- `node scripts/check-platform-object-tenancy-census.mjs --self-test`
exit 0
- `node scripts/check-plugin-teardown-shape.mjs` exit 0
- `node scripts/check-plugin-teardown-shape.mjs --self-test` exit 0
- `node scripts/check-position-name-fold-loaders.mjs` exit 0
- `node scripts/check-position-name-fold-loaders.mjs --self-test` exit 0
- `node scripts/check-registry-log-declared.mjs` exit 0
- `node scripts/check-registry-log-declared.mjs --self-test` exit 0
- `node scripts/check-rest-log-spy-declared.mjs` exit 0
- `node scripts/check-rest-log-spy-declared.mjs --self-test` exit 0
- `node scripts/check-scripts-symbol-anchors.mjs` exit 0
- `node scripts/check-scripts-symbol-anchors.mjs --self-test` exit 0
- `node scripts/check-system-context-census.mjs` exit 0
- `node scripts/check-system-context-census.mjs --self-test` exit 0
- `node scripts/check-tenant-audit-census.mjs` exit 0
- `node scripts/check-tenant-audit-census.mjs --self-test` exit 0
- `node scripts/check-undeclared-dep-imports.mjs` exit 0
- `node scripts/check-undeclared-dep-imports.mjs --self-test` exit 0
- `node scripts/docs-audit/check-affected-docs.mjs` exit 0
- `node scripts/docs-audit/check-drift-comment.mjs` exit 0
- `pnpm --filter @objectstack/lint run check:doc-formula-expressions`
exit 0
- `pnpm --filter @objectstack/spec run check:duration-unit-keys` exit 0
- `pnpm check:adr-anchors` exit 0
- `pnpm check:agent-test-spelling` exit 0
- `pnpm check:bash32-floor` exit 0
- `pnpm check:cli-command-ids` exit 0
- `pnpm check:closed-ceremony-text` exit 0
- `pnpm check:cross-package-test-inputs` exit 0
- `pnpm check:doc-authoring` exit 0
- `pnpm check:driver-memory-census` exit 0
- `pnpm check:dts-closure` exit 0
- `pnpm check:dual-build-cjs-loads` exit 0
- `pnpm check:entry-guard` exit 0
- `pnpm check:error-status-conformance` exit 0
- `pnpm check:gitlink-declared` exit 0
- `pnpm check:i18n` exit 0
- `pnpm check:i18n-stale-fill` exit 0
- `pnpm check:issue-citations` exit 0
- `pnpm check:lean-entry-closure` exit 0
- `pnpm check:logger-receiver-detach` exit 0
- `pnpm check:nul-bytes` exit 0
- `pnpm check:org-identifier` exit 0
- `pnpm check:page-declaration-shape` exit 0
- `pnpm check:parse-guard` exit 0
- `pnpm check:platform-checklist` exit 0
- `pnpm check:pnpm-filter-targets` exit 0
- `pnpm check:pnpm-flag-spellings` exit 0
- `pnpm check:published-files` exit 0
- `pnpm check:refd-timer-probe` exit 0
- `pnpm check:slot-lookup` exit 0
- `pnpm check:sourcemap-no-sources-content` exit 0
- `pnpm check:test-source-alias` exit 0
- `pnpm check:tier-file-adoption` exit 0
- `pnpm check:watch-hint-literal` exit 0
- `pnpm check:query-options-erasure` exit 0
- `node scripts/check-adr-symbol-anchors.mjs` exit 0
- `node scripts/check-spec-docblock-symbol-anchors.mjs` exit 0
- `pnpm --filter @objectstack/spec check:liveness` exit 0
- `node scripts/check-platform-checklist.mjs --changed-from origin/main`
exit 0
---
_Generated by [Claude
Code](https://claude.ai/code/session_017BoLT8Gaa8t9a7AWVH8qZa)_
🤖 Generated with [Claude Code](https://claude.com/claude-code)
https://claude.ai/code/session_017BoLT8Gaa8t9a7AWVH8qZa
Co-authored-by: Claude <noreply@anthropic.com>
1 parent 27b3f1f commit be318db
4 files changed
Lines changed: 462 additions & 333 deletions
File tree
- docs/qa/platform-checklist/areas
- packages/plugins/plugin-security/src
- scripts/adr-anchors
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
2579 | 2579 | | |
2580 | 2580 | | |
2581 | 2581 | | |
2582 | | - | |
| 2582 | + | |
2583 | 2583 | | |
2584 | 2584 | | |
2585 | 2585 | | |
| |||
3550 | 3550 | | |
3551 | 3551 | | |
3552 | 3552 | | |
3553 | | - | |
| 3553 | + | |
3554 | 3554 | | |
3555 | 3555 | | |
3556 | 3556 | | |
| |||
0 commit comments