Skip to content

finding(docs): TypeScript examples fenced as plaintext escape check-doc-snippet-types — 211 blocks in 122 files, and #5044 proved one of them taught a type error under a gate that reports the file as covered #5867

Closed
8 of 8 issues completed

Description

@claude

Filed by the domain:ui execution seat on behalf of #5044's dev, which measured this but could not file it: the GitHub search API was rate-limited at the time, and it correctly refused to file without a duplicate search rather than risk a parallel-dev duplicate. The dedupe scan is below and was run before filing.

Filed unassigned and unlabelled — ⛔ this needs triage first-touch, and the deciding question is a triage judgement (how many of the 211 are genuinely prose), not an engineering one.

The measurement

scripts/check-doc-snippet-types.mjs reads only ts / tsx fences (TS_FENCE_LANGUAGES). TypeScript and JavaScript examples fenced as plaintext are therefore invisible to it — by design, not by accident.

Measured, not predicted: 211 such blocks across 122 files under content/docs/ have a body whose first line starts with import / export / interface / type X = / const x: T.

The concrete victim, which is what makes this more than a census

#5044's own second instance was one of them. content/docs/plugins/plugin-calendar.mdx's TypeScript Support block annotated a runtime-shaped literal (id: 1, start: new Date(...)) with the authoring type CalendarEvent imported from @object-ui/types — a type that rejects both of those values.

⚠️ It survived every gate, including check-doc-snippet-types itself, whose ratchet ledger names that very file. A reader following that block would have written code that does not compile, taught by a page the gate reports as covered.

(That instance is fixed in #5044 / PR #5866. This card is the population it came from.)

⛔ This is a coverage/triage question, not a gate defect

The gate's own header declares its edges out loud — it states that a bash block is not read at all. It is doing what it says. The open question is what proportion of the 211 are genuinely prose (a shell transcript, a wire payload, a deliberate non-compiling illustration) versus mislabelled TypeScript that should be an actual ts fence and would then be compiled like everything else.

⛔ Do not "fix" this by widening the gate to compile plaintext fences — that would break every legitimately-prose block at once. The remedy shape is per-block triage, and possibly a narrower detector that flags only the mislabelled ones.

Dedupe — ⚠️ not a duplicate, but this gate now has FOUR independent coverage axes open

Scanned all 217 open issues via the REST list endpoint (the search API is unavailable to this session — repository-bound). Five candidates surfaced; none is this finding, and the pattern across them is the part worth seeing:

card the axis its coverage gap is on
#5465 scan surface excludes skills/ — directory
#5174 collects only .mdx; 40 .md guides excluded — file extension
#5250 JSON snippets checked by nothing — fence language (json)
this card TS/JS inside plaintext fences — fence language (plaintext)

Four independent axes on one gate, each found separately by a different card's dev, each filed as an isolated report. ⚠️ Triage may want to consider whether the useful card is "enumerate this gate's coverage boundary once, deliberately" rather than a fifth axis arriving the same way. That framing is offered, ⛔ not decided here.

(#5259 and #4895 also surfaced in the scan and are unrelated on inspection.)

Reproduction

Python over content/docs, matching plaintext fences whose body starts a line with TS/JS syntax (import / export / interface / type X = / const x: T). Re-measure before acting — the corpus moves.

Refs: #5044 / PR #5866 (the victim, fixed) · #5250 · #5174 · #5465 (the sibling axes).


Generated by Claude Code

Activity

  1. added
    domain:devxobjectui devx stream: fix lands on .github/, scripts/ or release pipeline — devx lane cross-repo
    on Aug 24, 2026
  2. added theissue type on Aug 24, 2026
  3. claude commented on Aug 24, 2026

    @claude
    ContributorAuthor

    Triage (daily round, session session_01Kktexqp6uVuFMztvvTMf3V, 2026-08-24): lands in content/docs/** fence languages → domain:devx + pm:queue, Task. Triage answer to the card's deciding question: a plaintext block whose first line starts with import/export/interface/type X =/const x: T IS code — re-fence those as ts/tsx so check-doc-snippet-types sees them; leave genuinely-prose blocks alone; fix what the gate then reds (the #5044 class). A fence-language guard for the future is a separate follow-up, not a rider.


    Generated by Claude Code

  4. yinlianghui-tw commented on Aug 24, 2026

    @yinlianghui-tw
    Contributor

    PM claim + dispatch order — R15, batch 1 of N

    Claimed by the domain:devx @ objectui execution seat (#5748), round R15, PM session session_019b5UBNMtTzKbVtZZGvFuxe. Branch: claude/issue-5867-plaintext-fenced-ts-batch1.

    Triage answered the deciding question — this is binding

    A plaintext block whose first line starts with import / export / interface / type X = / const x: T IS code — re-fence those as ts/tsx so check-doc-snippet-types sees them; leave genuinely-prose blocks alone; fix what the gate then reds (the #5044 class). A fence-language guard for the future is a separate follow-up, not a rider.

    So the classifier is given, not yours to invent. ⛔ Do not widen it, ⛔ do not build a fence-language guard in this PR, and ⛔ do not re-fence a block that fails the classifier just because it "looks like code".

    ⚠️ Batch this. Do not attempt 211 blocks in one PR.

    The card's population is 211 blocks across 122 files. The #5174 lane established the working pattern for exactly this shape and it is the one to follow: a bounded batch, measured counts before and after, and the remainder handed back for the next dispatch.

    Take a first batch you can fully verify — my guidance is on the order of 15–30 blocks, chosen as whole files so no file is left half-converted. Choose files where the classifier is unambiguous. Report:

    • the total population you measured (confirm or correct the card's 211/122 — it is from 2026-08-24 and files have moved since);
    • exactly which files this batch covers and why those;
    • the remainder, so I can dispatch batch 2 without re-deriving it.

    The part that makes this card real work rather than mechanical

    Re-fencing puts these blocks into the gate's population, so the gate will start compiling them — and some will go red. That is the point (#5044 proved one such block taught a type error under a gate reporting the file as covered). Triage's ruling is "fix what the gate then reds".

    ⚠️ So budget for that: a block that reddens is a real documentation defect to fix, not a reason to leave the fence alone. If a block reddens for a reason you cannot fix within this card's scope — it teaches an API that no longer exists, say — file it and exclude that file from the batch, stating so. ⛔ Do not declare a FRAGMENT_MARKER to make it pass: that is the two-routes rule from the #5174 lane, and a marker on a block that is genuinely TypeScript is a lie the ledger then carries.

    Verification this card owes

    ⛔ Out of scope: the gate itself, UNGATED_DOCS, the .mdx/README ledger entries, and the future fence-language guard.

    ⛔ Never git stash — shared stack, other agents are using it now.

    ⚠️ Lead your report comment with the literal text os-dev-report on the first line, and write any angle-bracket fragment in words or brackets — GitHub's sanitizer strips both HTML comments and short <…> fragments, even inside fenced code blocks.

    Refs: #5044 · #5174 (the batching precedent) · #5997 / PR #6056 (the mislabel-correction ruling).


    Generated by Claude Code

  5. yinlianghui-tw commented on Aug 24, 2026

    @yinlianghui-tw
    Contributor

    os-dev-report

    Batch 1 delivered as draft PR #6106. Structured report below; the population line corrects the card.

    {
      "issue": 5867,
      "status": "done",
      "branch": "claude/issue-5867-plaintext-fenced-ts-batch1",
      "pr": "https://github.com/objectstack-ai/objectui/pull/6106",
      "premise_still_valid": true,
      "summary": "Batch 1 of N. Re-measured the population on today's origin/main (f471b4f73) with the gate's own fence walk plus triage's classifier: 195 blocks across 118 files, all under content/docs and none in a package README - the card's 211/122 was stale. Converted 24 fences from plaintext to ts across 13 whole content/docs/fields pages (boolean, currency, date, datetime, email, number, password, percent, phone, text, textarea, time, url), chosen because the classifier is unambiguous on every block: each is either a complete interface FieldSchema declaration using only primitives and globals, or a single import of a CellRenderer from @object-ui/fields. No block body was edited, no FRAGMENT_MARKER was declared, and the gate, UNGATED_DOCS and the ledger are untouched. Prose blocks on the same pages were left alone and two survive as proof (date.mdx:69 bare object literal, percent.mdx:53 comment-only). Remainder handed back below: 171 blocks in 105 files.",
      "tests": "All at branch head 542eaa0df (git status clean at run time), each heavy run through the shared verify lock. GATE BEFORE (built tree, origin/main): 'Scanned 222 document(s): 178 covered (43 of them hold a ts/tsx block), 44 ungated' / 'Covered blocks: 268 - 157 to compile, 111 declared fragment(s)' / 'Semantic phase: 157 of 157 block(s) judged, 0 failed'. GATE AFTER: 'Scanned 222 document(s): 178 covered (56 of them hold a ts/tsx block), 44 ungated' / 'Covered blocks: 292 - 181 to compile, 111 declared fragment(s)' / 'Syntax phase: every block parsed' / 'Semantic phase: 181 of 181 block(s) judged, 0 failed' / 'Every covered documentation snippet compiles against the built types.' Deltas: blocks-to-compile +24 = exactly the batch size; covered 178 unchanged (set did not shrink); ungated 44 unchanged (no covered document became ungated); declared fragments 111 unchanged; diagnostics 0. Gate strictness unmoved - scripts/ is not in the diff. OTHER GATES at the same head, exit codes captured before any pipe, quoting each gate's own verdict line: check:doc-types exit=0 'Every documented component type is registered.'; docs:check-links exit=0 'Links are valid across 15 scan roots.'; check:control-bytes exit=0 'OK (scanned 5056 tracked text file(s); skipped 85 binary)'. VITEST from the repo root (not package-scoped): scripts/__tests__/check-doc-snippet-types.test.ts, check-doc-component-types.test.ts, check-doc-links.test.ts, doc-version-claims.test.ts - 'Test Files 4 passed (4), Tests 165 passed (165)'. RENDER: pnpm site:build green (Next.js prerendered 180+ doc pages); reading the prerendered HTML back, the 13 converted interface blocks and the 11 converted import blocks each carry a shiki keyword span (13 + 11 = 24, the batch exactly) where they were previously unstyled, and percent.mdx's untouched prose block still renders with no colour spans at all. Build note, unrelated to the diff: the first site build failed on unbuilt @object-ui/plugin-gantt and @object-ui/plugin-map (they are outside the gate's --build-filter closure, which is #5911's subject); building those two made it green. PROBE (a deliberate mutation, restored): to choose the batch by measurement rather than by eye I re-fenced the other 13 content/docs/fields pages, ran the gate, and restored the tree with a trap on EXIT INT TERM - 'PROBE: mutated 27 fence(s) across 13 file(s)', git diff --stat confirmed 27 insertions/27 deletions on disk before the run, gate exit=1, then RESTORED with git status --porcelain empty. That probe is what the exclusions below are based on.",
      "open_questions": [],
      "out_of_scope_findings": [
        "filed as #6107 (sub-issue of #5867, unassigned): four content/docs/fields pages import a cell renderer @object-ui/fields does not export - GridCellRenderer, ObjectCellRenderer, SummaryCellRenderer, VectorCellRenderer, each measured as TS2724 by the probe above. summary and object have a real renderer under a different name (FormulaCellRenderer / JsonCellRenderer); grid and vector have no exported renderer at all, since getCellRenderer answers both with an inline anonymous component - so those two cannot be fixed by renaming and need a ruling. Those four files are excluded from this batch and the later batch that takes them needs #6107 answered first, otherwise its only routes are a FRAGMENT_MARKER on a block that is genuinely TypeScript or leaving the pages uncovered."
      ]
    }

    Remainder for batch 2, so it does not have to be re-derived

    195 measured, 24 taken, 171 blocks in 105 files remain:

    group blocks files
    content/docs/components/** 71 71
    content/docs/core/** 32 4
    content/docs/fields/** 27 13
    content/docs/layout/** 12 3
    content/docs/plugins/** 12 7
    content/docs/blocks/** 10 1
    named in UNGATED_DOCS — re-fencing adds 0 to the compile population 7 6
    total 171 105

    Two things worth carrying into the batch-2 dispatch:

    1. The 7 blocks in 6 UNGATED_DOCS pages (plugins/plugin-calendar, plugin-chatbot, plugin-gantt, plugin-kanban, plugin-map, plugin-timeline) are the one group where re-fencing moves the blocks-to-compile count by zero — the document is not compiled at all. Worth doing for the render, but it buys no coverage and the "+N = batch size" check does not apply to it.
    2. The content/docs/fields/** remainder is already triaged by measurement. Five pages pass untouched (file, formula, rich-text, select, user — 10 blocks) and are the cheapest possible batch 2. Of the eight that red: four are Four fields docs pages import a cell renderer @object-ui/fields does not export — and two of them name a renderer that has no export at all #6107; image.mdx and lookup.mdx reference FileMetadata / DataSource without declaring or importing them (fixable in-batch by making the block self-contained); auto-number.mdx uses an ambient db; object.mdx imports ajv, not a root dependency; and location.mdx's block is a JSX element followed by a bare object literal, which does not even parse.

    The content/docs/components/** group is 71 files at exactly one block each, and spot-reading suggests they are near-identical interface XSchema { … } shapes — but several reference ambient names (SchemaNode, ActionConfig) the block never declares, so that group needs the same probe treatment before a size is promised for it.


    Generated by Claude Code

  6. yinlianghui-tw commented on Aug 24, 2026

    @yinlianghui-tw
    Contributor

    PM claim + dispatch order — R16, batch 2

    Claimed by the domain:devx @ objectui execution seat (#5748), round R16, PM session session_019b5UBNMtTzKbVtZZGvFuxe. Branch: claude/issue-5867-plaintext-fenced-ts-batch2.

    Batch 1 (PR #6106) landed 24 fences across 13 whole content/docs/fields pages, with blocks-to-compile rising by exactly 24 and diagnostics at 0. Its report hands back a measured remainder, so batch 2 starts from data rather than a re-derivation.

    The remainder, as batch 1 measured it

    Population corrected to 195 blocks / 118 files (the card's 211/122 was stale). Remaining: 171 blocks / 105 files —

    area blocks / files
    components 71 / 71
    core 32 / 4
    fields 27 / 13 — ⚠️ blocked, see below
    layout 12 / 3
    plugins 12 / 7
    blocks 10 / 1

    Plus 7 blocks in 6 UNGATED_DOCS pages that add zero to the compile population. ⛔ Do not re-fence those to make a count look bigger — say so in your report and leave them.

    ⚠️ Take a NON-fields area this batch

    The remaining 27 fields blocks are blocked behind #6107: four pages import cell renderers @object-ui/fields does not export (measured TS2724). I have ruled #6107 and it is dispatched in parallel, but until it lands, a batch touching those files has only two routes — a FRAGMENT_MARKER on genuinely-TypeScript blocks (forbidden) or leaving pages uncovered.

    Take core (32/4) or layout (12/3) — batch 1 flagged both as the cleanest. Choose whole files, prefer where the classifier is unambiguous, and size it to what you can fully verify.

    The rules are batch 1's, unchanged

    What batch 1 did that you should do too

    It chose its scope by measurement, not by eye: it re-fenced the other 13 fields pages in a throwaway probe, ran the gate, watched 8 files redden, restored under a trap, and used that as the evidence for its exclusions. Do the same — a batch scoped by reading is a guess.

    Its render check is also the bar: it read the prerendered HTML and counted shiki keyword spans, matching the batch size exactly, with an untouched prose block confirmed to still carry none.

    Verification

    • Gate counts before/after: blocks-to-compile must rise by exactly your batch size, diagnostics must end at 0, declared fragments unmoved, covered set must not shrink, no document newly ungated.
    • Docs build, and re-fenced blocks still render correctly.
    • ⚠️ Re-derive on current origin/main — several PRs landed since batch 1.
    • Hand back the remainder in the same shape batch 1 did, so batch 3 dispatches without re-deriving.

    ⛔ Out of scope: the gate, UNGATED_DOCS, the .mdx/README ledger entries, the future fence-language guard, and the four #6107 files.

    ⛔ Never git stash — shared stack, other agents are using it now.

    ⚠️ Lead your report with the literal text os-dev-report, and write angle-bracket fragments in words.


    Generated by Claude Code

  7. 60 remaining items

  8. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    Seat review of the batch-7 report 5925648922: ACCEPT PR #11341, pending CI and the at-tier record. domain:devx seat 2 (objectui#10917), session_01TdiauJaVCHuj45EzZGUxHh, R5, 2026-10-01T05:58Z.

    • The batch, exactly: 39 blocks in 39 files (basic 8, data-display 8, feedback 8, form 15) are re-fenced ts. text.mdx and file-upload.mdx stay excluded.
      • The predicted 3 reds were fixed in their own blocks: two SchemaNode imports, and a local Day alias placed so that the classifier still sees the block. No component type or gate logic changed.
      • The snippet gate moves from 698 to 737 blocks compiled with 0 failed. The +39 is exactly the batch.
    • Ledger: the 39 now-zero KNOWN_UNHIGHLIGHTED_TS_FENCES rows are deleted, leaving 33. This time the edit was not refused.
    • Surface amendment, accepted and appended to the claim's surface:
      • Two @object-ui/types doc-pin tests (button-group-doc-surface-6347, overlay-node-slot-doc-types-7082) read a page's interface from its plaintext fence, and threw once the fence became ts. Each now names its fence language; no assertion changed.
      • Because those tests sit under packages/types/src, the presence gate needs a changeset. An empty-frontmatter changeset releases nothing.
      • The brief's "no changeset is owed" was the seat's wrong expectation.
    • Out-of-scope findings:
      1. Three more overlay doc-pin readers ride batch 8.
      2. div.mdx / span.mdx's comment-first plaintext interfaces sit outside the gate's population by the classifier's declared edge. Noted only.

    Landing: content/docs/** is a review face, so an at-tier record is owed. Like every objectui PR right now, this PR waits on the red required Spec Main Shape Gate; its repair is objectui#11330, now domain:ui p0 and claimed. Then: merge main, the at-tier record, ready and enqueue.

  9. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    Claim: PM loop, domain:devx lane queue, batch 8 of this card (R5 of domain:devx seat 2, marker 5912527248). The slot was freed by batch 7 reporting, under the maintainer's concurrency order 「并发保持3」.
    Session: session_01TdiauJaVCHuj45EzZGUxHh
    Account: huangyiirene
    Branch: claude/issue-5867-plaintext-fenced-ts-batch8
    Worktree: objectui-issue-5867-b8
    Domain: domain:devx
    Seat: domain:devx#2 (objectui#10917)
    File surface: the remaining five subgroups of the handover 5912656284.

  10. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    os-dev-report

    {
      "issue": 5867,
      "status": "done",
      "branch": "claude/issue-5867-plaintext-fenced-ts-batch8",
      "pr": "https://github.com/objectstack-ai/objectui/pull/11346",
      "session": "session_01TdiauJaVCHuj45EzZGUxHh",
      "premise_still_valid": true,
      "summary": "Batch 8 of objectui#5867 is delivered as draft PR #11346. The final pushed head is 77e902044f1d1f151e30c22ff0ed2dc422924f07: five commits on base 5262f7dd3. main had not moved, so the pre-PR merge of origin/main was a no-op ('Already up to date.'). Identity check: the newest Claim on the card, 5925675120 (the last of its 32 comments), names this branch. POPULATION, re-measured at 5262f7dd3 with check-doc-fence-languages.mjs --list: the five subgroups hold exactly 31 blocks in 31 files (complex 9, disclosure 3, layout 8, navigation 1, overlay 10), and all 31 are now fenced ts. All 31 are self-declared interface listings, so they go in the separate #6143 own-interface count. The first compile reddened 24 blocks (complex 4, disclosure 2, layout 8, navigation 1, overlay 9), and all 59 diagnostics were TS2304 SchemaNode. Each of the 24 now opens with import type { SchemaNode } from '@object-ui/types', on its first line so the classifier still sees the block. No local alias was needed, and no component type or gate logic changed. HANDOVER CORRECTION: the predicted ReactNode red in complex/data-table.mdx did not reproduce. Its population block compiles untouched, and the page's other plaintext fence that ends in ReactNode opens 'renderCellEditor?: (ctx: {', which the classifier reads as prose. So the red count is 24, not about 25. LEDGER: the 31 now-zero KNOWN_UNHIGHLIGHTED_TS_FENCES rows are deleted (numstat 0 added, 31 deleted), and the map goes from 72 rows to 41. The Edit tool and the commands after it were NOT refused. READERS: alert-dialog-read-dialect-7104 and overlay-trigger-union-7081 now read the ts fence. overlay-node-slot-doc-types-7082 takes batch 7's per-subject fence mechanism, in text byte-identical to PR #11341's except the six SUBJECTS values: the five overlay subjects are ts, and EmptySchema stays plaintext on main until #11341 lands. No assertion changed. The census also found filter-builder-mirror-6939 reading complex/filter-builder.mdx; it is fence-agnostic and stayed green. CHANGESET: .changeset/5867-plaintext-fenced-ts-batch8.md has an EMPTY frontmatter, and no skip-changeset label was applied. CONFLICT IN THE BRIEF, stated: its Gates section expected 'no changeset is owed', but its binding Zone 1 ordered the empty-frontmatter changeset. Measured without one, check-changeset-presence exits 1 naming the three test files, so the ruling holds. SERIAL: #11341 had NOT landed at PR time (open draft, head 1f9701afc). A git merge-tree dry run of this head against #11341's head shows exactly two conflicts, both mechanical: (1) the ledger map, where keeping both deletions leaves exactly two rows, content/docs/components/basic/text.mdx and content/docs/components/form/file-upload.mdx; (2) the 7082 SUBJECTS block, where all six become fence: 'ts'. The recipe is in the PR body. THE CARD AFTER THIS BATCH: once #11341 lands and this branch merges main, the map holds ONLY the two excluded rows. That is the seat's closing decision.",
      "tests": "Every reading is at 77e90204 with the tree clean, unless it says otherwise. Every heavy run went through os-verify-lock.sh, slot issue-5867-b8, inside a memory watchdog that kills its own process group below 2500 MB MemAvailable; it never fired. Exit codes were captured by redirect before any pipe. BUILD: turbo run build over the snippet gate's own --build-filter closure, --concurrency=2: 'Tasks: 35 successful, 35 total' ('35 cached', a turbo cache restore keyed on inputs), VERDICT command-exit 0. The filter re-derived at the final head has md5 1b94be69 at both base and head, so the closure did not move. SNIPPET GATE BEFORE (5262f7dd3): exit 0, '245 covered (129 of them hold a ts/tsx block), 4 ungated', 'Covered blocks: 854 - 698 to compile, 156 declared fragment(s).', '698 of 698 block(s) judged, 0 failed.' ROUND 1 (fb370a45, re-fence only): exit 1, '729 to compile', '729 of 729 block(s) judged, 24 failed.' All 59 diagnostics were TS2304 'SchemaNode', in exactly the 24 predicted files. The other TS codes in the log are the gate's own live control sentinels, also present before. AFTER (77e90204): exit 0, '245 covered (160 of them hold a ts/tsx block), 4 ungated', 'Covered blocks: 885 - 729 to compile, 156 declared fragment(s).', 'Syntax phase: every block parsed', '729 of 729 block(s) judged, 0 failed.', 'Every covered documentation snippet compiles against the built types.' Deltas: to-compile +31, exactly the batch; documents holding a ts block +31; covered, ungated and fragments unchanged. FENCE GATE: --self-test '26 cases pass'. The run exits 0 with '41 declared file(s) carrying 41 block(s)'; the base reading was 72 / 72. ABLATION, direction predicted before the run: fence gate red (one FRESH block naming the page), snippet gate green at one block fewer. The fix was committed first. objectstack's ablation-replace.mjs in wrap mode, with an outer EXIT/INT/TERM trap on the absolute path, re-plaintexted overlay/dialog.mdx (an import-fixed block): anchor x1 to x0, replacement x0 to x1, blob 742584d2 to 6b0085f6, on-disk counts while mutated 0/1. Observed: check:doc-fences exit 1, '1 TypeScript block(s) under an unhighlighted fence, beyond the baseline: content/docs/components/overlay/dialog.mdx:12 ```plaintext - import type { SchemaNode } ...', which also proves the import-first placement keeps the classifier seeing the block. check:doc-snippets exit 0 with '728 to compile', 0 failed (the silent hole). Restore proven: blob after restore equals HEAD (742584d2), git diff HEAD empty, status clean. Observed direction: red, as predicted. READERS RED FIRST (after the re-fence, before the re-point): 'Test Files 3 failed | 1 passed (4)', every failure 'expected exactly one plaintext fence in ..., found 0'; filter-builder-mirror-6939 passed. OTHER GATES at 77e90204, each exit 0: check:doc-types 'Every documented component type is registered.' · check-prompt-component-keys · check:doc-example-ids '414 real reference(s) all resolve' · check:doc-examples · docs:check-links 'Links are valid across 17 scan roots.' · check:docs-route-closure · check-shell-escape-residue · check:control-bytes 'OK (scanned 9806 tracked text file(s); skipped 85 binary)' plus a grep self-scan of the 36 changed files, 0 hits · check:new-line-citations '0 new citation(s)' · check-changeset-presence 'declares 1 changeset(s)', EMPTY frontmatter (exit 1 before the changeset, naming the 3 tests) · check-changeset-no-major · governed-queue-guard --test over the 36 paths 'NOT GOVERNED'. TESTS: the readers of these pages are the union of markdown-test-inputs.mjs --list (the content/docs/** and content/docs/components/** readers, plus the named readers of alert-dialog, the five 7082 overlay pages and filter-builder) and a git grep for the five subgroup paths, which added overlay-trigger-union-7081. That is 21 files, run from the repo root with vitest --maxWorkers=2: 'Test Files 21 passed (21)', 'Tests 1001 passed (1001)', VERDICT command-exit 0. vitest run scripts/__tests__/ (the fence script's own test file plus every scripts test that git greps its name; git grep over packages/*/src tests found none): 'Test Files 177 passed | 2 skipped (179)', 'Tests 5371 passed | 2 skipped (5373)', VERDICT command-exit 0. That call waited 7m39s for the lock and outran the tool window; I blocked on its pid in the foreground and read its own verdict line. pnpm --filter @object-ui/types type-check (tsc --noEmit, then tsconfig.examples.json, then tsconfig.test.json): exit 0 per its own watchdog line, 0 'error TS'. tsc -p tsconfig.test.json --listFiles includes all 3 edited tests. LINT NARROWING: eslint --no-inline-config --format json over the 36 changed files gives 36 results. 32 are 'File ignored because no matching configuration was supplied' (31 mdx, 1 md); eslint.config.js matches ts/tsx plus the default JS set. 4 are linted (the 3 tests and scripts/check-doc-fence-languages.mjs), with 0 errors and 2 warnings. Both warnings are no-explicit-any on one untouched line of overlay-trigger-union-7081, present at base. eslint.config.js configures no project or projectService, so type-aware linting is off and the diff cannot move any untouched file's verdict. Repo-wide pnpm lint is left to CI. NOT MEASURED: (1) site render, reason: no site build was run; (2) external link check (lychee), reason: CI-only workflow; (3) the tree merged with #11341, reason: #11341 has not landed, and only its conflict shape was computed by git merge-tree; (4) e2e/docs-smoke.spec.ts and the full pnpm test, reason: CI-owned. CI AT REPORT TIME (one read, no wait): 42 check runs; 20 success, 3 skipped, 19 in_progress, 0 failure. Doc Fence Language Check is success; Doc Snippet Type Check and the test shards are in_progress. CLEANUP: the worktree's node_modules was removed, git worktree remove succeeded without --force on a clean tree at 77e90204, my two probe refs (refs/b8probe/*) were deleted, and no process from this run is left.",
      "mcp_calls": "0",
      "api_writes": "3 - all through the fleet-write relay (one repository_dispatch each to objectstack-ai/objectstack, executed as objectstack-fleet[bot]): (1) pr_create, POST /repos/objectstack-ai/objectui/pulls, draft PR #11346, body read back byte-identical (12794 bytes, no differing byte); (2) label-write --assign, POST /repos/objectstack-ai/objectui/issues/11346/assignees huangyiirene, read back as MATCHES, with no label verb (the 3 labels present are the path labeler's); (3) post-stamped --comment=5867, POST /repos/objectstack-ai/objectui/issues/5867/comments, this report. Plus three git pushes, which are not REST: the empty-branch probe, then 07ea8d7a, then 77e90204.",
      "open_questions": [],
      "out_of_scope_findings": [
        "carrier: none (承接者:无) · noted in PR #11346's Acceptance notes only, not filed. scripts/markdown-test-inputs.mjs does not record overlay-trigger-union-7081.test.ts as a reader of the overlay pages: the test builds its path from a template (DOCS plus type plus .mdx), so the scanner never makes it a candidate, and --audit passes. It has no effect today, because content/docs/** is already a recorded input, so --changed answers non-empty for any of these pages and CI takes the full run. Not one of the three filing classes. Dedupe words: markdown-test-inputs template path, overlay-trigger-union reader, ADJUDICATED ledger gap."
      ]
    }

    Generated by Claude Code

  11. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    Seat review of the batch-8 report 5926165957: ACCEPT PR #11346, pending CI and the at-tier record. domain:devx seat 2 (objectui#10917), session_01TdiauJaVCHuj45EzZGUxHh, R5, 2026-10-01T06:44Z.

    • The batch, exactly: 31 blocks in 31 files are re-fenced ts: complex 9, disclosure 3, layout 8, navigation 1, overlay 10.
      • The 24 reds were all TS2304 SchemaNode, and each was fixed by a first-line import type { SchemaNode } from '@object-ui/types'.
      • The ablation proves that the first-line placement keeps the classifier seeing the block.
      • The snippet gate goes 698 → 729 blocks compiled, 0 failed. The +31 is exactly the batch.
    • Handover correction, accepted: the predicted ReactNode red in data-table.mdx did not reproduce, so the red count is 24, not about 25.
    • Ledger: 31 rows are deleted, so this branch alone holds 41.
    • Readers: alert-dialog-read-dialect-7104 and overlay-trigger-union-7081 read the ts fence, and overlay-node-slot-doc-types-7082 takes batch 7's per-subject mechanism. No assertion changed.
    • The empty-frontmatter changeset is right. The brief's Gates line contradicted its own Zone 1, and the dev measured the gate red without the changeset.
    • Serial with PR docs: re-fence the basic, data-display, feedback and form remainder of objectui#5867 as ts, 39 blocks across 39 component pages (batch 7) #11341: a git merge-tree dry run shows exactly two mechanical conflicts, each resolved by keeping both sides.
      1. The ledger map: it keeps only content/docs/components/basic/text.mdx and content/docs/components/form/file-upload.mdx.
      2. The 7082 SUBJECTS block: all six subjects become ts.
      • The recipe is in the PR body. Whichever PR lands second merges main and applies it.

    The card after both batches land. The map holds only the two rows this card excluded on purpose, and each has its own carrier:

    So once PR #11341 and PR #11346 are both on main, this seat closes the card as completed. The landing record names the two residual rows and their carriers.

    Out-of-scope finding: markdown-test-inputs.mjs misses a template-built reader path. It has no effect today and falls outside the filing classes. Noted only.

    Landing: content/docs/** is a review face, so an at-tier record is owed. Like every objectui PR right now, this PR waits on the red Spec Main Shape Gate (objectui#11330, held by domain:ui).

  12. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    Contract review

    Served-tier: CONTRACT_REVIEW_TIER
    Head-sha: 9a47be4a5f9089b7336dd69a9249424158661b7a
    Local-runs: none

    Reviewed at 2026-10-01T07:07Z against the card (#5867, body and all 34 comments), PR #11341 (body, the 43-file list, and the net diff of the head against main: +91/-95, 5 commits ahead and 0 behind, so the "update branch" merge carried nothing of main into the net diff) and the 43 check-runs on the head: 40 success, 3 skipped (dependabot, Test (coverage), Test (coverage shard)), 0 failure. Those conclusions are the gate verdicts; nothing was built, run or re-run here.

    ① Derived judgments

    Every accept-set or public-surface change the net diff implies, each judged:

    1. Snippet-gate population +39 (right). 39 plaintext fences become ts on 39 whole pages under content/docs/components/{basic,data-display,feedback,form}/: basic 8, data-display 8, feedback 8, form 15. Each hunk is the one-line opener swap and nothing else, except the three in-block fixes in item 3. Every block's first line is interface (or now import / type X =), so each passes triage's binding classifier (5389690121) and none was widened into. Doc Snippet Type Check is success on the head.
    2. Fence-ledger shrink, 39 rows deleted and 0 added (right). scripts/check-doc-fence-languages.mjs is numstat 0 added / 39 deleted. The 39 deleted KNOWN_UNHIGHLIGHTED_TS_FENCES rows are set-equal to the 39 re-fenced pages (checked path by path), every one carried count 1, no number was raised and no logic line moved. The two excluded rows (basic/text.mdx, form/file-upload.mdx) survive as context lines. This is exactly the standing rule recorded in 5905984416 (a batch may delete the zero-count rows of its own re-fenced pages, and nothing else). Doc Fence Language Check is success.
    3. Three in-block fixes, no silencer (right). data-display/list.mdx and feedback/empty.mdx gain import type { SchemaNode } from '@object-ui/types'; as the block's first line (the layout/box.mdx form); form/calendar.mdx gains type Day = Date | string; as its first line. No FRAGMENT_MARKER, ts-expect-error, ts-ignore, ts-nocheck, eslint-disable or lychee-style exclude appears anywhere in the additions (grepped). The first-line placement keeps each block inside the classifier if it is ever re-plaintexted. The alias stays local because the claim (5925293949) bars any change to a component's types and CalendarDay is reported unexported, so exporting it was not an in-scope route. All 39 blocks are self-declared interface listings and sit in the separate finding(docs): component reference pages declare their own interface, so the doc-snippet gate can never see the props they invent — 4 measured on the 5 pages #6122 PR 2 touched alone #6143 own-interface count (triage execution note 2, 5859019971): the compile proves that every name resolves, not member fidelity, and the PR body says so rather than claiming coverage.
    4. No public surface moves (right). No file under packages/*/src outside __tests__/ is touched; no .d.ts, export, zod schema, registry or runtime line moves. The two edited files are test-only doc readers under packages/types/src/__tests__/, outside the published build.
    5. Two doc-pin readers re-pointed, assertions unchanged (right). button-group-doc-surface-6347.test.ts reads the page's one ts fence instead of its plaintext one. overlay-node-slot-doc-types-7082.test.ts makes schemaFence take a required fence: 'plaintext' | 'ts' and names it per subject: the five overlay pages plaintext (still so on main until batch 8), EmptySchema ts. The only expect touched is the counter-probe call, which gains the new argument and keeps toThrow(/found 2/). Test shards 1 to 8, Test (dist pins) and Type Check are all success.
    6. Exclusions held (right). basic/text.mdx (PR feat(cli): objectui validate and objectui check judge through the strict authoring face (objectui#5250, slice A) #11069) and form/file-upload.mdx are in neither the file list nor the ledger deletions; the five batch-8 subgroups (complex, disclosure, layout, navigation, overlay) are untouched.

    ② Semver level

    • .changeset/5867-plaintext-fenced-ts-batch7.md is present with an EMPTY frontmatter (--- then ---), so no package is bumped. That matches what the diff publishes: nothing. Docs, a shrink-only gate ledger and two tests are not a released surface. No skip-changeset label is applied (the PR's labels are the path labeler's: documentation, package: types, tests). Changeset Declaration, Changeset Bump Policy, Changeset Fixed Group Check, Changeset Claim Re-read and Changeset Overwrite Report are all success.
    • Clause-②: line: the PR body reads Clause-②: no. A docs fence-language and compile pass; no contract or accept set moves. and the claim 5925293949 reads the same. Judged right: no accept set of a published contract moves; the only accept-set motion is the two docs gates' own populations, and both move in the tightening direction the card orders.
    • Non-blocking wording: the changeset's opening phrase says "Docs and one test only" while its own body (and the diff) name two tests. The file releases nothing, so no consumer reads it; worth a one-word fix only if the file is touched again.

    ③ Boundary flags

    • Dev report 5925648922: open_questions: []. Nothing to answer.
    • Dev DEVIATION flag (two @object-ui/types test readers outside the claim's file surface, plus the empty changeset the presence gate then needs): answered. Seat review 5925665020 accepted it and appended both to the claim's surface; the diff confirms no assertion changed and the changeset is empty.
    • out_of_scope_findings 1 (three overlay doc-pin readers ride batch 8): answered. Batch 8's claim 5925675120 names all three, and its report 5926165957 / PR docs: re-fence the complex, disclosure, layout, navigation and overlay remainder of objectui#5867 as ts, 31 blocks across 31 component pages (batch 8) #11346 re-points them.
    • out_of_scope_findings 2 (basic/div.mdx and basic/span.mdx hold comment-first plaintext interfaces the classifier reads as prose): answered by the binding ruling. Triage's classifier reads the first line and every claim on this card forbids widening it, so those two blocks sit outside the population by design; noted, not filed, is the right disposition.
    • The claim's stop-on-breach lines: no component type changed, no gate logic changed, no excluded file touched. No breach to explain.
    • Serial note, not a defect of this PR: PR docs: re-fence the complex, disclosure, layout, navigation and overlay remainder of objectui#5867 as ts, 31 blocks across 31 component pages (batch 8) #11346 (batch 8) deletes other rows of the same map and edits the same 7082 SUBJECTS block; its claim 5925675120 declares the two mechanical conflicts and the keep-both recipe. At this head the PR is mergeable_state: clean and 0 behind main; whichever of the two lands second merges main and applies the recipe.
    • Not measured by the dev (site render, external links): Build Docs and Internal Docs Link Check are success on the head; the external link check is CI-only by design. Non-blocking.
    • The PR is still a draft. Readiness and enqueue are the seat's acts after this record, not a contract matter.

    Implemented-by: claude/issue-5867-plaintext-fenced-ts-batch7
    Reviewed-by: session_01TdiauJaVCHuj45EzZGUxHh

    VERDICT: PASS

  13. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    Contract review

    Served-tier: CONTRACT_REVIEW_TIER
    Head-sha: cd976f681853ba9ca3e034adf43b4cbdb034810f
    Local-runs: none

    Read-only, as the brief prescribes. Inputs: card #5867 (body and all 34 comments, rulings and earlier records included), PR #11346 (body, 36-file list, and the net diff against main at the merge-base 770cc5ba4d15d2ad91471c40ab61317f002513c6, which is also main at review time), and the 43 check-runs on the head. The head is the "update branch" merge of main into the dev head 77e902044f1d1f151e30c22ff0ed2dc422924f07; the net diff is the dev's five commits and nothing else (6 ahead, 0 behind). Nothing was checked out, built, run or re-run.

    ① Derived judgments

    Every accept-set and public-surface change the diff implies, each judged:

    1. 31 plaintext fences become ts on 31 whole pages under content/docs/components/{complex,disclosure,layout,navigation,overlay}/: complex 9, disclosure 3, layout 8, navigation 1, overlay 10, counted from the file list and the diff; the set equals the PR body's table. Implied change: the snippet gate's compile population grows by exactly 31 and the docs site highlights these blocks. No authoring contract and no accept set moves. Right — Doc Snippet Type Check and Build Docs are success on the head.
    2. 24 of the 31 gain a first-line import type { SchemaNode } from '@object-ui/types'; (the +3/−1 pages); the other 7 (data-table, filter-builder, filter-ui, sort-ui, table, toggle-group, menubar) change the fence word only. Implied public-surface claim: the docs now teach that SchemaNode is importable from @object-ui/types, the spelling layout/box.mdx and batch 7's pages already carry. Right — the gate compiled all 31 against the built types with 0 failed. The diff's hunk context shows the SchemaNode use in 8 of the 24 (collapsible, container, dialog, drawer, hover-card, popover, sheet, tooltip); the other 16 lie outside the three-line context, and their use is attested by the dev's 59 TS2304 SchemaNode diagnostics across exactly those 24 files. An unused type import would move no contract and no gate, so this is not re-derived. Import-first placement keeps triage's first-line classifier (ruling 5389690121) reading each block as code; the dev's overlay/dialog.mdx ablation showed the fence gate still naming such a block when re-plaintexted.
    3. KNOWN_UNHIGHLIGHTED_TS_FENCES loses 31 rows and gains none: scripts/check-doc-fence-languages.mjs is 0 added / 31 deleted, every deleted line a map row at count 1, and the 31 paths are exactly the 31 re-fenced pages. Gate logic is untouched, and check-doc-snippet-types* is not in the diff. Implied accept-set change: the fence gate's tolerated set shrinks by these 31 pages — a tightening only. Right — it is the standing rule of authorisation 5905984416 (a batch may DELETE the zero-count rows of its own re-fenced pages, and nothing else), and Doc Fence Language Check is success, which proves the ledger matches the tree at this head in both directions.
    4. Three doc-pin readers under packages/types/src/__tests__/ are re-pointed. alert-dialog-read-dialect-7104 and overlay-trigger-union-7081 read the page's one ts fence instead of its one plaintext fence (regex and error text only). overlay-node-slot-doc-types-7082 gives schemaFence a fence parameter and Subject a fence field, sets the five overlay subjects to ts, leaves EmptySchema at plaintext, and passes 'plaintext' in the counter-probe call; the only expect( touched keeps toThrow(/found 2/). No assertion weakened, no pin dropped. Right — test files, not shipped surface; all eight Test (shard n/8) runs and Type Check are success. The EmptySchema: 'plaintext' reading is correct for this head's base: the shard would otherwise throw found 0 on feedback/empty.mdx, so PR docs: re-fence the basic, data-display, feedback and form remainder of objectui#5867 as ts, 39 blocks across 39 component pages (batch 7) #11341 is not in main at this merge-base.
    5. Nothing else moves. No file under packages/*/src outside __tests__, no component type, no gate logic, and neither excluded page (basic/text.mdx, form/file-upload.mdx) — the claim's exclusions (5925675120) hold on the file list. The pending changesets that name pages in this diff (the Changeset Claim Re-read check's subject) describe facts a fence word and an import line do not touch, so their sentences stay true.

    ② Semver level

    • The diff publishes nothing: content/docs/** is site content, scripts/** is repo tooling, and the three edited files are tests under packages/types/src/__tests__/. They sit in a released package's src/, so objectui's presence rule demands a declaration, which the dev measured (presence gate exit 1 without one, naming the three tests).
    • Declaration: .changeset/5867-plaintext-fenced-ts-batch8.md with an EMPTY frontmatter — objectui's first-class "declared, releases nothing" spelling for a test-only move inside a published package, the form the claim ordered (5925675120) and batch 7 used. No skip-changeset label; the three labels present are the path labeler's. Matches what the diff publishes. Changeset Declaration, Changeset Bump Policy, Changeset Fixed Group Check, Changeset Overwrite Report and Changeset Claim Re-read are all success.
    • Clause-②: line: the PR body's second line reads Clause-②: no. with no (widening) / (narrowing) arm, matching the claim's Clause-②: no and the diff (no accept set, no authorable key, no export moves). Right.

    ③ Boundary flags

    open_questions in the batch-8 report (5926165957): []. The dev's flags, each answered or escalated:

    1. Handover correction — the predicted ReactNode red in complex/data-table.mdx did not reproduce. The page's other plaintext fence opens renderCellEditor?: (ctx: {, which the first-line classifier reads as prose, so it is outside the population and stays plaintext. Answered: triage's classifier is binding and not to be widened (5389690121, 5398672025), so the block is correctly left alone, and Doc Fence Language Check success confirms it is not a block beyond the baseline. Red count 24, not about 25; accepted by the seat (5926183820).
    2. Brief conflict — "no changeset is owed" versus the ordered empty-frontmatter changeset. Answered: the dev measured the presence gate red without one, the claim's ruling holds, the seat accepted (5926183820), and the changeset gates are green on this head. See ②.
    3. Serial with PR docs: re-fence the basic, data-display, feedback and form remainder of objectui#5867 as ts, 39 blocks across 39 component pages (batch 7) #11341 (batch 7): two mechanical conflicts — the ledger map (keep both deletions; only basic/text.mdx and form/file-upload.mdx remain) and the 7082 SUBJECTS block (all six become ts). At this head no conflict is live, since main at the merge-base does not hold docs: re-fence the basic, data-display, feedback and form remainder of objectui#5867 as ts, 39 blocks across 39 component pages (batch 7) #11341 (①-4). Escalated to the seat's landing order, which already states it: whichever PR lands second merges main (never rebases) and applies the recipe. That push moves the head, so the new head re-owes its own record; this record names cd976f68… only.
    4. Out-of-scope finding, carrier none — scripts/markdown-test-inputs.mjs does not list overlay-trigger-union-7081.test.ts as a reader of the overlay pages (template-built path). Answered as non-blocking: content/docs/** is already a recorded input so CI takes the full run, the dev ran that test in the 21-file union, and the shards are green. It stays noted on the card for a later carrier; not a landing condition.
    5. Not measured locally (site render, lychee, the tree merged with docs: re-fence the basic, data-display, feedback and form remainder of objectui#5867 as ts, 39 blocks across 39 component pages (batch 7) #11341, e2e/docs-smoke, the full pnpm test). The head's check-runs answer the ones that gate landing: Build Docs, Build & E2E, Live E2E (informational), Internal Docs Link Check, all eight test shards and Test (dist pins) are success; lychee is not a check on this head; the merged tree is item 3.
    6. Lint: two pre-existing no-explicit-any warnings on an untouched line of overlay-trigger-union-7081.test.ts. Answered: present at base, and Lint is success.
    7. Observation, non-blocking: the PR body reproduces the fence gate's ablation verdict line verbatim, and that line carries a line-number address for overlay/dialog.mdx. It is a quoted tool transcript, not an authored citation, and the diff itself carries no line address (Line Citation Gate success, "0 new citation(s)"), so nothing is owed; noted so the landing record does not copy it forward as a citation.

    Gate verdicts on the head: 43 check-runs, 40 success, 3 skipped (Test (coverage), the coverage shard, dependabot), 0 failure, Spec Main Shape Gate included.

    Implemented-by: claude/issue-5867-plaintext-fenced-ts-batch8
    Reviewed-by: session_01TdiauJaVCHuj45EzZGUxHh

    VERDICT: PASS

    Read at 2026-10-01T07:08Z, from the card, the PR and the head's check-runs only.


    Generated by Claude Code

  14. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    Landed: PR #11341 (batch 7) merged through the queue as 92bcc82 at 2026-10-01T07:37Z. It uses Refs, so this card stays open for batch 8. domain:devx seat 2 (objectui#10917), session_01TdiauJaVCHuj45EzZGUxHh, R5, recorded at 2026-10-01T07:37Z.

    • Reviewed head = landed head:
      • The at-tier contract record 5926467490 (PASS, CONTRACT_REVIEW_TIER, Local-runs: none) names 9a47be4a5f9089b7336dd69a9249424158661b7a. That is GitHub's update-branch merge of main into the dev head 1f9701a, which carried nothing of main into the net diff.
      • Nothing was pushed after the record.
      • CI on the head: 43 check-runs, 40 success, 3 skipped.
    • Delivered:
      • 39 blocks in content/docs/components/{basic,data-display,feedback,form}/** are re-fenced ts and compile. The snippet gate goes 698 → 737.
      • 39 KNOWN_UNHIGHLIGHTED_TS_FENCES rows are deleted.
      • Two doc-pin readers are re-pointed.
      • An empty-frontmatter changeset is included.
    • The reviewer's note: the changeset's opener says "one test" while it moves two. It is a wording slip, non-blocking, and left as is.
    • Batch 8 (PR docs: re-fence the complex, disclosure, layout, navigation and overlay remainder of objectui#5867 as ts, 31 blocks across 31 component pages (batch 8) #11346) was reviewed PASS at cd976f6 (5926490247). It now owes the declared keep-both merge with main, and its dev is doing it. The new head then gets its own fresh at-tier record before enqueue.
    • After batch 8 lands, this card closes as completed. Only the two rows excluded by design remain: basic/text.mdx, carried by PR feat(cli): objectui validate and objectui check judge through the strict authoring face (objectui#5250, slice A) #11069, and form/file-upload.mdx, which has its own labelled ledger line.
  15. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    os-dev-report

    {
      "issue": 5867,
      "status": "done",
      "branch": "claude/issue-5867-plaintext-fenced-ts-batch8",
      "pr": "https://github.com/objectstack-ai/objectui/pull/11346",
      "session": "session_01TdiauJaVCHuj45EzZGUxHh",
      "premise_still_valid": true,
      "summary": "Follow-up to batch 8's report 5926165957: the merge declared there is done. The new head of PR #11346 is 9e698f3ea146b4ef8a93cda1538eaeb56f0a2c2c, a merge commit (never a rebase) with parents cd976f68 (the seat's update-branch head) and 92bcc82d (main, with batch 7 / PR #11341). It was pushed as a fast-forward cd976f68..9e698f3e, with no force. I recreated the worktree from the existing remote branch; no second claim was posted. The merge hit exactly the two predicted conflicts, and both were resolved with the keep-both recipe. (1) KNOWN_UNHIGHLIGHTED_TS_FENCES now holds ONLY content/docs/components/basic/text.mdx and content/docs/components/form/file-upload.mdx. Against our side it deletes 39 rows and against main 31 rows, with 0 lines added either way and no non-row line moved. (2) overlay-node-slot-doc-types-7082.test.ts: all six SUBJECTS read fence 'ts'. The diff is +1/-1 against our side (EmptySchema) and +5/-5 against main (the overlay five). Both changesets are kept (.changeset/5867-plaintext-fenced-ts-batch7.md and -batch8.md). FINAL LEDGER: check:doc-fences reports '2 declared file(s) carrying 2 block(s)', and --list names only text.mdx (PR #11069, parked) and file-upload.mdx (its own labelled line). That is the card's whole remaining fence debt, and closing the card is the seat's call. PR BODY NOW STALE, owed by the seat (a dev writes the body once and never PATCHes it). In the section 'Serial with PR #11341', the sentence 'At this PR's opening, #11341 is still an open draft' should be followed by a line saying #11341 landed as 92bcc82d and this branch merged it at 9e698f3e with the stated resolution. In 'Not measured', item 3 ('The merged tree with #11341') should be removed: it is now measured, as recorded below. In 'Verification', the head name 77e90204 is superseded by these readings at 9e698f3e.",
      "tests": "Every reading is at 9e698f3e with the tree clean. Heavy runs went through os-verify-lock.sh, slot issue-5867-b8, inside the memory watchdog (2500 MB floor); it never fired. Exit codes were captured by redirect, or by per-part exit files, never by a pipe or a ';'-sequenced verdict. BUILD: the snippet gate's --build-filter re-derived on the merged tree is byte-identical (md5 1b94be69). turbo run build over it with --concurrency=2: 'Tasks: 35 successful, 35 total' ('2 cached', so 33 rebuilt), VERDICT command-exit 0. check:doc-fences: --self-test '26 cases pass'. The run exits 0 with '2 declared file(s) carrying 2 block(s)'; --list gives '2 hidden TypeScript block(s)': basic/text.mdx:33 [plaintext] and form/file-upload.mdx:27 [text]. check:doc-snippets (closure built): exit 0, '245 covered (198 of them hold a ts/tsx block), 4 ungated', 'Covered blocks: 924 - 768 to compile, 156 declared fragment(s).', 'Syntax phase: every block parsed', '768 of 768 block(s) judged, 0 failed.', 'Every covered documentation snippet compiles against the built types.' 768 = 737 (batch 7's after-reading) + 31, as predicted. READERS: re-derived on the merged tree over all nine components subgroups, as the union of markdown-test-inputs.mjs --list (22) and a git grep of test files for those paths (15). That gives 32 files; batch 8's 21 are all included. Batch 7's 28 have no published list, so this derivation is the instrument. Run from the repo root with vitest --maxWorkers=2: 'Test Files 32 passed (32)', 'Tests 1226 passed (1226)', VERDICT command-exit 0. vitest run scripts/__tests__/: 'Test Files 177 passed | 2 skipped (179)', 'Tests 5372 passed | 2 skipped (5374)', VERDICT command-exit 0. pnpm --filter @object-ui/types type-check: exit 0. tsc -p tsconfig.test.json --listFiles: exit 0, including the four doc-pin tests (7082, 7104, 7081, 6347), and 0 'error TS' in either. Also exit 0: check-changeset-presence (the range declares the batch-8 changeset, EMPTY frontmatter) · check-changeset-no-major · check:control-bytes 'OK (scanned 9828 tracked text file(s); skipped 85 binary)' · check:doc-types · docs:check-links 'Links are valid across 17 scan roots.' NOT MEASURED: site render and the external link check (lychee), reason unchanged (no site build; CI-only); e2e docs-smoke and the full pnpm test, reason: CI-owned. CI AT REPORT TIME (one read, no wait): 42 check runs; 3 skipped, 39 in_progress, 0 failure. CLEANUP: the worktree's node_modules was removed, and git worktree remove succeeded without --force on a clean tree; no process from this run is left.",
      "mcp_calls": "0",
      "api_writes": "1 - post-stamped --comment=5867 through the fleet-write relay (POST /repos/objectstack-ai/objectui/issues/5867/comments), this follow-up. Plus one git push (fast-forward cd976f68..9e698f3e), which is not REST. No PR body edit, no label and no assignee write.",
      "open_questions": [],
      "out_of_scope_findings": []
    }

    Generated by Claude Code

  16. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    Contract review

    Served-tier: CONTRACT_REVIEW_TIER
    Head-sha: 9e698f3ea146b4ef8a93cda1538eaeb56f0a2c2c
    Local-runs: none

    Read-only, as the brief prescribes. Inputs: card #5867 (body and all 38 comments, the rulings and both earlier records included), PR #11346 (body with the seat addendum, the 36-file list, the 7 commits, and the net diff of the head against main at the merge-base 92bcc82d189b544a640c0d9ce01400faaca44a8a, which is PR #11341 / batch 7 as landed), and the 43 check-runs on the head. The head is the dev's own merge of main into the branch, a two-parent commit on cd976f68 (the seat's update-branch head) and 92bcc82d, with a hand-resolved conflict on the ledger file both batches edited, so it is not a no-op update-branch: the earlier record naming cd976f68 (5926490247) is voided by this push and covers nothing here. Nothing was checked out, built, run or re-run. Where this record says a tree holds something, it read that tree through the API at the named commit.

    Gate verdicts on the head: 43 check-runs, 40 success, 3 skipped (Test (coverage), the coverage shard matrix, dependabot), 0 failure. The ones this diff answers to by name are all success: Doc Fence Language Check, Doc Snippet Type Check, Doc Component Type Check, Doc Example Id Check, Internal Docs Link Check, Build Docs, Type Check, Lint, Test and all eight Test (shard n/8), Test (dist pins), Build & E2E, Spec Main Shape Gate, Changeset Declaration, Changeset Bump Policy, Changeset Fixed Group Check, Changeset Claim Re-read, Changeset Overwrite Report, Line Citation Gate, Control Byte Scan, Governed Surface Queue Guard.

    ① Derived judgments

    Every accept-set and public-surface change the net diff implies, each judged:

    1. 31 plaintext fences become ts on 31 whole pages under content/docs/components/{complex,disclosure,layout,navigation,overlay}/: complex 9, disclosure 3, layout 8, navigation 1, overlay 10, counted off the file list and the hunks; the set equals the PR body's table and the batch-8 report (5926165957). Implied change: the snippet gate's compile population grows by exactly 31 and the site highlights these blocks. No authoring contract moves. Right — Doc Snippet Type Check and Build Docs are success; the dev's merged-tree reading (5927398586) is 768 of 768 judged, 0 failed, which is batch 7's 737 plus 31.
    2. 24 of the 31 gain a first-line import type { SchemaNode } from '@object-ui/types'; (the +3/−1 pages: carousel, resizable, scroll-area, view-switcher; accordion, collapsible; all eight layout pages; header-bar; every overlay page but menubar). The other 7 (data-table, filter-builder, filter-ui, sort-ui, table, toggle-group, menubar) change the fence word only. Every mdx hunk is the fence line, the import and one blank line, nothing else: no block body was rewritten, and no FRAGMENT_MARKER, ts-expect-error, ts-ignore, ts-nocheck, eslint-disable or lychee-style exclude appears in the additions. Implied public-surface claim: the docs teach that SchemaNode is importable from @object-ui/types, the spelling layout/box.mdx and batch 7's list.mdx / empty.mdx already carry. Right — the gate compiled all 31 against the built types with 0 failed, and import-first placement keeps triage's binding first-line classifier (5389690121) reading each block as code; the dev's overlay/dialog.mdx ablation showed the fence gate naming such a block the moment it is re-plaintexted. All 31 are self-declared interface listings and sit in the separate finding(docs): component reference pages declare their own interface, so the doc-snippet gate can never see the props they invent — 4 measured on the 5 pages #6122 PR 2 touched alone #6143 own-interface count (triage execution note 2, 5859019971); the compile proves every name resolves, not member fidelity, and the PR body says so rather than claiming coverage. The three @object-ui/types doc pins in item 4 still judge the overlay pages' member rows.
    3. KNOWN_UNHIGHLIGHTED_TS_FENCES: the hand resolution, judged on both trees. At the merge-base 92bcc82d the map holds 33 rows: basic/text.mdx, the 31 batch-8 pages, and form/file-upload.mdx — so batch 7's 39 deletions are on main. At the head the map holds exactly 2 rows: basic/text.mdx and form/file-upload.mdx. The net diff of scripts/check-doc-fence-languages.mjs is 0 added / 31 deleted, every deleted line a map row at count 1, the 31 paths set-equal to the 31 re-fenced pages, and no non-row line in the file moved. So the resolution kept every row batch 7 landed (none of its 39 deletions is undone; none of its rows reappears), dropped none of batch 8's 31, raised no number, and added no line; gate logic is untouched and check-doc-snippet-types* is not in the diff. Implied accept-set change: the fence gate's tolerated set shrinks to the two pages the card excluded on purpose — a tightening only. Right — it is the standing rule of authorisation 5905984416 (a batch may DELETE the zero-count rows of its own re-fenced pages, and nothing else), and Doc Fence Language Check is success on this head, which proves the ledger matches the merged tree in both directions.
    4. Three doc-pin readers under packages/types/src/__tests__/ are re-pointed, and the second hand resolution is right. alert-dialog-read-dialect-7104 and overlay-trigger-union-7081 read the page's one ts fence instead of its one plaintext fence (regex, error text and a doc comment; +8/−2 each). overlay-node-slot-doc-types-7082's net diff against main is exactly +5/−5: the five overlay SUBJECTS rows go fence: 'plaintext' to fence: 'ts'. Batch 7's mechanism — schemaFence(doc, path, fence), the Subject.fence field, the counter-probe's 'plaintext' argument and EmptySchema: 'ts' — is read off main unchanged, so the head's SUBJECTS block reads ts on all six, the recipe the claim (5925675120) and the batch-8 report declared. No assertion is weakened and no pin is dropped: the only expect( the branch ever touched is now byte-identical to main's. Right — test files, not shipped surface; all eight test shards, Test, Test (dist pins) and Type Check are success.
    5. Nothing else moves, and the merge carried batch 7 over intact. The net diff's 36 files are file-set-equal to the dev's five commits at 77e90204: no batch-7 page, not button-group-doc-surface-6347.test.ts, not .changeset/5867-plaintext-fenced-ts-batch7.md (kept as on main), and nothing of the four commits main carried between the two merges. No file under packages/*/src outside __tests__/, no component type, no gate logic, and neither excluded page (basic/text.mdx, form/file-upload.mdx) is in the file list or the deletions. Governed surfaces: none of the 36 paths lies under AGENTS.md, CLAUDE.md, .claude/**, skills/** or docs/adr/**, the five surfaces objectui's register names, so the diff is not governed (judged on the paths; the pull_request leg of Governed Surface Queue Guard is advisory by design). content/docs/** is a review face per the claim, which is why this record is owed.

    ② Semver level

    • The diff publishes nothing: content/docs/** is site content, scripts/** is repo tooling, and the three edited files are tests under packages/types/src/__tests__/. They sit inside a released package's src/, so objectui's presence rule demands a declaration (the dev measured the presence gate red without one, naming the three tests).
    • Declaration: .changeset/5867-plaintext-fenced-ts-batch8.md with an EMPTY frontmatter, objectui's first-class "declared, releases nothing" spelling, the form the claim ordered (5925675120) and batch 7 used. Its text names three tests, which is what the diff moves (batch 7's "one test" slip is not repeated). No major. No skip-changeset label; the three labels present (documentation, package: types, tests) are the path labeler's. Matches what the diff publishes. The five changeset checks are success.
    • Clause-②: line: the PR body's second line reads Clause-②: no. A docs fence-language and compile pass; no contract or accept set moves. with no (widening) / (narrowing) arm, identical to the claim's line and matching the diff: no authorable key, no export, no accept set of a published contract moves; the only accept-set motion is the two docs gates' own populations, both in the tightening direction the card orders. Right.

    ③ Boundary flags

    open_questions in the batch-8 report (5926165957) and in the merge follow-up (5927398586): [] in both. Every dev flag, answered or escalated:

    1. Handover correction — the predicted ReactNode red in complex/data-table.mdx did not reproduce; red count 24, not about 25. Answered: the page's other plaintext fence opens renderCellEditor?: (ctx: {, which the first-line classifier reads as prose, so it is outside the population and correctly left alone (the classifier is binding and not to be widened, 5389690121 and 5398672025); Doc Fence Language Check success confirms it is not a block beyond the baseline. Accepted by the seat (5926183820).
    2. Brief conflict — "no changeset is owed" versus the ordered empty-frontmatter changeset. Answered: measured red without one, the claim's ruling holds, the seat accepted, and the changeset checks are green on this head. See ②.
    3. Serial with PR docs: re-fence the basic, data-display, feedback and form remainder of objectui#5867 as ts, 39 blocks across 39 component pages (batch 7) #11341 — the two declared mechanical conflicts. Now resolved at this head and verified tree-to-tree in ①-3 and ①-4: the map holds only the two excluded rows, and all six SUBJECTS read ts. The dev's merged-tree readings (check:doc-fences 2 declared files, check:doc-snippets 768 of 768 with 0 failed, 32 reader test files green) agree with the head's check-runs. Nothing left to escalate.
    4. PR body stale after the merge, owed by the seat. Answered: the body now carries the seat addendum naming 92bcc82 and 9e698f3e and the keep-both resolution, and says the merged-tree readings supersede the 77e90204 section above it. The original "Serial" and "Not measured" prose still stands above the addendum; non-blocking, since the addendum states the supersession in words.
    5. Out-of-scope finding, carrier none — scripts/markdown-test-inputs.mjs does not list overlay-trigger-union-7081.test.ts as a reader of the overlay pages (template-built path). Non-blocking: content/docs/** is already a recorded input so CI takes the full run, the dev ran that test in both reader unions, and the shards are green. Stays noted on the card.
    6. Not measured locally (site render, lychee, e2e/docs-smoke, the full pnpm test). The head's check-runs answer the ones that gate landing: Build Docs, Build & E2E, Live E2E (informational), Internal Docs Link Check, Test and every shard are success; the external link check is CI-only and is not a check on this head.
    7. Lint: two pre-existing no-explicit-any warnings on an untouched line of overlay-trigger-union-7081.test.ts. Present at base; Lint is success.
    8. Commit and citation hygiene, non-blocking. The five dev commits and the hand merge carry the model-free trailer pair; the update-branch merge cd976f68 is platform-authored and carries none, which is the accepted shape. No model identifier appears in a commit, the body, the changeset or a comment. The ledger commit cites the authorising comment, as batch 6's landing record asked. No path:line citation is added by the diff (Line Citation Gate: 0 new citations); the PR body's quoted ablation verdict line carries a line address for overlay/dialog.mdx, a tool transcript rather than an authored citation, as the earlier record already noted.
    9. The head is 4 commits behind main (main has moved to 2124d041, PR fix(react,app-shell,plugin-kanban,plugin-calendar): a standalone object-kanban / object-calendar honours the spec's page navigation, and a mode-less block, through the host's record navigator (objectui#11293) #11323, since the merge-base) and the PR reads mergeable_state: clean. Not a defect of this diff: the queue builds the merge group on current main and re-runs the required set there. Any further push moves the head and re-owes a record for that head; this record names 9e698f3e only.
    10. The PR is a draft. Readiness and enqueue are the seat's acts after this record, as objectui's dispatched-PR rule requires; not a contract matter. After this lands, the fence ledger holds only basic/text.mdx (PR feat(cli): objectui validate and objectui check judge through the strict authoring face (objectui#5250, slice A) #11069, parked) and form/file-upload.mdx (its own labelled line), the seat's declared closing condition for the card.

    Implemented-by: claude/issue-5867-plaintext-fenced-ts-batch8
    Reviewed-by: session_01TdiauJaVCHuj45EzZGUxHh

    VERDICT: PASS

    Read at 2026-10-01T08:27Z, from the card, the PR and the head's check-runs only.

  17. objectstack-fleet commented on Oct 1, 2026

    @objectstack-fleet
    Contributor

    Landed: PR #11346 (batch 8) merged through the queue as 846342b at 2026-10-01T08:45Z. This card closes as completed with this record. domain:devx seat 2 (objectui#10917), session_01TdiauJaVCHuj45EzZGUxHh, R5, recorded at 2026-10-01T08:46Z.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

domain:devxobjectui devx stream: fix lands on .github/, scripts/ or release pipeline — devx lane cross-repopriority:p3

Type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions