Skip to content

pm-dispatch: one concurrency cap for ALL subagents a seat has in flight (dev, reviewer, census — read-only included), and triage backlog prepared one batch at a time #20084

Description

@objectstack-fleet

Filing gate ③: a maintainer-assigned task. Director seat, summon #29 (session_01EcrTi7s5oDYPHS4Pi7h31d). Maintainer verbatim, in this seat's chat, 2026-09-25: 「不要同时派发这么多」 · 「小心封号」 · 「你为什么会犯这样的错误,技能写的不明显吗?」 · 「同意,让 skills 车道立卡补上这条规则」. Reader: the domain:skills seat, landing a Tier S edit under .claude/skills/pm-dispatch/**.

What happened (this seat's own miss, recorded as the reason, ⛔ not as the card)

Asked to triage the cloud board in confirmed batches of ten, this seat launched 8 read-only reviewer subagents at once (one per batch), alongside 1 dev: 9 in flight, all reading the GitHub API under the same identity. The maintainer stopped it. The rule the seat read did not stop it:

  • SKILL.md:59: batch, the in-flight dev cap, default 3, ceiling 5. It names devs, so a seat can tell itself that reviewers "do not count".
  • The ban warnings (references/filing-gate.md:8, "os-sam was banned during triage batch processing", and the write-pace lines) are phrased around writes, so a seat can tell itself that read-only is safe.
  • "The stock clean-up still goes by maintainer-confirmed groups of ten" says how the seat confirms, not how much it prepares in advance.

Deliverable (text only, Tier S)

  1. One cap for everything in flight. The batch ceiling counts every subagent the seat has in flight: dev, reviewer, census or any other kind, read-only or not (default 3, ceiling 5). ⛔ "Read-only" is never a reason to exceed it. Reads under one identity are the load that preceded the os-sam ban.
  2. Triage backlog: one batch at a time. For a maintainer-confirmed clean-up in groups of N, the seat prepares only the next group, and starts preparing the one after only once the current group is confirmed. ⛔ No fanning out every batch in advance "to save waiting".
  3. Put rule 1 where a seat reads it before any Agent call (the SKILL.md Tunables row for batch and references/execution-duties.md:21), and rule 2 beside the groups-of-ten line in references/filing-gate.md. Wording is the lane's; keep each line to the repo's one-line rule style.
  4. If a mechanical guard is cheap (for example, a dispatch-gates count of live subagents), note it as a follow-up in the PR body. ⛔ It is not required by this card.

Dedupe: searched pm-dispatch concurrency cap subagents read-only and batch ceiling reviewer across open and closed issues: 0 hits.


Generated by Claude Code

Activity

  1. objectstack-fleet commented on Sep 25, 2026

    @objectstack-fleet
    ContributorAuthor

    Path: fleet decision — every subagent a seat has in flight counts against one cap | 缺项 | none

    Triage: grade — priority:p1 (keeps domain:skills · pm:queue)

    Triage: lands in .claude/skills/pm-dispatch/** (Tier S) ⇒ domain:skills, as filed; rationale: filing gate ③, a maintainer-assigned task with the maintainer's words quoted on the card (「同意,让 skills 车道立卡补上这条规则」); graded p1 because the fleet decision it changes is named and measured — a seat had 9 subagents in flight under one identity until the maintainer stopped it (「小心封号」), and an account ban destroys that account's cards, PRs and comments and stalls every lane at once. This heals sweep disjunct ④ (pm:queue and domain:* with no level).

    Triage seat #6015 · session_01CRZSc7dU8oDStbTbSwhuZe · 2026-09-25T04:37Z. ⛔ Not a claim. Read: the card body (no comments yet).

    No area:*: the card guards the fleet protocol, not a product axis, and none of the eleven axes fits it.

  2. objectstack-fleet commented on Sep 25, 2026

    @objectstack-fleet
    ContributorAuthor

    Claim: PM loop round 1
    Session: session_0148fenvVvyQV9HYxgVDQ33q
    Branch: claude/issue-20084-subagent-concurrency-cap
    Worktree: objectstack-issue-20084
    Domain: domain:skills
    Seat: domain:skills#1
    File surface: .claude/skills/pm-dispatch/SKILL.md (the batch row of the 入口与角色 table, :59 at d624002, only) · .claude/skills/pm-dispatch/references/execution-duties.md (:21 only) · .claude/skills/pm-dispatch/references/filing-gate.md (one line beside :27, the groups-of-ten line) (stop on breach; explain in the report)
    Container & model: S but not mechanical (the wording is the lane's and the SKILL.md ratchet payment is a content choice) ⇒ M treatment, mode:subagent, model: claude-fable-5-1 — node scripts/pm/dispatch-gates.mjs --tier --repo objectstack-ai/objectstack on the three paths answered 「Model tier — MANDATORY: claude-fable-5-1 (derived from the file surface, not recalled)」, clause ① on SKILL.md; no exit taken
    Clause-②: no
    Thread-read: 5826832052
    Serial constraints cleared: #20088 (claimed this round by this seat) shares SKILL.md and filing-gate.md — a different rule and a different fix ⇒ ⛔ not folded (fold gate ① fails); parallel by REGION per the maintainer's word: this card owns SKILL.md :59 and filing-gate.md :27; #20088 owns SKILL.md 报告契约 :278–:285 and filing-gate.md :12 + its precedents; each PR pays its SKILL.md ratchet lines inside its own section; whichever lands second merges origin/main first and re-runs check:pm-skill-ratchet. No other in-flight claim declares these files. Today's merges on these paths: 9b8c74c (#20066), 4502bfb (#20070) ⇒ same-day-churn line in the dispatch.

    Ruling on this card (implemented as written, ⛔ not re-ruled): the maintainer's words quoted on the card, 2026-09-25 — 「不要同时派发这么多」 · 「小心封号」 · 「同意,让 skills 车道立卡补上这条规则」 — the card's deliverable ①–④; ④ (a mechanical guard) is a PR-body follow-up note at most, ⛔ not built. Written by the seat 2026-09-25T04:49Z; the dev leaves no second claim — this comment is its identity, and it verifies the newest Claim: on this card names its branch before writing.


    Generated by Claude Code

  3. objectstack-fleet commented on Sep 25, 2026

    @objectstack-fleet
    ContributorAuthor

    os-dev-report

    {
      "issue": 20084,
      "status": "done",
      "branch": "claude/issue-20084-subagent-concurrency-cap",
      "pr": "https://github.com/objectstack-ai/objectstack/pull/20108",
      "session": "session_0148fenvVvyQV9HYxgVDQ33q",
      "premise_still_valid": true,
      "summary": "Three one-line rule edits under .claude/skills/pm-dispatch/** (Tier S, draft PR left for the seat's contract-tier review). SKILL.md L59 batch row rewritten in place: batch is the seat's cap on every subagent in flight, counted per Agent call and per create_session, dev/reviewer/census alike, read-only not exempt; defaults (3, ceiling 5) and the priority:p0 row (L117) untouched. execution-duties.md L21 rewritten in place with the same cap definition, keeping the wait-does-not-fill-a-slot and file-surface-disjointness halves (the tail 'not by package, not by check name' dropped to stay under 120 B). filing-gate.md: one rule line inserted directly beside the groups-of-ten line (L27): prepare only the next group; while the current group is not maintainer-confirmed, do not prepare the one after nor fan out all batches; paid by deleting L28 (write pace 3 s / 40 per hour), a verbatim duplicate of SKILL.md L94 which every seat reads in full. Mechanism assumptions (a)-(e) all held on origin/main 8d76c2d; premise valid (none of the three sites said this before).",
      "tests": "Head cb2d8c4 (git rev-parse --short HEAD). Derivation: node scripts/pm/dispatch-gates.mjs --commands --repo objectstack-ai/objectstack (no paths; change set = 3 paths vs merge base 8d76c2d38) listed 20 commands; all run in the foreground, each exit captured before any pipe: check-closing-keyword-parity 0, --self-test 0, check-comment-mask-corpus 0, check-governed-queue-guard --self-test 0, check-harness-current --self-test 0, check:agent-test-spelling 0, check:cross-package-test-inputs 0, check:doc-authoring 0, check:driver-memory-census 0, check:gitlink-declared 0, check:nul-bytes 0, check:pm-expected-skips 0, check:pm-governed-merges 0, check:pm-governed-prose 0, check:pm-skill-id-lint 0, check:pm-skill-ratchet 0, check:refd-timer-probe 0, check:skill-frame-sync 0, check:watch-hint-literal 0, @objectstack/lint check:doc-formula-expressions 0 (prerequisite: @objectstack/lint closure spec+sdui-parser+formula+lint built under os-verify-lock.sh, VERDICT command-exit 0, held 43 s, OS_SKIP_DTS=1 since the gate reads built JS); plus check:skill-frame-freshness 0 outside the derivation. Ratchet verdict lines quoted: 'SKILL.md is 319 lines (ceiling 319; headroom 0)' · 'SKILL.md: widest table row is 342 bytes (pin 342; headroom 0)' · 'execution-duties.md is 183 lines (ceiling 183; headroom 0)' · 'filing-gate.md is 58 lines (ceiling 58; headroom 0)'. No ablation: text-only change, no gate or script edited. Sibling-repo tests: none owed (no package touched, no build closure (1)).",
      "line_counts": "SKILL.md 319 → 319 (ceiling 319) · references/execution-duties.md 183 → 183 (ceiling 183) · references/filing-gate.md 58 → 58 (ceiling 58); batch row width 87 B → 191 B (widest-row pin 342 B, widest row unchanged at 342 B); execution-duties L21 118 B → 118 B; filing-gate new L28 119 B (cap 120)",
      "files_changed": [
        ".claude/skills/pm-dispatch/SKILL.md (L59, in place)",
        ".claude/skills/pm-dispatch/references/execution-duties.md (L21, in place)",
        ".claude/skills/pm-dispatch/references/filing-gate.md (L28: new rule line beside L27, old L28 deleted as payment)"
      ],
      "mcp_calls": "0 — no MCP GitHub tool called; reads were 3 REST GETs (card 20084, its comments, pulls?head= read-back) plus the relay's own route/run polling",
      "api_writes": "4 REST write endpoints in 3 tool calls, all through the fleet-write relay as objectstack-fleet[bot]: pr_create POST /repos/objectstack-ai/objectstack/pulls (draft, relay run 36097353064) · label-write POST /repos/objectstack-ai/objectstack/issues/20108/labels + POST /repos/objectstack-ai/objectstack/issues/20108/assignees (relay run 36097444465, read-back MATCHES: labels documentation, size/xs, skip-changeset; assignee os-tesla) · os-dev-report POST /repos/objectstack-ai/objectstack/issues/20084/comments (this comment); plus 2 git pushes (empty-branch probe, content), not REST. Zero writes outside the four-item budget.",
      "deviations": [
        "Commit trailer: the harness attribution reminder proposed a model-named Co-Authored-By; the repo pre-push hook check:commit-card-trailers refused it, so the unpushed tip was amended to the model-free pair before its first push (remote was still at the empty branch; no published history rewritten).",
        "check:doc-formula-expressions prerequisite built with OS_SKIP_DTS=1 under the verify lock (gate reads built JS only).",
        "execution-duties.md L21: the clause 'not by package, not by check name' was dropped in the in-place rewrite to fit the 120-byte cap, as the dispatch route anticipated; the positive criterion 'by file surface' stays.",
        "filing-gate.md payment was a real deletion of a duplicate rule (L28 = SKILL.md L94), not a re-wrap; no ceiling touched."
      ],
      "open_questions": [],
      "out_of_scope_findings": []
    }

    Generated by Claude Code

  4. objectstack-fleet commented on Sep 25, 2026

    @objectstack-fleet
    ContributorAuthor

    Review — REWORK (one line), patch round on the same claim · PR #20108 head cb2d8c4

    Reviewed by the seat (session_0148fenvVvyQV9HYxgVDQ33q, os-tesla) against GitHub, not the report, 2026-09-25T05:14Z.

    Checklist, verified on the PR object: draft ✓ · base main ✓ · first body line Fixes #20084 ✓ · Clause-②: no at line start ✓ · labels documentation · size/xs · skip-changeset (every path under .claude/**, nothing published — correct) ✓ · assignee os-tesla = the card's ✓ · 3 files, +3 / −3, all inside the claimed regions (SKILL.md :59 · execution-duties.md :21 · filing-gate.md :27–:28), no sibling region touched ✓ · report comment 5827160201 first line os-dev-report ✓ · mcp_calls 0, api_writes inside the four-item budget ✓ · no closing keyword near another card ✓ · no model identifier ✓. Check runs at cb2d8c4: every completed job success or an expected skip; Lint & Repo Gates and the two Type Check jobs still in_progress at this read (honest reading; the landing read is separate).

    Spot-check readings (seat's own, on origin/main aa04ea2):

    • SKILL.md :59 — the rewritten batch row (191 B, widest-row pin 342 B untouched) defines the cap over every subagent per Agent call and per create_session, read-only not exempt; the priority:p0 row stays intact. ✓ matches the card's ①.
    • filing-gate.md — the new line beside the groups-of-ten line (119 B) is the card's ② verbatim in substance. The payment line (write pace ≥3 s / ≤40 per hour) has a home every seat reads first: SKILL.md :94 「节奏 ≥3 秒/笔、每账号每小时 ≤40 笔,429 即停写」 plus the mechanical write-pace.mjs; git grep on origin/main finds no reader pinned to that filing-gate line. ✓ real deletion, not a re-wrap.
    • execution-duties.md :21 — ✗ the tail 「⛔ 不按包、不按 check 名」 was cut, and it has no other home: git grep -n '不按包' origin/main -- .claude AGENTS.md and the same for 不按 check 名 each hit exactly this one line. The lane's standing rule (references/lanes/skills.md 常设承诺): 被砍内容若在别处无家,砍掉就是丢规则. The positive criterion does not carry it — the ⛔ half names the two wrong readings the rule was written against.

    REWORK, one line, no other change: rewrite execution-duties.md :21 as
    - \batch` 封顶全部子代理,等待不填槽;同批独立按文件面不相交判,⛔ 不按包、不按 check 名。(117 bytes — under the 120-byte cap; the enumeration dev/复核/普查/只读 lives in theSKILL.md batchrow every seat reads first, so 「全部子代理」 is enough here and the ⛔ tail survives). Then re-run at leastcheck:pm-skill-ratchet·check:pm-skill-id-lint·check:nul-bytes·check:skill-frame-syncon the new head, push, and post a secondos-dev-report` comment quoting the new head. ⛔ Do not edit the PR body (the seat corrects the one stale sentence in item 2 after the patch lands); ⛔ no second claim.

    Everything else in this PR is accepted as it stands; the ACCEPT follows the patch head.


    Generated by Claude Code

  5. objectstack-fleet commented on Sep 25, 2026

    @objectstack-fleet
    ContributorAuthor

    os-dev-report

    {
      "issue": 20084,
      "status": "done",
      "branch": "claude/issue-20084-subagent-concurrency-cap",
      "pr": "https://github.com/objectstack-ai/objectstack/pull/20108",
      "session": "session_0148fenvVvyQV9HYxgVDQ33q",
      "premise_still_valid": true,
      "summary": "Patch round on the seat REWORK verdict (comment 5827189624), same claim, one line: execution-duties.md L21 rewritten in place as \"- `batch` 封顶全部子代理,等待不填槽;同批独立按文件面不相交判,⛔ 不按包、不按 check 名。\" — the ⛔ tail restored verbatim (git grep on origin/main aa04ea2 finds no other home for 不按包 or 不按 check 名), the dev/reviewer/census enumeration left to the SKILL.md batch row every seat reads first. No other file touched: SKILL.md and filing-gate.md unchanged since cb2d8c4; PR body not edited; no second claim; the newest Claim: on the card is still 5826928793 naming this branch.",
      "tests": "Head c66d03d (git rev-parse --short HEAD; remote head identical). L21 final width 120 bytes (printf | wc -c). Cap read from scripts/pm/check-skill-line-ratchet.mjs, not memory: MAX_LINE_BYTES = 120 and the verdict is bytes(line) <= MAX_LINE_BYTES, so the cap is inclusive and a 120-byte line passes (the verdict comment said 117: a miscount; the 114-byte fallback was not needed). Gates at c66d03d, foreground, each exit captured before any pipe: check:pm-skill-ratchet 0 (quoted: execution-duties.md is 183 lines (ceiling 183; headroom 0)), check:pm-skill-id-lint 0, check:nul-bytes 0, check:skill-frame-sync 0, check:pm-governed-prose 0; the rest of the derived set re-run on the same head: check-closing-keyword-parity 0, its --self-test 0, check-comment-mask-corpus 0, check-governed-queue-guard --self-test 0, check-harness-current --self-test 0, check:agent-test-spelling 0, check:cross-package-test-inputs 0, check:doc-authoring 0, check:driver-memory-census 0, check:gitlink-declared 0, check:pm-expected-skips 0, check:pm-governed-merges 0, check:refd-timer-probe 0, check:watch-hint-literal 0, check:skill-frame-freshness 0. NOT MEASURED at c66d03d: @objectstack/lint check:doc-formula-expressions, reason: the recreated worktree carried no built dist for the lint closure; it exited 0 at cb2d8c4 and this patch changes one .md line under .claude/skills that the gate does not scan.",
      "line_counts": "execution-duties.md 183 → 183 (ceiling 183); L21 118 B at cb2d8c4 → 120 B at c66d03d (cap 120, inclusive). SKILL.md 319 and filing-gate.md 58 unchanged from the first round.",
      "files_changed": [
        ".claude/skills/pm-dispatch/references/execution-duties.md (L21, in place)"
      ],
      "mcp_calls": "0 — this round's reads: 2 REST GETs (verdict comment 5827189624; the card comments to re-verify the newest Claim:) plus the relay's own run polling",
      "api_writes": "1 REST write this round: os-dev-report POST /repos/objectstack-ai/objectstack/issues/20084/comments (this comment, via the relay); plus 1 git push (cb2d8c4..c66d03d), not REST. PR body not edited, no label write, no claim. Cumulative over both rounds: 5 REST write endpoints in 4 tool calls, 3 git pushes.",
      "deviations": [
        "The worktree had been removed after the first report; recreated from the local branch at cb2d8c4, verified equal to the remote head, never from origin/main; removed again after the push.",
        "check:doc-formula-expressions not re-run at c66d03d (reason in tests)."
      ],
      "open_questions": [],
      "out_of_scope_findings": []
    }

    Generated by Claude Code

  6. objectstack-fleet commented on Sep 25, 2026

    @objectstack-fleet
    ContributorAuthor

    Review — ACCEPT · PR #20108 head c66d03db

    Reviewed by the seat (session_0148fenvVvyQV9HYxgVDQ33q, os-tesla) against GitHub and the fetched head, 2026-09-25T05:23Z. The patch round on REWORK 5827189624 is closed.

    The one REWORK item, read off the head (git fetch of the branch into a seat-owned ref, sed -n 21p): execution-duties.md :21 = - \batch` 封顶全部子代理,等待不填槽;同批独立按文件面不相交判,⛔ 不按包、不按 check 名。 — the ⛔ tail is back verbatim; 120 bytes, and the gate's cap is inclusive (MAX_LINE_BYTES = 120, verdict bytes(line) at-most MAX_LINE_BYTESincheck-skill-line-ratchet.mjs). The seat's 「117 bytes」 in the REWORK comment was a miscount — corrected here in the open. Patch delta cb2d8c4..c66d03d= that one file, +1 / −1; the merge-base diff vsorigin/main` is still 3 files, +3 / −3, all inside the claimed regions.

    Checklist (unchanged from the first round, re-verified on the PR object at c66d03db): draft ✓ · base main ✓ · Fixes #20084 first line ✓ · Clause-②: no at line start ✓ · skip-changeset correct (nothing published) ✓ · assignee os-tesla ✓ · second report 5827248075 (first line os-dev-report) ✓ · mcp_calls 0, writes inside budget ✓ · no second claim (newest Claim: still 5826928793) ✓. NOT MEASURED at the patch head: check:doc-formula-expressions (the gate does not scan .claude/**; exit 0 at cb2d8c4; CI's Lint & Repo Gates runs it) — accepted. Deviations recorded by the dev (worktree recreated from the branch head, never from origin/main) — fine.

    Landing: check-governed-merges.mjs --pr 20108 → GOVERNED, Tier S (.claude/** ×3), 6 changed lines ≤ 5000 ⇒ the seat's ## Contract review PASS record for c66d03db follows on the PR; the seat lands through the relay (pr_ready + automerge_enable) once every check on c66d03db is green — the TypeScript Type Check failure on the superseded cb2d8c4 was the new push cancelling that run's workspace lane (aggregator read cancelled), zero action per the checklist. Acceptance notes: none. out_of_scope_findings: none. The PR body's item 2 (which still describes the first head's dropped tail) is corrected by the seat in the same window.


    Generated by Claude Code

  7. added 2 commits that reference this issue on Sep 28, 2026
    7b27bd0
    7a13e05
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions