Skip to content

Add revision-guarded PTY send - #133

Draft
myobie wants to merge 3 commits into
agent/pty-activity-statusfrom
agent/pty-guarded-send
Draft

Add revision-guarded PTY send#133
myobie wants to merge 3 commits into
agent/pty-activity-statusfrom
agent/pty-guarded-send

Conversation

@myobie

@myobie myobie commented Jul 30, 2026

Copy link
Copy Markdown
Collaborator

What changed

  • expose top-level daemon generation and monotonic ioRevision through STATUS, queryStats(), and pty stats
  • advance the delivery revision on accepted input, child output, actual PTY resizes, activity transitions/releases, and child exit
  • add a bounded public compareAndSend() API and GUARDED_DATA protocol packet
  • validate generation/revision and perform the single PTY write in one daemon event-loop turn
  • reject mismatch, replay, malformed/oversized commands, exited sessions, and read-only sockets with zero guarded bytes
  • keep provider, composer, key, paste, ESC, human, Codex, Claude, and DING semantics outside PTY
  • add fixed combined fixtures for idle, active, alternate-screen/Vim-like state, user input, child output, resize, stale token, and daemon replacement

Why

An adapter can hold fresh idle authority and check its own composer fixtures, but input, output, resize, activity, or restart can race before delivery. A daemon-owned exact revision token closes that race without interpreting terminal bytes.

Closes #132. Depends on draft PR #131 / issue #129. This stacked draft targets agent/pty-activity-status so its diff contains only guarded-send work.

Race proof

The socket packet loop processes ordinary DATA, resize, activity, and guarded packets synchronously in order. All delivery-relevant mutation paths advance one per-generation counter. A guarded request compares both tokens immediately before pty.write() in that same event-loop turn; successful write advances the revision, making replay impossible. Rejection performs no PTY write and does not alter the activity lease.

The combined fixture contract keeps the layers separate: only explicit idle is adapter-eligible, while exact generation/revision independently gates the mechanical write. Alternate-screen/Vim-like state is diagnostic and never grants authority.

Validation

  • npm run typecheck
  • npm run build
  • combined activity/guarded-send fixture and race matrix — 108 passed
  • npm run verify-docs — 13 passed
  • predecessor full local suite — 1,473 passed, 21 skipped; only the two pre-existing host Nano cases failed with Incomplete terminfo entry
  • exact successor hosted build run 30615552244 — passed
  • exact successor hosted Vitest run 30615552132 — passed

Draft only. No merge or deployment.

# Conflicts:
#	docs/client.md
#	src/protocol.ts
#	src/server.ts
#	tests/protocol.test.ts
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant