Skip to content

docs(rest): drop the hand-written translatable-type list from translateMetaItem's comment - #15863

Merged
os-litant merged 5 commits into
mainfrom
claude/issue-14378-translate-meta-item-comment
Sep 5, 2026
Merged

docs(rest): drop the hand-written translatable-type list from translateMetaItem's comment#15863
os-litant merged 5 commits into
mainfrom
claude/issue-14378-translate-meta-item-comment

Conversation

@os-litant

@os-litant os-litant commented Sep 5, 2026

Copy link
Copy Markdown
Collaborator

Fixes #14378

The comment above translateMetaItem restated the translatable-type set by hand. The enumeration is deleted; the sentence keeps its actual point, which is that the spellings are SINGULAR.

Two commits: the comment deletion, and the re-anchoring the deletion forced in content/docs/permissions/system-context.mdx (see Census repair below).

Premise re-derived on today's tree — and it changed since triage

The card was filed as drift risk. Its triage verified on 2026-09-02 that the six were still accurate, because translateDataset had not landed yet. It has landed since, so as of this branch the comment and the table disagree.

Dispatch table, read mechanically out of packages/spec/src/system/i18n-resolver.ts rather than by eye:

count=7 ["view","action","object","app","dashboard","dataset","page"]

The comment, packages/rest/src/rest-server.ts:3254, before this change:

...and those are singular-only (view/action/object/app/dashboard/page), matching translateMetadataDocument's "Canonical metadata type string".

Seven against six — dataset is the one the parenthetical never grew. The card predicted exactly this and it happened within three days of the card being graded, which is the finding demonstrating itself rather than an argument for it.

The repair, and why it is deletion rather than a pin

Deletion, per the card's disposition. The two lines immediately above already name TRANSLATABLE_METADATA_TYPES and METADATA_DOCUMENT_TRANSLATORS, so nothing is lost by not restating them, and the table's own doc comment states the rule this violated: "Derived from the dispatch table — never restate it."

A gate or pin asserting comment-vs-table agreement was measured and rejected, with numbers rather than taste:

  • Population, scanned over 7660 tracked files for hand-written restatements of this set: 3 sites, of which one (packages/spec/src/conversions/registry.ts:3039) must be left exactly as it is — it is the recorded rationale for the 17.0.0 book.translations retirement and describes the set as it stood at that removal. So a gate would need a permanent by-name exemption list, i.e. a hand-maintained list of "places allowed to restate the set": the same defect class, one level up, bought for a live population of 1 after this PR.
  • The load-bearing half is already pinned. packages/spec/src/system/i18n-resolver.test.ts:3382 asserts TRANSLATABLE_METADATA_TYPES.has('dataset') under the title "is registered in the dispatch table, so the REST boundary follows". The behaviour — registering a translator reaches the REST boundary in one edit — has a test. What had no test was prose, and prose that has been deleted cannot rot.

Against the four axes: ① the measured need is one stale sentence, not a class needing machinery; ② (weight ≥50%) deletion leaves zero maintained artifacts behind, whereas a gate leaves an exemption list that itself goes stale; ③ a stale comment that reads authoritatively is exactly the input that makes an agent write wrong code, and deletion removes the input entirely rather than making it correct-for-now; ④ a new gate plus its self-tests is disproportionate to a one-line prose defect.

Census repair — and the narrowing it falsified

The first push was RED on Lint & Repo Gates: check-system-context-census reported ten problems in packages/rest/src/rest-server.ts, five site-without-a-row and five anchor-is-not-a-read-site, each pair differing by exactly one. content/docs/permissions/system-context.mdx row 51 cites that file by absolute line number, and deleting one comment line moved every anchor below it up by one.

Two things this falsified, and the second is the one worth carrying forward.

  1. Inert to the token stream is not inert to every gate. The original narrowing argued that a comment-only diff cannot change what the compiler sees. That is true and the mechanical check behind it was real — but this census gate reads line positions, not tokens, so a comment-only diff reddens it exactly as readily as a behavioural one.
  2. The gate list was named correctly and then filtered away. scripts/pm/dispatch-gates.mjs did name node scripts/check-system-context-census.mjs for the original one-file change set, matched via packages/rest/src/rest-server.ts ⇢ gate source 'packages/**'. It was lost downstream: the derived list was summarised with a pnpm check:* pattern, and this repo invokes a large share of its gates as bare node scripts/... (lint.yml even carries a "GATE INVOCATION IDIOM" note about it). Measured: the first derivation carried 121 gate entries, of which the pnpm check: summary kept 49. The stated "49 derived" was never the family — it was one filtered view of it, and the gate that went red was in the 72 it dropped.

Repair. node scripts/check-system-context-census.mjs --fix rewrote the five anchors on system-context.mdx:162 (5084 -> 5083, 6510 -> 6509, 6758 -> 6757, 7189 -> 7188, 7382 -> 7381). Nothing was hand-edited.

Verified structurally, not by comparing line content — several anchored lines in that file are the same string, so content comparison proves nothing. The census was re-derived on both sides of the diff (node scripts/isystem-census.mjs --json) by restoring the target file to its merge-base blob under an EXIT INT TERM trap: the mutation was proven on disk by blob-hash equality with the base blob and a second observation (the deleted enumeration back, count 1), and the restore by blob-hash equality with the HEAD blob and an empty git diff HEAD. Prediction was written before the run and held exactly:

measure base head
sites 107 107 unchanged
text.identifierAppearances 873 873 unchanged
text.classified 463 463 unchanged
roleCounts.read 113 113 unchanged
nonElevationReads 6 6 unchanged
staleLedgerRows 0 0 unchanged
elevation read sites ARRIVED 0 position-blind multiset of (file, receiver, package, text)
elevation read sites VANISHED 0 same
scannedFiles (control) 291 291 non-zero, re-validated in the same run

The only movement was positional: per-site delta in rest-server.ts was 0 -1 -1 -1 -1 -1 — the one site above the edit unmoved, the five below it shifted by one. A pure shift, which is the precondition --fix is allowed to act on.

Verification

All verified at 09a50122f2d, the final head after the last origin/main merge. Exit codes captured by redirecting to a file before any pipe, and each row quotes the gate's own verdict line rather than a bare status.

check exit its own verdict line
check:system-context-census 0 OK — 107 elevation read sites in 20 packages across 45 files, all anchored; 141 anchors resolve, 27 declared non-read
check:doc-anchors 0 310 internal fragment link(s) across 410 source file(s) all resolve to a real heading
check:nul-bytes 0 OK (scanned 7653 text file(s); no raw ASCII control bytes)
check:corpus-claim-drift 0 Scanned: 236 .md/.mdx file(s) across 2 root(s)
check:role-word 0 Scanned: 236 .md/.mdx file(s); ledger 44 baselined file(s)
check:docs-single-h1 0 405 page(s) under content/docs/ carry no body-level heading
check:docs-redirects 0 92 entries -- 89 page destination(s) resolved, 98 chain probe(s) matched
check:docs-audit-scope 0 190 hand-written doc(s) in sync
check:docs-transcript-drift 0 green after @objectstack/lint was built (it exits 3 unbuilt — NOT MEASURED, not a pass)
check:merge-driver 0 check-regen-pending self-test passed
check:published-readme-links · check:react-page-adapter-contract · check:skill-identifier-liveness · check:vendor-version-stamps 0 all green
check-doc-frontmatter · check-docs-section-name · check-section-landing-index · check-doc-route-spelling 0 self-test and run, both green
lint check:doc-formula-expressions · lint check:doc-security-posture 0 green
spec check:docs · check:yaml-examples · check:empty-state · check:liveness · check:strictness-ledger · check:variant-docs 0 green
spec check:skill-examples 0 257 prose examples type-check across 3 surface(s) — first run exited 1 refusing to measure against an unbuilt client-react; green after building it
check:doc-authoring · check:meta-type-normalized · check:pm-governed-prose 0 green
pnpm --filter @objectstack/rest typecheck 0 tsc --noEmit clean; check:test-typecheck: OK — 0 file(s) / 0 error(s)
vitest run src/meta-plural-i18n.test.ts src/import-prepare.test.ts 0 Test Files 2 passed (2) / Tests 18 passed (18)

Heavy runs went through scripts/pm/os-verify-lock.sh; every VERDICT line read command-exit 0.

Re-derived gate union. With the .mdx in the change set the derivation grows from 121 entries to 149 — the .mdx adds 33 entries, of which the census gate is one. Two gates in that set were NOT MEASURED on their first attempt and are reported as such rather than as passes: check:docs-transcript-drift (exit 3, PREREQUISITE NOT MET, @objectstack/lint unbuilt) and spec check:skill-examples (exit 1, refusing to read an unbuilt client-react dist). Both were built and re-run to a real verdict.

No ablation of shipped behaviour. No test is shipped. The one mutation performed was the base-side census restore described above, which is measurement, not a shipped assertion — its direction was predicted in writing first and is recorded in the table.

Clause ② — contract review, re-judged from the delivered diff

The diff grew from one file to two, so this is re-judged rather than reused:

  • Mechanical / path limb — NO. Neither delivered path is under packages/spec/src/** and no key is added to any published payload. packages/rest/src/rest-server.ts changes only comment lines inside a method body; content/docs/permissions/system-context.mdx changes five line-number citations in one documentation table row.
  • Non-mechanizable conformance limb — NO. No input class is re-selected and no shipped verdict moves. isTranslatableMetaType, TRANSLATABLE_METADATA_TYPES and METADATA_DOCUMENT_TRANSLATORS are all untouched; the census population is measured identical on both sides of the diff, so not even the documented elevation surface moved — only where it is cited.

No needs:contract-review label on either carrier.

Changeset

skip-changeset, ruled A by the dispatching seat on the card. Neither delivered path publishes anything: comments inside a method body reach neither the emitted JS nor the .d.ts, and content/docs/** ships no package.

Deliberately not touched

packages/spec/src/conversions/registry.ts:3039 carries a similar sentence and is left alone, per the card's fence: it is the recorded rationale for the 17.0.0 book.translations retirement and describes the set as it stood at that removal. Rewriting it to match today's set would falsify a historical record.

Out-of-scope finding, measured and filed

The population scan found a third restatement — packages/rest/src/meta-plural-i18n.test.ts:11, the header of the very test that pins this behaviour, stale by the same one entry. It is a different carrier and the card's triage scoped this PR to "genuinely one line" in rest-server.ts, so it was filed rather than folded in: #15860 (no assignee, finding). Dedup search was run first and its control returned the expected known hit, so the empty duplicate result is a reading rather than a silence.

…teMetaItem

`isTranslatableMetaType` reads `TRANSLATABLE_METADATA_TYPES`, which is derived
from `METADATA_DOCUMENT_TRANSLATORS`' keys. The comment restated those keys by
hand as a six-item parenthetical, so it went stale the moment the table grew:
`translateDataset` registered a seventh key and the parenthetical still named
six.

The sentence's actual point is that the keys are SINGULAR, which needs no list
to make. The enumeration is deleted rather than corrected -- a corrected
restatement rots again on the next registration, and the two lines above
already name both the derived set and the table, which is where a reader
should go. The table's own doc comment states the rule: "Derived from the
dispatch table -- never restate it."

Comment-only: every changed line is a `//` line comment, so the token stream
is unchanged.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01D47qPfEWVPmhguWgBZCi5N
@github-actions

github-actions Bot commented Sep 5, 2026

Copy link
Copy Markdown
Contributor

📓 Docs Drift Check

This PR changes 1 package(s): @objectstack/rest, touching 6 documentable anchor(s).

5 hand-written doc(s) NAME something this change touched and may need an implementation-accuracy re-verification:

  • content/docs/api/client-sdk.mdx (via /:object/import (route, bridged from symbol translateMetaItem — its route source's handler names it))
  • content/docs/api/wire-format.mdx (via /:object/import (route, bridged from symbol translateMetaItem — its route source's handler names it))
  • content/docs/data-modeling/fields.mdx (via /:object/import (route, bridged from symbol translateMetaItem — its route source's handler names it))
  • content/docs/data-modeling/import-mappings.mdx (via /:object/import (route, bridged from symbol translateMetaItem — its route source's handler names it), /:object/import/jobs (route, bridged from symbol translateMetaItem — its route source's handler names it))
  • content/docs/protocol/objectql/state-machine.mdx (via /:object/import (route, bridged from symbol translateMetaItem — its route source's handler names it), /:object/import/jobs (route, bridged from symbol translateMetaItem — its route source's handler names it))

2 release-owned page(s) also name something this change touched. These are read-only:

  • content/docs/releases/v12.mdx (via /:object/import (route, bridged from symbol translateMetaItem — its route source's handler names it))
  • content/docs/releases/v17.mdx (via /:object/import (route, bridged from symbol translateMetaItem — its route source's handler names it))

content/docs/releases/ is RELEASE-OWNED (AGENTS.md "Documentation Guardrails"): release
notes are written centrally at release time, and a code PR that edits them is the exact PR
that guardrail exists to stop. They are still audited — read-only. If one of them is actually
wrong, file an issue or open a dedicated docs-only PR; do not edit it here.

What this run could not see
  • the SDK route bridge reached 61 of 219 client-bound route-ledger rows — the other 158 have no registrar path: tail to select them, so pages documenting THEIR client methods cannot appear above, on this or any run. Of those 158: 0 are remediable by widening that discovery convention (an in-repo file declares the path; the convention did not scan it); 56 are structural — on a ledger where NOT ONE row is declared in-repo, so no discovery change reaches them at any price; 102 are undecided (no in-repo declaration, on a ledger that has other in-repo registrars — absence and an unreadable spelling are not distinguishable here). The rows themselves: node scripts/docs-audit/affected-docs.mjs --bridge-coverage
  • a page that states a rule by its inputs shares no identifier with the emitter that implements the rule, so an emitter-only diff cannot list it — not on this run and not on any run. Measured on fix(driver-sql): emit varchar(maxLength) for a text field a declared index keys on #11430: content/docs/protocol/objectql/types.mdx documents the text-family column mapping by the ObjectQL type names it maps FROM (text / textarea / html) while the diff changed createColumn; it went unlisted, and it was the page that diff falsified, in four places. No shared token exists to detect this on, so a rule your change carries has to be re-read by hand in the pages that restate it.

Coarse fallback — 13 page(s) merely mention a changed package (the pre-#9192 predicate, kept for the deliberately-wide backstop): node scripts/docs-audit/affected-docs.mjs --json b398ad258b9e477b5ef92b12c0e2ff6414eb4ec0packageMentionDocs.

Which tree this was computed on

This run read content/docs from 226e46ed355905bb28b31bd97c9246f23b7ca106 — the merge of head 028071cc16f7bfcd802ed264ef1d2e88dcf9ae35 into base b398ad258b9e477b5ef92b12c0e2ff6414eb4ec0, which is what actions/checkout gives a pull_request run. Not the PR head.

A worktree cut from an older main holds a different content/docs, so re-deriving there can legitimately return a different list — that is a different tree, not a wrong row. To answer on the same tree:

# while this PR is open — GitHub drops the merge commit once it closes
git fetch origin 226e46ed355905bb28b31bd97c9246f23b7ca106 && git checkout 226e46ed355905bb28b31bd97c9246f23b7ca106
# afterwards, rebuild it from the two parents, which stay fetchable
git fetch origin b398ad258b9e477b5ef92b12c0e2ff6414eb4ec0 028071cc16f7bfcd802ed264ef1d2e88dcf9ae35 && git checkout -B drift-repro b398ad258b9e477b5ef92b12c0e2ff6414eb4ec0 && git merge --no-ff 028071cc16f7bfcd802ed264ef1d2e88dcf9ae35

node scripts/docs-audit/affected-docs.mjs --json b398ad258b9e477b5ef92b12c0e2ff6414eb4ec0

⚠️ That checkout carried uncommitted changes, so the commit above does not fully identify what was read.

Advisory only, and a precision-first one (#9192): a page is listed because it names a
symbol, wire route or SDK method this diff touched — not because it mentions a changed
package. Each row says which anchor put it there, so a wrong row is reportable rather than
merely annoying. To re-verify, run the docs-accuracy-audit workflow scoped to these files:
node scripts/docs-audit/affected-docs.mjs b398ad258b9e477b5ef92b12c0e2ff6414eb4ec0 → pass the list as
args.docs, on the commit named under Which tree this was computed on.

…tions

The previous commit deleted one comment line from `rest-server.ts`, so the
five absolute line anchors that `content/docs/permissions/system-context.mdx`
row 51 carries into that file were each one line high. A pure positional
shift: `check-system-context-census` reported five `site-without-a-row` and
five `anchor-is-not-a-read-site` findings, each pair differing by exactly one.

Re-anchored by `node scripts/check-system-context-census.mjs --fix`, which
rewrites a pure shift and refuses a population change. Not hand-edited.

Verified structurally rather than by comparing line content (several anchored
lines in that file are the same string, so content proves nothing): the census
was re-derived on both sides of the diff and the population held —
sites 107 = 107, identifierAppearances 873 = 873, classified 463 = 463,
roleCounts.read 113 = 113, staleLedgerRows 0 = 0, and on the position-blind
multiset of (file, receiver, package, text) ARRIVED = 0 and VANISHED = 0.
Control `scannedFiles` = 291 on both sides, non-zero and re-validated in the
same run. The only movement was positional: per-site delta 0 -1 -1 -1 -1 -1,
the one site above the edit unmoved and the five below it shifted by one.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01D47qPfEWVPmhguWgBZCi5N
@github-actions github-actions Bot added the documentation Improvements or additions to documentation label Sep 5, 2026
…anslate-meta-item-comment

Conflict: content/docs/permissions/system-context.mdx.

main renumbered the elevation table (rows 49..61 became 48..60) and rewrote the
cross-reference prose with it ("row 51's doors" became "row 50's doors"), while
this branch had rewritten five absolute line anchors in the row that moved. The
`os-regen` merge driver declined to defer -- the file is MIXED, a generated half
plus hand-written prose -- and text-merged, which conflicted.

Resolved by taking main's side of the file whole (byte-identical to
origin/main), which keeps its renumbering and its prose intact and discards
only the five anchor numbers, then re-deriving those from the merged tree with
`node scripts/check-system-context-census.mjs --fix`. No line number was
hand-edited and no prose was hand-merged.

The conflicting path was identified with a driver-free instrument -- a
`--bare --shared` clone with no `merge.os-regen.driver` configured, which is
GitHub's condition -- because setting the driver to empty in the real checkout
makes git fail to execute it and report a conflict on every path routed to it.
The probe named exactly one conflicting path, and its control (the same probe
against the branch's own merge base) returned clean, so the instrument
discriminates.

Structurally re-verified at this head rather than reusing the previous
reading, because main's own numbers moved (107 sites became 106, 141 anchors
became 140, and that is main's change, not this branch's). Comparing the
merged tree against the merged tree carrying main's `rest-server.ts`:
sites 106 = 106, identifierAppearances 885 = 885, classified 462 = 462,
roleCounts.read 112 = 112, staleLedgerRows 0 = 0, and ARRIVED = 0 with
VANISHED = 0 on the position-blind multiset of (file, receiver, package,
text). Control `scannedFiles` = 293 on both sides, non-zero and re-validated
in the same run. Only movement positional: per-site delta 0 -1 -1 -1 -1 -1.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01D47qPfEWVPmhguWgBZCi5N
@os-litant
os-litant marked this pull request as ready for review September 5, 2026 13:16
@os-litant
os-litant enabled auto-merge September 5, 2026 13:16
@os-litant
os-litant added this pull request to the merge queue Sep 5, 2026
Merged via the queue into main with commit 5d02911 Sep 5, 2026
35 checks passed
@os-litant
os-litant deleted the claude/issue-14378-translate-meta-item-comment branch September 5, 2026 13:41
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

documentation Improvements or additions to documentation size/xs skip-changeset PR has no user-facing published change; bypasses the changeset gate

Projects

None yet

Development

Successfully merging this pull request may close these issues.

translateMetaItem's comment restates the translatable-type set by hand, so it goes stale every time the dispatch table grows

2 participants