pi-remote-control/docs/PHASE-0-spike-stream.md

129 lines
4.7 KiB
Markdown

# Phase 0 — Spike: tmux Stream PoC
> **Status:** ready to start.
> **Owner:** single agent, end-to-end (too small to parallelise).
> **Branch:** `feat/spike-stream`.
> **Estimated effort:** ~1 day.
## Goal
Verify the foundational assumption of the entire spec: that we can run `pi`
inside `tmux`, tee the pane output via `pipe-pane`, push it as a binary
WebSocket stream, and consume it from a client without rendering artefacts
or unacceptable latency.
Output is a decision: green light for Phase 1, or list of blockers that need
spec revision.
## Acceptance Criteria
- A new branch `feat/spike-stream` in `pi-remote-control`.
- A CLI invocation (e.g. `pi-remote spike`) that:
- Spawns a tmux session `pi-spike` running `pi`.
- Pipes the pane via `pipe-pane` to a WS endpoint on `ws://127.0.0.1:7799/spike`.
- Attaches the local terminal to the same tmux session.
- A test client (raw `wscat` script or a tiny throwaway HTML page) that
connects, dumps incoming binary frames to stdout (or a hex viewer) and
optionally re-renders them via `xterm.js`.
- A written PoC report `docs/reference/PHASE-0-report.md` answering:
- **R-1.** Does pi run cleanly inside tmux? (Ink redraws OK, no escape
sequence loss, no crashes during 10min uptime.)
- **R-2.** Does alternate-screen-buffer (`\e[?1049h`) work? Is the stream
parseable on the other side?
- **R-3.** Is per-chunk latency acceptable (< 50ms localhost,
< 200ms WAN)?
- **R-4.** Does the SSH session attached to the same tmux pane stay in
sync with the WS stream byte-for-byte?
- **R-5.** Edge cases observed (mouse mode, title sequences, very wide
output, etc.).
## Out of Scope for Spike-0
- No authentication, no TLS bind to 127.0.0.1 only.
- No reconnect, sequence numbers, snapshot or buffer.
- No `send-keys` direction (read-only stream is enough to verify rendering).
- No multi-session one fixed `pi-spike` session.
- No iOS code.
## Task Breakdown
### T-0.1 — Branch + skeleton
Create `feat/spike-stream`. Add a new file
`extensions/remote-control/spike.ts` and a CLI entry (a new flag
`--spike` on the existing extension or a separate npm-script
whichever is faster).
### T-0.2 — tmux helper
Spawn tmux session, attach pipe-pane to a Unix FIFO or a pseudo-stream we
can read from Node. Reference command:
```bash
tmux new-session -d -s pi-spike 'pi'
mkfifo /tmp/pi-spike.fifo
tmux pipe-pane -t pi-spike -o "cat > /tmp/pi-spike.fifo"
```
Node opens the FIFO read-side (`fs.createReadStream`) and exposes the byte
stream.
### T-0.3 — WS server
Stand up a minimal `ws` server on port 7799, route `/spike`, send the FIFO
bytes as binary frames. No backpressure handling, no permessage-deflate yet.
### T-0.4 — Test client
Two options, pick whichever is faster:
- **(a)** `wscat -b ws://127.0.0.1:7799/spike` and pipe through `od -c` for
raw inspection.
- **(b)** A 50-line HTML page with `xterm.js`, plain WebSocket, no styling.
### T-0.5 — Attach + dual-render test
Open a second terminal, run `tmux attach -t pi-spike`. Type into pi. Verify
that what you see in the SSH attach is identical to what arrives on the WS
client.
### T-0.6 — Stress / edge cases
Briefly try:
- Resize the SSH terminal see how tmux/pi react.
- Run a slash command that opens a full-screen menu (alternate screen).
- Paste a multi-line block.
- Let pi do a long tool call.
### T-0.7 — Report
Write `docs/reference/PHASE-0-report.md`. One paragraph per R-question,
plus a "go / no-go for Phase 1" verdict.
## File Plan
- New: `extensions/remote-control/spike.ts`
- New: `docs/reference/PHASE-0-report.md`
- Modified: `extensions/remote-control/index.ts` (add `--spike` flag or
separate entry).
- No changes to existing server.ts / html.ts / messages.ts.
## Dependencies
- `tmux` installed on the dev host. macOS: already present or
`brew install tmux`.
- `ws` library: already in `package.json`.
- `mkfifo` shell command (POSIX): already present on macOS/Linux.
## Risks
- **R-A.** Ink may refuse to run inside tmux due to TTY detection. If so,
set `FORCE_COLOR=1`, `TERM=xterm-256color`, pass `-tt` to tmux. Fall back
to spawning pi via `unbuffer` if necessary.
- **R-B.** FIFO can have buffering issues. If line buffering causes
visible lag, switch to a Unix domain socket and have Node read directly
from the socket.
- **R-C.** tmux's `pipe-pane` reproduces ANSI but may drop sequences during
bursts. If lossy, the alternative is to run pi inside our own `node-pty`
(a much larger change, but a fallback option).
## Exit / Handover
When Phase 0 closes:
- Merge `feat/spike-stream` into `main` only if PoC code is reusable for
Phase 1; otherwise close the branch and keep the report.
- Update `SYNC.md` with the verdict and any spec revisions needed.
- Trigger Phase 1.