feat(booterm): structured pty_exited WS notifications. Plan-validated, impl-validated, code-reviewed green (contracts build clean, contracts test 29/29, booterm + web typecheck clean). wip: in-progress inference/provider refactor (agents.ts, provider.ts, new llama-providers.ts, removed llama-args-validator), plus arena, dispatcher, compaction, schema changes. openspec: pty-exit-notifications complete; x-agent-flags planned (not yet implemented).
2.1 KiB
Why
When a process running in a booterm terminal pane exits, the browser currently receives a bare {type: 'exit', code: N} frame and the socket closes (apps/booterm/src/ws/attach.ts:170-183). There is no structured metadata: no last output lines, no session title, no parent agent attribution. The inference loop in apps/server and apps/coder cannot react when a long-running task completes because the notification carries no context beyond the exit code.
The reference implementation (/opt/forks/opencode-extras/opencode-pty) solves this with <pty_exited> structured notifications carrying exit code, last output lines, session metadata, and timeout status. Booterm already tracks all of this data (registry SessionMeta with sessionId, paneId, title, description, parentAgent; ring buffer with output lines via appendOutput). The data is present but never surfaced on exit.
What Changes
- Enhance the booterm WS exit notification from a bare
{type: 'exit', code}to a structuredpty_exitedframe carrying: exit code, last N output lines from the ring buffer, session metadata (title, description, parentAgent), and timeout status. - Add
pty_exitedas a new frame type in the cross-app WsFrame contract (packages/contracts). - Update the web frontend to parse and handle the new frame type.
Scope
- In scope: structured exit notification over booterm WS; new WsFrame type in contracts; web frontend handling.
- Out of scope: log-search extras (already implemented in booterm registry ring buffer + search route), per-session timeouts (already implemented in registry + sweepExpired), pattern-based PTY log search (already in
searchRingBuffer). These exist; this change only adds the exit notification. Broker publish for inference-loop consumption is deferred (see Deferred section).
Non-goals
- Changing the booterm WS binary/text frame protocol for ongoing data.
- Adding persistence for exit events (no DB table; frames are ephemeral like all broker frames).
- Modifying the coder's PTY dispatch flow (which uses
child_process.spawn, not booterm PTYs).