Repository navigation
Commit b33dd25
docs(pm-dispatch,os-dev): a PR whose metadata-protocol kind is not none, or whose Clause-② carries (narrowing), owes a Skills-docs line (#26381)
Part of #26184
Clause-②: no
Metadata-protocol: none
## 维护者速读
- 改了什么:pm-dispatch 规则文本新增一条 PR 正文声明行 `Skills-docs:`——元数据协议种类非 `none`,或
`Clause-②:` 带 `(narrowing)` 的 PR,dev 按 diff 写明技能与文档是「已随本 PR 更新 /
欠后续(列文件) / 已有后续卡 / 不欠(写原因)」;席位核对该行、代立后续卡并把它改写成卡号;分诊给会改作者可写面的卡写 skills +
docs + eval 三项 done-when。四个 `.claude/**` 文件各 0 净行;无门禁、无脚本读它。
- 为什么改:维护者在席位线程的决策卡上选了「B:种类非 none 或带
(narrowing)」;此前协议变了之后没有任何一行要求技能与文档跟上——字段权限 `when` 落地后技能里一字未提,就是本卡的起因。
- 风险与回滚:只改四个规则文件,不发布、不改代码、不加门禁;每个新增一行的文件退掉一行,退掉的每一条都在别处有家(见 What
changes);回滚 = revert 本 PR 的一个提交。
- 先看:① `.claude/agents/os-dev.md` L279(dev 何时写、拼法在哪)与被退掉的 Tier S/H 一行;②
`.claude/skills/pm-dispatch/references/review-checklist.md` L18(缺即
REWORK)与被退掉的 NUL 理由行(其 `+0/-0` 触发词并入 L75);③
`.claude/skills/pm-dispatch/SKILL.md` L313 认领模板(取值、`updated here`
判据、席位改写 `#N`)。
- 两分钟验证:`pnpm check:pm-skill-ratchet` 预期退出 0 且四个文件各印 `headroom 0`;`git
grep -c 'Skills-docs:' -- .claude` 预期 os-dev.md 1、SKILL.md
2、review-checklist.md 1,别无命中。
- 需要你做的:无,席位落地。
## What changes
The maintainer chose trigger B on the seat thread's decision card (tap
label quoted verbatim in the brief above). The content is Part B's
draft, comment 6425690779 on #26184, items 1–4, written for B; triage's
「新增门禁默认否」 holds — the line is read by the seat and by triage, by nothing
mechanical.
All four files sit at their line ceilings (SKILL.md 319, os-dev.md 404,
review-checklist.md 77, triage-duties.md 103; headroom 0), and every
prose line is held to 120 bytes. The draft's after-texts for items 2, 3b
and 4 were far over that, so each rule is said once in its shortest true
form, and where a rule could not fit in place one line was retired in
that file — every clause of a retired line already lives elsewhere,
named below.
**1. `.claude/skills/pm-dispatch/SKILL.md` (319 → 319)**
- L313, the claim template's `Metadata-protocol:` line (inside the
```text fence, so length-exempt; 251 → 634 B): the parenthetical now
states the trigger (a kind other than `none`, or a `(narrowing)` arm),
the third line's spelling `Skills-docs: updated here | follow-up owed —
FILES | follow-up #N | none — REASON`, what `updated here` means (this
diff teaches it in `skills/**` or the docs and the package's evals
exercise it), and the division of labour (the dev writes it from the
diff; the seat files the owed card and rewrites `owed — FILES` to `#N`
before ACCEPT).
- L191, 核对六项 (114 → 115 B): `范围外去向` becomes `范围外去向+`Skills-docs:``. To
fit, the reader marker 「(席位读此)」 is dropped — L188 already names this
block the seat's (`## 席位核对`), and review-checklist.md L3 says whose
checklist it expands.
**2. `.claude/agents/os-dev.md` (404 → 404)**
- +L279 (112 B): 「种类非 `none` 或带 `(narrowing)` ⇒ 按 diff 加写 `Skills-docs:`
行;拼法与分工住认领模板。」 — the dev writes it once, in the PR body, from the diff;
never files the card.
- −old L284 (120 B), the Tier S / Tier H landing summary: every clause
is homed in AGENTS.md Prime Directive 14 (Tier S = all of `.claude/**`,
landed by the owning seat on a `## Contract review` PASS record; Tier H
= an authorized APPROVED review) and Post-Task Checklist step 2 (a
governed diff: push, open the PR, stop), and on the seat side in
SKILL.md L183–189.
- L285 (108 → 105 B): 「两声明行后」 → 「声明行后」. A third declaration line now
exists on exactly the PRs that owe it, so "after the two" would be false
there; "after the declaration lines" is true on every PR.
**3. `.claude/skills/pm-dispatch/references/review-checklist.md` (77 →
77)**
- +L18 (120 B): 「种类非 `none` 或带 `(narrowing)`:`Skills-docs:`
行在且属实;`follow-up owed` 立卡改 `#N`;缺 ⇒ REWORK。」 — the seat's check, with
the verdict word this file uses.
- −old L74 (102 B), the NUL harm rationale (`+0/-0` is no proof of an
empty file; NUL makes git render binary and hides the file from grep):
its trigger token `+0/-0` moves onto the action line (L75, 91 → 99 B,
now 「`+0/-0` 先疑 NUL,以 blob 定论 …」); the rationale itself is homed in
os-dev.md 〈字节与 sanitizer 纪律〉 and in the header of
`scripts/check-nul-bytes.mjs`, which os-dev.md names as the authority on
the harm argument.
**4. `.claude/skills/pm-dispatch/references/triage-duties.md` (103 →
103)**
- +L59 (117 B): 「改作者可写面(种类非 `none` 或带 `(narrowing)`)的卡,首触 done-when 写
skills + docs + eval 三项。」
- −old L96 (115 B), decision-shaped cards go to `needs-user-decision`
with the four-axis block and a recommendation, the director seat claims
them: homed in this file's L32–34, SKILL.md L107 (state table), L270
(决策卡带选项、推荐、证据、四棱块) and L276 (总监席是唯一呈裁席), filing-gate.md L15 and L27, and
lanes/director.md L54–55 (入箱勤务).
Deliberately not done: no gate, script or ledger reads the new key
(`scripts/pm/clause2-line.mjs` and `record-recognisers.mjs` still read
only `Clause-②:` and `Metadata-protocol:`); AGENTS.md is untouched
(1112/1112); no back-fill of landed PRs (Part A's eight cards are the
back-fill).
## Tests
Rule text only, all under `.claude/**`: no package moves, no test suite
is owed, and `skills/**` is untouched (no before/after readings owed).
The surface is held by gates — the local union is the `dispatch-gates
--commands` derivation at head `72b08a34`, re-run on the rework head
`9dd75f01` (25 derived / 25 run / 0 NOT-MEASURED), every command run
with its exit captured before any pipe and reconciled with `--ran` (25
derived / 25 run / 0 NOT-MEASURED / 0 UNRUN).
`check:skill-frame-freshness` (local-only, outside the derivation) also
ran. Dogfood battery: n/a — no `!` in the title and no `(narrowing)`
arm.
## Acceptance notes
- This PR does not owe a `Skills-docs:` line itself: `Metadata-protocol:
none`, no arm.
- Dispatch hypotheses, measured on `origin/main` at `f02e6443`: (1) the
draft's line numbers had moved — every target was re-found by its text
(SKILL.md L191/L313, os-dev.md L278 as the insertion anchor,
review-checklist.md L17, triage-duties.md L58); (2) the separate-line
variant's payer (the old three-safe-spellings line) is already gone, so
only in-place or retire-to-pay remained; (3) `MAX_LINE_BYTES` 120 binds;
fence lines are exempt (the template line widened in place) and table
rows carry their own widest-row pin (none touched); (4) 「声明行后」 chosen,
reason above; (5) nothing parses a third line-initial key —
`keyLineRegex` is used only for `Reviewed-by`, `Served-tier`,
`Local-runs`; `Skills-docs` had zero hits repo-wide before this PR; `#N`
is not an issue id for `check:pm-skill-id-lint` (pattern `#` + three
digits); (6) who does which is on the template line and the seat's
checklist line.
- Branch: the seat container's thread branch, per the claim (the
measured platform exception to `claude/issue-N-slug`). It was behind
`origin/main` at worktree creation and was fast-forwarded; the single
commit was then rebased once onto `f02e6443` before its first push
because the derivation flagged a stale tree — the branch had never been
pushed, so no force-push.
- Commit trailers are the model-free pair; the harness-side attribution
reminder asked for a model-named trailer and was not followed, per
os-dev.md.
- Out of scope, noted not filed: the ratchet prints a tighten hint for
`spec-property-retirement/SKILL.md`'s table-row pin (326 → 324 headroom
2), unrelated to this diff. carrier: none.
## Verification
Head `9dd75f01` (rework commit on `72b08a34`: SKILL.md L313 restores the
eval clause of `updated here`, triage-duties.md L59 spells 「或带
`(narrowing)`」, per the contract review 6431523599); readings below are
from that tree, the two reworked lines re-read on it.
<details><summary>Ratchet, id-lint and frame gates — exit 0
each</summary>
```text
pnpm check:pm-skill-ratchet :: exit 0
✓ check-skill-line-ratchet: .claude/skills/pm-dispatch/SKILL.md is 319 lines (ceiling 319; headroom 0).
✓ check-skill-line-ratchet: .claude/skills/pm-dispatch/references/review-checklist.md is 77 lines (ceiling 77; headroom 0).
✓ check-skill-line-ratchet: .claude/skills/pm-dispatch/references/triage-duties.md is 103 lines (ceiling 103; headroom 0).
✓ check-skill-line-ratchet: .claude/agents/os-dev.md is 404 lines (ceiling 404; headroom 0).
pnpm check:pm-skill-id-lint :: exit 0
✓ check-skill-id-lint: 104 file(s) clean (pattern /#[0-9]{3,}/g).
pnpm check:skill-frame-sync :: exit 0
✓ check-skill-frame-sync: the one declared copy of the decision frame is internally coherent (.claude/skills/pm-dispatch/SKILL.md; no second copy to compare — the cross-copy comparison is discharged until a second COPIES entry is declared)
pnpm check:skill-frame-freshness :: exit 0
✓ check-skill-frame-freshness: the decision frame in this tree is current with origin/main (fetched just now).
pnpm check:nul-bytes :: exit 0
check-nul-bytes: OK (scanned 21521 text file(s) -- 21521 tracked, 0 untracked-not-ignored; skipped 102 binary; no raw ASCII control bytes).
grep -naP control-byte self-scan over the four files :: exit 1 (no hit)
```
</details>
<details><summary>Derived union — 25 families, each exit captured before
any pipe, reconciled with --ran</summary>
```text
pnpm check:pm-skill-ratchet :: exit 0
pnpm check:pm-skill-id-lint :: exit 0
pnpm check:skill-frame-sync :: exit 0
pnpm check:skill-frame-freshness :: exit 0
pnpm check:agent-model-declared :: exit 0
pnpm check:agent-test-spelling :: exit 0
pnpm check:commit-card-trailers :: exit 0
pnpm check:nul-bytes :: exit 0
pnpm check:pm-expected-skips :: exit 0
pnpm check:pm-governed-merges :: exit 0
pnpm check:pm-governed-prose :: exit 0
pnpm check:pm-half-states :: exit 0
pnpm check:pm-label-write :: exit 0
pnpm check:required-contexts :: exit 0
node scripts/check-closing-keyword-parity.mjs :: exit 0
node scripts/check-closing-keyword-parity.mjs --self-test :: exit 0
node scripts/check-comment-mask-corpus.mjs :: exit 0
node scripts/pm/check-governed-queue-guard.mjs --self-test :: exit 0
node scripts/pm/check-harness-current.mjs --self-test :: exit 0
pnpm --filter @objectstack/lint run check:doc-formula-expressions :: exit 0
pnpm check:cross-package-test-inputs :: exit 0
pnpm check:doc-authoring :: exit 0
pnpm check:driver-memory-census :: exit 0
pnpm check:gitlink-declared :: exit 0
pnpm check:refd-timer-probe :: exit 0
pnpm check:watch-hint-literal :: exit 0
---
Run reconciliation — 25 derived, 25 run, 0 NOT-MEASURED, 0 UNRUN.
✓ dispatch-gates --ran: 25 derived famil(ies) accounted for — 25 run, 0 NOT-MEASURED (a DERIVED zero — all 25 recorded an exit code and none of them is 3).
```
</details>
<details><summary>The one build (prerequisite of
check:doc-formula-expressions), under the shared verify lock</summary>
```text
OS_VERIFY_LOCK_SLOT=issue-26184-partb bash scripts/pm/os-verify-lock.sh -c 'NODE_OPTIONS=--max-old-space-size=4096 pnpm exec turbo run build --filter=@objectstack/formula --filter=@objectstack/lint --concurrency=2'
os-verify-lock: VERDICT command-exit 0 · held the lock 107s (1m47s) · waited 0s · ⚠ SHARED-BOX SECONDS — this lock excluded other LOCKED runs, NOT unlocked sibling work (`check:*` gates and the rest), so these are not idle-box figures
pnpm --filter @objectstack/lint run check:doc-formula-expressions :: exit 0 (first run exit 3 = PREREQUISITE NOT MET, not measured; re-run after the build)
✓ check:doc-formula-expressions self-test: 61 cases passed
✓ check:doc-formula-expressions: 23 record-scoped formula example(s) across 492 files / 1516 TS blocks judged clean by @objectstack/formula.
✓ check:doc-formula-expressions (spec TSDoc, #6763): 9 @example(s) judged clean across 2210 packages/spec/src files — rls-predicate=8, hook-record-condition=1, record-formula=0; 0 exempt.
✓ check:doc-formula-expressions (field-level `*When`, #11407): 15 predicate(s) on a statically determinable field layer judged clean; 6 skipped as undeterminable.
```
</details>
<details><summary>Byte table of every added or respelled line (limit
120; fence lines exempt)</summary>
```text
SKILL.md L191 115 B (was 114)
SKILL.md L313 (fence) 634 B (was 251; exempt)
os-dev.md L279 (new) 112 B
os-dev.md L285 105 B (was 108)
review-checklist.md L18 (new) 120 B
review-checklist.md L75 99 B (was 91; the +0/-0 trigger folded in)
triage-duties.md L59 (new) 117 B
retired: os-dev.md old L284 (120 B), review-checklist.md old L74 (102 B), triage-duties.md old L96 (115 B)
```
</details>
<details><summary>Nothing parses the new key</summary>
```text
git grep -n 'keyLineRegex(' -- scripts
scripts/pm/record-recognisers.mjs: Reviewed-by, Served-tier, Local-runs (and the self-test pins of those three)
git grep -n -E 'readMetadataProtocolLine|readClause2Line' -- scripts .github
scripts/pm/clause2-line.mjs (the one reader), check-adr-0087-registration.mjs, check-changeset-no-major.mjs, post-stamped.mjs — two keys only
git grep -i 'skills-docs' (before this PR) :: no hit
git grep -c 'Skills-docs:' -- .claude (after) :: os-dev.md 1 · SKILL.md 2 · review-checklist.md 1
```
</details>
---
_Generated by [Claude
Code](https://claude.ai/code/session_01LqKsGyMNFwwnbF5FTAqyPn)_
---------
Co-authored-by: Claude <noreply@anthropic.com>1 parent 13136f7 commit b33dd25
4 files changed
Lines changed: 7 additions & 7 deletions
File tree
- .claude
- agents
- skills/pm-dispatch
- references
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
276 | 276 | | |
277 | 277 | | |
278 | 278 | | |
| 279 | + | |
279 | 280 | | |
280 | 281 | | |
281 | 282 | | |
282 | 283 | | |
283 | 284 | | |
284 | | - | |
285 | | - | |
| 285 | + | |
286 | 286 | | |
287 | 287 | | |
288 | 288 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
188 | 188 | | |
189 | 189 | | |
190 | 190 | | |
191 | | - | |
| 191 | + | |
192 | 192 | | |
193 | 193 | | |
194 | 194 | | |
| |||
310 | 310 | | |
311 | 311 | | |
312 | 312 | | |
313 | | - | |
| 313 | + | |
314 | 314 | | |
315 | 315 | | |
316 | 316 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
15 | 15 | | |
16 | 16 | | |
17 | 17 | | |
| 18 | + | |
18 | 19 | | |
19 | 20 | | |
20 | 21 | | |
| |||
71 | 72 | | |
72 | 73 | | |
73 | 74 | | |
74 | | - | |
75 | | - | |
| 75 | + | |
76 | 76 | | |
77 | 77 | | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
56 | 56 | | |
57 | 57 | | |
58 | 58 | | |
| 59 | + | |
59 | 60 | | |
60 | 61 | | |
61 | 62 | | |
| |||
93 | 94 | | |
94 | 95 | | |
95 | 96 | | |
96 | | - | |
97 | 97 | | |
98 | 98 | | |
99 | 99 | | |
| |||
0 commit comments