Skip to content

fix(runtime): converge terminal execution failures across hierarchy - #366

Open
boadij wants to merge 9 commits into
mainfrom
fix/hierarchy-execution-recovery
Open

boadij wants to merge 9 commits into
mainfrom
fix/hierarchy-execution-recovery

Conversation

@boadij

@boadij boadij commented Oct 11, 2026 •

Copy link
Copy Markdown
Owner

Summary

Context: #302

  • Use Pi's correlated execution outcomes to distinguish successful managed-Agent results and Lead handoffs from aborted or terminally failed runs. Partial assistant text does not imply success.
  • Preserve assignments, owned child work, and nonterminal project status when a Lead execution fails. Assigned Lead failures use project messages; an unassigned ordinary Lead can report through the currently verified Chief path.
  • Persist stable report intents and retry them without marking required reports sent when publication fails. Serialize herd finalization to avoid concurrent duplicate transitions.
  • Keep project-assignment refresh replacement semantics, bound partial-output details, and make actionable failure backlog wake a replacement Manager only once.
  • Add a disposable custom-provider smoke scenario that exercises real Pi retry exhaustion and settlement for an exactly assigned Lead, plus current smoke documentation.

External Review #1 corrections

  • Existing project_assignment IDs may be refreshed while pending; immutable-payload conflict checks remain for other Chief message kinds.
  • An unassigned Lead without a Git worktree scope can route failure to its verified Chief. Scope-verification errors still fail closed.
  • Failure details are bounded; required publication returning false leaves the durable intent pending and the herd unfinished.
  • Concurrent finalization shares one in-flight operation. Recovery preserves report identity/linkage and does not duplicate already sent reports.
  • Added regressions for assignment refresh and delivery, non-Git Chief routing, bounded failure details, Manager failure-backlog wake/receipt behavior, publication recovery, and concurrent finalization.

External Review #2 corrections

  • Successful unassigned Lead herds finish without creating an unnecessary project-message intent; assigned Lead completion still requires handoff publication.
  • Restoration does not finish a herd while a newer report intent is unsent, even when an earlier failure report was acknowledged.
  • Assigned successful completion without final assistant text sends a factual nonterminal handoff noting that no verified integration summary was available.
  • Cancellation-report publication errors are caught and durably diagnosed; pending intent remains recoverable and Agent-result settlement still runs.

Controlled terminal-failure smoke

npm run smoke -- terminal-failure passed with reportCount: 1 and cleanup passing. It used an isolated custom provider to emit partial assistant text followed by a retryable error, exhausted Pi's bounded native retries, and observed final error settlement and one actionable project failure report. The exact Lead session, assignment, and worktree remained intact; there was no success handoff, extra Lead writer, or automatic tool replay.

Validation

  • npm test -- extension/controller-lifecycle.test.ts — PASS (81 tests).
  • Live smoke — PASS with cleanup passing for terminal-failure, continuation, manager-recovery, and chief-tree.
  • npm run format — run once as the final pre-commit mutation; formatter changed only the two intended files.
  • npm run format:check — PASS.
  • git diff --check — PASS.
  • npm run validate — PASS (970 passed, 1 skipped, 0 failed); build succeeded and package audit passed (70 files).

Limitations

This update does not claim full completion of #302, so it intentionally does not add Closes #302. The controlled live injection covers an assigned Lead failure; the full issue's hierarchy-wide role/outcome and supervisor-absence/replacement acceptance matrix is broader than this PR's demonstrated live scenario.

When no Chief can be verified, failure evidence remains in the originating Pi session; there is no durable future-Chief inbox. Stable report identity and replay-safe writes do not provide transactional exactly-once delivery across independent stores. No automatic model retry, tool replay, process restart, or worktree recreation is introduced.

External Review #3 corrections

  • Route herd finalization through the existing currentProjectAssignment() authority. A managed Lead whose worktree scope cannot be verified now fails closed with a durable diagnostic, does not record finished, and retains its pending handoff; genuinely unassigned Leads still finish normally.
  • Make Agent-result settlement run even when Lead handoff publication throws. Assigned direct success handoffs now record stable report_pending intents, publish using the existing project-message transport, and can replay without another Lead model execution. Publication errors are durably diagnosed; unassigned direct responses create no project intent.
  • Serialize finishIfIdle() restoration and completion so concurrent idle recovery cannot replay the same report or write duplicate completion transitions.

External Review #3 validation

  • npm test -- extension/controller-lifecycle.test.ts — PASS (86 tests).
  • Live smoke — PASS with cleanup confirmed for terminal-failure, manager-recovery, and continuation.
  • npm run format completed; npm run format:check and git diff --check — PASS.
  • npm run validate — PASS (975 passed, 1 skipped, 0 failed); build succeeded and package audit passed (70 files).

This revision still does not claim the full hierarchy-wide acceptance criteria for #302 and intentionally does not add Closes #302.

External Review #4 corrections

  • Persist the original successful report intent for managed direct Lead handoffs and herd completion before attempting the fallible current-assignment lookup. Publication remains gated on verifying the current exact assignment authority.
  • Keep genuinely unassigned Leads from acquiring project-message intents. Require currentProjectAssignment() on the Lead runtime host and remove the weaker worktree-scope fallback callbacks.
  • Add restart regressions covering direct handoff and herd completion: after initial authority verification fails, restore assignment visibility and replay the exact original summary once without replacing it with an unknown-outcome report.
  • Remove the manually incremented modelExecutions counters; they did not instrument or verify model execution during restore.

External Review #4 validation

  • npm test -- extension/controller-lifecycle.test.ts — PASS (88 passed, 0 failed).
  • Live smoke — PASS with cleanup passing for terminal-failure and manager-recovery.
  • npm run format:check — PASS.
  • git diff --check — PASS.
  • npm run validate — PASS (977 passed, 1 skipped, 0 failed); package audit passed (70 files).

This revision still does not claim the full hierarchy-wide acceptance criteria for #302 and intentionally does not add Closes #302.

External Review #5 correction

  • Persist the intended project or chief destination with each durable Lead report before authority lookup, and preserve that destination during replay.
  • A project-target report is published only after the existing currentProjectAssignment() path verifies the current assignment; the existing project-message publication authority is retained. If /takeover released the assignment, the old Manager-directed report remains pending and is not rerouted to Chief.
  • A newly occurring failure from an unassigned Lead still uses the existing Chief failure path and its current authority checks. Legacy pending reports without a persisted destination fail closed rather than inferring a new recipient.
  • Add regression coverage for takeover, targetless legacy reports, and a new post-takeover unassigned failure. Clean up the prior test assertion so it checks the durable report state directly rather than a disconnected in-memory message array.

External Review #5 validation

  • npm test -- extension/controller-lifecycle.test.ts — PASS (89 passed, 0 failed).
  • npm run format:check — PASS.
  • git diff --check — PASS.
  • npm run validate — PASS (978 passed, 1 skipped, 0 failed); build succeeded and package audit passed (70 files).
  • No live smoke rerun was required for this destination-persistence correction.

This revision still does not claim the full hierarchy-wide acceptance criteria for #302 and intentionally does not add Closes #302.

External Review #6 correction

  • Make the persisted report destination the first replay-routing decision. Project-directed reports require Lead role and the current exact assignment; they cannot fall back to Chief or Manager delivery.
  • Chief-directed reports require Chief-path role and unassigned Lead authority. Publication is bound to the verified Chief session and lease, preventing supervisor or assignment changes from redirecting the report.
  • Targetless legacy reports fail closed across roles. Regression coverage verifies no unauthorized publication or sent receipt, and that the original stable report ID and payload remain usable when authorized destination authority is restored.

External Review #6 validation

  • npm test -- extension/controller-lifecycle.test.ts — PASS (89 passed, 0 failed).
  • npm run format:check — PASS.
  • git diff --check — PASS.
  • npm run validate — PASS (978 passed, 1 skipped, 0 failed); build succeeded and package audit passed (70 files).
  • No live smoke rerun was required for this routing-only change.

This revision still does not claim the full hierarchy-wide acceptance criteria for #302 and intentionally does not add Closes #302.

External Review #7 corrections

  • Capture managed Lead state once and keep a successful managed herd unfinished when its required current project assignment is unavailable. The durable project report intent remains pending; after the exact assignment is restored, retry publishes the original report ID and message once, then writes one finished marker. Persisted report targets continue to govern replay.
  • Restore the blocked-publication concurrent idle-recovery regression alongside the Chief-routing regression. It verifies one publication, one durable report_sent, and one finished marker under competing recovery calls.

External Review #7 validation

  • npm test -- extension/controller-lifecycle.test.ts — PASS (91 passed, 0 failed, 0 skipped).
  • npm run format:check — PASS.
  • git diff --check — PASS.
  • npm run validate — PASS (980 passed, 1 skipped, 0 failed); build completed and package audit passed (70 files).
  • No live smoke rerun was required for this lifecycle correction.

This revision still does not claim the full hierarchy-wide acceptance criteria for #302 and intentionally does not add Closes #302.

boadij and others added 9 commits October 11, 2026 11:24
Use Pi execution outcomes instead of assistant text to classify managed Agent results and Lead handoffs. Preserve pending work and route interruption reports through existing Manager and Chief authority paths with stable report identities and replay-safe publication.

Document current recovery behavior and cover terminal errors, retry outcomes, Lead failures, and report replay.
Preserve project-assignment refreshes, route unassigned Lead failures through the verified Chief path, bound failure details, and serialize retryable herd finalization. Recover pending reports without falsely marking required publication complete.

Add regression coverage for report recovery, Manager backlog wake, assignment refresh, and concurrent finalization. Add an isolated real-Pi terminal-failure smoke scenario and document its acceptance evidence.
Allow successful unassigned Lead herds to finish without a project recipient, while preserving required assigned handoffs and reporting factual completion when no integration summary is available. Keep restoration pending when a newer report is unsent, and guard cancellation-report failures so Agent results still reconcile.
Use the existing project-assignment authority for herd finalization so managed Leads cannot finish when worktree scope is unverifiable. Persist assigned direct handoffs for replay, keep Agent-result settlement running when publication fails, and serialize idle replay with completion.
Persist successful report intents for managed Lead direct handoffs and herd completion before fallible assignment verification, while continuing to require the current assignment for publication. Keep unassigned Leads free of project-message intents and require currentProjectAssignment in the runtime host instead of the weaker scope lookup fallback.

Add restart regressions for preserving and replaying the original direct and herd summaries once. Remove manually incremented model-execution counters that did not test execution behavior.
Persist each durable Lead report destination before fallible authority lookup and honor it during replay. Project-directed reports still require the current assignment to be verified; a released assignment cannot redirect an old report to Chief. New unassigned failures retain the authorized Chief route, while legacy reports without a destination fail closed.\n\nAdd takeover and targetless-legacy regressions, and clean up the test assertion to verify the durable report state directly.
Route replay from the saved project or Chief destination, and require current role and assignment authority without substituting another recipient. Bind Chief publication to the verified session and lease; fail closed for targetless legacy reports across roles.

Add lifecycle regressions for assignment and role changes, preserving the original report ID and payload until its authorized destination is restored.
Keep a successful managed herd unfinished while its required project assignment is unavailable, preserving the durable report intent for an authorized retry. Restore the blocked-publication idle-recovery regression alongside the Chief-routing test.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant