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
{{ message }}
Repository navigation
bootstrapDeclaredCapabilities seeds sys_capability one at a time too — the same per-item read + unconditional UPDATE #10946 removed from the two sibling loops #11096
Found while implementing #10946 (batching the permission-set and position boot seeds). The sys_capability seeder next door has the identical shape and was not in that card's scope.
line 210 — const existing = (await tryFind(ql, 'sys_capability', { name: cap.name }, 1))[0]; — a per-item existence SELECT, issued inside the loops at lines 136/138 (curated: every systemPermissions entry of every declared set) and line 290 (the derived half);
line 241 — if (await tryUpdate(ql, 'sys_capability', { id: existing.id, ...fields })) out.updated += 1; — an UPDATE on the seeder's own row that fires whether or not fields differ from what is stored.
So each declared capability costs its own sequential round trip pair on every kernel boot, exactly as permission sets and positions did. On a local file database this is invisible; on a remote libsql/Turso database — every hosted environment — each leg is its own HTTP request, awaited one after another.
Why it is worth a card of its own
Capability names come from systemPermissions on every declared permission set, so the count is not bounded by the number of sets — it is the union of every capability every package declares, which is typically larger than either axis #10946 measured. The cost competes for the same 20 s request budget (objectstack-ai/cloud#1555).
Not measured here
I did not re-run the hosted bootstrap-curve.mjs rig for this axis — that lives in objectstack-ai/cloud, outside the session that found this. What is established is the code shape above, and that it is the same shape whose cost was measured at slope 4.0000 / R² = 1.000000 on the two sibling loops in #10946. The capability axis' own slope is not measured.
Direction
The same two halves #10946 applied, and the machinery is already in the package:
compare before writing, so an unchanged row costs nothing.
⚠️ Whatever lands must keep the reconciliation leg pinned: a row whose stored value differs still needs its UPDATE. An implementation that skipped all writes would show a perfect round-trip curve while silently reconciling nothing. Note also that this seeder has provenance branches (skippedUnowned, skippedForeign) and a curated/derived split that #10946's two loops do not — the refusal messages at lines 215-219 depend on whether a row was found, so the batched read has to preserve that distinction, not just the row.
Refs #10946 · objectstack-ai/cloud#1555 · #10979 and #10945 are the same boot-cost campaign in other packages.
Triage: lands in packages/plugins/plugin-security/src/bootstrap-declared-capabilities.ts ⇒ domain:services, Task, pm:queue. Rationale: mechanical continuation of #10946 with the machinery already landed (buildExistingByName in seed-name-lookup.ts); the capability axis is typically the largest of the three (union of every declared set's systemPermissions) and competes for the same 20s budget (cloud#1555). Binding clauses: ① keep the reconciliation leg pinned — a changed row must still get its UPDATE (an implementation that skips all writes shows a perfect curve while reconciling nothing); ② the batched read must preserve the provenance branches (skippedUnowned/skippedForeign) and the found/not-found distinction the refusal messages at lines 215-219 depend on. Size S-M. Serial note: same file surface family as #11097 and in-flight #10946 — fold-or-serial must-answer for the services seat; #11096+#11097 look foldable on the five-gate test (same defect shape, same package, both now graded, independently checkable, exclusion: the derived/curated split here has no sibling in #11097) but the seat decides.
The counter-direction is the load-bearing pin and it is ablated: drift in every written column (label/description/scope/facets/customized) still gets its UPDATE with the healed value asserted; both write-skip ablations disk-proven (git hash-object pre/post, trap-guarded byte-identical restores) — 4 and 18 tests red respectively.
Fail-closed edges: a throwing/non-array batched read falls back to per-item reads (never blind-inserts); duplicate names keep the loud skippedForeign refusal; row-id stability separately pinned pre-existing and unmodified.
The dev upgraded clause-② from the dispatch's "no" to "yes" by the dispatch's own test — the honest direction, and the reason this review exists.
Verdict: PASS. Clearing needs:contract-review on all three carriers (#11096, #11097, PR #11470). Enqueue/flip belongs to the dispatching seat's landing window.
{
"issue": 11096,
"issues": [11096, 11097],
"status": "done",
"branch": "claude/issue-11096-batch-capability-and-overlay-boot-seeds",
"pr": "https://github.com/objectstack-ai/objectstack/pull/11470",
"premise_still_valid": { "11096": true, "11097": true },
"summary": "bootstrapDeclaredCapabilities and reconcilePermissionSetProjection each now pay one batched $in existence read instead of one per item, and skip the UPDATE when the stored row already matches (equality test, not presence). Recovered a killed prior agent's 3-commit branch, reviewed the diff as my own, reverted then RESTORED (with fuller reasoning) the customized:false insert-path fix after ablation proved it's required for the write-skip's own steady-state claim to hold -- not a separable rider. Fixed a real CI failure the PM caught after my first push: a new drift fixture (scope 'platform'->'org') narrowed by an inferred-literal return type on declaredCaps, pushing plugin-security's TEST_DEBT ledger from 11 to 12. Typed declaredCaps explicitly (matching the pre-existing DeclaredSet pattern) and confirmed 11 again, both locally (exact generated re-measure project) and via CI's own green run.",
"tests": "Package suite: `pnpm --filter @objectstack/plugin-security exec vitest run src/bootstrap-declared-capabilities.test.ts src/bootstrap-seed-round-trips.test.ts src/permission-set-projection.test.ts` -> 'Test Files 3 passed (3), Tests 122 passed (122)' (re-run after the TEST_DEBT fix, on 8eef2233).\n\nLocal dispatch-gates.mjs union (commit 3cb2101a3f, before the TEST_DEBT fix landed; re-derived again at 8eef2233 with an identical file list, so the gate set did not move): 17/17 path-derived + convention-triggered gates green -- check:changeset-gate-self-tests, check:cross-package-test-inputs, check:objectui-changeset, check:published-files, check:slot-lookup, check:test-source-alias, check:type-source-resolution, check-adr-0087-registration, check-changeset-no-major, check-ci-filter-parity, check-empty-changeset, check-plugin-teardown-shape, docs-audit/check-affected-docs, check:query-options-erasure, check:engine-double-contract, check:where-matcher, check:i18n -- each command's own printed verdict line captured, exit codes read before any pipe (os-verify-lock's own VERDICT line each time).\n\nTEST_DEBT (the actual CI failure): reproduced with the EXACT generated tsconfig scripts/check-type-check-coverage.mjs's --re-measure builds for a TEST_DEBT package (extends plugin-security's own tsconfig, drops the **/*.test.ts exclude, adds the identical typeRoots chain) -- 12 raw tsc errors before the fix (the +1 was bootstrap-seed-round-trips.test.ts(518,37) TS2322 'org' not assignable to 'platform'), exactly 11 after (matching the frozen ledger). CI's own 'Type Check . debt ledger' job (run 32668616399, commit 8eef2233): completed/success, verdict line quoted verbatim: 'check-type-check-coverage --re-measure: OK -- 33 ledger entr(ies) re-measured in 164.9s, 1897 raw tsc error(s) total, none above its recorded number.' The rollup 'TypeScript Type Check' check-run: completed/success. A local full `pnpm exec turbo run build ... && pnpm check:type-check-debt` run (bv3sm9i13) was ALSO measured pre-fix and reproduced the PM's exact quoted verdict ('plugin-security: TEST_DEBT records 11 ... tsc now reports 12 (+1)'), confirming my local generated-project reproduction and CI's own answer agree.\n\nAblation (both pins, predicted in writing before running, confirmed on disk via git hash-object, restored via `git checkout HEAD -- <path>` inside a trap): mutating bootstrap-declared-capabilities.ts's capabilityRecordDiffers to `return false` (always no-op) -> 4 tests fail (the 3 capability drift-heal cases + the provenance-preserving re-seed case), steady-state round-trip tests stay green (as predicted, demonstrating why the paired drift tests are necessary). Mutating permission-set-projection.ts's write-skip condition to `if (true)` (always skip) -> 18 tests fail (drift-heal + customized-stamp cases), steady-state/insert-path tests stay green. Both restores verified byte-identical (git hash-object match) before continuing.\n\nCI as of last check (commit 8eef2233, run 32668616399/32668616512): green -- TypeScript Type Check, Type Check . source/consumer/workspace/debt-ledger gates, Lint & Repo Gates (was in_progress, not yet re-polled), Build Core, Test Core 1-6/6 (5/6 confirmed green, 1/6 was in_progress at last poll), Dogfood Regression Gate + subjobs, Temporal Conformance, Dogfood Verify CLI, Check Changeset, Check PR Size, docs/label/issue-claim gates. No exit-99/queue-timeout/PREREQUISITE-NOT-MET encountered on any command that produced a reported result (two local verify-lock attempts DID time out at exit 99 while queued behind other agents' full-repo builds during heavy contention -- both explicitly retried per the NOT-MEASURED discipline rather than folded into a pass; the retries succeeded and are what's quoted above).",
"clause2": {
"judgement": "yes",
"reasoning": "Reversed from the dispatch's initial 'no' -- confirmed by measurement, not by re-reading the diff. upsertEnvPermissionSet's INSERT now stamps customized:false unconditionally instead of !!customized (the caller's raw opinion / main's current behaviour). This changes the RESULTING PROJECTED STATE, not just the write count: today a brand-new environment-authored permission set with no package baseline can be observed customized:true for the one boot between its creation and the next reconciliation pass; after this PR it never is. The change is required for the round-trip fix's own steady-state claim to hold on this path (proven by reverting it and watching two round-trip-count tests fail), so it isn't a separable rider that could simply be dropped to keep this a pure perf PR -- but it IS a real behaviour change beyond write count, which is exactly the dispatch's own test for clause-2 = yes. needs:contract-review applied to the PR (re-applied once after Auto Label's PUT silently dropped it -- read back and confirmed present)."
},
"adr_0094_projection_outcome_answer": "Yes, the resulting projected state can differ from today -- see clause2.reasoning above. Confined to the customized provenance flag on freshly-created admin-owned rows; no facet/definition column, no accept/reject surface, and no published API shape moves. The write-COUNT reduction itself (batched read + no-op skip) is behaviour-preserving on every other axis, verified by the paired drift/ablation tests.",
"pr_state": {
"draft": true,
"auto_merge_armed": false,
"mergeable_state": "blocked",
"labels_confirmed_present": ["needs:contract-review"],
"note": "Auto Label bot's own PUT relabel dropped needs:contract-review once (read-back caught it); re-added via the additive labels endpoint and re-confirmed present."
},
"out_of_scope_findings": [
"filed as #11460: upsertEnvPermissionSet's INSERT customized-flag defect -- closed as not-planned/superseded once measurement showed the fix belongs in this PR rather than separately (see clause2.reasoning)."
],
"open_questions": []
}
Contract review — PASS carries forward to the new head (fable seat, session 5213b871-5164-5bc3-8874-28b336bbcd40; fuse reading claude-fable-5 = CONTRACT_REVIEW_TIER). The 21:54Z re-hang on PR #11470 accompanied a real push, so it was the correct posture — reviewed the delta 3cb2101a3f...8eef223370: exactly one commit, a test-fixture type annotation (explicit DeclaredCapability interface fixing a TEST_DEBT ratchet +1). Zero product-code bytes, zero contract movement. The standing PASS above covers the new head. Re-clearing needs:contract-review on PR #11470.
Activity
os-zhuang commentedon Aug 22, 2026
Triage: lands in
packages/plugins/plugin-security/src/bootstrap-declared-capabilities.ts⇒domain:services, Task,pm:queue. Rationale: mechanical continuation of #10946 with the machinery already landed (buildExistingByNameinseed-name-lookup.ts); the capability axis is typically the largest of the three (union of every declared set'ssystemPermissions) and competes for the same 20s budget (cloud#1555). Binding clauses: ① keep the reconciliation leg pinned — a changed row must still get itsUPDATE(an implementation that skips all writes shows a perfect curve while reconciling nothing); ② the batched read must preserve the provenance branches (skippedUnowned/skippedForeign) and the found/not-found distinction the refusal messages at lines 215-219 depend on. Size S-M. Serial note: same file surface family as #11097 and in-flight #10946 — fold-or-serial must-answer for the services seat; #11096+#11097 look foldable on the five-gate test (same defect shape, same package, both now graded, independently checkable, exclusion: the derived/curated split here has no sibling in #11097) but the seat decides.Generated by Claude Code
claude commentedon Aug 23, 2026
Contract review — PASS (fable seat, session
5213b871-5164-5bc3-8874-28b336bbcd40, hourly sub-round; fuse readingget_session→external_metadata.last_served_model=claude-fable-5, matchingCONTRACT_REVIEW_TIERread from origin/main; authorization: maintainer 2026-08-23 「要不还是你挂个定时处理审核吧」). Independence: dispatched by the services seat — independent review. Covers the #11096+#11097 family PR #11470 @3cb2101a3f; a pointer verdict sits on #11097.$inexistence read + equality-gated writes, reusing Boot seeds permission sets and positions one at a time: 4 sequential DB round trips each, 2 of them an unconditional UPDATE #10946'sbuildExistingByName; the in-memory registry sync correctly gated on any observed row (not on "a write happened") so steady-state boots don't enforce a stale entry.customized: falseunconditionally aligns a row's birth with its own UPDATE rule (managed_by !== 'package'⇒ forced false); reverting that one line fails two named Boot reconciliation projects env permission-set overlays one at a time, and re-writes every record unconditionally — the #10946 shape on the ADR-0094 door #11097 tests (a permanent one-boot-late corrective UPDATE appears). What is removed is a one-boot transient (customized: trueon a fresh env-authored row with no package baseline) — provenance display, not an access-control semantic; no permission boundary moves. Superseded card upsertEnvPermissionSet's INSERT can stamp customized:true on a record with no package baseline #11460 correctly closed with provenance.customized) still gets its UPDATE with the healed value asserted; both write-skip ablations disk-proven (git hash-objectpre/post, trap-guarded byte-identical restores) — 4 and 18 tests red respectively.skippedForeignrefusal; row-id stability separately pinned pre-existing and unmodified.Verdict: PASS. Clearing
needs:contract-reviewon all three carriers (#11096, #11097, PR #11470). Enqueue/flip belongs to the dispatching seat's landing window.Generated by Claude Code
claude commentedon Aug 23, 2026
{ "issue": 11096, "issues": [11096, 11097], "status": "done", "branch": "claude/issue-11096-batch-capability-and-overlay-boot-seeds", "pr": "https://github.com/objectstack-ai/objectstack/pull/11470", "premise_still_valid": { "11096": true, "11097": true }, "summary": "bootstrapDeclaredCapabilities and reconcilePermissionSetProjection each now pay one batched $in existence read instead of one per item, and skip the UPDATE when the stored row already matches (equality test, not presence). Recovered a killed prior agent's 3-commit branch, reviewed the diff as my own, reverted then RESTORED (with fuller reasoning) the customized:false insert-path fix after ablation proved it's required for the write-skip's own steady-state claim to hold -- not a separable rider. Fixed a real CI failure the PM caught after my first push: a new drift fixture (scope 'platform'->'org') narrowed by an inferred-literal return type on declaredCaps, pushing plugin-security's TEST_DEBT ledger from 11 to 12. Typed declaredCaps explicitly (matching the pre-existing DeclaredSet pattern) and confirmed 11 again, both locally (exact generated re-measure project) and via CI's own green run.", "tests": "Package suite: `pnpm --filter @objectstack/plugin-security exec vitest run src/bootstrap-declared-capabilities.test.ts src/bootstrap-seed-round-trips.test.ts src/permission-set-projection.test.ts` -> 'Test Files 3 passed (3), Tests 122 passed (122)' (re-run after the TEST_DEBT fix, on 8eef2233).\n\nLocal dispatch-gates.mjs union (commit 3cb2101a3f, before the TEST_DEBT fix landed; re-derived again at 8eef2233 with an identical file list, so the gate set did not move): 17/17 path-derived + convention-triggered gates green -- check:changeset-gate-self-tests, check:cross-package-test-inputs, check:objectui-changeset, check:published-files, check:slot-lookup, check:test-source-alias, check:type-source-resolution, check-adr-0087-registration, check-changeset-no-major, check-ci-filter-parity, check-empty-changeset, check-plugin-teardown-shape, docs-audit/check-affected-docs, check:query-options-erasure, check:engine-double-contract, check:where-matcher, check:i18n -- each command's own printed verdict line captured, exit codes read before any pipe (os-verify-lock's own VERDICT line each time).\n\nTEST_DEBT (the actual CI failure): reproduced with the EXACT generated tsconfig scripts/check-type-check-coverage.mjs's --re-measure builds for a TEST_DEBT package (extends plugin-security's own tsconfig, drops the **/*.test.ts exclude, adds the identical typeRoots chain) -- 12 raw tsc errors before the fix (the +1 was bootstrap-seed-round-trips.test.ts(518,37) TS2322 'org' not assignable to 'platform'), exactly 11 after (matching the frozen ledger). CI's own 'Type Check . debt ledger' job (run 32668616399, commit 8eef2233): completed/success, verdict line quoted verbatim: 'check-type-check-coverage --re-measure: OK -- 33 ledger entr(ies) re-measured in 164.9s, 1897 raw tsc error(s) total, none above its recorded number.' The rollup 'TypeScript Type Check' check-run: completed/success. A local full `pnpm exec turbo run build ... && pnpm check:type-check-debt` run (bv3sm9i13) was ALSO measured pre-fix and reproduced the PM's exact quoted verdict ('plugin-security: TEST_DEBT records 11 ... tsc now reports 12 (+1)'), confirming my local generated-project reproduction and CI's own answer agree.\n\nAblation (both pins, predicted in writing before running, confirmed on disk via git hash-object, restored via `git checkout HEAD -- <path>` inside a trap): mutating bootstrap-declared-capabilities.ts's capabilityRecordDiffers to `return false` (always no-op) -> 4 tests fail (the 3 capability drift-heal cases + the provenance-preserving re-seed case), steady-state round-trip tests stay green (as predicted, demonstrating why the paired drift tests are necessary). Mutating permission-set-projection.ts's write-skip condition to `if (true)` (always skip) -> 18 tests fail (drift-heal + customized-stamp cases), steady-state/insert-path tests stay green. Both restores verified byte-identical (git hash-object match) before continuing.\n\nCI as of last check (commit 8eef2233, run 32668616399/32668616512): green -- TypeScript Type Check, Type Check . source/consumer/workspace/debt-ledger gates, Lint & Repo Gates (was in_progress, not yet re-polled), Build Core, Test Core 1-6/6 (5/6 confirmed green, 1/6 was in_progress at last poll), Dogfood Regression Gate + subjobs, Temporal Conformance, Dogfood Verify CLI, Check Changeset, Check PR Size, docs/label/issue-claim gates. No exit-99/queue-timeout/PREREQUISITE-NOT-MET encountered on any command that produced a reported result (two local verify-lock attempts DID time out at exit 99 while queued behind other agents' full-repo builds during heavy contention -- both explicitly retried per the NOT-MEASURED discipline rather than folded into a pass; the retries succeeded and are what's quoted above).", "clause2": { "judgement": "yes", "reasoning": "Reversed from the dispatch's initial 'no' -- confirmed by measurement, not by re-reading the diff. upsertEnvPermissionSet's INSERT now stamps customized:false unconditionally instead of !!customized (the caller's raw opinion / main's current behaviour). This changes the RESULTING PROJECTED STATE, not just the write count: today a brand-new environment-authored permission set with no package baseline can be observed customized:true for the one boot between its creation and the next reconciliation pass; after this PR it never is. The change is required for the round-trip fix's own steady-state claim to hold on this path (proven by reverting it and watching two round-trip-count tests fail), so it isn't a separable rider that could simply be dropped to keep this a pure perf PR -- but it IS a real behaviour change beyond write count, which is exactly the dispatch's own test for clause-2 = yes. needs:contract-review applied to the PR (re-applied once after Auto Label's PUT silently dropped it -- read back and confirmed present)." }, "adr_0094_projection_outcome_answer": "Yes, the resulting projected state can differ from today -- see clause2.reasoning above. Confined to the customized provenance flag on freshly-created admin-owned rows; no facet/definition column, no accept/reject surface, and no published API shape moves. The write-COUNT reduction itself (batched read + no-op skip) is behaviour-preserving on every other axis, verified by the paired drift/ablation tests.", "pr_state": { "draft": true, "auto_merge_armed": false, "mergeable_state": "blocked", "labels_confirmed_present": ["needs:contract-review"], "note": "Auto Label bot's own PUT relabel dropped needs:contract-review once (read-back caught it); re-added via the additive labels endpoint and re-confirmed present." }, "out_of_scope_findings": [ "filed as #11460: upsertEnvPermissionSet's INSERT customized-flag defect -- closed as not-planned/superseded once measurement showed the fix belongs in this PR rather than separately (see clause2.reasoning)." ], "open_questions": [] }Generated by Claude Code
claude commentedon Aug 23, 2026
Contract review — PASS carries forward to the new head (fable seat, session
5213b871-5164-5bc3-8874-28b336bbcd40; fuse readingclaude-fable-5=CONTRACT_REVIEW_TIER). The 21:54Z re-hang on PR #11470 accompanied a real push, so it was the correct posture — reviewed the delta3cb2101a3f...8eef223370: exactly one commit, a test-fixture type annotation (explicitDeclaredCapabilityinterface fixing a TEST_DEBT ratchet +1). Zero product-code bytes, zero contract movement. The standing PASS above covers the new head. Re-clearingneeds:contract-reviewon PR #11470.Generated by Claude Code