Desktop should dedupe/reap MCP bridge process trees and batch bridge tool updates
Summary
When Codex Desktop renderer freezes, MCP/codex_apps bridge tools can still be alive and mostly functional. However, repeated app-server/runtime setup can leave many bridge/helper process trees around, which increases event/tool-list pressure and makes renderer freezes harder to diagnose.
This issue is about bridge lifecycle and renderer-facing bridge/tool update pressure, not a single bridge plugin failing.
Local evidence
During the investigation, process inspection showed multiple live bridge/helper families, including variants of:
cua_node/bin/node_repl
components/codegraph/dist/serve.js
components/lsp-daemon/dist/cli.js mcp
SkyComputerUseClient mcp
These appeared under multiple app-server/session process trees. The important observation was:
- bridge/helper processes were still running;
- the app-server was still running;
- the renderer/UI was the component that became unusable;
- repeated bridge/runtime process sets increased the amount of status/tool/runtime state the renderer could receive.
I am intentionally not pasting full process command lines because some app-server command lines can include local paths or token-file paths.
Problem
Desktop currently makes it hard to distinguish these states:
- a bridge process is dead;
- a bridge process is alive but disconnected from the current renderer/session;
- a bridge process is duplicated/stale from an older app-server/session tree;
- bridge/tool-list/status updates are alive but creating too much renderer-facing churn.
When the renderer is already under pressure, repeated bridge/tool-list updates can worsen the UI failure even if the tools themselves are not the root cause.
Suggested fix
Add stronger lifecycle ownership and batching for Desktop bridge processes:
- each app-server/session should own a process group for spawned bridge helpers;
- bridge helpers should be reaped when their owning app-server/session disconnects;
- duplicate bridge process trees for the same plugin/workspace should be deduped or intentionally shared through a supervisor;
list_tools/ bridge health / runtime-status updates should be debounced or coalesced before sending to the renderer;- the renderer should receive bounded bridge-state projections, not every low-level lifecycle event;
- expose bridge states explicitly:
starting,ready,stale,disconnected,failed,reaped; - add diagnostics that report bridge process counts by owner/session/plugin without leaking command-line secrets.
Expected behavior
A renderer freeze or reload should not multiply bridge process trees. Restarting or reconnecting Desktop should either reuse healthy bridges or reap stale ones, and renderer-facing bridge/tool status updates should remain bounded.
Acceptance criteria
- Repeated renderer reloads or session reconnects do not leave unowned bridge helper processes.
- Repeated bridge/tool listing does not emit unbounded renderer updates.
- The UI can show whether bridges are healthy independently from renderer health.
- Diagnostic output redacts token paths and sensitive command-line arguments by default.
Related issues
Related but not identical:
- #28502
- #26362
- #24347
- #28479
- #25779
This issue has 1 comment on GitHub. Read the full discussion on GitHub ↗