mirror of
https://github.com/Ark0N/Codeman.git
synced 2026-10-07 07:59:42 +02:00
Merge pull request #431 from rounakdatta/feat/mobile-terminal-resilience
fix(terminal): four silent-failure paths — renderer freeze, replay race, reconnect gap, unbounded fetches
This commit is contained in:
@@ -2124,7 +2124,13 @@ export function registerSessionRoutes(
|
||||
const session = findSessionOrFail(ctx, id, req);
|
||||
|
||||
session.resize(cols, rows, { viewportType, force });
|
||||
return {};
|
||||
// Answer with the geometry the PTY ACTUALLY holds, which is not always the
|
||||
// one asked for: `Session.resize` declines small-viewport requests while a
|
||||
// desktop connection holds an active sizing claim. A browser terminal left
|
||||
// at a shape the PTY refused renders garbled output, not merely wrong-sized
|
||||
// output, so the client adopts this (issue #464). A session with no pane
|
||||
// reports nothing rather than the constructor defaults — see `ptyGeometry`.
|
||||
return session.ptyGeometry ?? {};
|
||||
});
|
||||
|
||||
// ========== Get Last Response (from transcript JSONL) ==========
|
||||
|
||||
@@ -22,6 +22,9 @@
|
||||
* {"t":"c"} — clear terminal
|
||||
* {"t":"r"} — needs refresh (reload buffer)
|
||||
* {"t":"ia","seq":N} — input ACK (echoes the seq of an applied/deduped input frame)
|
||||
* {"t":"zc","c":N,"r":N} — resize confirm: the geometry the PTY now holds, which
|
||||
* is NOT always the one requested (see Session.resize
|
||||
* arbitration). Clients adopt it — issue #464.
|
||||
* Client -> Server:
|
||||
* {"t":"i","d":"...","seq":N,"cid":"..."} — input (keystroke or paste). seq+cid are
|
||||
* optional reliable-delivery tags: the server applies each
|
||||
@@ -240,6 +243,19 @@ export function registerWsRoutes(app: FastifyInstance, ctx: SessionPort, getHost
|
||||
}
|
||||
const force = msg.f === true;
|
||||
session.resize(msg.c, msg.r, { viewportType, force });
|
||||
// Report the geometry that actually took. Resize used to be
|
||||
// write-only, so a client whose request was declined by the
|
||||
// arbitration above — or floored, or overridden by another device
|
||||
// — had no way to find out, and went on rendering a CLI's repaints
|
||||
// against a screen shape that did not exist (issue #464). Sent
|
||||
// unconditionally: it is ~30 bytes on a debounced, rare message,
|
||||
// and always-send means the client needs no "did it take?" state.
|
||||
// A session with no pane sends nothing at all: its `_ptyCols`/
|
||||
// `_ptyRows` are constructor defaults no process was ever told.
|
||||
const applied = session.ptyGeometry;
|
||||
if (applied && socket.readyState === 1) {
|
||||
socket.send(`{"t":"zc","c":${applied.cols},"r":${applied.rows}}`);
|
||||
}
|
||||
}
|
||||
} catch {
|
||||
// Ignore malformed messages
|
||||
|
||||
Reference in New Issue
Block a user