diff --git a/.release-please-manifest.json b/.release-please-manifest.json index f1c1e588..bcd05228 100644 --- a/.release-please-manifest.json +++ b/.release-please-manifest.json @@ -1,3 +1,3 @@ { - ".": "0.5.0" + ".": "0.6.0" } diff --git a/CHANGELOG.md b/CHANGELOG.md index f567b599..a6b226c6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,73 @@ ## [Unreleased] +## [0.6.0] - 2026-11-09 + +### Added + +- `record diff ` replays two sessions offline and reports an LCS line diff between their canonical visible screens, with `--at-seq-a`/`--at-seq-b` for self-diffs against earlier state ([#170](https://github.com/coder/agent-tty/pull/170)). +- `record export --format svg [--animate]` writes a deterministic, byte-stable SVG (SMIL-animated or still) with no browser or ffmpeg; bundles JetBrains Mono and symbol-font subsets ([#171](https://github.com/coder/agent-tty/pull/171), [#349](https://github.com/coder/agent-tty/pull/349)). +- `screenshot --out ` writes the PNG to an explicit path (relative or absolute), with a shared `--out` resolver that also refuses paths inside session storage ([#241](https://github.com/coder/agent-tty/pull/241)). +- `screenshot --out` and `record export --out` now create missing parent folders like `mkdir -p`, except inside `sessions/` ([#290](https://github.com/coder/agent-tty/pull/290)). +- `mouse` CLI/RPC command and batch step: mode-aware native mouse input (clicks, drags, wheel) through the libghostty-vt backend, logged as `input_mouse` events; introduces the `CAPABILITY_UNAVAILABLE` error (exit 12) ([#179](https://github.com/coder/agent-tty/pull/179)). +- `wait --scope cursor-line` matches `--text`/`--regex` against the cursor row only, avoiding echo-of-command false positives; also available on batch `wait` steps ([#169](https://github.com/coder/agent-tty/pull/169)). +- `screenshot --json` reports glyphs drawn as `.notdef` boxes in `missingGlyphs` with their cells, plus `missingGlyphsTruncated`; `record export --format webm` reports the same per-code-point list ([#240](https://github.com/coder/agent-tty/pull/240), [#278](https://github.com/coder/agent-tty/pull/278)). +- Noto Sans Symbols 2 and Noto Sans Math subsets are now bundled and fall back after host monospace, so many previously-boxed symbols render without changing text-default emoji ([#278](https://github.com/coder/agent-tty/pull/278)). +- Session programs now get `AGENT_TTY_ACTIVE=true` and `AGENT_TTY_SESSION_ID=` in their environment ([#166](https://github.com/coder/agent-tty/pull/166)). +- Sessions now default `COLORTERM=truecolor`, and the PTY query responder answers XTGETTCAP `Tc`/`RGB`/`setrgbf`/`setrgbb` and declines DECRQSS SGR, so programs like Neovim enable 24-bit color under `env -i` or `--env COLORTERM=` ([#231](https://github.com/coder/agent-tty/pull/231), [#271](https://github.com/coder/agent-tty/pull/271)). +- `inspect --json` reports `eventLogStop` (`reason`, `seq`) when the host has stopped appending at a limit; `WAIT_TIMEOUT` and offline `REPLAY_ERROR` messages/details name the stop ([#340](https://github.com/coder/agent-tty/pull/340), [#357](https://github.com/coder/agent-tty/pull/357)). + +### Changed + +- **Build:** migrated from aube to pnpm (10.34.5); contributors run `pnpm install` / `mise run bootstrap` and Dependabot can now update `pnpm-lock.yaml` ([#176](https://github.com/coder/agent-tty/pull/176)). +- **`wait` default timeout is now 30 s** (was 600 s); `wait --help` shows the default. Windows that cannot finish inside the timeout (`--idle-ms`, `--screen-stable-ms`) are rejected up front with `INVALID_DURATION`. Batch `wait` steps share the same default and the same window rule ([#236](https://github.com/coder/agent-tty/pull/236), [#250](https://github.com/coder/agent-tty/pull/250), [#277](https://github.com/coder/agent-tty/pull/277)). +- **Timed-out `wait` now returns an error envelope** with `ok: false`, `error.code: "WAIT_TIMEOUT"` (exit 11 unchanged), while preserving `result.timedOut`/`matched`. Fail-fast `batch` failures emit the matching error envelope with step details ([#232](https://github.com/coder/agent-tty/pull/232), [#273](https://github.com/coder/agent-tty/pull/273), [#301](https://github.com/coder/agent-tty/pull/301)). +- A render `wait` that fails every poll now stops with the renderer's error (for example `REPLAY_ERROR`) instead of reporting `WAIT_TIMEOUT` ([#301](https://github.com/coder/agent-tty/pull/301)). +- Unexpected errors print one `INTERNAL_ERROR` JSON envelope on stdout under `--json`, and the CLI exits promptly after it instead of hanging on open handles. Empty/invalid session IDs return `INVALID_SESSION_ID` (exit 2) on every command. Commander usage errors emit an `INVALID_INPUT` envelope under `--json` ([#237](https://github.com/coder/agent-tty/pull/237), [#287](https://github.com/coder/agent-tty/pull/287)). +- Live-command errors from the session host now carry `details` across RPC (e.g. `details.path`, `details.errno`), matching offline errors ([#313](https://github.com/coder/agent-tty/pull/313)). +- Node version is checked against `engines.node` (`>=24.0.0 <27`) at startup with a one-line stderr warning; `doctor` fails on versions outside that range ([#245](https://github.com/coder/agent-tty/pull/245)). +- `snapshot --include-cells` now accepts RPC responses up to 64 MiB (previously capped at 1 MiB); larger successes return `PROTOCOL_ERROR` with the size ([#320](https://github.com/coder/agent-tty/pull/320)). +- `config.json` errors are typed: unreadable → `STORAGE_READ_ERROR`, invalid JSON/schema → `INVALID_INPUT`. `list` on an unreadable sessions dir returns `STORAGE_READ_ERROR`. `help` exits 0 ([#287](https://github.com/coder/agent-tty/pull/287)). +- `screenshot`/`record export` with a non-folder or dangling symlink at `artifacts/` now give `STORAGE_WRITE_ERROR` (exit 8) with a clear message ([#287](https://github.com/coder/agent-tty/pull/287), [#301](https://github.com/coder/agent-tty/pull/301)). +- WebM exports no longer impose a total 5-minute replay deadline. The replay fails only when the renderer makes no progress for 5 minutes, and the error names the window and the last event ([#356](https://github.com/coder/agent-tty/pull/356)). +- `record export --format webm` on a session that printed nothing exits 0 with a blank video at `capturedAtSeq: -1`; asciicast reports `-1` instead of `0` ([#270](https://github.com/coder/agent-tty/pull/270)). +- `destroy` typed into the session's own shell now forwards SIGINT/SIGTERM to its detached re-run copy and exits 130/143 to match ([#281](https://github.com/coder/agent-tty/pull/281)). +- `destroy --force` records a session as `destroyed` when the program-group read fails twice with EACCES/EPERM/EIO/EISDIR/ENOTDIR/ELOOP/ENAMETOOLONG, or when it cannot read the program group at all ([#327](https://github.com/coder/agent-tty/pull/327), [#331](https://github.com/coder/agent-tty/pull/331), [#334](https://github.com/coder/agent-tty/pull/334)). + +### Fixed + +- **`snapshot`/`screenshot` on a session that has printed nothing** now return an empty screen or blank PNG at `capturedAtSeq: -1` instead of failing with `RPC_ERROR` ([#235](https://github.com/coder/agent-tty/pull/235)). +- **`screenshot --hide-cursor`** actually hides the block cursor in the PNG (was previously byte-identical to `--show-cursor`) ([#289](https://github.com/coder/agent-tty/pull/289)). +- **WebM output now shows printed lines at their recorded time** instead of batching to the next non-output event ([#285](https://github.com/coder/agent-tty/pull/285)). +- **ghostty-web replay is roughly 50x faster**: 20,000-event screenshots dropped from ~386 s to ~7 s. Each replay flush now writes in one animation frame; `max-speed` WebM respects recorded time and holds one video frame before resizes ([#358](https://github.com/coder/agent-tty/pull/358), [#364](https://github.com/coder/agent-tty/pull/364)). +- Live `screenshot`/`snapshot --renderer ghostty-web` on long logs no longer time out at 5 s: the host streams keep-alives and replays the backlog in bounded slices, so clients wait as long as replay progresses ([#359](https://github.com/coder/agent-tty/pull/359)). +- A `ghostty-web` page crash during replay is now reported as `REPLAY_ERROR` (exit 10, `retryable: false`) on live and offline paths with a message that names the known cause, instead of `RPC_ERROR`/`INTERNAL_ERROR` with retries that can never succeed ([#363](https://github.com/coder/agent-tty/pull/363)). +- `create` under heavy host load now waits for the detached host as long as it is alive (up to 30 s on a monotonic clock) and treats first-probe `EPIPE` as "not ready yet", instead of failing with `HOST_UNREACHABLE` after a fixed 50-poll budget ([#362](https://github.com/coder/agent-tty/pull/362)). +- `create` that gives up on its host now instructs that host to stop the session, so no orphan `running` session is left behind ([#247](https://github.com/coder/agent-tty/pull/247)). +- Concurrent captures no longer drop entries from `artifacts/manifest.json`: appends run under a cross-process lock with stale-owner recovery ([#282](https://github.com/coder/agent-tty/pull/282)). +- Multiple session-lifecycle race fixes across `create`/`reconcile`/`gc`/`destroy`: hosts record pids up front, `writeManifest` no longer resurrects removed session folders, `gc` keeps exited sessions whose program group still runs (so `destroy` can end them), and `destroy --force` provably covers unshared/hidden-proc cases ([#181](https://github.com/coder/agent-tty/pull/181), [#194](https://github.com/coder/agent-tty/pull/194), [#200](https://github.com/coder/agent-tty/pull/200), [#201](https://github.com/coder/agent-tty/pull/201), [#216](https://github.com/coder/agent-tty/pull/216), [#221](https://github.com/coder/agent-tty/pull/221), [#302](https://github.com/coder/agent-tty/pull/302), [#312](https://github.com/coder/agent-tty/pull/312)). +- Event log stops gracefully at the 50 MiB / 250,000-event limit with a labeled stop marker instead of crashing the host or failing every subsequent export/snapshot ([#340](https://github.com/coder/agent-tty/pull/340)). +- `pty` no longer leaks an outer session id into session-less PTYs ([#178](https://github.com/coder/agent-tty/pull/178)). +- Waited `run` input is now logged in PTY order, and mouse motion dedup state is preserved across renderer swaps ([#234](https://github.com/coder/agent-tty/pull/234)). +- Repeated captures keep earlier artifact files instead of clobbering each other; exports are taken from their temp file to avoid races ([#191](https://github.com/coder/agent-tty/pull/191), [#316](https://github.com/coder/agent-tty/pull/316), [#321](https://github.com/coder/agent-tty/pull/321)). +- Per-session sockets are now rooted under a per-uid path and dead-host sockets are removed; `host.json` refuses to grow a hostname-mismatched stub ([#239](https://github.com/coder/agent-tty/pull/239), [#288](https://github.com/coder/agent-tty/pull/288), [#305](https://github.com/coder/agent-tty/pull/305)). +- RPC: request `id` capped at 128 chars; response cap raised to 64 MiB with `PROTOCOL_ERROR` above; truncated error messages no longer split surrogate pairs; older-host oversize responses are reported as `PROTOCOL_ERROR` ([#315](https://github.com/coder/agent-tty/pull/315), [#319](https://github.com/coder/agent-tty/pull/319), [#320](https://github.com/coder/agent-tty/pull/320), [#322](https://github.com/coder/agent-tty/pull/322)). +- `create` validates `cwd` and shell before creating the session directory ([#188](https://github.com/coder/agent-tty/pull/188)). +- `--out` writes retry against a swapped output folder and refuse unsearchable parents, and a failed `screenshot --out` undoes its in-session capture ([#279](https://github.com/coder/agent-tty/pull/279), [#300](https://github.com/coder/agent-tty/pull/300)). +- SVG export now succeeds as a still when the session clock stepped backward; `--animate` surfaces a clear `EXPORT_ERROR` naming the first bad event ([#349](https://github.com/coder/agent-tty/pull/349)). +- Numerous additional host, storage, destroy, verify-skill and lifecycle-model fixes — see the full changelog for the complete list. + +### Breaking Changes + +- **`wait` default timeout dropped from 600 s to 30 s** ([#236](https://github.com/coder/agent-tty/pull/236)). Scripts that relied on waiting longer than 30 s must pass `--timeout` explicitly (or `--timeout 0` to wait without a limit). Batch `wait` steps share the new default ([#250](https://github.com/coder/agent-tty/pull/250)). +- **Timed-out `wait` returns `ok: false`** with `error.code: "WAIT_TIMEOUT"`; consumers checking `.ok === true` on a timeout will now see `false`. `.result.timedOut`/`matched` still carry the old fields. Fail-fast `batch` failures also now emit `ok: false` ([#232](https://github.com/coder/agent-tty/pull/232)). +- **Render `wait` on persistent renderer failure now exits 9 `RPC_ERROR`** (or the renderer's own `CliError` code such as `REPLAY_ERROR`), not exit 11 `WAIT_TIMEOUT` ([#301](https://github.com/coder/agent-tty/pull/301)). +- **Inherited `COLORTERM` from the shell that runs `agent-tty create` no longer reaches the session**; sessions see `COLORTERM=truecolor` unless overridden with `--env COLORTERM=` ([#231](https://github.com/coder/agent-tty/pull/231)). +- Invalid session IDs on most commands now return exit 2 `INVALID_SESSION_ID` instead of exit 1 with a stack trace ([#237](https://github.com/coder/agent-tty/pull/237)). +- Downgrade compatibility note: an older CLI against a new host may see `RPC_ERROR` "RPC result failed validation" for new optional fields such as `eventLogStop`, `mouse-input` capability, or `details` on live errors; newer CLI against older hosts works fine ([#179](https://github.com/coder/agent-tty/pull/179), [#313](https://github.com/coder/agent-tty/pull/313), [#357](https://github.com/coder/agent-tty/pull/357)). +- `record export --format asciicast` on an empty log names its file `recording--1-asciicast.cast` (was `recording-0-asciicast.cast`); `capturedAtSeq` can now be `-1` in result schemas ([#235](https://github.com/coder/agent-tty/pull/235), [#270](https://github.com/coder/agent-tty/pull/270)). +- `screenshot`/`record export --out` paths that resolve inside `sessions/` are rejected with exit 7 `EXPORT_ERROR` (previously accepted for `record export`) ([#241](https://github.com/coder/agent-tty/pull/241)). + ## [0.5.0] - 2026-06-23 ### Added diff --git a/README.md b/README.md index e145d453..9d28e187 100644 --- a/README.md +++ b/README.md @@ -139,7 +139,7 @@ See [`docs/AGENT-SKILLS.md`](./docs/AGENT-SKILLS.md). ## Status & platform support -`agent-tty` is `0.5.0` and focused on reliable, isolated, reviewable terminal and TUI automation through a stable CLI. +`agent-tty` is `0.6.0` and focused on reliable, isolated, reviewable terminal and TUI automation through a stable CLI. - Linux and macOS are tier-1; Windows is tier-2 and not CI-tested. - Semantic snapshots and render-backed waits prefer the optional `libghostty-vt` backend when it is available, then fall back to `ghostty-web`. diff --git a/package.json b/package.json index c94ed2ad..449444c5 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "agent-tty", - "version": "0.5.0", + "version": "0.6.0", "description": "Terminal automation CLI for AI agents and humans", "license": "Apache-2.0", "keywords": [