@monotykamary/localterm-server 2.71.1 → 2.72.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/constants.d.ts +5 -0
- package/dist/constants.d.ts.map +1 -1
- package/dist/constants.js +15 -0
- package/dist/constants.js.map +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/dist/kitty-apc-scanner.d.ts +27 -0
- package/dist/kitty-apc-scanner.d.ts.map +1 -0
- package/dist/kitty-apc-scanner.js +134 -0
- package/dist/kitty-apc-scanner.js.map +1 -0
- package/dist/kitty-frame-file-relay.d.ts +13 -0
- package/dist/kitty-frame-file-relay.d.ts.map +1 -0
- package/dist/kitty-frame-file-relay.js +71 -0
- package/dist/kitty-frame-file-relay.js.map +1 -0
- package/dist/schemas.d.ts +5 -0
- package/dist/schemas.d.ts.map +1 -1
- package/dist/schemas.js +23 -0
- package/dist/schemas.js.map +1 -1
- package/dist/session-client-hub.d.ts +1 -1
- package/dist/session-client-hub.d.ts.map +1 -1
- package/dist/session-client-hub.js +9 -1
- package/dist/session-client-hub.js.map +1 -1
- package/dist/session-manager.d.ts +2 -1
- package/dist/session-manager.d.ts.map +1 -1
- package/dist/session-manager.js +5 -2
- package/dist/session-manager.js.map +1 -1
- package/dist/session-output-coordinator.d.ts +13 -1
- package/dist/session-output-coordinator.d.ts.map +1 -1
- package/dist/session-output-coordinator.js +107 -5
- package/dist/session-output-coordinator.js.map +1 -1
- package/dist/session-output-transport.d.ts +1 -0
- package/dist/session-output-transport.d.ts.map +1 -1
- package/dist/session-output-transport.js +21 -3
- package/dist/session-output-transport.js.map +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
import { MAX_APC_BUFFER_BYTES } from "./constants.js";
|
|
2
|
+
const ESC = "\x1b";
|
|
3
|
+
const ESCAPE_START = ESC + "_";
|
|
4
|
+
const ESCAPE_END = ESC + "\\";
|
|
5
|
+
// The single final byte after ESC _ that identifies the kitty graphics protocol.
|
|
6
|
+
const APC_FINAL_KITTY = 0x47; // 'G'
|
|
7
|
+
// Screen-state transitions that invalidate an on-screen pixel picture: leaving
|
|
8
|
+
// the alternate screen restores the pre-app main buffer (fresh content under
|
|
9
|
+
// the overlay), and ESC c wipes the whole terminal state.
|
|
10
|
+
const SCREEN_RESET_SEQUENCES = ["\x1b[?1049l", "\x1b[?1047l", "\x1b[?47l", "\x1bc"];
|
|
11
|
+
// A reset sequence can straddle two PTY data events; carry enough of the
|
|
12
|
+
// previous chunk's tail to match any of them across the boundary.
|
|
13
|
+
const SCREEN_RESET_TAIL_BYTES = 7;
|
|
14
|
+
const parseControl = (control) => {
|
|
15
|
+
const fields = {};
|
|
16
|
+
for (const part of control.split(",")) {
|
|
17
|
+
const eq = part.indexOf("=");
|
|
18
|
+
if (eq === -1)
|
|
19
|
+
continue;
|
|
20
|
+
fields[part.slice(0, eq)] = part.slice(eq + 1);
|
|
21
|
+
}
|
|
22
|
+
return fields;
|
|
23
|
+
};
|
|
24
|
+
const toInt = (value) => {
|
|
25
|
+
if (value === undefined)
|
|
26
|
+
return undefined;
|
|
27
|
+
const parsed = Number(value);
|
|
28
|
+
return Number.isInteger(parsed) ? parsed : undefined;
|
|
29
|
+
};
|
|
30
|
+
const decodeName = (payload) => Buffer.from(payload, "base64").toString("utf8");
|
|
31
|
+
// Scans PTY output for kitty graphics APCs that use the file medium (t=f): the
|
|
32
|
+
// payload is a base64 filesystem path instead of inline pixel bytes. Detects:
|
|
33
|
+
//
|
|
34
|
+
// 1. Medium probes (a=q) — the app asking whether this terminal can read a
|
|
35
|
+
// named frame file. These are stripped from the stream and answered by the
|
|
36
|
+
// daemon so nothing else races an answer.
|
|
37
|
+
// 2. Named transmits (a=T / a=t) — the app saying "display the pixels in this
|
|
38
|
+
// file". These pass through normally while the daemon relays the pixels
|
|
39
|
+
// over the WS pixel-frame channel.
|
|
40
|
+
//
|
|
41
|
+
// PTY data arrives chunked, so an APC sequence can span multiple pushes; the
|
|
42
|
+
// incomplete tail is buffered until its ESC \\ terminator lands.
|
|
43
|
+
export class KittyApcScanner {
|
|
44
|
+
isAllowedPath;
|
|
45
|
+
partial = "";
|
|
46
|
+
resetTail = "";
|
|
47
|
+
constructor(isAllowedPath) {
|
|
48
|
+
this.isAllowedPath = isAllowedPath;
|
|
49
|
+
}
|
|
50
|
+
push(chunk) {
|
|
51
|
+
const buffer = this.partial + chunk;
|
|
52
|
+
this.partial = "";
|
|
53
|
+
let output = "";
|
|
54
|
+
const frames = [];
|
|
55
|
+
const probes = [];
|
|
56
|
+
const screenReset = this.detectScreenReset(buffer);
|
|
57
|
+
let from = 0;
|
|
58
|
+
while (from < buffer.length) {
|
|
59
|
+
const start = buffer.indexOf(ESCAPE_START, from);
|
|
60
|
+
if (start === -1) {
|
|
61
|
+
output += buffer.slice(from);
|
|
62
|
+
break;
|
|
63
|
+
}
|
|
64
|
+
output += buffer.slice(from, start);
|
|
65
|
+
const end = buffer.indexOf(ESCAPE_END, start + ESCAPE_START.length);
|
|
66
|
+
if (end === -1) {
|
|
67
|
+
const tail = buffer.slice(start);
|
|
68
|
+
if (tail.length <= MAX_APC_BUFFER_BYTES) {
|
|
69
|
+
this.partial = tail;
|
|
70
|
+
}
|
|
71
|
+
else {
|
|
72
|
+
output += tail;
|
|
73
|
+
}
|
|
74
|
+
break;
|
|
75
|
+
}
|
|
76
|
+
const after = end + ESCAPE_END.length;
|
|
77
|
+
const classification = this.classify(buffer.slice(start + ESCAPE_START.length, end));
|
|
78
|
+
if (classification.kind === "probe") {
|
|
79
|
+
probes.push(classification.probe);
|
|
80
|
+
}
|
|
81
|
+
else {
|
|
82
|
+
if (classification.kind === "frame")
|
|
83
|
+
frames.push(classification.frame);
|
|
84
|
+
output += buffer.slice(start, after);
|
|
85
|
+
}
|
|
86
|
+
from = after;
|
|
87
|
+
}
|
|
88
|
+
return { output, frames, probes, screenReset };
|
|
89
|
+
}
|
|
90
|
+
// Match reset sequences against the chunk plus the carried tail so a sequence
|
|
91
|
+
// split across PTY reads still trips. Each push yields a single flag: multiple
|
|
92
|
+
// resets in one push collapse, and a boundary match only fires on the later
|
|
93
|
+
// push (the earlier one merely prepared the tail).
|
|
94
|
+
detectScreenReset(buffer) {
|
|
95
|
+
const hay = this.resetTail + buffer;
|
|
96
|
+
this.resetTail = hay.slice(-SCREEN_RESET_TAIL_BYTES);
|
|
97
|
+
for (const sequence of SCREEN_RESET_SEQUENCES) {
|
|
98
|
+
if (hay.includes(sequence))
|
|
99
|
+
return true;
|
|
100
|
+
}
|
|
101
|
+
return false;
|
|
102
|
+
}
|
|
103
|
+
classify(body) {
|
|
104
|
+
if (body.charCodeAt(0) !== APC_FINAL_KITTY)
|
|
105
|
+
return { kind: "other" };
|
|
106
|
+
const content = body.slice(1);
|
|
107
|
+
const semi = content.indexOf(";");
|
|
108
|
+
const control = semi === -1 ? content : content.slice(0, semi);
|
|
109
|
+
const payload = semi === -1 ? "" : content.slice(semi + 1);
|
|
110
|
+
const fields = parseControl(control);
|
|
111
|
+
if (fields.t !== "f")
|
|
112
|
+
return { kind: "other" };
|
|
113
|
+
const path_ = decodeName(payload);
|
|
114
|
+
if (!path_ || !this.isAllowedPath(path_))
|
|
115
|
+
return { kind: "other" };
|
|
116
|
+
const imageId = toInt(fields.i);
|
|
117
|
+
if (imageId === undefined || imageId < 0)
|
|
118
|
+
return { kind: "other" };
|
|
119
|
+
if (fields.a === "q") {
|
|
120
|
+
return { kind: "probe", probe: { imageId, quiet: toInt(fields.q) ?? 0, path: path_ } };
|
|
121
|
+
}
|
|
122
|
+
if (fields.a === "T" || fields.a === "t") {
|
|
123
|
+
const width = toInt(fields.s);
|
|
124
|
+
const height = toInt(fields.v);
|
|
125
|
+
const format = toInt(fields.f);
|
|
126
|
+
// f=32 is the raw RGBA format the relay supports.
|
|
127
|
+
if (!width || !height || width <= 0 || height <= 0 || format !== 32)
|
|
128
|
+
return { kind: "other" };
|
|
129
|
+
return { kind: "frame", frame: { width, height, imageId, path: path_ } };
|
|
130
|
+
}
|
|
131
|
+
return { kind: "other" };
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
//# sourceMappingURL=kitty-apc-scanner.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"kitty-apc-scanner.js","sourceRoot":"","sources":["../src/kitty-apc-scanner.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { SessionOutputTransport } from "./session-output-transport.js";
|
|
2
|
+
import type { ManagedSession } from "./session-manager.js";
|
|
3
|
+
import type { KittyPixelFrame } from "./kitty-apc-scanner.js";
|
|
4
|
+
export declare const readPixelFrame: (frame: KittyPixelFrame, tmpdirRoot: string) => Promise<Uint8Array | null>;
|
|
5
|
+
export declare class KittyFrameFileRelay {
|
|
6
|
+
private readonly transport;
|
|
7
|
+
private readonly states;
|
|
8
|
+
constructor(transport: SessionOutputTransport);
|
|
9
|
+
push(managed: ManagedSession, frame: KittyPixelFrame, tmpdirRoot: string): void;
|
|
10
|
+
cancel(managed: ManagedSession): void;
|
|
11
|
+
private pump;
|
|
12
|
+
}
|
|
13
|
+
//# sourceMappingURL=kitty-frame-file-relay.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"kitty-frame-file-relay.d.ts","sourceRoot":"","sources":["../src/kitty-frame-file-relay.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,+BAA+B,CAAC;AAC5E,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAC3D,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAW9D,eAAO,MAAM,cAAc,UAClB,eAAe,cACV,MAAM,KACjB,OAAO,CAAC,UAAU,GAAG,IAAI,CAa3B,CAAC;AAMF,qBAAa,mBAAmB;IAGlB,OAAO,CAAC,QAAQ,CAAC,SAAS;IAFtC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAA6C;IAEpE,YAA6B,SAAS,EAAE,sBAAsB,EAAI;IAElE,IAAI,CAAC,OAAO,EAAE,cAAc,EAAE,KAAK,EAAE,eAAe,EAAE,UAAU,EAAE,MAAM,GAAG,IAAI,CAW9E;IAKD,MAAM,CAAC,OAAO,EAAE,cAAc,GAAG,IAAI,CAKpC;YAEa,IAAI;CAmBnB"}
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
import fs from "node:fs/promises";
|
|
2
|
+
import path from "node:path";
|
|
3
|
+
import { MAX_PIXEL_FRAME_BYTES } from "./constants.js";
|
|
4
|
+
export const readPixelFrame = async (frame, tmpdirRoot) => {
|
|
5
|
+
const expected = frame.width * frame.height * 4;
|
|
6
|
+
if (expected <= 0 || expected > MAX_PIXEL_FRAME_BYTES)
|
|
7
|
+
return null;
|
|
8
|
+
try {
|
|
9
|
+
const real = await fs.realpath(frame.path);
|
|
10
|
+
if (!real.startsWith(tmpdirRoot + path.sep))
|
|
11
|
+
return null;
|
|
12
|
+
const stat = await fs.stat(real);
|
|
13
|
+
if (!stat.isFile() || stat.size !== expected)
|
|
14
|
+
return null;
|
|
15
|
+
const pixels = await fs.readFile(real);
|
|
16
|
+
return pixels.length === expected ? new Uint8Array(pixels) : null;
|
|
17
|
+
}
|
|
18
|
+
catch {
|
|
19
|
+
return null;
|
|
20
|
+
}
|
|
21
|
+
};
|
|
22
|
+
// latest-wins relay: the app renders at display cadence while a frame read +
|
|
23
|
+
// broadcast is async, so frames must not queue (that would pile up megabytes of
|
|
24
|
+
// RGBA). The newest frame replaces any previous one still pending, bounding
|
|
25
|
+
// memory and keeping the client as fresh as possible.
|
|
26
|
+
export class KittyFrameFileRelay {
|
|
27
|
+
transport;
|
|
28
|
+
states = new WeakMap();
|
|
29
|
+
constructor(transport) {
|
|
30
|
+
this.transport = transport;
|
|
31
|
+
}
|
|
32
|
+
push(managed, frame, tmpdirRoot) {
|
|
33
|
+
let state = this.states.get(managed);
|
|
34
|
+
if (!state) {
|
|
35
|
+
state = { pending: null, active: false, generation: 0 };
|
|
36
|
+
this.states.set(managed, state);
|
|
37
|
+
}
|
|
38
|
+
state.pending = frame;
|
|
39
|
+
if (!state.active) {
|
|
40
|
+
state.active = true;
|
|
41
|
+
void this.pump(managed, state, tmpdirRoot);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
// Drop the queued frame and invalidate in-flight reads — the app's screen
|
|
45
|
+
// content reset, so its pixels would overlay fresh main-buffer text if they
|
|
46
|
+
// arrived late.
|
|
47
|
+
cancel(managed) {
|
|
48
|
+
const state = this.states.get(managed);
|
|
49
|
+
if (!state)
|
|
50
|
+
return;
|
|
51
|
+
state.pending = null;
|
|
52
|
+
state.generation++;
|
|
53
|
+
}
|
|
54
|
+
async pump(managed, state, tmpdirRoot) {
|
|
55
|
+
try {
|
|
56
|
+
while (state.pending) {
|
|
57
|
+
const frame = state.pending;
|
|
58
|
+
state.pending = null;
|
|
59
|
+
const generation = state.generation;
|
|
60
|
+
const pixels = await readPixelFrame(frame, tmpdirRoot);
|
|
61
|
+
if (pixels && state.generation === generation) {
|
|
62
|
+
this.transport.broadcastPixelFrame(managed, frame.width, frame.height, pixels);
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
finally {
|
|
67
|
+
state.active = false;
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
//# sourceMappingURL=kitty-frame-file-relay.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"kitty-frame-file-relay.js","sourceRoot":"","sources":["../src/kitty-frame-file-relay.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,kBAAkB,CAAC;AAClC,OAAO,IAAI,MAAM,WAAW,CAAC;AAC7B,OAAO,EAAE,qBAAqB,EAAE,MAAM,gBAAgB,CAAC;AAcvD,MAAM,CAAC,MAAM,cAAc,GAAG,KAAK,EACjC,KAAsB,EACtB,UAAkB,EACU,EAAE;IAC9B,MAAM,QAAQ,GAAG,KAAK,CAAC,KAAK,GAAG,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC;IAChD,IAAI,QAAQ,IAAI,CAAC,IAAI,QAAQ,GAAG,qBAAqB;QAAE,OAAO,IAAI,CAAC;IACnE,IAAI,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,EAAE,CAAC,QAAQ,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;QAC3C,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,UAAU,GAAG,IAAI,CAAC,GAAG,CAAC;YAAE,OAAO,IAAI,CAAC;QACzD,MAAM,IAAI,GAAG,MAAM,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjC,IAAI,CAAC,IAAI,CAAC,MAAM,EAAE,IAAI,IAAI,CAAC,IAAI,KAAK,QAAQ;YAAE,OAAO,IAAI,CAAC;QAC1D,MAAM,MAAM,GAAG,MAAM,EAAE,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QACvC,OAAO,MAAM,CAAC,MAAM,KAAK,QAAQ,CAAC,CAAC,CAAC,IAAI,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;IACpE,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,IAAI,CAAC;IACd,CAAC;AACH,CAAC,CAAC;AAEF,6EAA6E;AAC7E,gFAAgF;AAChF,4EAA4E;AAC5E,sDAAsD;AACtD,MAAM,OAAO,mBAAmB;IAGD,SAAS;IAFrB,MAAM,GAAG,IAAI,OAAO,EAA8B,CAAC;IAEpE,YAA6B,SAAiC;yBAAjC,SAAS;IAA2B,CAAC;IAElE,IAAI,CAAC,OAAuB,EAAE,KAAsB,EAAE,UAAkB;QACtE,IAAI,KAAK,GAAG,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;QACrC,IAAI,CAAC,KAAK,EAAE,CAAC;YACX,KAAK,GAAG,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,UAAU,EAAE,CAAC,EAAE,CAAC;YACxD,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC;QAClC,CAAC;QACD,KAAK,CAAC,OAAO,GAAG,KAAK,CAAC;QACtB,IAAI,CAAC,KAAK,CAAC,MAAM,EAAE,CAAC;YAClB,KAAK,CAAC,MAAM,GAAG,IAAI,CAAC;YACpB,KAAK,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,KAAK,EAAE,UAAU,CAAC,CAAC;QAC7C,CAAC;IACH,CAAC;IAED,0EAA0E;IAC1E,4EAA4E;IAC5E,gBAAgB;IAChB,MAAM,CAAC,OAAuB;QAC5B,MAAM,KAAK,GAAG,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;QACvC,IAAI,CAAC,KAAK;YAAE,OAAO;QACnB,KAAK,CAAC,OAAO,GAAG,IAAI,CAAC;QACrB,KAAK,CAAC,UAAU,EAAE,CAAC;IACrB,CAAC;IAEO,KAAK,CAAC,IAAI,CAChB,OAAuB,EACvB,KAAiB,EACjB,UAAkB;QAElB,IAAI,CAAC;YACH,OAAO,KAAK,CAAC,OAAO,EAAE,CAAC;gBACrB,MAAM,KAAK,GAAG,KAAK,CAAC,OAAO,CAAC;gBAC5B,KAAK,CAAC,OAAO,GAAG,IAAI,CAAC;gBACrB,MAAM,UAAU,GAAG,KAAK,CAAC,UAAU,CAAC;gBACpC,MAAM,MAAM,GAAG,MAAM,cAAc,CAAC,KAAK,EAAE,UAAU,CAAC,CAAC;gBACvD,IAAI,MAAM,IAAI,KAAK,CAAC,UAAU,KAAK,UAAU,EAAE,CAAC;oBAC9C,IAAI,CAAC,SAAS,CAAC,mBAAmB,CAAC,OAAO,EAAE,KAAK,CAAC,KAAK,EAAE,KAAK,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;gBACjF,CAAC;YACH,CAAC;QACH,CAAC;gBAAS,CAAC;YACT,KAAK,CAAC,MAAM,GAAG,KAAK,CAAC;QACvB,CAAC;IACH,CAAC;CACF"}
|
package/dist/schemas.d.ts
CHANGED
|
@@ -292,6 +292,7 @@ export declare const clientToServerMessageSchema: z.ZodDiscriminatedUnion<[z.Zod
|
|
|
292
292
|
"br-ctx": "br-ctx";
|
|
293
293
|
gzip: "gzip";
|
|
294
294
|
}>>>;
|
|
295
|
+
binaryFraming: z.ZodDefault<z.ZodBoolean>;
|
|
295
296
|
}, z.core.$strict>], "type">;
|
|
296
297
|
export declare const gitDiffFileStatusSchema: z.ZodEnum<{
|
|
297
298
|
added: "added";
|
|
@@ -3163,6 +3164,10 @@ export declare const serverToClientMessageSchema: z.ZodDiscriminatedUnion<[z.Zod
|
|
|
3163
3164
|
"br-ctx": "br-ctx";
|
|
3164
3165
|
gzip: "gzip";
|
|
3165
3166
|
}>>;
|
|
3167
|
+
}, z.core.$strict>, z.ZodObject<{
|
|
3168
|
+
type: z.ZodLiteral<"binary-framing">;
|
|
3169
|
+
}, z.core.$strict>, z.ZodObject<{
|
|
3170
|
+
type: z.ZodLiteral<"pixel-frames-clear">;
|
|
3166
3171
|
}, z.core.$strict>, z.ZodObject<{
|
|
3167
3172
|
type: z.ZodLiteral<"peer-attached">;
|
|
3168
3173
|
}, z.core.$strict>, z.ZodObject<{
|
package/dist/schemas.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"schemas.d.ts","sourceRoot":"","sources":["../src/schemas.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAkFxB,eAAO,MAAM,eAAe;;;;kBASf,CAAC;AAEd,eAAO,MAAM,YAAY;;;;;;;;kBAMd,CAAC;AAOZ,eAAO,MAAM,kBAAkB;;;;;kBAOpB,CAAC;AAOZ,eAAO,MAAM,sBAAsB;;;;;kBAOxB,CAAC;AAeZ,eAAO,MAAM,0BAA0B;;;;EAA8C,CAAC;AAQtF,eAAO,MAAM,0BAA0B;;;kBAK5B,CAAC;AAEZ,eAAO,MAAM,qBAAqB;;;;;;;;;;;;;;;;;;;;kBAevB,CAAC;AAEZ,eAAO,MAAM,0BAA0B;;;;;;;;;;;;;;;;;;;;;;kBAE5B,CAAC;AAMZ,eAAO,MAAM,wBAAwB;;;;;;;;kBAU1B,CAAC;AAEZ,eAAO,MAAM,qBAAqB;;;;;;;;;;;;;;;;;;;;;;kBAAwD,CAAC;AAE3F,eAAO,MAAM,wBAAwB;;;kBAK1B,CAAC;AAEZ,eAAO,MAAM,kBAAkB;;;kBASpB,CAAC;AAEZ,eAAO,MAAM,mBAAmB;;;kBAKrB,CAAC;AAEZ,eAAO,MAAM,eAAe;;;;kBAMjB,CAAC;AAEZ,eAAO,MAAM,sBAAsB;;;;;;;;;kBAWxB,CAAC;AAEZ,eAAO,MAAM,gBAAgB;;;;;;kBAQlB,CAAC;AAEZ,eAAO,MAAM,yBAAyB;;kBAA0C,CAAC;AAMjF,eAAO,MAAM,eAAe;;;;;;;;;;;;;4BAuB1B,CAAC;AAEH,eAAO,MAAM,gBAAgB;;;;kBAMlB,CAAC;AASZ,eAAO,MAAM,gBAAgB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;8BAoF3B,CAAC;AAEH,eAAO,MAAM,iBAAiB;;;;;;;;;;kBASnB,CAAC;AAEZ,eAAO,MAAM,gBAAgB;;;;kBAMlB,CAAC;AAEZ,eAAO,MAAM,wBAAwB;;kBAE1B,CAAC;AAWZ,eAAO,MAAM,mBAAmB;;;;;;;;kBAUrB,CAAC;AAEZ,eAAO,MAAM,4BAA4B;;;;;;;;;;kBAE9B,CAAC;AAoCZ,eAAO,MAAM,oBAAoB;;;;EAAqC,CAAC;AAyFvE,MAAM,MAAM,YAAY,GAAG,QAAQ,GAAG,IAAI,GAAG,MAAM,GAAG,IAAI,CAAC;
|
|
1
|
+
{"version":3,"file":"schemas.d.ts","sourceRoot":"","sources":["../src/schemas.ts"],"names":[],"mappings":"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"}
|
package/dist/schemas.js
CHANGED
|
@@ -431,6 +431,14 @@ const readyMessageSchema = z
|
|
|
431
431
|
type: z.literal("ready"),
|
|
432
432
|
replay: z.boolean(),
|
|
433
433
|
compress: compressModeSchema.default(null),
|
|
434
|
+
// Advertises that the client can parse binary WS messages that ALWAYS carry
|
|
435
|
+
// a 1-byte type header — 0x00 raw output, 0x01—0x03 compressed output,
|
|
436
|
+
// 0x04 relayed pixel frame — even when compress is null (loopback raw). The
|
|
437
|
+
// server confirms with a {binary-framing} control message; without the
|
|
438
|
+
// advertisement it keeps legacy semantics (header only when a compress mode
|
|
439
|
+
// is negotiated), where raw output is untyped and 0x04 can't be
|
|
440
|
+
// distinguished from terminal bytes.
|
|
441
|
+
binaryFraming: z.boolean().default(false),
|
|
434
442
|
})
|
|
435
443
|
.strict();
|
|
436
444
|
export const clientToServerMessageSchema = z.discriminatedUnion("type", [
|
|
@@ -1369,6 +1377,19 @@ const replayEndMessageSchema = z.object({ type: z.literal("replay-end") }).stric
|
|
|
1369
1377
|
const compressMessageSchema = z
|
|
1370
1378
|
.object({ type: z.literal("compress"), mode: compressModeSchema })
|
|
1371
1379
|
.strict();
|
|
1380
|
+
// Confirms always-on binary framing: the server will prefix every binary WS
|
|
1381
|
+
// message to this client with a 1-byte type header (0x00 raw output,
|
|
1382
|
+
// 0x01—0x03 compressed output, 0x04 relayed pixel frame) even when the
|
|
1383
|
+
// negotiated compress mode is null. Sent on promote right after {compress},
|
|
1384
|
+
// and only to clients that advertised binaryFraming in {ready}. Unknown to
|
|
1385
|
+
// older clients, which drop it and keep legacy parsing.
|
|
1386
|
+
const binaryFramingMessageSchema = z.object({ type: z.literal("binary-framing") }).strict();
|
|
1387
|
+
// The app owning the session left the alt screen / hard-reset after relaying at
|
|
1388
|
+
// least one pixel frame: the terminal now shows main-buffer content that a
|
|
1389
|
+
// stale relayed picture would cover, so clients should drop their overlay.
|
|
1390
|
+
// Only sent when the session actually produced a pixel frame — a vim-style
|
|
1391
|
+
// alt-screen exit without frames is a no-op wasteful to signal.
|
|
1392
|
+
const pixelFramesClearMessageSchema = z.object({ type: z.literal("pixel-frames-clear") }).strict();
|
|
1372
1393
|
// A second client just attached to this PTY (a mobile ingested a desktop's
|
|
1373
1394
|
// share QR, or another tab joined via the session picker). Broadcast to the
|
|
1374
1395
|
// existing subscribers at attach time — before the joiner is added — so a
|
|
@@ -1893,6 +1914,8 @@ export const serverToClientMessageSchema = z.discriminatedUnion("type", [
|
|
|
1893
1914
|
cdpControlledMessageSchema,
|
|
1894
1915
|
replayEndMessageSchema,
|
|
1895
1916
|
compressMessageSchema,
|
|
1917
|
+
binaryFramingMessageSchema,
|
|
1918
|
+
pixelFramesClearMessageSchema,
|
|
1896
1919
|
peerAttachedMessageSchema,
|
|
1897
1920
|
ptySizeMessageSchema,
|
|
1898
1921
|
]);
|