Commit de47b98
skills(pm-dispatch): write the maintainer's base adjudication principle into the four-axis frame (#17734)
Fixes #17389
## What
Writes the maintainer's base adjudication principle into the four-axis
decision frame of `.claude/skills/pm-dispatch/SKILL.md` 〈升级与决策〉 as a
**named** principle (`**基本裁决原则**`), quoted verbatim with its date,
inside the frame block next to the two maintainer quotes already
embedded there (2026-08-04, 2026-08-27). The three clauses, verbatim and
untranslated (director chat, 2026-09-10):
> 我们的项目以objectstack 协议为准,文档应该以实际实现为准。协议不正确的应该先修改协议。
The same lines carry the derived reading the next adjudicator applies
mechanically: the shape `@objectstack/spec` declares is above the actual
implementation, which is above every documentation face; a declared arm
the implementation does not honour is an implementation gap (implement
it or retire it through a spec card, never narrow it in a consumer); an
undeclared key follows its implementation and the documentation follows
the implementation. The third clause fixes the order: a wrong protocol
is corrected first, as its own card.
Same PR: the matching clause in `references/core-rules.md` 〈升级与决策〉
replaces that file's derived-only line with the named principle (net 0
lines).
## Landing points
- `.claude/skills/pm-dispatch/SKILL.md` — three lines (now 751–753)
inserted inside the frame block, between the fourth axis and the binding
sentence 「推荐意见必须基于这四条轴给出理由…」, in the binding sentence's paragraph so no
blank line is spent. The block stays 734–755. Paid at 812/812 by three
density folds inside the same 〈升级与决策〉 section:
- 「权重按缩小而非扩大特例与契约增生读…」 + 「权重是推荐规则不是授权规则…」 → one line (116 B).
- 「四维分析从业务的角度写;写法六项与四棱块固定形状见 …」 + 「四棱是四轴的卡面序列化…」 → one line (119 B); the
pointer to `references/decision-analysis.md` is already carried above
the block (「分析模板见 …」), so no rule loses its home.
- 「收件箱由维护者定期消化,⛔ 不 assign 推送。」 folded into 「卡先于弹窗…」 → one line (118 B).
No re-wrap was used as payment; every payment deletes restated content,
and every clause of each folded line survives in the folded line.
- `.claude/skills/pm-dispatch/references/core-rules.md` — line 143
rewritten (120 B) to carry the principle's three clauses in digest form;
151/151.
- The two existing derived lines are kept untouched by ruling: SKILL.md
「协议为基准:spec 与代码不一致默认改代码对齐;改协议单独立卡,⛔ 不作缺陷卡的选项。」 and the 分诊 section's
「说明书脱节不进:有裁定出处才是 (b),否则改文档」.
## Line budget
| file | before | after | ceiling |
|:--|--:|--:|--:|
| `.claude/skills/pm-dispatch/SKILL.md` | 812 | 812 | 812 |
| `.claude/skills/pm-dispatch/references/core-rules.md` | 151 | 151 |
151 |
Changed-line byte lengths (all ≤ 120 B): 104 · 116 · 116 (principle) ·
116 · 119 · 118 (folds) · 120 (core-rules).
## Verification (head `ea98fed9d`)
Named gates, exit captured before any pipe, all on `ea98fed9d`:
- `pnpm check:pm-skill-ratchet` → exit 0 — `✓ check-skill-line-ratchet:
declared cross-file moves: 1, total ceilings down 9 lines.`
- `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; …) 4 axes: business-need →
long-term-soundness → ai-authoring-safety → startup-scope-discipline;
binding sentence present in it; 1 count mention(s) agree; 74 markdown
files scanned for undeclared copies.`
- `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). 1 copy across 1 file; 4 axes …; 0/1
framework files are byte-identical to the ref (wording differences are
not drift).`
- `pnpm check:pm-skill-id-lint` → exit 0 — `✓ check-skill-id-lint: 27
file(s) clean (pattern /#[0-9]{3,}/g).`
- `pnpm check:nul-bytes` → exit 0 — `check-nul-bytes: OK (scanned 8435
text file(s) … no raw ASCII control bytes).`
Derived gate list (`node scripts/pm/dispatch-gates.mjs --commands`, no
paths, derived at `ea98fed9d`: 16 families) run in full and reconciled:
`✓ dispatch-gates --ran: 16 derived famil(ies) accounted for — 16 run, 0
NOT-MEASURED`. Every family exit 0: closing-keyword-parity (+
--self-test), comment-mask-corpus, governed-queue-guard --self-test,
lint `check:doc-formula-expressions` (first run refused with exit 3
PREREQUISITE NOT MET on an unbuilt `@objectstack/formula`; rebuilt
`@objectstack/formula` + `@objectstack/lint` under
`scripts/pm/os-verify-lock.sh` — `VERDICT command-exit 0` — and re-ran:
exit 0, `9 @example(s) judged clean across 1387 packages/spec/src
files`), agent-test-spelling, doc-authoring, driver-memory-census,
nul-bytes, pm-governed-merges, pm-governed-prose, pm-skill-id-lint,
pm-skill-ratchet, refd-timer-probe, skill-frame-sync,
watch-hint-literal.
Path face: `node scripts/pm/check-governed-merges.mjs --test …` → `⛔
GOVERNED — a human merge is the review record for this PR` (2 of 2 paths
hit `.claude/**`; exit 3 is that script's GOVERNED code).
## Deviations from the dispatch route
- The card's 「and in the framework's synced copy」 premise is stale
(verified in `scripts/check-skill-frame-sync.mjs`: `COPIES` declares ONE
copy with an anti-dormancy scan; `check:skill-frame-freshness` judges
that copy's structure against `origin/main`). No second copy was
written. The frame's structure (4 bullets, declaring and binding
anchors) is unchanged, which is what both guards judge; the principle is
a non-bullet paragraph, invisible to the axis parser by design
(`ENTRY_START` admits only list bullets and `**Axis` paragraphs).
- Placement: the suggested route put the principle at the head of the
block, above the bold opener. Measured against the anchors: the frame is
extracted and pasted between its declaring sentence and its binding
sentence (the guards' `start`/`binding` anchors, and the dispatch's own
md5 was taken from the bold opener), so a head placement lands outside
the span an anchored paste carries — measured: with the head placement
the opener-to-拍板 span was byte-identical to `origin/main` (md5
`22f2339f…`). The principle therefore sits inside the anchors,
immediately before the binding sentence; the block md5 at 734–755 is now
`3327d02c56f8a0eca88569dad2270f32`.
- The suggested route's other half — tagging the two derived lines with
the principle's name — was not taken: 「说明书脱节不进…」 sits at 120/120 B with
no room, and both lines are outside the claim's declared file surface
(block + payment). The block carries the named principle; the derived
lines are unchanged.
- The verbatim quote follows this file's punctuation convention (ASCII
comma inside Chinese prose, exactly as the two existing verbatim quotes
in the block are spelled; the file carries zero fullwidth commas). The
characters are otherwise byte-for-byte the maintainer's.
- core-rules digest: 「必带」 → 「带」, and the sentence 「spec 与代码不一致默认改代码」 is
folded into the principle's first clause (协议为准) to fit 120 B;
「改协议单独立卡非选项」 survives as 「协议错另立卡先改」.
## Acceptance notes
- noted, not filed: SKILL.md 〈机械守卫索引〉 row for `check:skill-frame-sync` /
`-freshness` still reads 「四维决策框架两份拷贝的同构与新鲜度」 — one copy since the
published PM skill was deleted; a one-word doc nit outside this card's
declared surface. 承接者: none known.
- Commit messages carry no card relation; the relation is declared once,
in this body.
## 维护者速读(草稿)
**改了什么**:把您 2026-09-10 那句「以 objectstack 协议为准,文档以实际实现为准,协议不正确先改协议」写进 PM
派发技能的四轴决策框架里,命名为「基本裁决原则」,逐字引用带日期;同一处写清推导序:spec 声明 > 实现 > 文档面。core-rules
摘要同笔改一行。
**为什么改**:每次遇到「声明与实际不一致」的卡,各席位都在重新推导这条原则,结论会漂移;写成具名原则后,分诊与裁决直接引用它,不再各自推。
**风险与代价(含回滚)**:两个文件都在行数上限,新增三行用同节三处重复表述的合并支付,内容无丢失;门禁全绿。回滚 = revert 本
PR,无发布物、无 changeset。
**席位意见**:
**你要做的**:确认原则措辞与推导序无误后人工合并;不需要其他动作。
---
_Generated by [Claude
Code](https://claude.ai/code/session_01MCLBsUgfykL74aU716rzVK)_
---------
Co-authored-by: Claude <noreply@anthropic.com>1 parent 01388fe commit de47b98
2 files changed
Lines changed: 7 additions & 7 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
748 | 748 | | |
749 | 749 | | |
750 | 750 | | |
| 751 | + | |
| 752 | + | |
| 753 | + | |
751 | 754 | | |
752 | 755 | | |
753 | 756 | | |
754 | 757 | | |
755 | 758 | | |
756 | 759 | | |
757 | | - | |
758 | | - | |
759 | | - | |
760 | | - | |
761 | | - | |
762 | | - | |
| 760 | + | |
| 761 | + | |
| 762 | + | |
763 | 763 | | |
764 | 764 | | |
765 | 765 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
140 | 140 | | |
141 | 141 | | |
142 | 142 | | |
143 | | - | |
| 143 | + | |
144 | 144 | | |
145 | 145 | | |
146 | 146 | | |
| |||
0 commit comments