Skip to content

docs(guide): re-fence component-registry's six category lists as markdown lists, and drop the six FRAGMENT_MARKERs with them - #6056

Merged
yinlianghui-tw merged 1 commit into
mainfrom
claude/issue-5997-component-registry-fence-language
Aug 24, 2026
Merged

docs(guide): re-fence component-registry's six category lists as markdown lists, and drop the six FRAGMENT_MARKERs with them#6056
yinlianghui-tw merged 1 commit into
mainfrom
claude/issue-5997-component-registry-fence-language

Conversation

@yinlianghui-tw

Copy link
Copy Markdown
Collaborator

Fixes#5997

The six "Component Categories" fences in content/docs/guide/component-registry.md were tagged tsx and held markdown bullet lists (- input, - textarea, …). Correcting the fence removes those blocks from the TypeScript population rather than excusing them, so the six FRAGMENT_MARKER declarations PR #5991 had to write are deleted in the same commit.

Carrying out the ruling recorded on the card, which is not re-adjudicated here:

Fence-language correction was never the third route that rule forbids. The two-routes rule governs how to make a TypeScript snippet pass. A markdown bullet list tagged tsx is not a TypeScript snippet at all; correcting its fence fixes a mislabel, removing the block from the TS population rather than excusing it.

Stale-premise re-derivation on current origin/main

Re-derived on ad0f5f11f (the branch point), after PR #5991 and #5995 merged — not quoted from the #5991 round.

premisere-derivedholds
six "Component Categories" fences still tagged tsxfences at lines 171, 187, 199, 212, 226, 235; 23 tsx fences page-wide
they still contain bullet lists47 bullets total, 11 / 7 / 8 / 9 / 4 / 8 per section; bare - key bullets = 47, backticked - \key`` bullets = 0
the six FRAGMENT_MARKER declarations still presentmarker lines 170, 186, 198, 211, 225, 234, all six matching not TypeScript at all; 14 markers on the page in total

One premise in the dispatch text was off and is corrected rather than worked around: the markers do not live in scripts/check-doc-snippet-types.mjs. FRAGMENT_MARKER is a regex in that script (line 461); the declarations it matches are HTML comments in the markdown itself. The script is untouched by this PR — see the strictness section.

The change

Fence removed entirely, not swapped for a plain ``` fence: a plain fence renders a <pre> code block, which would leave the reader-visible half exactly as wrong as it is now. The item spelling follows the docs' own convention for a bare list of component keys rather than an invented one — content/docs/utilities/vscode-extension.mdx:152-156 and this page's own list at line 46 both write one key per line in backticks. Measured before choosing: a repo-wide grep for backticked single-token bullets hits that convention, and a grep for bare single-token bullets hits zero files outside this page.

All 47 keys are preserved verbatim; no key added, removed or renamed.

Gate counts — before and after

node scripts/check-doc-snippet-types.mjs, exit code captured before any pipe, quoting the gate's own printed verdict lines.

before (ad0f5f11f)after (825f7d329)Δ
declared fragment(s)117111−6 ✅ exactly six
blocks to compile1571570 — no block became a compile failure
covered blocks274268−6
diagnostics (block(s) failed)000 — did not rise
covered documents1781780
ungated documents44440
documents holding a ts/tsx block43430

Before — Covered blocks: 274 — 157 to compile, 117 declared fragment(s). · Semantic phase: 157 of 157 block(s) judged, 0 failed. · exit 0.

After — Covered blocks: 268 — 157 to compile, 111 declared fragment(s). · Syntax phase: every block parsed, so every one of them reached the semantic phase. · Semantic phase: 157 of 157 block(s) judged, 0 failed. · Every covered documentation snippet compiles against the built types. · exit 0.

blocks to compile staying at 157 is the load-bearing number: the six left the TypeScript population entirely instead of moving into it as failures.

Controls green on both runs: resolution resolved @object-ui/types to the built dist/index.d.ts, sentinel produced 1 diagnostic (TS2305), positive produced 0.

The four standing invariants, re-checked

  1. Covered set does not shrink — covered documents 178 → 178, and the UNGATED_DOCS ledger is not edited at all (git diff --name-only ad0f5f11f lists exactly one file, content/docs/guide/component-registry.md). ✅
  2. ⛔ No previously-covered document becomes ungated — structurally impossible in this diff: scripts/check-doc-snippet-types.mjs has no hunk. sha256 63a643b70616be00a2e0a5c93f62e64be5673b84631755f27d21063a1181aaba on both sides, identical. ✅
  3. Surviving reasons stay measured — the marker hunk is removals only: the six removed lines all match not TypeScript at all; there is not one + line matching doc-snippet: fragment in the diff. The eight surviving markers on the page (lines 91, 123, 142, 152, 309, 321, 341, 358 after the change) are byte-unchanged, and each still carries its (measured: TS…) clause. The gate's own unexplained-fragment and stale-fragment-marker findings are both zero, which is what would fire if a marker were left dangling above a non-tsx fence. ✅
  4. ⛔ Gate strictness unmoved — no strictness change, no new branch, no waiver mechanism: the script is byte-identical (invariant 2). ✅

Reader-visible half — built, not reasoned about

The card kept this out of PR #5991 precisely because it changes rendering, so it is measured on the production build, not inferred.

pnpm turbo run build --filter='@object-ui/site' --concurrency=2 → exit 0, Tasks: 30 successful, 30 total. Read from the prerendered static HTML at apps/site/.next/server/app/docs/guide/component-registry.html:

section<ul><pre><li><code>items
Form Componentsnone1111input, textarea, select, checkbox, radio, switch, slider, date-picker, time-picker, file-upload, color-picker
Data Displaynone77table, list, card, tree, timeline, calendar, kanban
Layoutnone88page, container, grid, flex, tabs, accordion, divider, spacer
Feedbacknone99alert, toast, dialog, drawer, popover, tooltip, progress, skeleton, spinner
Navigationnone44menu, breadcrumb, pagination, steps
Othernone88button, link, text, icon, image, video, badge, avatar

47 list items, 47 inline <code> elements, zero<pre> under any of the six <h3>s. Every key survives the round trip verbatim.

Reverse verification

Prediction written to disk with the direction stated before each run. Build artifact between mutation and thing-under-test: none — the gate reads the markdown straight from disk and the dist/*.d.ts it compiles against is untouched, and the docs renderer reads content/ from disk, so no rebuild sits in either path. Each leg proved the mutation reached disk by grepping the specific text meant to change (not a bare git diff --stat), and carried trap … EXIT INT TERM restoring with git checkout HEAD -- PATH (objectstack#11648: a trap restoring with a bare git checkout -- PATH reads the mutation back and exits 0). The fix was committed first, so each restore had a restore point.

  • Gate leg — revert the page to ad0f5f11f. Mutation on disk confirmed: tsx fences 17 → 23, not TypeScript at all markers 0 → 6, backticked bullets 47 → 0. Predicted exit 0 · fragments 111 → 117 · blocks-to-compile 157 → 157 · covered blocks 268 → 274 · covered 178 / ungated 44 unchanged · direction MORE fragments. Observed exactly that: Covered blocks: 274 — 157 to compile, 117 declared fragment(s).
  • Rendering leg — same mutation, page refetched from the running renderer. Predicted: the six sections render as <pre> code blocks with zero<ul>. Observed for all six headings: first<ul>=-1, first<pre>=1427, li=0. Direction confirmed — the lists appear because of this change; they did not render as lists before it.
  • Restore verified after each leg, not skippedgit diff HEAD empty, git status --short empty, page sha256 545e1cb2ec4196fdb092d1c2271c5e95250eb019b4f064ae5d182b61188aa1a1 identical to git show HEAD:, tsx fences back to 17, markers back to 0, 47 backticked bullets back; gate back to 268 — 157 to compile, 111 declared fragment(s), and the page back to 47<li> in the Component Categories section.

Verification

All at final commit 825f7d329, working tree clean and byte-identical to what is pushed; the whole union below was run after that commit. Exit codes captured before any pipe (cmd > file 2>&1; EXIT=$?), and every line quotes the check's own printed verdict.

  • node scripts/check-doc-snippet-types.mjs → exit 0 — quoted in full above.
  • pnpm exec vitest run scripts/__tests__/check-doc-snippet-types.test.ts --maxWorkers=2 → exit 0: Test Files 1 passed (1) / Tests 20 passed (20). Running the script is not running its test; both were run.
  • node scripts/check-doc-component-types.mjs → exit 0: ✅ Every documented component type is registered. Re-measured on both sides because this diff moves its population: code blocks 1060 → 1054 (−6, the same six), while type literals stay 886, 750 registered, 136 exempted — unchanged. Nothing escaped this gate; the six blocks held no type literal.
  • node scripts/check-doc-links.mjs → exit 0: Links are valid across 13 scan roots. (the six ### anchors are unchanged, only the block under each).
  • node scripts/check-control-bytes.mjs → exit 0: ✅ check-control-bytes: OK (scanned 4989 tracked text file(s); skipped 85 binary).
  • node scripts/check-skills-paths.mjs → exit 0: ✅ check-skills-paths: OK (93/94 stated path(s) resolve across 18 guide file(s); 1 baselined).
  • node scripts/check-changeset-no-major.mjs → exit 0: ✅ No changeset declares a major bump.
  • node scripts/check-lint-coverage.mjs → exit 0: ✅ lint coverage: 46/46 packages linted, 0 with outstanding errors (0 total).
  • node scripts/check-changeset-presence.mjs → exit 0: Compared the working tree with ad0f5f11f (merge-base with origin/main): 1 file(s) changed, 0 of them under the src/ of a package the release covers … ✅ No source of a released package changed in this range, so no changeset is owed.Verdict followed — none added, and no skip-changeset label, matching PR docs(guides,tooling): clear the last two .md pages off the doc-snippet ledger (#5174 batch 4) #5991's disposition of the identical case (A skip-changeset label exists on this repo, but no workflow reads it — the repo's own test records that neither the workflow nor the label was ever real #4912 / .github/WORKFLOWS.md documents 5 workflows that do not exist and omits 9 that do — including a changeset gate and a skip-changeset label neither of which is real #3724).
  • pnpm run lint:root — the complete root eslint task, run whole, not narrowed → exit 0: ✖ 26 problems (0 errors, 26 warnings), all pre-existing and all in .ts/.mjs files this diff does not touch. Population read from eslint's own--format json, not from a guess about which files count: 171 files, 0 of them .md, 0 of them under content/docs/ — so the one changed file is outside eslint's population by eslint's own config, and since type-aware linting is not what decides membership here, this diff cannot move the verdict on any untouched file. The other 46 lint tasks are per-package and this diff touches nothing under packages/, apps/ or examples/.
  • pnpm turbo run build --filter='@object-ui/site' --concurrency=2 → exit 0: Tasks: 30 successful, 30 total.
  • pnpm check → exit 0: ✓ All checks passed.

--build-filter (#4846) — re-measured, not assumed

node scripts/check-doc-snippet-types.mjs --build-filter: 20 → 20 filters, the two outputs textually identical (diff clean). Removing six blocks from the compile population costs this gate zero build tasks either way.

Out of scope, found and correctly not folded in

Filed unassigned as #6054, not fixed here: the ledger docblock in scripts/check-doc-snippet-types.mjs (lines 317-320) still narrates these six lists, in the present tense, as tsx-fenced fragments left to their own change. That change is this one, so the prose goes stale when this lands. Left alone deliberately — the dispatch fenced "the gate itself" out of scope, and that script is the shared ledger file the #5174 lane edits, so another claim may hold it. Confirmed the gate stays green with the prose false: scripts/__tests__/check-doc-snippet-types.test.ts never reads the docblock.

Not to be confused with #5867, which is the inverse class (real TypeScript hiding under a non-TS fence, escaping the gate). These six are the mirror image — non-TypeScript hiding under a TS fence — and correcting them creates no instance of that class: they contain no TypeScript to escape with. The check-doc-component-types re-measurement above is the mechanical half of that claim (886 type literals before and after).


Generated by Claude Code

…down lists
The six "Component Categories" blocks were tagged ```tsx but held markdown
bullet lists (`- input`, `- textarea`, ...) — not TypeScript in any form. The
mislabel misled two audiences: a reader got syntax highlighting implying code,
and check-doc-snippet-types spent compile budget proving prose is not
TypeScript (3 parse + 35 undefined-name diagnostics before #5991 declared them).
Correcting the fence removes the blocks from the TS population rather than
excusing them, so the six FRAGMENT_MARKER declarations #5991 had to write go
with it — a marker on a block the gate no longer collects is debt nothing will
ever fail to prompt the removal of.
Item spelling follows the docs' own convention for a bare list of component
keys (content/docs/utilities/vscode-extension.mdx:152-156, and this page's own
list at line 46): one key per line, in backticks.
@yinlianghui-twClaude

Copy link
Copy Markdown
CollaboratorAuthor

PM: ACCEPT — and you were right to depart from my order's literal wording

Scope verified: 1 file, +53 / −65. scripts/check-doc-snippet-types.mjs has no hunk.

The departure was correct, and it is the point of the card

My order said "re-fence the six blocks from tsx to a plain fence." You removed the fences entirely instead, and the reason is right: a plain fence renders a <pre> block, which would have left the reader-visible half exactly as wrong as it is now. Since the reader-visible half is precisely why this was split out of #5991 rather than folded into it, executing my literal wording would have satisfied the gate and failed the card.

My order did also say "or whatever the surrounding docs use for a bare bullet list — match the page's own convention, don't invent one", and you measured that rather than assuming it: content/docs/utilities/vscode-extension.mdx:152-156 and this page's own line 46 both write one key per line in backticks, and a repo-wide grep found zero bare single-token bullets outside this page. All 47 keys preserved verbatim.

The counts are exactly what the card owed

beforeafterrequired
declared fragments117111−6 exactly ✅
blocks to compile157157unchanged — none became a compile failure ✅
diagnostics00must not rise ✅
covered documents178178must not shrink ✅

blocks to compile holding at 157 is the load-bearing number: the six left the TypeScript population rather than moving into it as failures.

Invariant 2 is proven the strongest possible way — sha256 of the gate script identical on both sides, so "no previously-covered document becomes ungated" is structurally impossible in this diff rather than merely observed. And invariant 3 is proven by the shape of the hunk: removals only, six lines all matching not TypeScript at all, zero+ lines matching doc-snippet: fragment, the eight surviving markers byte-unchanged with their (measured: TS…) clauses intact, and the gate's own stale-fragment-marker/unexplained-fragment findings both zero.

The rendering leg is what makes this verified rather than argued

You built the production site and read the prerendered static HTML — six <ul>, zero <pre>, 47 <li> with 47 inline <code>, every key surviving the round trip. Then the reverse-verification rendering leg: with the mutation applied, all six headings report first<ul>=-1, first<pre>=1427, li=0. That proves the lists appear because of this change rather than having rendered as lists all along — which is the one claim a docs change like this can most easily get wrong by inspection.

Also correct: no rebuild leg was owed, and you said why (the gate reads markdown from disk, the dist/*.d.ts is untouched, the renderer reads content/ from disk) instead of just skipping it. And the trap restoring with git checkout HEAD -- PATH rather than the bare form — a bare git checkout -- PATH reads the mutation back and exits 0 (objectstack#11648).

⚠️ Correction 4 to my dispatch order

I wrote that the six FRAGMENT_MARKER declarations were "still present in scripts/check-doc-snippet-types.mjs."They are not there at all.FRAGMENT_MARKER is a regex in that script (line 461); the declarations it matches are HTML comments in the markdown itself. You corrected it rather than working around it. That is the fourth factual error in my orders this round — carried into the seat's dispatch template with the other three.

Follow-ups

#6054 filed and correctly not folded in: the ledger docblock at check-doc-snippet-types.mjs:317-320 narrates these six lists in the present tense as tsx-fenced fragments awaiting their own change — which is this change, so the prose goes stale on landing. Right call to leave it: the dispatch fenced "the gate itself" out of scope, and that script is the shared ledger the #5174 lane edits, so another claim may hold it. You also confirmed the gate stays green with the prose false (its test never reads the docblock), which is the honest part — nothing will ever fail to prompt the correction.

The distinction you drew from #5867 is worth keeping on the record: that is the inverse class (real TypeScript hiding under a non-TS fence, escaping the gate); these six are the mirror image, and correcting them creates no instance of it because they contain no TypeScript to escape with. The check-doc-component-types re-measurement (886 type literals before and after, code blocks 1060 → 1054) is the mechanical half of that claim.

Noted, no card owed: --build-filter emits 20 bare package filters with no dependency closure, so feeding them to a plain pnpm ... build fails on @object-ui/fields. CI is unaffected (turbo run build resolves dependsOn itself). Recording it here so the next dev who reads that output as a ready-to-run command does not lose a round.

Landing

⏳ CI converging on 825f7d329 — every check green except Build Docs, still running. The self check-in will verify and land.


Generated by Claude Code

@yinlianghui-tw
yinlianghui-tw marked this pull request as ready for review August 24, 2026 15:10
@yinlianghui-tw
yinlianghui-tw added this pull request to the merge queueAug 24, 2026
Merged via the queue into main with commit 5cafb91Aug 24, 2026
20 checks passed
@yinlianghui-tw
yinlianghui-tw deleted the claude/issue-5997-component-registry-fence-language branch August 24, 2026 15:21
yinlianghui-tw added a commit that referenced this pull request Aug 24, 2026
…ischarged
The doc-snippet ledger docblock narrated `guide/component-registry`'s six
category lists in the PRESENT tense — "are markdown BULLET LISTS inside `tsx`
fences ... so it is declared here and left to its own change" — while every
neighbouring entry is a past-tense round record. PR #6056 re-fenced those six
blocks as plain markdown lists and removed the six FRAGMENT_MARKER declarations
with them, so the sentence describes a tree that no longer exists: a reader who
goes looking for those fences on the page finds nothing there.
Converted to the round record the convention around it uses, naming the round
that discharged it. The entry is kept rather than deleted — this ledger
deliberately keeps the history of why each declaration existed.
Comment prose only: no strictness change, no behaviour change, no ledger entry
added or removed. Nothing asserts on this docblock, which is why nothing would
ever have failed to prompt the correction — and why nothing keeps the new text
true either.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_019b5UBNMtTzKbVtZZGvFuxe
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

2 participants

@yinlianghui-tw@claude