Skip to content

spec: 4 duration key(s) in system/logging.zod.ts name their unit only in JSDoc — #15939 Ruling A remediation (4 of the 21-row delta) #17782

Description

@os-bill

Filed by the domain:spec execution seat from Ruling A on #15939, 2026-09-12T04:15Z. ⛔ No domain:* and no priority:* asserted — both have exactly one producer, the triage seat. ⚠️ Triage's first touch is owed before this can be dispatched.

The ruling this card executes

Recorded by the director seat on #15939, 2026-09-11T14:08Z, carrying the maintainer's own 「同意」 (decision batch #115):

Ruling A. Batch #65's direction stands (the gate refuses a duration key whose JSDoc names a unit its describe does not). Sequencing: the remediation lands first, per file, each as its own Clause-②: no / patch round following the #15678 / #15679 shape (rename the key with its unit token, ADR-0087 conversion + tombstone + pin where the key is published; describe-only fixes where no rename is needed), and PR #17635 (the gate + self-test + the two corrected prose sites) lands last, into a tree it already reads as clean. ⛔ Not B (18 published-key renames in one PR); ⛔ C is gate weakening.

⇒ this is one of the per-file remediation cards that ruling calls for. PR #17635 (the gate) must land LAST, into a tree these cards have already cleaned.

The rows this card owns

packages/spec/src/system/logging.zod.ts — 4 row(s) of the 21-row delta enumerated in PR #17635:

line key unit named in JSDoc
:278 flushInterval ms
:293 initialDelay ms
:304 timeout ms
:672 flushInterval ms

Each names its unit in JSDoc only; the .describe() an author or an AI actually reads does not carry it. ⇒ whoever writes this value has to guess between milliseconds and seconds.

The shape the ruling prescribes

Follow #15678 / #15679: rename the key so the unit is in the key name, plus an ADR-0087 conversion + tombstone + pin where the key is published. One Clause-②: no / patch round per file.

⚠️ Every rename here touches a published key. Per the ruling's execution note: git grep the pinned objectui checkout at its pinned SHA before landing (AGENTS.md Post-Task Checklist step 4).

Premise verified by the filing seat

Measured on origin/main @ fce7cd4c46, 2026-09-12T04:15Z — every key above is declared in that file, with z.number as the lit control and a fabricated key name as the dark control (0). ⚠️ Line numbers are from PR #17635's enumeration and rot fast — several keys in these files are declared more than once, so the line, not the key name, identifies the row. Re-locate by symbol before editing; ⛔ never trust the number alone.

Dedupe. Full enumeration of open issues by REST pages ⇒ 546 titles (2026-09-12T04:15Z), grepped for logging.zod.ts (0), duration unit (0), and each key name above. Lit controls on the same corpus: spec → 70, finding → 178. Dark control qqzzxx → 0. ⚠️ Declared limit: TITLES only — bodies were not searched (REST /search/* is 403 for this session).

Refs: #15939 (the ruling) · PR #17635 (the gate, lands last) · #15678 / #15679 (the shape).

domain:spec execution seat · session_01MkQhmuuJAVDjmeWNixwDDH · filed 2026-09-12T04:15Z


Generated by Claude Code

Activity

  1. added
    findingRecorded observation — held, not dispatchable until the findings triage round grades it
    on Sep 12, 2026
  2. added
    pm:epicReserved by a dedicated epic PM, parent or sub-issue; other PMs never take it; never with pm:queue
    pm:dispatchedDispatched to a dev agent by /pm-dispatch
    needs:contract-reviewMarker only — PR awaits its at-tier Contract review PASS; no check reads it, the record decides
    and removed
    pm:queueReady for the PM dispatch loop
    on Sep 13, 2026
  3. zhuangjianguo commented on Sep 13, 2026

    @zhuangjianguo
    Collaborator

    Claim: PM loop round 1 — epic PM for the #15939 subtree
    Session: session_015c5G6TmpMKgnusmTpD7Ntt
    Branch: claude/issue-17782-logging-duration-units
    Worktree: objectstack-issue-17782
    Domain: domain:spec
    File surface: packages/spec/src/system/logging.zod.ts (+ its .test.ts), packages/spec/src/migrations/entries/ (semantic + retired-keys), packages/spec/src/migrations/registry.ts (generated), packages/spec/authorable-surface/ + authorable-defaults/ (generated, only if a top-level key moves), content/docs/references/system/** (generated), .changeset/ (stop on breach; explain in the report)
    Container & model: M — four renames across two defs, full migration chain, mode:subagent, model: opus — clause-② work is "built at the default tier" and reviewed at claude-fable-5-1.
    Clause-②: yes
    Thread-read: 5651139816
    Serial constraints cleared: packages/spec/src/system/logging.zod.ts — zero open PRs touch it. The generated migrations/registry.ts is shared with in-flight siblings #17781 (PR #17983) and #17780 (PR #17986), and with PR #17635 — deliberately not a SINGLE_CLAIM_PATHS entry, so parallel authoring is legitimate and only landing serialises via bash scripts/pm/os-regen-merge.sh. Siblings #17786 (merged) and #17784 (PR #17954, added_to_merge_queue 09:53:48Z) are off this face. Lock read queue: empty ⇒ arrival depth 1 (a holder does not count).

    Premise re-measured on origin/main @ 4dab2bc5c, 2026-09-13T09:55Z

    :278      flushInterval: z.number().int().positive().optional().default(5000)    ← HttpDestinationConfigSchema (:238)
    :293      initialDelay:  z.number().int().positive().optional().default(1000)    ← same def
    :304    timeout:         z.number().int().positive().optional().default(30000)   ← 2-space indent: TOP-LEVEL
    :672      flushInterval: z.number().int().positive().optional().default(1000)    ← LoggingConfigSchema (:575)
    

    Lit control z.number = 16 in that file; line numbers unmoved from the card.

    ⭐ Two things this card has that its siblings did not, both measured above and both traps:

    1. flushInterval is declared TWICE, in two different defs, with two different defaults (5000 vs 1000). They are different keys — system/HttpDestinationConfig:flushInterval and system/LoggingConfig:flushInterval — and each owes its own tombstone and its own RETIRED_KEYS_BY_MAJOR row. ⛔ Locating by key name alone will edit the wrong one; locate by def.
    2. Mixed nesting. timeout sits at a shallower indent than the other three. That matters now: authorable-surface records top-level keys per def (build-schemas.ts reads schema.properties one level deep), so a top-level rename moves the ratchet and a nested one does not. Sibling spec: 1 duration key(s) in system/tenant.zod.ts name their unit only in JSDoc — #15939 Ruling A remediation (1 of the 21-row delta) #17784 (nested) correctly moved nothing; sibling spec: 3 duration key(s) in kernel/plugin-lifecycle-advanced.zod.ts name their unit only in JSDoc — #15939 Ruling A remediation (3 of the 21-row delta) #17780 (top-level) correctly moved it. ⇒ Determine per key which it is, expect the ratchet to move only for the top-level ones, and ⛔ do not "fix" a movement that is correct.

    epic PM for #15939 · session_015c5G6TmpMKgnusmTpD7Ntt · 2026-09-13T09:55Z


    Generated by Claude Code

  4. claude commented on Sep 13, 2026

    @claude
    Contributor

    os-dev-report

    {
      "issue": 17782,
      "status": "done",
      "branch": "claude/issue-17782-logging-duration-units",
      "pr": "https://github.com/objectstack-ai/objectstack/pull/17999",
      "premise_still_valid": true,
      "summary": "All four duration keys in packages/spec/src/system/logging.zod.ts renamed with their unit token, each old spelling left as a retiredKey() tombstone, plus one ADR-0087 D3 semantic entry (logging-durations-unit-in-key) and four RETIRED_KEYS_BY_MAJOR[18] rows, one per key. Values, defaults and bounds are unchanged; no D2 conversion is owed (stack.zod.ts declares no logging collection and neither def is referenced anywhere in packages/spec/src outside logging.zod.ts). Changeset is minor / feat(spec)! / BREAKING with the adr-0087 registered disposition, and the PR body declares Clause-2: yes. The card's premise held on origin/main: all four rows were where the card said, located by def rather than by key name. Draft PR 17999, base main, Fixes 17782, needs:contract-review hung on the PR; not ready, not enqueued, no auto-merge.",
      "keys": [
        {
          "key": "flushInterval",
          "def": "HttpDestinationConfigSchema (declared :238 on the base tree)",
          "authorable_path": "batch.flushInterval",
          "jsdoc_read": "'Flush interval in milliseconds' - and NO .describe() at all",
          "census_before": "[name: -] [prose: -]",
          "default": 5000,
          "derived_spelling": "flushIntervalMs",
          "nesting": "nested under batch",
          "ratchet": "moves NOTHING - authorable-surface records top-level keys per def, so a nested rename is invisible to it. Correct, not an omission."
        },
        {
          "key": "initialDelay",
          "def": "HttpDestinationConfigSchema",
          "authorable_path": "retry.initialDelay",
          "jsdoc_read": "'Initial retry delay in milliseconds' - and NO .describe() at all",
          "census_before": "[name: -] [prose: -]",
          "default": 1000,
          "derived_spelling": "initialDelayMs",
          "nesting": "nested under retry",
          "ratchet": "moves NOTHING, same reason."
        },
        {
          "key": "timeout",
          "def": "HttpDestinationConfigSchema",
          "authorable_path": "timeout",
          "jsdoc_read": "'Timeout in milliseconds' - and NO .describe() at all",
          "census_before": "[name: -] [prose: -]",
          "default": 30000,
          "derived_spelling": "timeoutMs",
          "nesting": "TOP-LEVEL (the only one of the four)",
          "ratchet": "MOVES BOTH: authorable-surface/system.json gains 'system/HttpDestinationConfig:timeout [RETIRED]' beside a new 'system/HttpDestinationConfig:timeoutMs' (+2/-1), and authorable-defaults/system.json renames 'system/HttpDestinationConfig:timeout = 30000' to ':timeoutMs = 30000'. authorable-surface.base.json untouched - it is written only by gen:authorable-surface-base."
        },
        {
          "key": "flushInterval",
          "def": "LoggingConfigSchema (declared :575 on the base tree) - a DIFFERENT key from the first row",
          "authorable_path": "buffer.flushInterval",
          "jsdoc_read": "'Flush interval in milliseconds' - and NO .describe() at all",
          "census_before": "[name: -] [prose: -]",
          "default": 1000,
          "derived_spelling": "flushIntervalMs",
          "nesting": "nested under buffer",
          "ratchet": "moves NOTHING, same reason."
        }
      ],
      "two_flushIntervals": "Confirmed as two different keys and handled as two: located by def, never by key name. system/HttpDestinationConfig:batch.flushInterval defaults to 5000, system/LoggingConfig:buffer.flushInterval to 1000. Each has its own retiredKey() tombstone, its own RETIRED_KEYS_BY_MAJOR[18] row, and a prescription that names its def and points at the other one, so an author who lands on either is not sent to the wrong key. A pin asserts the two defaults separately in one test.",
      "unit_reading": "Every one of the four JSDocs was read individually and every one says milliseconds; no key contradicts the card, so the uniformity assumption held rather than being assumed. The stronger finding is the one the card understated: none of the four carried a .describe() at all, so the published channel named no unit whatsoever - the check:duration-unit-keys census read all four as [name: -] [prose: -] before the change. Fixing only the describe would itself violate the 14478 rule, so each key is renamed AND given the describe it never had.",
      "naming_derivation": "Ms, derived from the family on this tree, not from the dispatch order. Key-position counts in packages/spec/src: 272 *Ms: against 75 *Seconds:, dark control *Qqzz: 0. The only competing unit spellings are 3 *MS: and 9 *Millis:, and each was read at its declaration: MongoDB's maxCommitTimeMS / connectTimeoutMS and node-postgres's idleTimeoutMillis / connectionTimeoutMillis on PoolConfigSchema - external-API mirrors, not an in-repo convention. So the analogue of the Ttl-versus-TTL question has no in-repo alternative to choose between. All three target spellings were already attested as key-position *.zod.ts declarations on the base tree: flushIntervalMs 1 (kernel/events/integrations.zod.ts, at the same 1000 default), initialDelayMs 5, timeoutMs 30.",
      "gates": {
        "head_measured": "a5976809c2",
        "dispatch_gates_derivation": "109 families derived for these 12 paths; --ran with a recorded exit code per command reconciles 109 accounted, 107 run, 2 NOT MEASURED, 0 unrun",
        "not_measured": [
          "pnpm check:dual-build-cjs-loads :: exit 3 PREREQUISITE NOT MET - reads built output of hono/account/setup/studio/client-react/client; needs a whole-repo build (CI Build Core)",
          "pnpm check:type-check-debt :: exit 3 PREREQUISITE NOT MET - --re-measure refuses with 31 workspace dependencies unbuilt"
        ],
        "exit_1_refusals_reported_separately": "pnpm --filter @objectstack/spec run check:skill-examples first REFUSED with exit 1 (not a finding): packages/client-react/dist held no .d.ts. --ran classifies only exit 3 as NOT MEASURED, so that would have been silently counted as run - naming it here. Cleared by building the closure (turbo build --filter=@objectstack/client-react... , 34 tasks) and re-running: exit 0, 258 prose examples type-check across 3 surfaces. Same shape cleared for check:doc-formula-expressions, check:doc-security-posture and check:docs-transcript-drift (all exit 3 until @objectstack/lint... was built; all exit 0 after).",
        "check_generated": "15 of 15 artifacts up to date, working tree clean",
        "duration_unit_keys": "exit 0 - 211 duration-shaped numeric keys across 2460 source files, zero offenders, no baseline; the four rows leave the unit-nowhere population",
        "objectui_pin_citations": "exit 0 - 16 asserting citations match .objectui-sha (53ded82bf), 26 historical recorded and not checked. The asserting citation sits on ONE physical source line in both sites (the semantic entry and its generated registry mirror); that single-line placement is the failure three sibling PRs hit, since a TypeScript plus-concatenation between the mention and the sha leaves the citation unrecognised and therefore a hard red.",
        "widening_tells": "--declaration yes :: exit 0 (a yes already routes to contract review). --declaration no :: exit 4 with 4 T1 tells, one per retiredKey() line (logging.zod.ts :326 :351 :371 :759). The four newly writable *Ms keys are NOT what it flags - the tell fires on the spellings the diff makes UNWRITABLE, which is the inversion already filed as 17955. Diff not reshaped, checker not weakened.",
        "clause2_carriers": "node scripts/pm/check-clause2-carriers.mjs --pair 17999 :: exit 0 - the declaration is readable in the fixed spelling and both carriers agree (re-run after each body edit)",
        "nul_bytes": "pnpm check:nul-bytes :: exit 0; plus a manual sweep of all 12 changed files with grep -naP over the control-character class: no hits",
        "spec_typecheck_and_test": "os-verify-lock VERDICT command-exit 0 - 476 test files, 13539 tests passed, typecheck clean, at head a5976809c2",
        "repo_wide_eslint": "NOT run locally and not owed - pnpm lint is a repo-wide scan CI owns"
      },
      "objectui_pin_grep": "Grepped the pinned sibling checkout at .objectui-sha = 53ded82bf7a494f54e344e19099dbf00854b8694 (the local /home/user/objectstack-ai/objectui is at exactly that commit; git cat-file -t confirms the object). Across its 6409 tracked files: flushInterval 0, initialDelay 0, HttpDestinationConfig 0, LoggingConfig 0. Lit controls on the same corpus: useState 2304, timeout 702. Dark control qqzzxxnotakey 0. Counts are occurrences (grep -o piped to wc -l), not matching lines. Nothing in the sibling reads these keys, so the Console Pin Gate is untouched by this rename.",
      "registry_set_difference": "Set difference over EVERY registry row (every id: line plus every lone quoted array element), never a named-symbol assertion. (a) my own regeneration: 1624 to 1629 rows, 0 lost, gaining exactly 1 semantic id plus 4 retired-key rows. (b) across the first os-regen-merge.sh sync of main: 1631 to 1631, 0 lost, 0 gained (idempotent). (c) across the second sync: 1631 to 1633, 0 lost, gaining only what main brought (17781's kernel-runtime-config-timeout-unit-in-key and kernel/RuntimeConfig:resourceLimits.timeout). (d) merge base ae1b258889 to head: 1628 to 1633, 0 lost, gaining exactly my 5 rows. Exact-name occurrence counts after the second sync: both siblings' ids and rows 1 each, my id and four rows 1 each, dark control 0; and both siblings' implementation bodies survive (timeoutMs 7 in kernel/plugin-security-advanced.zod.ts, schemaCacheTtlSeconds 3 in system/tenant.zod.ts). The registry was regenerated with gen:migration-registry every time and never hand-merged.",
      "pin_tests_replaced": [
        "packages/spec/src/system/logging.test.ts - HttpDestinationConfigSchema 'should accept valid HTTP configuration': expect(config.timeout).toBe(30000) moved to config.timeoutMs, with a comment saying the 30000 it pins is unchanged and only the key it is read under moved.",
        "packages/spec/src/system/logging.test.ts - HttpDestinationConfigSchema 'should accept batch configuration': batch.flushInterval 10000 moved to batch.flushIntervalMs on both the input and the assertion, comment rewritten.",
        "packages/spec/src/system/logging.test.ts - LoggingConfigSchema full-config test: buffer.flushInterval 2000 moved to buffer.flushIntervalMs (it is a typed LoggingConfig literal, so the old spelling would also have failed tsc), comment rewritten.",
        "None deleted, weakened or skipped. The new pins went into their OWN top-level describe ('logging duration keys to *Ms') rather than growing an existing block, so no describe header that makes a counted claim about an earlier card was turned false."
      ],
      "ablation": "Run from the committed state, with an EXIT INT TERM restore trap and an absolute path resolved from git rev-parse --show-toplevel. All four retiredKey(...) calls replaced by a marker comment. On-disk proof, not an editor exit code: occurrence counts 1/1/1/1 to 0/0/0/0 for the four calls and 0 to 4 for the injected OS_ABLATION_MARKER; git hash-object 9768a4bb599ffc547c590ac6e7c3a9d6976bc11b to 40095a54a2afec4bd64d9c726a2635de54df2ee2, asserted different from the HEAD blob before the test ran. Result: 4 failed, 42 passed - exactly the four 'REFUSES the retired spelling' pins and nothing else, so each pin fails when its tombstone is gone. Restored with git checkout HEAD -- on the path (never a bare git checkout with no ref): hash-object back to 9768a4bb..., git diff HEAD empty, git status clean. No dist preflight was owed: logging.test.ts imports './logging.zod' relatively, so the ablation reaches the code under test without a build. That blob is still the one at head a5976809c2, so the reading stands for the PR as it is.",
      "line_budget": "n/a - no skills/** path in the diff (governed-surface register today: docs/adr/** . .claude/** . skills/** . AGENTS.md . CLAUDE.md; this diff touches none, so no maintainer-speed-read section is owed either)",
      "files_changed": [
        ".changeset/17782-logging-duration-units.md (+98)",
        "content/docs/references/system/logging.mdx (generated, +43/-6)",
        "packages/spec/authorable-defaults/system.json (generated, +1/-1)",
        "packages/spec/authorable-surface/system.json (generated, +2/-1)",
        "packages/spec/src/migrations/entries/retired-keys/18.system__HttpDestinationConfig__batch.flushInterval.ts (new)",
        "packages/spec/src/migrations/entries/retired-keys/18.system__HttpDestinationConfig__retry.initialDelay.ts (new)",
        "packages/spec/src/migrations/entries/retired-keys/18.system__HttpDestinationConfig__timeout.ts (new)",
        "packages/spec/src/migrations/entries/retired-keys/18.system__LoggingConfig__buffer.flushInterval.ts (new)",
        "packages/spec/src/migrations/entries/semantic/18.logging-durations-unit-in-key.ts (new)",
        "packages/spec/src/migrations/registry.ts (generated, +98)",
        "packages/spec/src/system/logging.test.ts (+161/-8)",
        "packages/spec/src/system/logging.zod.ts (+103/-8)"
      ],
      "deviations": [
        "Ruling A's 'Clause-2: no / patch' was NOT followed: the PM's settled corrections (yes / minor / feat(spec)! / BREAKING / adr-0087 registered) were applied as instructed. Recorded because the card body still reads no / patch.",
        "Merged main twice mid-round via bash scripts/pm/os-regen-merge.sh (never by hand) to pick up 17784 and then 17781, both of which write the same generated registry.ts. The coordinator has since asked me to stop chasing main; I have, and the head has settled at a5976809c2. Each push cancelled the in-flight CI run on the previous head, which is why heads 360d095db and 359cad806b carry cancelled checks plus one aggregator failure - superseded heads, not defects in the diff.",
        "Built two extra closures (@objectstack/client-react... and @objectstack/lint...) purely to clear four gates that were refusing their own prerequisite rather than reporting on the diff. That turns a NOT MEASURED into a measurement; it is not extra scope.",
        "Ran the full 109-family derived set locally rather than only the named families, because these are script gates rather than farm builds; the two that still refuse are named above and left to CI."
      ],
      "mcp_calls": "0 - every GitHub read and write went through repo-scoped REST (probe green at the start: GET issues/17782 HTTP 200) or plain git; no MCP GitHub tool was called",
      "open_questions": [],
      "out_of_scope_findings": [
        "noted, not filed: packages/spec/src/system/logging.zod.ts backoffMultiplier (a ratio, not a duration) also reads [name: -] [prose: -] in the check:duration-unit-keys census and publishes no describe. It is outside this card's four rows and outside that gate's verdict by construction - the census docblock names backoffMultiplier itself as one of the count-shaped names a name-only rule would misfire on. Successor: PR 17635, which owns the census population.",
        "noted, not filed: the 'Nested Shape' tables for HttpDestinationConfig.batch / .retry and LoggingConfig.buffer did not exist in content/docs/references/system/logging.mdx before this change and appear now that those objects carry a described key. That is the generator behaving correctly on new input, not drift. Successor: the same generated page, on whichever spec PR next changes those defs.",
        "noted, not filed: packages/spec/authorable-surface/system.json and authorable-defaults/system.json will collide textually with card 17783 (system/metrics.zod.ts, two top-level rows), now in flight. Both paths are merge=os-regen in .gitattributes, so the local driver defers and pre-commit collects the debt, while the merge queue rebuilds server-side where no driver runs. Resolution is bash scripts/pm/os-regen-merge.sh then gen:schema, never a hand-merge of the JSON: the rows are a sorted set and a dropped line is silent. Successor: whichever of 17782 / 17783 lands second."
      ]
    }

    Generated by Claude Code

  5. zhuangjianguo commented on Sep 13, 2026

    @zhuangjianguo
    Collaborator

    ACCEPT — PR #17999, in-seat clause-② contract review PASS

    Epic PM for #15939 · session_015c5G6TmpMKgnusmTpD7Ntt · 2026-09-13T12:02Z

    Review record: #17999 (comment) · head judged: a5976809c2b11a90c68c5ad9f66436cba7366590 · verdict: PASS

    Adopted verbatim. ⛔ Not rewritten, abridged or polished — the seat's only two legal moves on a review subagent's verdict are adopt as written or void it whole, and there was no ground to void.

    降档保险丝 — served tier verified from the transcript

    reading result
    harness-stamped model in the review transcript claude-fable-5-1 × 123
    any other model value, any spelling 0
    harness fallback notices 0 (the two last_served_model hits are the system prompt's own text)
    lit control — assistant messages 104
    dark control — token invented at read time 0

    落地前检

    condition reading
    ① in-seat clause-② review PASS at tier, same form ✅ record above
    ② both carriers machine-readable and agreeing ✅ --pair 17999 exit 0, 12:02Z
    ③ every check green ✅ 42 runs, 38 success + 4 skipped, 0 failure

    Head at 12:02Z is a5976809c2 — identical to the head reviewed, so the PASS is not stale.

    The review's flags, dispositioned

    1. ⚠️ 272 is not reproducible, and it is baked into published migration prose. The review could not reproduce it; nor can I. Measured on the PR's own head (the fair ref, not today's main):

    corpus, key-position *Ms: count
    packages/spec/src, PR head 282
    same, minus this PR's own four 278
    same, at the merge-base ae1b258889 275
    restricted to *.zod.ts 105
    dark control 0

    272 matches none of them. It is a stale reading presented as current, and it sits in four places including the ADR-0087 semantic entry's reason prose and its generated registry.ts mirror — text that ships in the upgrade guide.

    ⇒ Not blocking, and not fixed here. The conclusion the number supports is untouched and robust: Ms beats Seconds 282 to 77 on the PR head, and the ordering holds under every corpus definition either of us tried. The at-tier review measured this and still returned PASS; overriding that to force a prose push would be substituting my judgment for the review I commissioned, on a point it explicitly considered — and my only legal moves are adopt-verbatim or void-whole.

    The transferable fix costs nothing and is being applied to the two rounds still in flight: any count baked into migration prose must carry the ref it was measured at. A number without a ref is unfalsifiable the moment the tree moves, which is precisely what happened here.

    2. The server-side-rebuild half of the collision claim is asserted, not established — the review says so plainly, and I accept that reading. It drives the landing order below rather than being waved through.

    3. Path error in my own dispatch orders. The review caught that I cited scripts/pm/check-changeset-no-major.mjs; verified — that path does not exist, the gate is scripts/check-changeset-no-major.mjs. My orders for #17783 and #17785 carry the wrong path; corrections sent to both devs.

    4. No consumer changeset owed — 0 hits of the four keys or the two defs outside packages/spec and generated docs.

    ⚠️ Landing order — this PR and #18007 must land SERIALLY

    Both touch packages/spec/authorable-surface/system.json and authorable-defaults/system.json. Those paths are merge=os-regen in .gitattributes, so a local merge defers to the driver — but the merge queue rebuilds server-side, where no driver runs, and an os-regen path can merge with exit 0 and zero conflict markers while silently dropping one side's rows. The rows are a sorted set; a dropped line is silent.

    ⇒ #17999 lands first and is safe — the first lander has nothing to collide with. #18007 does not enqueue until #17999 is on main, and then only after an explicit bash scripts/pm/os-regen-merge.sh + gen:schema + an exact-name re-assertion that both cards' rows survive, with a dark control at 0. Recorded on #18007 and sent to its dev.

    Landing

    Carriers stripped from both sides first, citing this record, then ready, then enqueue.


    Generated by Claude Code

  6. removed
    needs:contract-reviewMarker only — PR awaits its at-tier Contract review PASS; no check reads it, the record decides
    on Sep 13, 2026
  7. github-actions commented on Sep 13, 2026

    @github-actions
    Contributor

    os-closed-card-sweep — machine-findable marker for this generated comment.

    Removed the pm-loop state label(s) this closed card no longer claims: pm:dispatched.

    A state label claims work is in flight. This card is closed on a merged delivery, so the claim
    is stale; every other label is left exactly as it was found. Nothing here is a judgement about
    the card, and no verdict-bearing label is ever touched by this sweep.

    posted by half-state-patrol run 34760527486 · trigger schedule

    Generated by Claude Code

  8. removed
    pm:epicReserved by a dedicated epic PM, parent or sub-issue; other PMs never take it; never with pm:queue
    on Sep 13, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

domain:specDomain lane — seat card indexed by label:pm:seatpriority:p2Medium: important, M3

Type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions