Documentation
¶
Index ¶
- type PTY
- func (p *PTY) ArchiveSpool(_ context.Context, runtimeName string) error
- func (p *PTY) Capture(_ context.Context, runtimeName string) ([]byte, error)
- func (p *PTY) Check(context.Context) error
- func (p *PTY) Create(_ context.Context, runtimeName, directory, command string) error
- func (p *PTY) CreatedPath(runtimeName string) string
- func (p *PTY) EnsurePipe(_ context.Context, runtimeName string) error
- func (p *PTY) Exists(_ context.Context, runtimeName string) bool
- func (p *PTY) Input(_ context.Context, runtimeName string, data []byte) error
- func (p *PTY) Kill(_ context.Context, runtimeName string) error
- func (p *PTY) List(context.Context) (map[string]bool, error)
- func (p *PTY) ListCreated(context.Context) (map[string]time.Time, error)
- func (p *PTY) PIDPath(runtimeName string) string
- func (p *PTY) Recover(_ context.Context, runtimeName string, offset, end int64) ([]byte, error)
- func (p *PTY) RemoveSpool(runtimeName string)
- func (p *PTY) Resize(_ context.Context, runtimeName string, columns, rows int) error
- func (p *PTY) SpoolPath(runtimeName string) string
- func (p *PTY) SpoolSize(_ context.Context, runtimeName string) (int64, error)
- func (p *PTY) TruncateSpool(_ context.Context, runtimeName string) error
- type QueryResponder
- type SpoolRecoverer
- type SpoolWatcher
- type VTTerminal
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type PTY ¶
type PTY struct {
OutputDir string
// contains filtered or unexported fields
}
PTY is a tmux-free runtime that owns one pseudo-terminal per session. The daemon keeps the child alive after every client disconnects, and raw PTY bytes are appended to the same per-session spool consumed by SpoolWatcher, so the output pipeline (ring, recovery anchors, reanchor) is unchanged.
Known differences from the tmux adapter:
- Input bytes are written to the PTY verbatim, so there is no tmux paste-vs-key translation layer and kitty-protocol keys (for example Shift+Enter) reach the application unchanged.
- A daemon restart closes the PTY master and ends its sessions. tmux sessions survive a daemon restart because tmux owns them; the PTY runtime owns children directly and does not implement adoption yet.
func (*PTY) ArchiveSpool ¶
ArchiveSpool compresses the current spool to a timestamped .gz file and prunes old archives. Best-effort diagnostics; truncation must not depend on archive success. Mirrors the tmux adapter's spool helpers.
func (*PTY) Capture ¶
Capture renders the current emulated screen (visible grid + scrollback) with SGR styles preserved, so the client can replay a complete snapshot at its own size. This replaces the raw spool replay, which could not restore the screen when the PTY history was produced at a different size.
func (*PTY) Check ¶
Check reports whether the runtime can start. Unlike tmux there is no external binary to find, so the check always succeeds.
func (*PTY) CreatedPath ¶
func (*PTY) EnsurePipe ¶
EnsurePipe is idempotent by construction: the PTY runtime owns the spool from Create on, so there is no pipe to install on adopt.
func (*PTY) ListCreated ¶
ListCreated returns live sessions with their creation time, persisted in metadata files so a restarted daemon can reclaim orphans it no longer has a process handle for.
func (*PTY) Recover ¶
Recover returns the spool bytes in [offset, end), the raw PTY output a client still needs after its anchor. Host prefers this over a full reanchor snapshot whenever the spool still covers the anchor, so switching back to a retained surface renders the missing tail without clearing the screen.
func (*PTY) RemoveSpool ¶
func (*PTY) TruncateSpool ¶
TruncateSpool compacts the live spool in place. The copyOutput goroutine keeps its O_APPEND file descriptor, so output continues into the same inode from byte zero; Host bumps the epoch and reanchors clients.
type QueryResponder ¶
type QueryResponder struct {
// contains filtered or unexported fields
}
QueryResponder answers terminal capability queries while a session has no attached terminal client. TUIs such as Codex send DA/DSR/OSC/kitty keyboard queries at startup; tmux answers them through its own emulator, but a raw PTY has nobody to answer until a client attaches, so the application would downgrade itself (for example disabling colors). Replies are written back into the PTY as input, never into the output spool.
func NewQueryResponder ¶
func NewQueryResponder() *QueryResponder
func (*QueryResponder) Feed ¶
func (r *QueryResponder) Feed(data []byte) [][]byte
Feed scans output bytes for complete terminal queries and returns the replies to write back into the PTY. Queries split across chunks are buffered until complete or until they prove not to be queries.
func (*QueryResponder) Resize ¶
func (r *QueryResponder) Resize(columns, rows int)
type SpoolRecoverer ¶
SpoolRecoverer reads a contiguous byte range from a session's append-only spool. PTY implements it so Host can recover from the spool even after the in-memory ring evicted the client's anchor, avoiding a full screen reset and replay.
type SpoolWatcher ¶
type SpoolWatcher struct {
// contains filtered or unexported fields
}
SpoolWatcher reads an append-only spool from a persisted byte offset, draining to EOF whenever the file grows. It is the Go counterpart of the Swift OutputSpoolWatcher: capture-pane is no longer used for live output.
The watcher also detects in-place truncation (spool compaction). After a truncate the file size drops below the watcher offset; the watcher re-bases to offset zero and calls onRotate so Host can bump the epoch and reanchor every client instead of silently skipping bytes.
func NewSpoolWatcher ¶
func NewSpoolWatcher(path string, offset int64, onBytes func([]byte), onRotate func(), onOverflow func()) (*SpoolWatcher, error)
func (*SpoolWatcher) Close ¶
func (w *SpoolWatcher) Close()
func (*SpoolWatcher) Offset ¶
func (w *SpoolWatcher) Offset() int64
func (*SpoolWatcher) Pause ¶
func (w *SpoolWatcher) Pause()
Pause blocks until any in-flight drain finishes, then prevents new drains. Host uses it while preparing a reanchor so the snapshot replay can never race with live reads.
func (*SpoolWatcher) Ping ¶
func (w *SpoolWatcher) Ping()
Ping nudges the watcher after input, matching the old outputWake behavior without making it the delivery mechanism.
func (*SpoolWatcher) Resume ¶
func (w *SpoolWatcher) Resume()
func (*SpoolWatcher) SetMaxBytes ¶
func (w *SpoolWatcher) SetMaxBytes(maxBytes int64)
SetMaxBytes configures the spool size cap before Start. When the watcher passes the cap it calls onOverflow; Host archives, truncates, bumps the epoch, and reanchors clients.
func (*SpoolWatcher) SkipTo ¶
func (w *SpoolWatcher) SkipTo(offset int64) error
SkipTo re-bases the watcher to a byte position covered by a snapshot. It must be called while paused; any unread bytes below the target were already rendered by the snapshot and must not be delivered again.
func (*SpoolWatcher) Start ¶
func (w *SpoolWatcher) Start()
type VTTerminal ¶
type VTTerminal struct {
// contains filtered or unexported fields
}
VTTerminal is a libghostty-vt terminal emulator that renders raw PTY bytes into a complete screen snapshot (visible grid + scrollback) with SGR styles preserved. It is the server-side counterpart of the Ghostty client, so a replayed snapshot matches exactly what the client would have rendered.
func NewVTTerminal ¶
func NewVTTerminal(cols, rows int) (*VTTerminal, error)
func (*VTTerminal) Close ¶
func (v *VTTerminal) Close()
func (*VTTerminal) Feed ¶
func (v *VTTerminal) Feed(data []byte)
Feed parses raw PTY bytes into the emulated terminal state.
func (*VTTerminal) Resize ¶
func (v *VTTerminal) Resize(cols, rows int)
Resize reflows the emulated terminal. The caller keeps the real PTY size in sync so snapshots are rendered at the client's dimensions.
func (*VTTerminal) Snapshot ¶
func (v *VTTerminal) Snapshot() ([]byte, error)
Snapshot renders the current emulated screen (visible grid + scrollback) as VT sequences that preserve colors and styles.