A turn that walked away from a background job now finishes the work instead of
printing "Done" over it; a terminal pane that loses its socket reconnects when you
touch it instead of staying dead until a page reload; and an error_max_turns that
did not come from this chat's budget is named as such rather than sending the user to
the wrong dial. Plus a split tmux window that is composited rather than cropped, a
paste button that stopped pasting twice, corrected toolbar tooltips, an Electron
popup that no longer escapes the window-open policy.
A turn that strands a background task is not a finished turn
- The gap:
subtype:'success'is the one rung the auto-continue ladder does not
cover. A run that started something withrun_in_backgroundand then ended its
turn saying it would wait and continue reports a cleanend_turn. Nothing resumes
a headlessclaude -p— the process exits and takes the background shell with it —
so the chat printed✅ Doneover work that had not happened, and the promised
continuation could never arrive. - Detection is structural, never textual. A
Bashcall carrying
run_in_backgroundis the same JSON on every install; user-facing prose is written
in the UI language, so a regex over English phrases like "I'll check back" is dead
on a French or Ukrainian one. The flag is read off a parsed object, so a foreground
grep '"run_in_background": true'is not mistaken for a launch. - The debt is incremental and counted across the whole turn. An agent that starts a
background job and collects it inside the same turn — exactly what the new
system-prompt rule asks for — is not charged a rescue run. The harvest side matches a
Read/Viewof thetasks/<id>.outputfile the CLI actually writes, not just a
BashOutputcall: measured on 2.1.231,BashOutputis never called. A harvest pays
down only a debt that already exists, once per shell id — so reading a leftover log
from an earlier turn cannot pay for a launch that comes afterwards, and polling one
job twice cannot cancel a second job that really was abandoned. - One harvest run, and an honest ending if it is not enough. When even the rescue
run walks away, the turn says how many tasks were left running, as a real---status
line so the SPA does not stamp its own "Done" badge over the warning. - The system prompt states the constraint up front — collect a background job's
result inside the same turn, because there is no later moment in which to get it.
The rescue is the second line of defence, not the first. - Kanban/scheduled tasks, multi-agent members and bots get that instruction too,
each through the channel that actually reaches it.--system-promptis dropped
whenever there is a session to resume, and is absent entirely for a task with no bot —
so for a multi-agent worker, a bot with a live session, and every Kanban task, the
instruction rides the user turn instead. An unattended task that walks away from a
background job is the worst version of this bug — nobody is reading that chat to
notice. Riding the user turn also covers a Kanban task on thesubscriptionengine
for free: it passes no system prompt at all, but its prompt is typed into the tmux
pane like any other. - Known limit: a process backgrounded with shell syntax (
cmd &,nohup) inside a
foregroundBashcall is not detected — separating that froma && band2>&1
needs a shell parser. The system-prompt rule covers it in words.
An error_max_turns that is not ours says so (#67 follow-up)
- "Raise Max turns" is wrong advice when that is not the cap being hit. Measured
against CLI 2.1.231, a run capped at N reportsnum_turns === N + 1, so a genuine
exhaustion lands AT the cap. A stop at 3 turns against a 50-turn dial is a limit
imposed somewhere else — a different CLI version, asettings.json, a hook on the
machine the agent runs on — and the message now says that instead, on the FIRST
retry notice rather than only after all three are spent. - The remote auto-continue notice names the budget and what was spent. The local
CLI loop has done this since it was written; the SSH one said only "resuming on
remote", which is why diagnosing the report needed a round trip. - The SSH auto-continue path logs. It previously logged nothing at all, on either
the max-turns or the non-success branch.
A terminal pane that loses its socket now reconnects when you touch it
- Typing into a dead pane was a silent drain.
term.onDataguarded on
readyState === 1and did nothing else, so every keystroke vanished with no
reconnect and no sign anything was wrong. xterm renders locally, so the pane looked
alive — that is the "terminal freezes until I reload the browser" report. - Paste and the send line named the problem and did nothing about it. Both toasted
"Terminal is not connected" and returned, on the two controls that exist precisely
because a pane has gone unresponsive. All three paths now revive the socket and
carry the frame through, so the first thing you type is not the thing that is lost. - A terminal socket failure used to leave no trace.
ws.onclosetook no argument
(the close code was discarded) and there was noonerrorat all. Both exist now, so
the next occurrence says whether it was an abnormal close, an oversized frame or a
server error instead of looking identical to every other cause.
Note: this fixes what the UI does about a dropped terminal socket. What drops it in
the first place is not yet identified — the close code added here is what will name it.
A split tmux window is composited, not cropped
- Claude Code's agent-teams splits whatever tmux window it runs in, one pane per
teammate. Measured on a live session: a 155x39 window with the user's ownclaude
squeezed into 46x38 on the left and four teammates stacked 108x9 down the right —
and the viewer showed the 46-column strip and nothing else. The window is now
composited whole.
The ›_ paste button no longer pastes again on every Enter
- Click ›_ beside a saved command or skill, press Enter to submit, and the same text
was pasted a second time — and a third. The button kept focus, so Enter kept
re-triggering it; it only stopped once focus moved elsewhere.
Terminal tooltips, and three of them were wrong
- The mode, agent and model toolbar buttons and the max-turns input gained tooltips,
following the pattern the Room button already used. turns.tipclaimed Claude "stops automatically" at the limit. It does not: it
auto-continues up to three more times before surfacing an incomplete-run notice, so
real usage can reach roughly four times the number shown. Corrected in all five
locales, along with two other inaccurate tips.
A popup window no longer escapes the window-open policy
setWindowOpenHandlerwas applied only to the top-level Electron window, so a
same-origin link opened inside a popup fell back to Electron's allow-anything
default instead of the app's own same-origin/external policy. The policy is now
re-attached to every window it creates.- Kanban: a stale response from a previously opened task could be appended to
whatever modal happened to be open by the time it arrived.
Bot bubbles no longer flicker on reload
- A full browser reload mid bot-turn lost
streaming.agent(in-memory only), so the
next live chunk looked like a genuinely new speaker and opened a second bubble.
Room mode and the mid-turn bot hand-off are documented
- Both shipped as user-facing features with no mention anywhere in the README. Added
in all three translations (EN/RU/UA).