[Bug] Closing an Alt+O pop-out terminal removes an inline swarm worker and aborts its task
Nobody has claimed this yet.
- Dominant language
- Rust
- Stars
- 19.9k
- Forks
- 2.3k
- Avg merge
- 2d 7h
- Merged PRs (30d)
- 30
Description
Summary
With agents.swarm_spawn_mode = "inline", pressing Alt+O on a running swarm worker opens that worker in a separate terminal. Closing the pop-out terminal removes the worker from the swarm and aborts its running task.
Based on the current UI contract and source comments, this appears to be a bug rather than intentional behavior. The UI calls the action open / pop out; it does not indicate that the new terminal takes ownership of the worker lifecycle or that closing it is destructive.
If this behavior is intentional, the missing destructive warning is still a UX bug. For an inline worker that was already server-managed before the pop-out, keeping the worker alive after the viewer disconnects seems more consistent with both inline and pop out semantics.
Environment
- Jcode:
v0.80.1 (59aaacc) - OS: Windows 11
- Configuration:
[agents]
swarm_spawn_mode = "inline"
swarm_strip_layout = "vertical"
The relevant Alt+O and disconnect-cleanup paths are still present on the current upstream master.
Steps to reproduce
- Start a Jcode session.
- Spawn an inline swarm worker with a task that runs long enough to inspect.
- Press
Alt+Nto focus the swarm panel. - Select the running worker with
Alt+Up/Alt+Down. - Press
Alt+Oto open the worker in a new terminal. - Close that terminal before the worker completes.
- Return to the coordinator and inspect the swarm panel/task state.
Actual behavior
- The worker disappears from the swarm panel.
- The worker is removed from swarm membership.
- Its running task is aborted.
- The coordinator can no longer await its normal completion/report.
Expected behavior
Closing an Alt+O viewer for an inline worker should:
- disconnect only that terminal client;
- keep the inline worker running on the server;
- retain its swarm membership and plan participation;
- not abort the active task;
- allow it to report completion to the coordinator normally.
Source analysis
Alt+O calls spawn_resume_in_new_terminal from:
crates/jcode-tui/src/tui/app/tui_state.rs
pop_out_selected_swarm_agent()
The inline worker was originally created as an in-process/headless worker in:
crates/jcode-app-core/src/server/comm_session.rs
spawn_swarm_agent()
The pop-out reuses the ordinary --resume <session_id> path without identifying the connection as a temporary attachment, observer, or detachable viewer.
When the pop-out terminal exits, the shared disconnect path runs:
crates/jcode-app-core/src/server/client_disconnect_cleanup.rs
cleanup_client_connection()
With no successor client attached, it performs destructive cleanup, including the equivalents of:
remove_session_entry(...)
members.remove(client_session_id)
remove_session_from_swarm(...)
processing_task.take().abort()
This makes a viewer connection the effective lifecycle owner of a worker that was previously server-managed.
Platform scope
The issue has been observed on Windows.
The session attach and disconnect cleanup paths are shared cross-platform and do not contain a Windows-specific branch for this behavior. macOS and Linux therefore appear likely to behave the same way once the spawned jcode --resume client actually exits, but that is source-based inference and has not been reproduced there yet.
Suggested direction
Give Alt+O pop-outs for inline workers an explicit non-owning connection mode, such as observer or detachable.
On disconnect, that mode should unregister only the client connection/event sender and should not:
- remove the worker from
sessions; - remove the swarm member;
- call
remove_session_from_swarm(); - abort the worker's active task.
Visible workers whose terminal intentionally owns their lifecycle can retain the current behavior.
Workaround
Keep the Alt+O terminal open (or minimized) until the worker finishes. The Alt+N panel is not a full replacement because it mainly shows status/Todos and only a transient tail of in-progress assistant text, not the complete worker transcript or tool output.
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start with pop_out_selected_swarm_agent() in crates/jcode-tui/src/tui/app/tui_state.rs, then trace spawn_swarm_agent() in crates/jcode-app-core/src/server/comm_session.rs and cleanup_client_connection() in crates/jcode-app-core/src/server/client_disconnect_cleanup.rs. Reproduce the Alt+O workflow and inspect disconnect handling; done means closing the viewer leaves the inline worker, swarm membership, and active task intact until normal completion.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- rust
- Domain
- backend, cli
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Active
- Clarity
- Clearly specified
- Newbie friendliness
- 65/100