feat(bin): add pre-dispatch admission gate for ship spawns - #2864
feat(bin): add pre-dispatch admission gate for ship spawns#2864pramendra wants to merge 7 commits into
Conversation
Refuse a ship spawn before any worktree or endpoint exists unless push path, delivery mode, quota headroom, and host concurrency are each independently proven rather than assumed (fleet-engineering-plan workstream 2, closes A + E). Wired into fm-spawn.sh's ship-spawn path; hermetic ship-spawn suites opt out via FM_PREFLIGHT_GATE_BYPASS (tests/lib.sh), mirroring FM_GATE_REFUSE_BYPASS's precedent.
…n bin toolbelt inventory
Confidence Score: 3/5The PR is not yet safe to merge because valid workflow syntax can bypass the direct-PR delivery admission check and launch work whose PR will be rejected. The workflow scanner misses both valid commented or flow-style pull-request triggers and ordinary shell-variable indirection from the PR body, so the gate can admit delivery paths that cannot complete. Files Needing Attention: bin/fm-preflight-gate.sh Reviews (6): Last reviewed commit: "no-mistakes: apply CI fixes" | Re-trigger Greptile |
| /^on:[[:space:]]*pull_request[[:space:]]*$/ { found = 1; next } | ||
| /^on:[[:space:]]*$/ { in_on = 1; next } | ||
| in_on && /^[^[:space:]]/ { in_on = 0 } | ||
| in_on && /^[[:space:]]+pull_request:([[:space:]]|$)/ { found = 1 } |
There was a problem hiding this comment.
Valid pull-request triggers are missed
When a workflow declares on: pull_request # comment, places a comment after on:, or uses a flow mapping such as on: {pull_request: {types: [opened]}}, these patterns do not recognize the valid pull_request trigger. The delivery gate therefore admits a direct-PR spawn whose resulting PR is rejected by the required workflow.
| if (trimmed ~ /^[A-Za-z_][A-Za-z0-9_]*:[[:space:]]*\$\{\{.*pull_request\.body.*\}\}/) { | ||
| name = trimmed; sub(/:.*/, "", name); body_vars[name] = 1 | ||
| } |
There was a problem hiding this comment.
Shell-assigned PR bodies go untracked
When a workflow assigns body="${{ github.event.pull_request.body }}" inside a run script and later compares $body with the no-mistakes marker, this YAML-only assignment pattern never records body as PR-body-derived. The comparison is missed, so the gate admits a direct-PR spawn whose resulting PR cannot satisfy the workflow.
Intent
Build a pre-dispatch admission gate that fm-spawn.sh calls before launching a ship worker, refusing dispatch when any of four independently-proven preconditions fails: (1) push path reachable - the resolved push target (fork remote if configured, else origin) actually accepts a push from the authenticated GitHub identity; (2) delivery path completes end to end - the requested delivery mode (no-mistakes/direct-PR/local-only) is actually valid for this repo, e.g. direct-PR must be refused when a required CI workflow demands a no-mistakes-produced PR body, as on firstmate's own repo; (3) quota headroom measured - quota-axi reports a fresh, non-exhausted measurement for the resolved harness's provider, never assumed; (4) concurrency inside measured capacity - current host load average and available memory are inside a configured safe ceiling. The refusal must name exactly which precondition(s) failed, not a generic error, and a spawn must actually be refused by this gate in testing. Each check must be provably able to fail (mutation-tested), and any deliberately narrowed scope must be stated plainly rather than silently assumed to be complete.
What Changed
bin/fm-preflight-gate.sh, a new admission gate invoked beforefm-spawn.shcreates a worktree or launches a ship worker. It independently proves four preconditions — reachable push path (fork remote if configured, else origin, viagh-axi api .../permissions.push), a delivery mode that can actually complete for the repo (no-mistakes init state, or a structural scan of.github/workflows/*.ymlfor apull_request-triggered workflow requiring a no-mistakes-produced PR body when mode is direct-PR), fresh non-exhausted quota headroom fromquota-axi --jsonfor the resolved harness's provider, and host load average/free memory inside configurable ceilings — and refuses with onerefused [<check>]: <reason>line per failed check (exit 4), or anadmitted: ...line on success (exit 0).bin/fm-spawn.sh's ship-spawn path: it now shells out tofm-preflight-gate.shwith the resolved project dir, mode, and harness, and aborts the spawn (exit 4) on refusal, unlessFM_PREFLIGHT_GATE_BYPASS=1is set.tests/fm-preflight-gate.test.shcovering admission and each of the four refusal paths, exportFM_PREFLIGHT_GATE_BYPASS=1fromtests/lib.shso existing hermeticfm-spawnsuites (which fake tmux/git but notgh-axi/quota-axi/no-mistakes) aren't refused by checks they don't exercise, document the gate indocs/architecture.mdanddocs/scripts.md, and add a.serena/project config/gitignore.Risk Assessment
✅ Low: The change is additive and self-contained (a new bin/fm-preflight-gate.sh plus a 9-line call site in fm-spawn.sh gated behind a test-only bypass); every failure mode in the four checks fails closed (refuses rather than silently admitting), all four required preconditions from the intent are implemented and named on refusal, the scope narrowing (github.com-only push check, structural grep for the no-mistakes PR-body marker, quota-axi-mapped harnesses only, host-wide rather than per-task concurrency) is disclosed plainly in the script's own header exactly as the intent requires, and the new test suite exercises real refuse/pass behavior per check plus two live fm-spawn.sh integration tests rather than asserting on source text.
Testing
All four admission preconditions (push-path, delivery-path, quota-headroom, concurrency) are covered by refuse-case and pass-case tests plus a combined-failure naming test and two live fm-spawn.sh integration tests that demonstrate real refusal (exit 4, worktree/metadata/launch never created) and real admission (normal launch path unchanged); the full new suite (17/17) and four pre-existing fm-spawn ship-path suites all pass with no regressions, and a manual mutation of the push-path check confirmed the suite actually detects a broken precondition, satisfying the "provably able to fail" requirement.
Evidence: fm-preflight-gate.test.sh full run (17/17 passing)
Evidence: Mutation check: disabling push-path is caught by the suite
Pipeline
Updates from git push no-mistakes
✅ **intent** - passed
✅ No issues found.
✅ **Rebase** - passed
✅ No issues found.
✅ **Review** - passed
✅ No issues found.
✅ **Test** - passed
✅ No issues found.
bash tests/fm-preflight-gate.test.sh (17/17 passing)bash tests/fm-spawn-batch.test.shbash tests/fm-spawn-dispatch-profile.test.shbash tests/fm-spawn-pool-base-freshen.test.shbash tests/fm-spawn-worktree-settle.test.shManual mutation test: neutered fm_preflight_check_push_path to always return 0, reran the suite, confirmed the push-path refusal test failed as expected, then restored the original file and verifiedgit status --shortshows no diff✅ **Document** - passed
✅ No issues found.
✅ **Lint** - passed
✅ No issues found.
✅ **Push** - passed
✅ No issues found.