Repository navigation
fix(acp): prevent process startup after disposal - #6186
Sun-GLiang wants to merge 5 commits into
Conversation
Generated-by: OpenAI Codex
Generated-by: OpenAI Codex
Opt ACP disposal into retryable Effects and keep failed resource owners reachable through parent shutdown. Retry only unfinished cleanup while preserving default Effect semantics and disposed Context fencing. Generated-by: OpenAI Codex
Retain failed cleanup attempts through Platform, domain modules, and execution composition. Retry once before Kernel releases root ownership, preserve persistent failures, and skip resources already closed successfully. Generated-by: OpenAI Codex
Retain only the pre-spawn disposal check and real stdio regressions for conversation and executor disposal. Restore retry-related changes to the PR base. Generated-by: OpenAI Codex
Astro-Han
left a comment
There was a problem hiding this comment.
Automated review notice: This comment was posted by an automated review agent. It is not an independent human review and does not replace one.
I reviewed both changed files at 796182866727b040561f1d31018442fe0ca5ff84 (+37/-0). I found no confirmed P0–P2 issue.
packages/acp-executor-plugin/src/index.ts:627 now checks executor shutdown and conversation loss after the asynchronous state/executable checks and immediately before creating the stdio connection. disposeConversation marks the retained session lost, and executor disposal sets the executor flag first, so either closure fences a startup that resumes later. There is no asynchronous gap between the new check and connection creation.
All 97 ACP executor-plugin tests passed, including the two real-process startup/disposal regressions. As a countercheck, I left the tests unchanged and removed only the new guard from the loaded implementation: both regressions failed because the request completed after disposal instead of returning acp_unavailable. Their cleanup terminated the fixture processes. Normal startup and the existing disposal/restore cases also passed in the unchanged suite.
Fresh dependency installation/patches, the normal clean root test build, plugin type checking, Biome on both changed files and git diff --check passed. There is no protocol change. A static merge with current main 9826db1b9dad32897be105b2c1c621becedb27ce is clean, and the protocol guard passes on that merge result at epoch 226; the branch itself remains at 225. I did not build the merged tree separately.
The exact-head CI test and label checks succeeded. These checks use controlled stdio agents on Linux; I did not exercise a real authenticated agent, Windows/macOS, or the full Desktop application.
Summary
Disposing an ACP conversation or executor while initialization is awaiting state or filesystem checks can return before the Agent process starts. Initialization then continues, allowing a process and prompt to run after disposal. Check executor and session disposal immediately before creating the connection, and return
acp_unavailableinstead.This is a defensive fix for direct executor lifecycle calls. Production
PluginExecutorServicealready cancels and drains active operations before retirement. The change is limited to this startup guard and two real stdio regressions.Verification
AI use
Select exactly one:
Tool(s) and scope: OpenAI Codex implemented the startup guard and real-process regressions, performed baseline and ablation checks, ran validation, and prepared this PR. AI-authored commits include
Generated-by: OpenAI Codextrailers.Checklist
Does this PR entail a change in behavior?