You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Session close and server shutdown leave session-scoped resources alive #1246
Several session-scoped resources are only released by explicit per-resource close paths or full process disposal. When a session is archived or the daemon/server shuts down, live sessions and related server-side state can remain active longer than intended.
Observed cleanup gaps:
server shutdown disposes the DI graph without first closing live agent sessions
terminal records and pty processes are not cleaned up when a session closes
filesystem watcher entries are not disposed when a session closes
WebSocket broadcast per-session buffers, journal state, and in-flight turn tracking are not removed when a session closes
tool-call start timestamps can remain after interrupted/aborted turns
Expected behavior
Session archive and server shutdown should use the normal session/resource cleanup paths so session-owned processes, watchers, buffers, journals, and turn bookkeeping are released promptly.
Proposed fix
add a bulk live-session close path and call it during server shutdown before DI disposal
subscribe session-scoped services to session close events
drop per-session terminal, fs watcher, and WebSocket broadcast state on close
clear tool-call timing state on turn boundaries/abort paths
Scope
This issue is limited to session lifecycle cleanup. Longer-term retention policies for completed background tasks/subagents and unrelated timeout hardening can be handled in separate follow-ups.
Create a session and subscribe to its WebSocket events.
Submit a prompt and confirm that turn/prompt events arrive normally.
Call POST /api/v1/sessions/{id}:archive, then POST /api/v1/sessions/{id}:restore.
Re-subscribe to the session. A fresh WebSocket connection gives the same result.
Submit another prompt.
The prompt is accepted and completes: GET /api/v1/sessions/{id}/status returns busy=false. However, no turn.started, assistant.delta, thinking.delta, turn.ended, or prompt.completed events arrive. Only session.meta.updated is observed. A newly created session works normally.
Expected: restoring a session also restores its event stream. Actual: the restored session executes prompts without emitting their events.
Activity
zhiyuan1i commentedon Oct 19, 2026
A related minimal reproduction on 2.2.0:
The prompt is accepted and completes: GET /api/v1/sessions/{id}/status returns busy=false. However, no turn.started, assistant.delta, thinking.delta, turn.ended, or prompt.completed events arrive. Only session.meta.updated is observed. A newly created session works normally.
Expected: restoring a session also restores its event stream. Actual: the restored session executes prompts without emitting their events.