Repository navigation
Commit 6ea8342
pm-dispatch(execution): an empty-queue report is a per-card table with live labels and a named blocker; a remainder under ui/ is dispatched, never skipped (#28773)
<!-- claude-projects-attribution: {"github_login":"marchtian"} -->
_Requested by **田騏** · [project
thread](https://claude.ai/code/project/chan_01VmuUhXU9SSUzqJYyXSmYSi?thread=cmsg_01VmuUhXU9SSUzqJYyXSmYSiHXKqxUqDPJKZyNHP7BoqTb)_
Fixes #28638
Clause-②: no
Metadata-protocol: none
## 维护者速读
- 改了什么:席位报「无卡可派」时必须逐卡列表(卡号、当轮现读的标签与
assignee、具名卡点),无具名卡点的卡就是候选,不得报「空」;余项落在 `ui/**` 的排队卡照常派发,不再当「UI
的」或「别的仓的」跳过。三个文件各改一两行,行数棘轮内付清。
- 为什么改:server 车道席位对着 7 张已定级、无人认领的卡报了「队列空」,只因每张卡剩下的一半是 UI;`ui/`
早已并入本仓,无任何外部阻塞。没有逐卡表,唯一的核对就是维护者亲手再跑一次查询。
- 风险与回滚:只改 `.claude/skills/pm-dispatch/**`
规则文本,无代码、无门禁改动;风险是付行数时删掉的五行(各自主节仍载同一规则,PR 正文逐行列出处)。回滚 = revert 本 PR。
- 先看:① `references/seat-lifecycle.md` 〈停止条件与待命〉新增三行(规则本体);②
`references/execution-duties.md` 〈候选与批次〉新增两行(`ui/**` 余项与「他车道项」的边界);③
五处删行的出处对照(本正文 What changes)。
- 两分钟验证:`pnpm check:pm-skill-ratchet && pnpm check:pm-skill-id-lint &&
pnpm check:skill-frame-sync && pnpm check:pm-governed-prose` 全绿;`wc -l`
三文件仍为 319 / 96 / 188。
- 需要你做的:Tier S(`.claude/**`):席位达档复核 PASS 后由席位落地;无需维护者动作。
## What changes
Scope is the three Wanted items of the card, text only, under
`.claude/skills/pm-dispatch/**`.
**Item 1 — an empty-queue report is a per-card table**
(`references/seat-lifecycle.md` 〈停止条件与待命〉, three lines after
「队列空是待命非退场」):
- 「队列空」is a per-card table, not a verdict: whoever hears "nothing to
dispatch" (maintainer, coordinator, round report) gets every card the
lane's queue filter returns at that moment.
- Per card: the number, the labels and assignee read in the same turn
(never a cached reading), and a named blocker. A card with no named
blocker is a candidate, and the report may not say "empty".
- One blocker vocabulary, not two: the inverse of the candidate
definition in `execution-duties.md` (assigned, `needs-user-decision`,
`pm:retriage`, the `tooling` exclusion), plus an open `Blocked-by:`
line, a missing triage audit comment and a sibling seat's `Claim:`.
- `SKILL.md` L74 (the self-exit line) now points at that section — a
net-zero edit, 120 bytes.
**Item 2 — a remainder under `ui/` is dispatched as normal**
(`references/execution-duties.md` 〈候选与批次〉, two lines right after the
self-split pair):
- A queue card whose remaining work lands under `ui/**` is dispatched as
normal: `ui/` is in this repo, so the same worktree, gates and merge
queue apply; it is never skipped as "UI".
**Item 3 — reconciliation with the self-split line and the `domain:ui`
lane row**, measured on `origin/main` at 706ac52:
- The lane table's `domain:ui` row does make `ui/**` a `domain:ui`
surface — for *file ownership*. The same section says a `domain:*` label
decides file ownership only and is never a queue unit (域车道 bullet 2),
and the cross-boundary channels name "the claiming seat follows its own
cross-boundary surface to the end" (域车道, 越界只四通道).
`cross-repo-coordination.md` already ships a new spec key in the same PR
as its first `ui/` reader. So dispatching the `ui/**` remainder from the
lane that holds the card on its queue needs no change to the lane row,
and no choice the maintainer did not make: the maintainer's own words
(「写明 UI 已在 objectstack 的 `ui/` 里,剩下部分是 UI 的卡照常派」, approved with
「立卡更新skills」) pick dispatch over split-at-once, and the corrected seat
then dispatched three of the seven cards that way.
- The self-split line beside it (「排队卡含他车道项 ⇒ 发现席自拆」) is where "skip" and
"dispatch" could sit side by side, so the second new line draws the
boundary: a `ui/**` remainder is not "another lane's item" — this seat
dispatches it and does not split; self-split applies only to a
card-listed, independently landable item that lands wholly in another
lane's tree outside `ui/**` (spec, skills, devx, cloud keep their own
routing). The lane row is untouched (it sits at 332 of its 341-byte
table-row cap, with nothing to add).
**Paying the line ratchet** — every file stays at its ceiling
(`SKILL.md` 319, `seat-lifecycle.md` 96, `execution-duties.md` 188),
every edited line is within the 120-byte cap, and no line was re-wrapped
to buy room. Five lines were deleted, each one restating a rule its main
section still carries:
| Deleted line | Where the rule still lives |
|:--|:--|
| `seat-lifecycle.md` 开轮互斥 「同 session 的 subagent dev 认领不触发自退,甄别靠分支」 |
reading three in the same section is defined as the newest `Claim:`
*not* from this session, which already excludes a same-session dev;
`execution-duties.md` 认领 「`mode:subagent` 下 dev 与 PM 同 ID,身份看分支」 |
| `seat-lifecycle.md` Epic 子树车道 「顺带发现只经立卡门:三类内缺陷才立…其余进 Acceptance notes
或座位贴」 | `SKILL.md` 报告契约 (dev files nothing; the seat files the three
classes; the rest goes to Acceptance notes) and `triage-duties.md` 立卡门 |
| `seat-lifecycle.md` 断粮与跨墙恢复 「权威的墙信号是失败本身:撞墙报文里的重置时刻在那一刻可得…」 |
`platform-readings.md` 断粮检测与跨墙恢复 「撞墙报文 `limit reached, resets at
HH:MM`,重置时刻只此刻可得」 |
| `execution-duties.md` 候选与批次 「每轮每次唤醒首读本车道开着的 `priority:p0`,无人认领即同轮认领派发」
| `SKILL.md` 状态模型 `priority:p0` row (插队:同轮立即派发) and the 取卡前置 line above
it (开放 P0/P1 每次取卡现读) |
| `execution-duties.md` 候选与批次 「该假设以机制假设身份进派发令,被证伪就在同一张卡公开更正」 |
`execution-duties.md` 派发 三分区 lines (PM 机制假设须实测、鼓励证伪;⛔ 不把假设写成裁决) and
`os-dev.md` 三分区义务 (证伪照实报告) |
No issue number is cited in the skill text (`pnpm
check:pm-skill-id-lint` green). No package publishes from this diff:
`skip-changeset`.
## Tests
No code changes; the gates are the tests. Derived with `node
scripts/pm/dispatch-gates.mjs --commands --repo
objectstack-ai/objectstack` on the final diff (merge base 706ac52, 3
paths, +6/−6) and run one by one with the exit code captured before any
pipe:
<details><summary>20 derived commands — see Verification for the exit
codes</summary>
```
node scripts/check-closing-keyword-parity.mjs
node scripts/check-closing-keyword-parity.mjs --self-test
node scripts/check-comment-mask-corpus.mjs
node scripts/pm/check-governed-queue-guard.mjs --self-test
node scripts/pm/check-harness-current.mjs --self-test
pnpm --filter @objectstack/lint run check:doc-formula-expressions
pnpm check:agent-test-spelling
pnpm check:cross-package-test-inputs
pnpm check:doc-authoring
pnpm check:driver-memory-census
pnpm check:gitlink-declared
pnpm check:nul-bytes
pnpm check:pm-expected-skips
pnpm check:pm-governed-merges
pnpm check:pm-governed-prose
pnpm check:pm-skill-id-lint
pnpm check:pm-skill-ratchet
pnpm check:refd-timer-probe
pnpm check:skill-frame-sync
pnpm check:watch-hint-literal
```
</details>
## Acceptance notes
- `execution-duties.md` 认领 「部分落地…余项整树归他席 ⇒ 点名该席改标,拆分加 `pm:retriage`」 is
the release-time route for a card whose remainder belongs to another
seat's tree. It is not a "skip" (the card returns to `pm:queue` on this
lane and is a candidate at the next refill under item 2), and the
`domain:ui` seat may still relabel it, so both routes stand; it is
outside this card's file surface and left as is. Noted, not filed.
- The `domain:ui` lane row and `references/lanes/ui.md` 「跨层功能的 `ui/`
子单归本席」 speak of sub-cards that triage split per layer, not of an unsplit
remainder; no edit needed.
## Verification
Head sha and readings are in the `os-dev-report` comment on #28638
(session `session_017ihL2g7RyXa8ErM6GAkHyc`, seat `domain:skills#2`).
Line budget after the edit: `SKILL.md` 319/319, `seat-lifecycle.md`
96/96, `execution-duties.md` 188/188; longest edited line 120 bytes.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
---------
Co-authored-by: marchtian <noreply@anthropic.com>1 parent 2cba2eb commit 6ea8342
3 files changed
Lines changed: 8 additions & 8 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
71 | 71 | | |
72 | 72 | | |
73 | 73 | | |
74 | | - | |
| 74 | + | |
75 | 75 | | |
76 | 76 | | |
77 | 77 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
39 | 39 | | |
40 | 40 | | |
41 | 41 | | |
42 | | - | |
43 | 42 | | |
44 | 43 | | |
| 44 | + | |
| 45 | + | |
| 46 | + | |
45 | 47 | | |
46 | 48 | | |
47 | 49 | | |
48 | 50 | | |
49 | 51 | | |
50 | 52 | | |
51 | | - | |
52 | 53 | | |
53 | 54 | | |
54 | 55 | | |
55 | 56 | | |
56 | 57 | | |
57 | 58 | | |
58 | | - | |
59 | 59 | | |
60 | 60 | | |
61 | 61 | | |
62 | 62 | | |
63 | 63 | | |
64 | 64 | | |
65 | | - | |
| 65 | + | |
66 | 66 | | |
67 | 67 | | |
68 | 68 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
10 | 10 | | |
11 | 11 | | |
12 | 12 | | |
13 | | - | |
14 | 13 | | |
15 | 14 | | |
16 | 15 | | |
| |||
58 | 57 | | |
59 | 58 | | |
60 | 59 | | |
61 | | - | |
62 | 60 | | |
63 | 61 | | |
64 | 62 | | |
| |||
86 | 84 | | |
87 | 85 | | |
88 | 86 | | |
| 87 | + | |
| 88 | + | |
| 89 | + | |
89 | 90 | | |
90 | 91 | | |
91 | 92 | | |
92 | 93 | | |
93 | 94 | | |
94 | 95 | | |
95 | | - | |
96 | 96 | | |
0 commit comments