@linkshell/gateway 0.3.2 → 0.3.4
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/Dockerfile +1 -0
- package/dist/gateway/src/embedded.js +30 -2
- package/dist/gateway/src/embedded.js.map +1 -1
- package/dist/gateway/src/index.js +30 -2
- package/dist/gateway/src/index.js.map +1 -1
- package/dist/gateway/src/relay.js +44 -25
- package/dist/gateway/src/relay.js.map +1 -1
- package/dist/gateway/src/sessions.d.ts +11 -0
- package/dist/gateway/src/sessions.js +34 -1
- package/dist/gateway/src/sessions.js.map +1 -1
- package/dist/gateway/tsconfig.tsbuildinfo +1 -1
- package/dist/shared-protocol/src/index.d.ts +6429 -2405
- package/dist/shared-protocol/src/index.js +73 -4
- package/dist/shared-protocol/src/index.js.map +1 -1
- package/package.json +2 -2
- package/src/embedded.ts +32 -2
- package/src/index.ts +32 -2
- package/src/relay.ts +48 -21
- package/src/sessions.ts +37 -1
package/src/sessions.ts
CHANGED
|
@@ -33,12 +33,16 @@ export interface HostDevice {
|
|
|
33
33
|
}
|
|
34
34
|
|
|
35
35
|
const OUTPUT_BUFFER_CAPACITY = 200;
|
|
36
|
+
const OUTPUT_BUFFER_MAX_PAYLOAD_BYTES = Number(
|
|
37
|
+
process.env.OUTPUT_BUFFER_MAX_PAYLOAD_BYTES ?? 64 * 1024,
|
|
38
|
+
);
|
|
36
39
|
const HOST_RECONNECT_WINDOW = 60_000;
|
|
37
40
|
const CLEANUP_INTERVAL = 30_000;
|
|
38
41
|
|
|
39
42
|
export class DeviceManager {
|
|
40
43
|
private devices = new Map<string, HostDevice>();
|
|
41
44
|
private cleanupTimer: ReturnType<typeof setInterval>;
|
|
45
|
+
private droppedClients = 0;
|
|
42
46
|
|
|
43
47
|
constructor() {
|
|
44
48
|
this.cleanupTimer = setInterval(() => this.cleanup(), CLEANUP_INTERVAL);
|
|
@@ -106,7 +110,7 @@ export class DeviceManager {
|
|
|
106
110
|
removeClient(hostDeviceId: string, deviceId: string): void {
|
|
107
111
|
const device = this.devices.get(hostDeviceId);
|
|
108
112
|
if (!device) return;
|
|
109
|
-
device.clients.delete(deviceId)
|
|
113
|
+
if (device.clients.delete(deviceId)) this.droppedClients++;
|
|
110
114
|
if (device.controllerId === deviceId) {
|
|
111
115
|
const next = device.clients.keys().next();
|
|
112
116
|
device.controllerId = next.done ? undefined : next.value;
|
|
@@ -126,6 +130,7 @@ export class DeviceManager {
|
|
|
126
130
|
device.clients.delete(deviceId);
|
|
127
131
|
closed++;
|
|
128
132
|
}
|
|
133
|
+
this.droppedClients += closed;
|
|
129
134
|
if (device.controllerId && !device.clients.has(device.controllerId)) {
|
|
130
135
|
const next = device.clients.keys().next();
|
|
131
136
|
device.controllerId = next.done ? undefined : next.value;
|
|
@@ -154,6 +159,14 @@ export class DeviceManager {
|
|
|
154
159
|
bufferOutput(hostDeviceId: string, envelope: Envelope): void {
|
|
155
160
|
const device = this.devices.get(hostDeviceId);
|
|
156
161
|
if (!device) return;
|
|
162
|
+
const payload = envelope.payload as { data?: unknown } | undefined;
|
|
163
|
+
if (
|
|
164
|
+
typeof payload?.data === "string" &&
|
|
165
|
+
Buffer.byteLength(payload.data, "utf8") > OUTPUT_BUFFER_MAX_PAYLOAD_BYTES
|
|
166
|
+
) {
|
|
167
|
+
device.lastActivity = Date.now();
|
|
168
|
+
return;
|
|
169
|
+
}
|
|
157
170
|
const terminalId = envelope.terminalId ?? "default";
|
|
158
171
|
let buffer = device.outputBuffers.get(terminalId);
|
|
159
172
|
if (!buffer) {
|
|
@@ -257,6 +270,29 @@ export class DeviceManager {
|
|
|
257
270
|
};
|
|
258
271
|
}
|
|
259
272
|
|
|
273
|
+
getStats() {
|
|
274
|
+
let clientCount = 0;
|
|
275
|
+
let bufferedTerminalFrames = 0;
|
|
276
|
+
let hostAbsentDevices = 0;
|
|
277
|
+
let terminalCount = 0;
|
|
278
|
+
for (const device of this.devices.values()) {
|
|
279
|
+
clientCount += device.clients.size;
|
|
280
|
+
terminalCount += device.outputBuffers.size;
|
|
281
|
+
bufferedTerminalFrames += [...device.outputBuffers.values()].reduce((sum, buf) => sum + buf.length, 0);
|
|
282
|
+
if (!device.host || device.host.socket.readyState !== device.host.socket.OPEN) hostAbsentDevices++;
|
|
283
|
+
}
|
|
284
|
+
return {
|
|
285
|
+
devices: this.devices.size,
|
|
286
|
+
activeDevices: this.listActive().length,
|
|
287
|
+
clients: clientCount,
|
|
288
|
+
droppedClients: this.droppedClients,
|
|
289
|
+
hostAbsentDevices,
|
|
290
|
+
terminalsWithReplay: terminalCount,
|
|
291
|
+
bufferedTerminalFrames,
|
|
292
|
+
bufferedAgentFrames: 0,
|
|
293
|
+
};
|
|
294
|
+
}
|
|
295
|
+
|
|
260
296
|
setMetadata(
|
|
261
297
|
hostDeviceId: string,
|
|
262
298
|
_provider?: string,
|