Select an import-list doc block as module description only on an explicit @module marker, and re-attach the eight wedged schema comments - #13794
Conversation
…icit @module marker Route 1 of #13334: inside the import list — imports before the block, an import the first thing after it — no positional signal separates a genuine module header from one schema's detached comment (the card measured every signal; only the prose differs). The selector now asks the author instead: only a block carrying @module on a prose line selects there, in both directions, with the one exception of plumbing that runs to EOF (a pure re-export module has no symbol the block could have been torn from). The two genuine headers in that position, shared/mapping and system/cache, each gain the one-line marker — the repo's existing spelling, fourteen headers above their imports already open with it. No other source is touched. Measured over all 208 corpus sources, old selector vs new: 200 verdicts byte-identical, exactly the 8 misattributed openings flip SELECTED->null, 0 change to a different block. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PBjwYLS6BciTQW3c9xQiD2
Route 2 of #13334. The lazify codemod's injected import had wedged itself between each block and its symbol; the injected imports move up into the import block and each comment moves back against its subject — verbatim, a position fix, not a rewrite. Editor hover is restored for the four symbols that had no attached doc at all: AIModelConfigSchema, DriverType, ActionParamSchema, PageRegionSchema. In the other four modules (data/hook, security/permission, ui/app, ui/component) the documented symbol or family head already carries its own richer JSDoc, so the moved block sits directly above it as a section lead and hover was already correct — a refinement of the card's reading, recorded in the PR. Regenerated: 10 reference pages (8 lose the misattributed opening, 2 gain their @module line) and 4 published skill indexes (8 pointer rows fall back to the honest export list). Changeset included; no schema behavior changes. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PBjwYLS6BciTQW3c9xQiD2
📓 Docs Drift CheckThis PR changes 1 package(s): 8 hand-written doc(s) NAME something this change touched and may need an implementation-accuracy re-verification:
⛔ 3 release-owned page(s) also name something this change touched. These are read-only:
What this run could not see
Coarse fallback — 128 page(s) merely mention a changed package (the pre-#9192 predicate, kept for the deliberately-wide backstop): Which tree this was computed onThis run read A worktree cut from an older # while this PR is open — GitHub drops the merge commit once it closes
git fetch origin 9998df3a0813d3aad47f2c5b943eb5054f3de637 && git checkout 9998df3a0813d3aad47f2c5b943eb5054f3de637
# afterwards, rebuild it from the two parents, which stay fetchable
git fetch origin 102a5047e6d3a2c841f2174470dc0d09652b5afa b25f061c68df855f5098b44b0580a76cb034e3cf && git checkout -B drift-repro 102a5047e6d3a2c841f2174470dc0d09652b5afa && git merge --no-ff b25f061c68df855f5098b44b0580a76cb034e3cf
node scripts/docs-audit/affected-docs.mjs --json 102a5047e6d3a2c841f2174470dc0d09652b5afa
|
|
受治理面放行(维护者词)+ 落地跟进 — Provenance:维护者于本席 Claude Code 会话(session_01PBjwYLS6BciTQW3c9xQiD2,2026-08-31 ~20:4xZ)原话:
本 PR 触发布面
复核结论不变(ACCEPT,见 #13334 comment 5478663412):两路线按序、208 语料新旧选择器对账恒等、 Generated by Claude Code |
…ollows) Resolved the one source conflict in packages/spec/src/ui/component.zod.ts by stacking both intents: this branch's hoist of the wedged import group to the top import block, and main's new section-group-reference import, which travels with the group it was appended to. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PBjwYLS6BciTQW3c9xQiD2
Discharges the os-regen deferral recorded by the merge commit. The page now carries main's section-group-reference body and no longer opens with the misattributed 'Empty Properties Schema' block, which is this branch's route-1 gate acting on the merged tree. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PBjwYLS6BciTQW3c9xQiD2
|
os-dev-report {
"issue": "PR#13794-sync",
"status": "done",
"branch": "claude/issue-13334-module-doc-block-selection",
"pr": "https://github.com/objectstack-ai/objectstack/pull/13794",
"premise_still_valid": true,
"summary": "main-sync only, zero behavior change, no shape re-litigated and the diff neither narrowed nor widened (still 27 files vs main). Worktree REUSED: ../objectstack-13794-sync already existed at the PR head a78e3871, tree clean, no merge in progress, but node_modules absent (the 429 killed the previous dev before pnpm install) - so it was reused as-is after a fresh install. Merged origin/main 62a137ba into the branch as a MERGE COMMIT (no rebase, no amend, no force-push), following scripts/pm/os-regen-merge.sh's fixed order with the merge base 8ab4ace4 recorded BEFORE the merge. CONFLICT INVENTORY - exactly two files, one per class. (1) SOURCE, hand-resolved keeping both sides: packages/spec/src/ui/component.zod.ts, a single hunk. This branch hoists the wedged import group (lazySchema, ExpressionInputSchema, retiredKey, SortItemSchema, strictObject, KeySetGuidance) out of mid-file up into the top import block; #13855 on main had appended SectionGroupKeySchema + sectionGroupReferenceRefinement to the TAIL of that same wedged group. Orthogonal intents, so they stack: the new import travels with the group it was appended to, keeping its explanatory comment, and lands at the top block. Verified after resolution - 0 conflict markers repo-wide, all 13 imports at top, no wedged import left, the branch's relocated 'Empty Properties Schema' section lead still at line 316, and #13855's group key present at all 4 use sites (declaration, describe, two superRefine/link references). (2) GENERATED, tool-regenerated not hand-merged: content/docs/references/ui/component.mdx, the ONLY os-regen path both sides moved (computed against the pre-merge base: branch moved 10 reference pages, main moved 13 regen paths, intersection = this one). Took main's side into the WORKTREE only via git restore --source=origin/main (never the index), committed the merge FIRST, then regenerated. The nine other branch-edited reference pages and the four skill indexes were branch-only - main did not touch them - so the branch's bytes were kept per the script's per-file rule, and regeneration reproduced them byte-unchanged. skills/*/references/_index.md did not conflict at all: main touched SKILL.md files, this branch touches only references/_index.md, disjoint. No census-anchor conflict. REGENERATION: pnpm --filter @objectstack/spec build closure, then gen:schema, gen:docs, gen:skill-refs. The whole chain produced exactly ONE changed file - component.mdx, 2 deletions - i.e. the misattributed opening this PR removes, and nothing else drifted. The os-regen pre-commit hook recorded the deferral on the merge commit and confirmed 'deferred regeneration discharged - all artifacts current, marker cleared' on the regeneration commit. Staged diff (not the working-tree diff) was inspected before committing, per the runbook. Silent-drop check passed: main's deriveFieldGroupLayout body is present in the regenerated page and matches origin/main's copy, so the driver's dropped side was restored rather than ridden into the merge. 208-CORPUS RECONCILIATION RE-RUN on the merged tree (the committed PR carried no such script - it was ad-hoc, so it was reconstructed: old selector extracted from the merge base 8ab4ace4, new selector from the branch, both run over every .zod.ts under packages/spec/src): 208 sources scanned, 208 verdicts byte-identical, 0 SELECTED-to-null, 0 null-to-SELECTED, 0 changed-to-a-different-block. Corpus is still 208 after main's advance, so the identity conclusion re-verifies unchanged. FOLLOW-ON FACT CORRECTIONS applied to the PR body (random facts moving with main, not behavior): check:generated 14 to 15 artifacts (#13939's declaration-map GATED row) and it is green at 15; spec suite 444 files/11893 tests to 447/12000; dispatch-derived gate family 47 to 51; skills catalog sum 10505 to 10475 - that last one moved because MAIN edited SKILL.md files in the window, and the branch's own governed-surface contribution is still exactly zero net growth (the four indexes read 45/65/61/56 identical before and after). PR body was read back in full after the PATCH - intact to the footer, no sanitizer truncation. mergeable_state moved dirty to blocked, i.e. the conflict is gone and what remains is the governed-surface gate, which is not mine to touch. Left untouched per dispatch: still DRAFT, not readied, not merged, no label changes, no releases/ edits. DEVIATION DECLARED: the worktree ../objectstack-13794-sync was deliberately NOT torn down, because the maintainer instruction is to follow this PR to merge and further sync rounds on this same branch are likely; the tree is clean and every commit is pushed, so nothing uncommitted is at risk there.",
"tests": "All at final head b25f061c6 (= remote head; the union below was re-run after the last commit, nothing landed since). Heavy runs serialized through scripts/pm/os-verify-lock.sh with OS_VERIFY_LOCK_SLOT=dev-13794-sync; every step redirected to a file FIRST and the exit code captured before any pipe, and verdicts quoted from each gate's own printed line rather than a bare exit status. (1) pnpm --filter @objectstack/spec exec vitest run --maxWorkers=2 scripts/file-description.test.ts - EXIT 0, 'Test Files 1 passed (1) / Tests 87 passed (87)' - the PR's 87 cases all green after the merge. (2) pnpm --filter @objectstack/spec test - EXIT 0, 'Test Files 447 passed (447) / Tests 12000 passed (12000)' (grew from 444/11893; the growth is main's). (3) pnpm --filter @objectstack/spec typecheck - EXIT 0, 'check:test-typecheck: OK'. (4) pnpm --filter @objectstack/spec check:generated - EXIT 0, 'All 15 generated artifacts are up to date.' - confirms #13939's 14-to-15 change and that all 15 are current on the merged tree. (5) pnpm --filter @objectstack/spec check:skill-refs - EXIT 0, '9 generated files in sync with packages/spec'. (6) Full workspace build for the gates that refuse an unbuilt tree: pnpm exec turbo run build --filter=./packages/* --filter=./packages/*/* - EXIT 0, '70 successful, 70 total'. (7) node scripts/pm/dispatch-gates.mjs --repo objectstack-ai/objectstack (no paths passed - the script derived its own change set) - EXIT 0; it asserted the answer belongs to objectstack-ai/objectstack at b25f061c6 and derived 27 changed paths vs merge base 62a137bae, i.e. exactly the branch's own files with the merge fully absorbed. 51 gate families derived; all 51 run: 50 EXIT 0, 1 non-zero. (8) The single non-zero is check:react-declaration-parity, which is NOT a regression and NOT a measurement: its right-hand input is objectui's sdui.manifest.json, which this repo cannot produce (needs a browser run at the objectui pin); its log is the standard 'produce one, then re-run' refusal. The PR body already recorded it as NOT MEASURED before this round and that reading is unchanged. (9) check:nul-bytes - not in this diff's derived family, so run additionally - EXIT 0, 'scanned 7668 text file(s) ... no raw ASCII control bytes'; plus a direct control-byte scan over every file changed vs main, clean. (10) Reconciliation harness re-run on the merged tree - EXIT 0, 'RECONCILE VERDICT: IDENTICAL - 208/208 agree under both selectors'.",
"mcp_calls": "6 - two pull_request_read at the start (get, get_comments), one update_pull_request, one pull_request_read readback, plus this report comment and its readback. No searches, no wide listings.",
"open_questions": [],
"out_of_scope_findings": []
}Generated by Claude Code Generated by Claude Code |
|
Sync 轮验收:PASS,转 ready 入队 — head 冲突处置核验(逐类)
放行动作按维护者授权(见更正后的 provenance)转 ready 并入队。⛔ 席位不代批:若受治理面在机制层要求人工 approval,本席只报告「还差维护者一次 approval / 直合」,不寻变通。 Generated by Claude Code |
Fixes #13334
Session: https://claude.ai/code/session_01PBjwYLS6BciTQW3c9xQiD2
Both routes of the triage ruling (comment 5476358037), landed in order: the marker gate first, the corpus repair second.
Route 1 — the
@modulegate (commit 505d711)packages/spec/scripts/lib/file-description.ts: a doc block sitting inside the import list — imports before it, an import the first thing after it — is selected as the module description only when it carries an explicit@modulemarker on a prose line. The marker decides in both directions: with it the block selects whatever lies beyond the plumbing; without it the block is refused even where a far-side comment once kept it. One deliberate exception: plumbing that runs to the end of the file (a pure re-export module) still selects bare — no symbol exists for the block to have been torn from. No positional or wording heuristic was added, per the dispatch order; the card measured all of them dead.The two genuine headers in the ambiguous position —
shared/mapping.zod.ts,system/cache.zod.ts— each gain the one-line marker, the repo's existing spelling (fourteen headers above their imports already open with it, and the marker line renders on their published pages the same way today). No other source header was touched.Selection reconciliation, old selector vs new, all 208 corpus sources (script re-run at b25f061, on the merged tree): after route 1 alone — 200 verdicts byte-identical, exactly the 8 misattributed openings flip SELECTED to null, 0 change to a different block. After route 2 — 208 of 208 identical under both selectors: the corpus is unambiguous again, and the gate is what keeps drift-back from republishing a wrong opening (an unmarked block in that position now renders nothing).
Route 2 — the eight corpus repairs (commit a78e387)
Each wedged
lazySchemaimport (and its co-wedged companions) moved up into the import block; each doc block moved back against its subject, verbatim — position fix, not rewrite:ai/agent.zod.tsAIModelConfigSchemadata/datasource.zod.tsDriverTypeui/action.zod.tsActionParamSchemaui/page.zod.tsPageRegionSchemadata/hook.zod.tsHookEvent's own JSDocsecurity/permission.zod.tsui/app.zod.tsBaseNavItemSchema's own JSDocui/component.zod.tsemptyPropsfactory's own JSDocCard-reading refinement: the card's hover claim ("broken for every one of the eight") holds for four of the eight. In
data/hook,security/permission,ui/appandui/componentthe documented symbol (or family head) already carries its own, richer JSDoc directly attached, so hover there was already correct; the wedged block was a redundant title. Those four blocks are placed as section leads directly above the existing docs — content preserved, position honest, and none is selectable as a module description any more. Attachment for the four restored symbols is verified by a blank-free adjacency check (closing delimiter line immediately above the declaration), 4 of 4 OK.Regenerated artifacts (same commit as the source change)
content/docs/references/: 8 lose the misattributed opening (they now honestly print no module description — the card's own 宁可缺,不要错),shared/mappingandsystem/cachegain their@moduleline, consistent with the fourteen pages that already render one.@moduleheaders keep their real titles).skills/diff readings (generated pointer rows only, zero net growth; re-measured againstmainat 62a137b):whole files before/after —
objectstack-ai/references/_index.md45/45 ·objectstack-data/references/_index.md65/65 ·objectstack-platform/references/_index.md61/61 ·objectstack-ui/references/_index.md56/56; whole catalog, sum of every SKILL.md underskills/: 10475/10475 (untouched). The catalog total reads 10475 rather than the 10505 recorded before the main-sync becausemainitself edited SKILL.md files in the merge window — the branch's own contribution to the governed surface is unchanged at zero.skills/**is a governed surface (Prime Directive 14): this PR stays draft for the maintainer's hand-merge or pinned-approval path. The skill-index files are generated artifacts thatcheck:skill-refsrequires in the same PR as the source change, so the diff is deliberately not split.Clause-2: no
Zero accept/reject behavior changes: the diff moves imports and comments and changes the docs generator's block selection. Evidence: full
@objectstack/specsuite 447 files / 12000 tests pass andcheck:authorable-surface+check:api-surface(viacheck:generated, "All 15 generated artifacts are up to date") report no surface movement, all re-run at b25f061.main-sync round (merge commit 3f4d5c7 + regeneration commit b25f061)
mainmoved ~11 hours under this branch and the PR wentdirty. Resolved by merge commit (never rebase, never force-push), followingscripts/pm/os-regen-merge.sh's fixed order — merge, choose the generated side per file, commit the merge FIRST, then regenerate.packages/spec/src/ui/component.zod.ts. Both intents stack and neither is lost — this branch hoists the wedged import group (lazySchema,ExpressionInputSchema,retiredKey,SortItemSchema,strictObject,KeySetGuidance) to the top import block, while [Decision] 字段分组漂移已裁定为平台问题(hotcrm#806)—— 定统一机制:lint 镜像规则(不动契约)与/或 section 差量引用形式(契约扩宽) #13855 had appendedSectionGroupKeySchema, sectionGroupReferenceRefinementto the tail of that same wedged group. The new import travels with the group it was appended to, keeping its explanatory comment; [Decision] 字段分组漂移已裁定为平台问题(hotcrm#806)—— 定统一机制:lint 镜像规则(不动契约)与/或 section 差量引用形式(契约扩宽) #13855'sgroupkey, itsdescribetext and itssuperRefinemixing rule are untouched, verified present at all four use sites.content/docs/references/ui/component.mdx. Not hand-merged — main's side was taken into the worktree, the merge was committed, and the page was then regenerated from the merged tree (gen:schemathengen:docs). The regenerated page carries main'sderiveFieldGroupLayoutbody (matchingorigin/main) and differs from it by exactly the two lines this PR removes: the misattributedEmpty Properties Schemaopening. Theos-regenpre-commit hook recorded the deferral on the merge commit and confirmed it discharged on the regeneration commit.maindid not touch them, so the branch's bytes were kept and regeneration reproduced them unchanged.check:generatednow reports 15 artifacts, not 14 — spec: generate declaration-map/ — TS declaration names to spec registry names (docs-audit option D, spec half) #13939 added the declaration-map GATED row. The spec suite grew from 444 files / 11893 tests to 447 / 12000, and the dispatch-derived gate family from 47 to 51, both frommain.Verification (all at b25f061, after the final commit)
pnpm --filter @objectstack/spec test— "Test Files 447 passed · Tests 12000 passed" (includesfile-description.test.ts, 87 cases, run separately as well and green: the new positive/negative marker pins, the marker-wins pin, the fenced/mid-sentence non-marker pins, and three new corpus limbs re-deriving the gate from the real tree).pnpm --filter @objectstack/spec typecheck— green ("check:test-typecheck: OK").pnpm --filter @objectstack/spec check:generated— "All 15 generated artifacts are up to date."pnpm exec turbo run build(70/70 tasks), 50 exit 0 — includingcheck:docs,check:skill-refs,check:authorable-surface,check:strictness-ledger,check:docs-single-h1,check:skill-examples,check:pm-governed-merges,check:merge-driver,check:type-check-debtand the two@objectstack/lintdoc gates.check:nul-bytesis not in the derived family for this diff and was run additionally — green (7668 text files scanned, no raw control bytes).check:react-declaration-parity— its right-hand input is objectui'ssdui.manifest.json, produced only by a browser run at the objectui pin; it is an on-demand gate whose trigger is a pin bump (maintainer ruling 2026-08-07), which this PR does not perform, and no prop declaration moved. It exits 1 with the "cannot produce the manifest here" refusal, unchanged by the sync.The selection-rule change subsumes the far-side rule that #13263 introduced (that card is not reopened; its corpus limb still passes verbatim). An unmarked block with a declaration beyond the plumbing is still refused — now by the marker gate.
Generated by Claude Code