feat: rescue exhausted direct-account crews - #27
Conversation
366a2ec to
6f36458
Compare
Validation evidence (current head
|
…to fm/fm-account-rescue-a2 # Conflicts: # AGENTS.md # bin/backends/herdr.sh # bin/fm-account-routing-lib.sh # bin/fm-checkout-lock-lib.sh # bin/fm-teardown.sh # bin/fm-watch.sh # docs/account-capacity-rescue.md # docs/architecture.md # docs/configuration.md # tests/fm-account-routing.test.sh # tests/fm-backend-herdr.test.sh # tests/fm-secondmate-liveness.test.sh # tests/fm-watch-triage.test.sh
Intent
Build automatic account-exhaustion rescue for direct-account ship/scout crews so unattended fleets recover from verified Codex model-capacity and Claude session-limit TUI states even when panes remain alive. Detect only empirically captured per-harness chrome and avoid ordinary limit prose. Serialize a naive fresh-agent handoff through the existing fm-spawn.sh --recover-direct-account path in the same task brief and worktree, force selection of a different account that still has capacity through fm-account-directory.sh, and do not invent session migration. Record every attempt and exhausted account in task metadata, bound attempts per task, make interrupted attempts auditable, and stop with a single blocked report rather than retrying when no eligible capacity remains or rescue cannot be proved. Keep this direct-account behavior scoped to ship/scout crews; do not extend legacy Agent Fleet routing or auto-rescue secondmates. Acceptance requires real captured signatures for both Codex and Claude, negative prose tests, proof that rescue changes accounts, clean no-capacity stop behavior, bounded audited attempts, and fm-lint.sh -x cleanliness for changed files.
What Changed
Risk Assessment
✅ Low: The credential-state fix is narrowly scoped, preserves the approved deterministic Claude rotation, emits one durable blocked report without consuming rescue accounting, and introduces no substantiated source defect.
Testing
Completed 1 recorded test check.
Pipeline
Updates from git push no-mistakes
✅ **intent** - passed
✅ No issues found.
✅ **Rebase** - passed
✅ No issues found.
🔧 **Review** - 1 issue found → auto-fixed ✅
bin/fm-account-directory.sh:347- Intent requires selecting “a different account that still has capacity through fm-account-directory.sh,” but the Claude path explicitly skips capacity verification and selects the first non-excluded directory:selected=$(first_account_home claude "$@"), while logging that usage is unreadable. This can launch another already-exhausted Claude account and cannot substantiate the required capacity guarantee. Either provide a verifiable Claude capacity signal or obtain explicit approval to weaken this requirement to deterministic unused-account rotation.🔧 Fix: Distinguish Claude credential failures from capacity rescue
✅ Re-checked - no issues remain.
command -v tmux >/dev/null || { echo "tmux is required for e2e tests" >&2; exit 1; }; tmux -V; rc=0; for t in tests/*.test.sh; do echo "== $t =="; bash "$t" || rc=1; done; uv run --directory tools/agent-fleet --locked pytest || rc=1; uv run --directory tools/agent-fleet --locked python -m compileall -q src || rc=1; exit "$rc"bin/fm-lint.sh:70-bin/fm-lint.sh -xforwards-xto ShellCheck without files and fails. Fixing this acceptance-command mismatch requires an executable change, which this documentation-only task forbids.✅ **Push** - passed
✅ No issues found.