docs(agents,skills,pm): make the remaining one-shot-executor fences executable, and re-lock the retirement pin - #16357
Conversation
…xecutable, and re-lock the retirement pin Every instruction addressed to a one-shot executor must be terminal within the run. Four sites still asked for a mid-run channel that executor does not have; three of them are rewritten here (the fourth rides its own PR on SKILL.md): - os-dev.md — "go ask" about PR state a dev did not set becomes forbid plus a terminal route: never correct it, put the question in the report, and report `blocked` where it blocks the work. - dispatch-runbook.md — the verbatim dispatch-word sentence about a producer in another package drops its "notify first, then fix" sequencing and keeps the trace: fix at the producer, record the landing point and the reasoning. - checklist-test/SKILL.md and its RUNNER.md twin — an auth/authz repro no longer says "stop and wait for the maintainer"; the run ends with that report, which the RUNNER rule already calls a completed verdict. Both copies move together. Two clauses on the same file, both line-neutral and paid for by deleted rationale, never by re-wrap: the line-ratchet clause gains the ruled measurement-first exception for a governed ledger at zero headroom, and the PR rules gain the clause-2 carrier line (the dev hangs `needs:contract-review` on the PR in the same write and reports the pair predicate's exit). The skill line ratchet's `max-table-row-bytes` pin for the retirement playbook drops 328 to 326, the value the gate has been printing as an advisory on every run. Lowering a shrink-only pin needs no ruling; the gate now prints none. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019RfFHiRCSs3JXLK4cwcfox
|
ACCEPT — contract-tier review of PR #16357, head Implemented-by: Verified in a detached compare worktree at the PR head, not from the report:
Ruling on the open question — A. SKILL.md's PM-side ratchet summary row does not carry the new measurement-first exception; the exception fires only when the dispatch itself names measurement-first, so the PM is by construction the party who knows it. No line is bought on a zero-headroom file to restate a rule the PM authors; if the next SKILL.md flight (#16352 / #16229, after PR #16339 and PR #16271 land) finds a fold that pays for it, it rides there as a rider — recorded on those cards' dispatch, not owed. Landing regime: governed ( Generated by Claude Code |
维护者速读改了什么:三处写给一次性执行者、却要求它「先问 / 先报备 / 停下等人」的指令,改成它真能做完的形态——要么直接做并把判断写进报告,要么明确禁止并把问题留在报告里;另外在 dev 定义里补两条规则(零余量受管账本的测量优先例外; 为什么改:一次性 dev / runner 没有中途提问的通道。一条要求它「问完再继续」的围栏,实际上把「做、不做、还是自己拿主意」整个交回给了它,而作者以为已经把这个选择拦下了。判据早已落地(dev 契约里的「一次性执行者」原则),这里只是把存量文本改到判据上。 要请您看一眼的:安全漏洞复现那一条(checklist-test 与 RUNNER 规则 2 两处同文)。改后运行以那份报告终局,复现仍留在会话里、不上 GitHub;RUNNER 原文本来就把这份报告称作完整判定,所以禁令强度未降,只是删掉了「等维护者」这个执行者做不到的动作。请确认这是您要的强度。 代价与回滚:纯指令文本加一个棘轮 pin,不动运行时代码,门禁全绿;席位逐句核过被删的三句都是「为什么」而不是规则本身。回滚是一次 席位意见:建议合并。受管面( Generated by Claude Code |
Fixes #14768
Fixes #15959
Fixes #15957
Fixes #15975
Deliverable 2 of the census card — the rewrites — for the three hits that sit
outside
.claude/skills/pm-dispatch/SKILL.md(that fourth hit rides its own PRon the same file), folded with the corpus programme's re-lock pass and the two
protocol clauses that land on the same governed files.
The criterion is not re-argued here. It is the landed bullet in
.claude/skills/pm-dispatch/references/dispatch-runbook.md: an instructionaddressed to a one-shot executor must be terminal within the run — either
allow-with-trace, or forbid. Each site below becomes one of those two forms, one
sentence per rule, and no sentence outside the hits moves.
What changed
The three rewrites
.claude/agents/os-dev.mdblockedwhere it blocks the work.claude/skills/pm-dispatch/references/dispatch-runbook.md.claude/skills/checklist-test/SKILL.md+docs/qa/platform-checklist/RUNNER.mdThe runbook line is dispatch-word boilerplate the PM copies verbatim, so the
unexecutable form reached a one-shot dev unaltered. The checklist-test clause
declares itself the same rule as RUNNER rule 2, so both copies move in one
stroke — RUNNER already calls that report a completed verdict, which is exactly
what makes the wait removable rather than merely shortened.
Two clauses on
.claude/agents/os-dev.mdmeasurement-first for a governed ledger at zero headroom, land the lines,
leave the ceiling row untouched, let the ratchet read red and report the
measured count.
blockedstays the default for every other unpayable ratchet,and raising a ceiling yourself stays forbidden in both branches.
contract-review clause hangs
needs:contract-reviewon the PR in the samewrite that opens it, and reports the pair predicate's exit code. A
single-carrier hang converts a legitimate future clear into an unprovable one,
and the defect is committed at hang time.
The re-lock pass
scripts/pm/check-skill-line-ratchet.mjs— one pin row, the retirementplaybook's
max-table-row-bytes, 328 to 326. That is the value the gate itselfhas been printing as an advisory on every run; lowering a shrink-only pin is
always legitimate and needs no ruling. No other row moves. After the change the
gate prints no advisory at all — every ceiling and every pin sits at its
landed count.
Line accounting — the currency is deleted content, never re-wrap
os-dev.mdis 403/403 with zero headroom, and this PR adds two rules to it. The2026-08-17 ruling is that re-wrap may not be used to buy lines; the legal
currency is deleting content. So both lines are paid for by deletions, and the
deletions are named:
content volume with lines as its machine-readable proxy, and that the gate
cannot tell the two net-0 shapes apart. Both are why text; the operative
discriminator (does the fold buy lines for new content) and the operative rules
around it are kept verbatim.
commit message. The rule it justifies — card relations are declared once in
the body, never as a per-commit trailer — is unchanged and complete alone.
Landed counts, from the gate's own verdict lines at the head below:
checklist-test/SKILL.mdcame in at 234 lines before and after — the bulletre-wraps inside itself around the changed sentence and buys nothing. Both other
ratcheted files are line-neutral.
One reading correction worth recording:
scripts/check-skills-token-ratchet.mjsdoes not cover
.claude/skills/**at all — its population is the publishedskills/catalog. The ratchet that governschecklist-test/SKILL.mdis the lineratchet above. The token ratchet was run anyway, self-test and live, both green.
Verification
Every exit code captured before any pipe (redirect, then read
$?), and eachverdict quoted from the gate's own line rather than from a bare status.
f5c08e9589:node scripts/pm/dispatch-gates.mjs --commands --repo objectstack-ai/objectstackover the five-path change set — 39 families. All 39 run, all green.
Reconciled:
--ranreports 39 derived, 39 run, 0 NOT-MEASURED, 0 UNRUN.pnpm check:pm-skill-ratchet(self-test then live) green, and the live runprints zero advisory lines.
node scripts/check-skills-token-ratchet.mjs --self-testand the live run:both green.
pnpm check:pm-skill-id-lint,pnpm check:skill-frame-sync,pnpm check:pm-governed-prose,pnpm check:agent-model-declared,pnpm check:nul-bytes,pnpm check:platform-checklist,pnpm check:ratchet-remedy-authority,pnpm check:pm-dispatch-gates: green.node scripts/pm/check-half-states.mjs --self-test: green. Every rewritten andevery deleted sentence was grepped across
scripts/,.github/,packages/and
docs/— no pin names any of them, in either the old or the new spelling.node scripts/pm/check-governed-merges.mjs --testover the five paths:exit 3, GOVERNED, naming exactly one regime —
.claude/**, three paths.No second regime, which is why this is one PR.
.claude/hooks/*.selftest.sh: five files, all green.pnpm lint(eslint . --no-inline-config) throughscripts/pm/os-verify-lock.sh, slotissue-14768:VERDICT command-exit 0.Whole-repo, not narrowed.
Everything above was re-run at
f5c08e9589after the merge ofmain, not onlyat the pre-merge commit.
Governed endgame
The diff hits
.claude/**, so this stays a draft PR: no seat flips it ready,enqueues it, arms auto-merge, or approves it.
skip-changesetapplies — nothingin the diff publishes from any released package.
维护者速读(草稿)
改了什么 —— 三处写给一次性执行者、却要求它「先问 / 先报备 / 停下等人」的指令,改成
它真能做完的形态:要么直接做并把判断写进报告,要么明确禁止并把问题留在报告里。另外在
dev 定义里补两条规则(零余量受管账本的测量优先例外、clause-2 双载体在开 PR 同笔挂上),
并把技能行数棘轮里一条 2 字节的 pin 收紧到实测值。
为什么改 —— 一次性 dev / runner 没有中途提问的通道。一条要求它「问完再继续」的围栏,
实际上把「做还是不做还是自己拿主意」整个三选一交回给了它,而作者以为自己已经把这个选择
拦下了。这是一类事故,不是措辞偏好;判据本身早已落地,这里只是把存量文本改到判据上。
风险与代价(含回滚) —— 纯指令文本 + 一个棘轮 pin,不动任何运行时代码,门禁全绿。
风险面在于「安全漏洞复现要不要等人」那一条:改后运行以报告终局,复现仍然留在会话里、
不上 GitHub,RUNNER 原文本来就把这份报告称作完整判定,所以禁令强度未降。回滚是单次
git revert,无数据迁移、无下游依赖。席位意见 ——
你要做的 —— 读一下三处改写后的句子是否仍然是你要的强度(尤其是安全复现那条),然后
人工合并。⛔ 不要由任何 AI 席位合并、入队或批准;
.claude/**是受管面。Generated by Claude Code
Generated by Claude Code
Generated by Claude Code