@adhdev/daemon-standalone 0.9.82-rc.99 → 1.0.0
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/index.js +86588 -43350
- package/dist/index.js.map +1 -1
- package/package.json +7 -5
- package/public/assets/index-DuHZKmcF.js +121 -0
- package/public/assets/index-p-ehiI_L.css +1 -0
- package/public/assets/{terminal-D46M5EWH.js → terminal-CqjiB824.js} +21 -21
- package/public/assets/vendor-B6OqYKvq.js +2776 -0
- package/public/index.html +3 -3
- package/public/snake.html +229 -0
- package/vendor/mcp-server/index.js +6539 -2572
- package/vendor/mcp-server/index.js.map +1 -1
- package/vendor/mcp-server/package.json +3 -2
- package/vendor/session-host-daemon/index.d.mts +0 -10
- package/vendor/session-host-daemon/index.d.ts +0 -10
- package/vendor/session-host-daemon/index.js +305 -196
- package/vendor/session-host-daemon/index.js.map +1 -1
- package/vendor/session-host-daemon/index.mjs +299 -188
- package/vendor/session-host-daemon/index.mjs.map +1 -1
- package/public/assets/index-Bso1b8Lh.css +0 -1
- package/public/assets/index-DaIkPFUd.js +0 -99
- package/public/assets/vendor-CgiI0UIA.js +0 -2745
|
@@ -38,13 +38,13 @@ var import_crypto = require("crypto");
|
|
|
38
38
|
var fs4 = __toESM(require("fs"));
|
|
39
39
|
var os3 = __toESM(require("os"));
|
|
40
40
|
var path2 = __toESM(require("path"));
|
|
41
|
-
var
|
|
41
|
+
var import_session_host_core5 = require("@adhdev/session-host-core");
|
|
42
42
|
|
|
43
43
|
// src/server.ts
|
|
44
44
|
var import_events = require("events");
|
|
45
45
|
var fs3 = __toESM(require("fs"));
|
|
46
46
|
var net = __toESM(require("net"));
|
|
47
|
-
var
|
|
47
|
+
var import_session_host_core4 = require("@adhdev/session-host-core");
|
|
48
48
|
|
|
49
49
|
// src/runtime.ts
|
|
50
50
|
var fs = __toESM(require("fs"));
|
|
@@ -82,7 +82,8 @@ function formatXtermViewportPlain(terminal, rows) {
|
|
|
82
82
|
const lines = [];
|
|
83
83
|
for (let i = start; i < end; i++) {
|
|
84
84
|
const line = buffer.getLine(i);
|
|
85
|
-
|
|
85
|
+
const raw = line ? line.translateToString(false) : "";
|
|
86
|
+
lines.push(raw.replace(/\s+$/, ""));
|
|
86
87
|
}
|
|
87
88
|
let first = 0;
|
|
88
89
|
let last = lines.length;
|
|
@@ -145,6 +146,9 @@ function createXtermMirror(options) {
|
|
|
145
146
|
if (serializer) return serializeXtermViewport(terminal, serializer, currentRows);
|
|
146
147
|
return formatXtermViewportPlain(terminal, currentRows);
|
|
147
148
|
},
|
|
149
|
+
formatPlainText() {
|
|
150
|
+
return formatXtermViewportPlain(terminal, currentRows).replace(/\r\n/g, "\n");
|
|
151
|
+
},
|
|
148
152
|
getCursorPosition() {
|
|
149
153
|
const buffer = terminal.buffer.active;
|
|
150
154
|
return {
|
|
@@ -177,6 +181,9 @@ function normalizeGhosttyBinding(mod) {
|
|
|
177
181
|
formatVT() {
|
|
178
182
|
return viewportSnapshot.formatVT();
|
|
179
183
|
},
|
|
184
|
+
formatPlainText() {
|
|
185
|
+
return viewportSnapshot.formatPlainText();
|
|
186
|
+
},
|
|
180
187
|
getCursorPosition() {
|
|
181
188
|
if (typeof handle.getCursorPosition === "function") return handle.getCursorPosition();
|
|
182
189
|
return viewportSnapshot.getCursorPosition();
|
|
@@ -225,6 +232,10 @@ var PtySessionRuntime = class {
|
|
|
225
232
|
ptyProcess = null;
|
|
226
233
|
screenMirror = null;
|
|
227
234
|
pendingQueryScanTail = "";
|
|
235
|
+
terminalModeScanTail = "";
|
|
236
|
+
altScreen = false;
|
|
237
|
+
pasteMode = false;
|
|
238
|
+
scrollRegion;
|
|
228
239
|
onDataCallback;
|
|
229
240
|
onExitCallback;
|
|
230
241
|
constructor(options) {
|
|
@@ -232,6 +243,7 @@ var PtySessionRuntime = class {
|
|
|
232
243
|
this.payload = options.payload;
|
|
233
244
|
this.cols = (0, import_session_host_core.resolveSessionHostCols)(options.payload.cols);
|
|
234
245
|
this.rows = (0, import_session_host_core.resolveSessionHostRows)(options.payload.rows);
|
|
246
|
+
this.scrollRegion = { top: 0, bot: this.rows - 1 };
|
|
235
247
|
this.onDataCallback = options.onData;
|
|
236
248
|
this.onExitCallback = options.onExit;
|
|
237
249
|
}
|
|
@@ -263,6 +275,7 @@ var PtySessionRuntime = class {
|
|
|
263
275
|
});
|
|
264
276
|
this.ptyProcess.onData((data) => {
|
|
265
277
|
this.screenMirror?.write(data);
|
|
278
|
+
this.trackTerminalModes(data);
|
|
266
279
|
this.respondToTerminalQueries(data);
|
|
267
280
|
this.onDataCallback(data);
|
|
268
281
|
});
|
|
@@ -271,6 +284,7 @@ var PtySessionRuntime = class {
|
|
|
271
284
|
this.screenMirror?.dispose();
|
|
272
285
|
this.screenMirror = null;
|
|
273
286
|
this.pendingQueryScanTail = "";
|
|
287
|
+
this.terminalModeScanTail = "";
|
|
274
288
|
this.onExitCallback(exitCode ?? null);
|
|
275
289
|
});
|
|
276
290
|
return this.ptyProcess.pid;
|
|
@@ -282,6 +296,12 @@ var PtySessionRuntime = class {
|
|
|
282
296
|
resize(cols, rows) {
|
|
283
297
|
if (!this.ptyProcess) throw new Error(`Session not running: ${this.sessionId}`);
|
|
284
298
|
this.ptyProcess.resize(cols, rows);
|
|
299
|
+
this.cols = Math.max(1, cols | 0);
|
|
300
|
+
this.rows = Math.max(1, rows | 0);
|
|
301
|
+
this.scrollRegion = {
|
|
302
|
+
top: Math.min(this.scrollRegion.top, this.rows - 1),
|
|
303
|
+
bot: Math.min(Math.max(this.scrollRegion.top, this.scrollRegion.bot), this.rows - 1)
|
|
304
|
+
};
|
|
285
305
|
this.screenMirror?.resize(cols, rows);
|
|
286
306
|
}
|
|
287
307
|
stop() {
|
|
@@ -305,6 +325,55 @@ var PtySessionRuntime = class {
|
|
|
305
325
|
getSnapshotText() {
|
|
306
326
|
return this.screenMirror?.formatVT() || "";
|
|
307
327
|
}
|
|
328
|
+
getTerminalSnapshot() {
|
|
329
|
+
if (!this.ptyProcess || !this.screenMirror) {
|
|
330
|
+
throw new Error(`Session not running: ${this.sessionId}`);
|
|
331
|
+
}
|
|
332
|
+
const cursor = this.screenMirror.getCursorPosition();
|
|
333
|
+
return {
|
|
334
|
+
text: this.screenMirror.formatPlainText(),
|
|
335
|
+
state: {
|
|
336
|
+
cursor: {
|
|
337
|
+
row: Math.max(0, cursor.row | 0),
|
|
338
|
+
col: Math.max(0, cursor.col | 0)
|
|
339
|
+
},
|
|
340
|
+
altScreen: this.altScreen,
|
|
341
|
+
pasteMode: this.pasteMode,
|
|
342
|
+
rawMode: true,
|
|
343
|
+
scrollRegion: { ...this.scrollRegion },
|
|
344
|
+
cols: this.cols,
|
|
345
|
+
rows: this.rows
|
|
346
|
+
}
|
|
347
|
+
};
|
|
348
|
+
}
|
|
349
|
+
trackTerminalModes(data) {
|
|
350
|
+
if (!data) return;
|
|
351
|
+
const combined = this.terminalModeScanTail + data;
|
|
352
|
+
const privateMode = /\x1b\[\?([0-9;]*)([hl])/g;
|
|
353
|
+
let privateMatch;
|
|
354
|
+
while ((privateMatch = privateMode.exec(combined)) !== null) {
|
|
355
|
+
const enabled = privateMatch[2] === "h";
|
|
356
|
+
for (const mode of privateMatch[1].split(";")) {
|
|
357
|
+
if (mode === "47" || mode === "1047" || mode === "1049") this.altScreen = enabled;
|
|
358
|
+
if (mode === "2004") this.pasteMode = enabled;
|
|
359
|
+
}
|
|
360
|
+
}
|
|
361
|
+
const scrollRegion = /\x1b\[(\d*)(?:;(\d*))?r/g;
|
|
362
|
+
let scrollMatch;
|
|
363
|
+
while ((scrollMatch = scrollRegion.exec(combined)) !== null) {
|
|
364
|
+
const top = scrollMatch[1] ? Number.parseInt(scrollMatch[1], 10) - 1 : 0;
|
|
365
|
+
const bot = scrollMatch[2] ? Number.parseInt(scrollMatch[2], 10) - 1 : this.rows - 1;
|
|
366
|
+
this.scrollRegion = {
|
|
367
|
+
top: Math.max(0, Math.min(this.rows - 1, top)),
|
|
368
|
+
bot: Math.max(0, Math.min(this.rows - 1, bot))
|
|
369
|
+
};
|
|
370
|
+
if (this.scrollRegion.bot < this.scrollRegion.top) {
|
|
371
|
+
this.scrollRegion = { top: 0, bot: this.rows - 1 };
|
|
372
|
+
}
|
|
373
|
+
}
|
|
374
|
+
const lastEscape = combined.lastIndexOf("\x1B");
|
|
375
|
+
this.terminalModeScanTail = lastEscape >= 0 && combined.length - lastEscape < 64 ? combined.slice(lastEscape) : "";
|
|
376
|
+
}
|
|
308
377
|
respondToTerminalQueries(data) {
|
|
309
378
|
if (!this.ptyProcess || !this.screenMirror || !data) return;
|
|
310
379
|
const combined = this.pendingQueryScanTail + data;
|
|
@@ -369,11 +438,200 @@ var SessionHostStorage = class {
|
|
|
369
438
|
}
|
|
370
439
|
};
|
|
371
440
|
|
|
441
|
+
// src/session-diagnostics.ts
|
|
442
|
+
var import_session_host_core2 = require("@adhdev/session-host-core");
|
|
443
|
+
var MAX_RECENT_DIAGNOSTICS = 200;
|
|
444
|
+
function pushRecent(bucket, entry, max = MAX_RECENT_DIAGNOSTICS) {
|
|
445
|
+
bucket.push(entry);
|
|
446
|
+
if (bucket.length > max) {
|
|
447
|
+
bucket.splice(0, bucket.length - max);
|
|
448
|
+
}
|
|
449
|
+
}
|
|
450
|
+
function getSessionHostRecoveryLabel(record) {
|
|
451
|
+
const recoveryState = typeof record.meta?.runtimeRecoveryState === "string" ? String(record.meta.runtimeRecoveryState).trim() : "";
|
|
452
|
+
if (!recoveryState) return null;
|
|
453
|
+
if (recoveryState === "auto_resumed") return "restored after restart";
|
|
454
|
+
if (recoveryState === "resume_failed") return "restore failed";
|
|
455
|
+
if (recoveryState === "host_restart_interrupted") return "host restart interrupted";
|
|
456
|
+
if (recoveryState === "orphan_snapshot") return "snapshot recovered";
|
|
457
|
+
return recoveryState.replace(/_/g, " ");
|
|
458
|
+
}
|
|
459
|
+
function getSessionSurfaceKind(record) {
|
|
460
|
+
if (["starting", "running", "stopping", "interrupted"].includes(record.lifecycle)) {
|
|
461
|
+
return "live_runtime";
|
|
462
|
+
}
|
|
463
|
+
if ((record.lifecycle === "stopped" || record.lifecycle === "failed") && (record.meta?.restoredFromStorage === true || getSessionHostRecoveryLabel(record))) {
|
|
464
|
+
return "recovery_snapshot";
|
|
465
|
+
}
|
|
466
|
+
return "inactive_record";
|
|
467
|
+
}
|
|
468
|
+
function annotateSessionSurface(record) {
|
|
469
|
+
return {
|
|
470
|
+
...record,
|
|
471
|
+
surfaceKind: getSessionSurfaceKind(record)
|
|
472
|
+
};
|
|
473
|
+
}
|
|
474
|
+
function sanitizeDiagnosticsRecord(record) {
|
|
475
|
+
return {
|
|
476
|
+
...record,
|
|
477
|
+
launchCommand: {
|
|
478
|
+
command: record.launchCommand.command,
|
|
479
|
+
args: Array.isArray(record.launchCommand.args) ? [...record.launchCommand.args] : []
|
|
480
|
+
}
|
|
481
|
+
};
|
|
482
|
+
}
|
|
483
|
+
function buildHostDiagnostics(params) {
|
|
484
|
+
const limit = Math.max(1, Math.min(200, Number(params.payload?.limit) || 50));
|
|
485
|
+
const allSessions = params.payload?.includeSessions === false ? void 0 : params.sessions.map((record) => annotateSessionSurface(record)).map((record) => sanitizeDiagnosticsRecord(record));
|
|
486
|
+
const liveRuntimes = allSessions?.filter((record) => record.surfaceKind === "live_runtime");
|
|
487
|
+
const recoverySnapshots = allSessions?.filter((record) => record.surfaceKind === "recovery_snapshot").slice(0, limit);
|
|
488
|
+
const inactiveRecords = allSessions?.filter((record) => record.surfaceKind === "inactive_record").slice(0, limit);
|
|
489
|
+
const sessions = allSessions ? [
|
|
490
|
+
...liveRuntimes || [],
|
|
491
|
+
...recoverySnapshots || [],
|
|
492
|
+
...inactiveRecords || []
|
|
493
|
+
] : void 0;
|
|
494
|
+
return {
|
|
495
|
+
hostStartedAt: params.hostStartedAt,
|
|
496
|
+
endpoint: params.endpointPath,
|
|
497
|
+
runtimeCount: params.runtimeCount,
|
|
498
|
+
supportedRequestTypes: [...import_session_host_core2.SESSION_HOST_SUPPORTED_REQUEST_TYPES],
|
|
499
|
+
sessions,
|
|
500
|
+
liveRuntimes,
|
|
501
|
+
recoverySnapshots,
|
|
502
|
+
inactiveRecords,
|
|
503
|
+
recentLogs: params.recentLogs.slice(-limit),
|
|
504
|
+
recentRequests: params.recentRequests.slice(-limit),
|
|
505
|
+
recentTransitions: params.recentTransitions.slice(-limit)
|
|
506
|
+
};
|
|
507
|
+
}
|
|
508
|
+
|
|
509
|
+
// src/session-lifecycle.ts
|
|
510
|
+
var import_session_host_core3 = require("@adhdev/session-host-core");
|
|
511
|
+
function compareDuplicateCandidates(a, b) {
|
|
512
|
+
const score = (record) => {
|
|
513
|
+
const lifecycleScore = record.lifecycle === "running" ? 4 : record.lifecycle === "starting" ? 3 : record.lifecycle === "stopping" ? 2 : record.lifecycle === "interrupted" ? 1 : 0;
|
|
514
|
+
return [
|
|
515
|
+
lifecycleScore,
|
|
516
|
+
record.writeOwner ? 1 : 0,
|
|
517
|
+
Array.isArray(record.attachedClients) ? record.attachedClients.length : 0,
|
|
518
|
+
record.lastActivityAt || 0,
|
|
519
|
+
record.startedAt || 0,
|
|
520
|
+
record.createdAt || 0
|
|
521
|
+
];
|
|
522
|
+
};
|
|
523
|
+
const aScore = score(a);
|
|
524
|
+
const bScore = score(b);
|
|
525
|
+
for (let i = 0; i < aScore.length; i += 1) {
|
|
526
|
+
if (aScore[i] === bScore[i]) continue;
|
|
527
|
+
return bScore[i] - aScore[i];
|
|
528
|
+
}
|
|
529
|
+
return 0;
|
|
530
|
+
}
|
|
531
|
+
function planDuplicatePrune(sessions, filters) {
|
|
532
|
+
const candidates = sessions.filter((record) => ["starting", "running", "stopping", "interrupted"].includes(record.lifecycle)).filter((record) => !filters.providerFilter || record.providerType === filters.providerFilter).filter((record) => !filters.workspaceFilter || record.workspace === filters.workspaceFilter);
|
|
533
|
+
const groups = /* @__PURE__ */ new Map();
|
|
534
|
+
for (const record of candidates) {
|
|
535
|
+
const providerSessionId = typeof record.meta?.providerSessionId === "string" ? String(record.meta.providerSessionId).trim() : "";
|
|
536
|
+
if (!providerSessionId) continue;
|
|
537
|
+
const bindingKey = `${record.providerType}::${record.workspace}::${providerSessionId}`;
|
|
538
|
+
const bucket = groups.get(bindingKey) || [];
|
|
539
|
+
bucket.push(record);
|
|
540
|
+
groups.set(bindingKey, bucket);
|
|
541
|
+
}
|
|
542
|
+
const duplicateGroups = [];
|
|
543
|
+
const keptSessionIds = [];
|
|
544
|
+
const duplicateRecords = [];
|
|
545
|
+
for (const [bindingKey, records] of groups.entries()) {
|
|
546
|
+
if (records.length < 2) continue;
|
|
547
|
+
const sorted = [...records].sort((a, b) => compareDuplicateCandidates(a, b));
|
|
548
|
+
const kept = sorted[0];
|
|
549
|
+
const duplicates = sorted.slice(1);
|
|
550
|
+
const providerSessionId = typeof kept.meta?.providerSessionId === "string" ? String(kept.meta.providerSessionId) : "";
|
|
551
|
+
duplicateGroups.push({
|
|
552
|
+
bindingKey,
|
|
553
|
+
providerType: kept.providerType,
|
|
554
|
+
workspace: kept.workspace,
|
|
555
|
+
providerSessionId,
|
|
556
|
+
keptSessionId: kept.sessionId,
|
|
557
|
+
prunedSessionIds: duplicates.map((record) => record.sessionId)
|
|
558
|
+
});
|
|
559
|
+
keptSessionIds.push(kept.sessionId);
|
|
560
|
+
for (const duplicate of duplicates) {
|
|
561
|
+
duplicateRecords.push(duplicate);
|
|
562
|
+
}
|
|
563
|
+
}
|
|
564
|
+
return { duplicateGroups, keptSessionIds, duplicateRecords };
|
|
565
|
+
}
|
|
566
|
+
function buildPayloadFromRecord(record) {
|
|
567
|
+
return {
|
|
568
|
+
sessionId: record.sessionId,
|
|
569
|
+
runtimeKey: record.runtimeKey,
|
|
570
|
+
displayName: record.displayName,
|
|
571
|
+
providerType: record.providerType,
|
|
572
|
+
category: record.category,
|
|
573
|
+
workspace: record.workspace,
|
|
574
|
+
launchCommand: record.launchCommand,
|
|
575
|
+
cols: (0, import_session_host_core3.resolveSessionHostCols)(typeof record.meta?.sessionHostCols === "number" ? record.meta.sessionHostCols : void 0),
|
|
576
|
+
rows: (0, import_session_host_core3.resolveSessionHostRows)(typeof record.meta?.sessionHostRows === "number" ? record.meta.sessionHostRows : void 0),
|
|
577
|
+
meta: record.meta
|
|
578
|
+
};
|
|
579
|
+
}
|
|
580
|
+
function buildRecoveredRecord(persisted) {
|
|
581
|
+
const wasLiveRuntime = !["stopped", "failed"].includes(persisted.record.lifecycle);
|
|
582
|
+
const hadAttachedClients = Array.isArray(persisted.record.attachedClients) && persisted.record.attachedClients.length > 0;
|
|
583
|
+
const hadWriteOwner = !!persisted.record.writeOwner;
|
|
584
|
+
const hadRecoveryInterest = hadAttachedClients || hadWriteOwner;
|
|
585
|
+
const recoveredRecord = {
|
|
586
|
+
...persisted.record,
|
|
587
|
+
attachedClients: [],
|
|
588
|
+
writeOwner: null,
|
|
589
|
+
lifecycle: wasLiveRuntime ? "stopped" : persisted.record.lifecycle,
|
|
590
|
+
lastActivityAt: Date.now(),
|
|
591
|
+
meta: {
|
|
592
|
+
...persisted.record.meta || {},
|
|
593
|
+
restoredFromStorage: true,
|
|
594
|
+
runtimeRecoveryState: wasLiveRuntime ? "orphan_snapshot" : "snapshot",
|
|
595
|
+
runtimeHadAttachedClientsAtCrash: hadAttachedClients,
|
|
596
|
+
runtimeHadWriteOwnerAtCrash: hadWriteOwner,
|
|
597
|
+
runtimeAutoResumeSkipped: wasLiveRuntime && hadRecoveryInterest
|
|
598
|
+
}
|
|
599
|
+
};
|
|
600
|
+
return { recoveredRecord, wasLiveRuntime, hadRecoveryInterest };
|
|
601
|
+
}
|
|
602
|
+
|
|
603
|
+
// src/session-protocol.ts
|
|
604
|
+
function getRequestSessionId(request) {
|
|
605
|
+
const payload = request.payload;
|
|
606
|
+
return typeof payload?.sessionId === "string" ? payload.sessionId : void 0;
|
|
607
|
+
}
|
|
608
|
+
function getRequestClientId(request) {
|
|
609
|
+
const payload = request.payload;
|
|
610
|
+
return typeof payload?.clientId === "string" ? payload.clientId : void 0;
|
|
611
|
+
}
|
|
612
|
+
function mergeRuntimeSnapshot(base, record, opts) {
|
|
613
|
+
const cols = typeof record?.meta?.sessionHostCols === "number" ? record.meta.sessionHostCols : 80;
|
|
614
|
+
const rows = typeof record?.meta?.sessionHostRows === "number" ? record.meta.sessionHostRows : 24;
|
|
615
|
+
if (typeof opts.sinceSeq === "number" || !opts.runtimeText) {
|
|
616
|
+
return {
|
|
617
|
+
...base,
|
|
618
|
+
cols,
|
|
619
|
+
rows
|
|
620
|
+
};
|
|
621
|
+
}
|
|
622
|
+
return {
|
|
623
|
+
...base,
|
|
624
|
+
text: opts.runtimeText,
|
|
625
|
+
truncated: false,
|
|
626
|
+
cols,
|
|
627
|
+
rows
|
|
628
|
+
};
|
|
629
|
+
}
|
|
630
|
+
|
|
372
631
|
// src/server.ts
|
|
373
|
-
var SessionHostServer = class
|
|
374
|
-
static MAX_RECENT_DIAGNOSTICS = 200;
|
|
632
|
+
var SessionHostServer = class extends import_events.EventEmitter {
|
|
375
633
|
endpoint;
|
|
376
|
-
registry = new
|
|
634
|
+
registry = new import_session_host_core4.SessionHostRegistry();
|
|
377
635
|
runtimes = /* @__PURE__ */ new Map();
|
|
378
636
|
storage;
|
|
379
637
|
ipcServer = null;
|
|
@@ -390,7 +648,7 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
390
648
|
lastNoOutputInputWarnAt = /* @__PURE__ */ new Map();
|
|
391
649
|
constructor(options = {}) {
|
|
392
650
|
super();
|
|
393
|
-
this.endpoint = options.endpoint || (0,
|
|
651
|
+
this.endpoint = options.endpoint || (0, import_session_host_core4.getDefaultSessionHostEndpoint)(options.appName || "adhdev");
|
|
394
652
|
this.storage = new SessionHostStorage({ appName: options.appName || "adhdev" });
|
|
395
653
|
}
|
|
396
654
|
async start() {
|
|
@@ -415,7 +673,7 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
415
673
|
} catch {
|
|
416
674
|
}
|
|
417
675
|
});
|
|
418
|
-
socket.on("data", (0,
|
|
676
|
+
socket.on("data", (0, import_session_host_core4.createLineParser)((envelope) => {
|
|
419
677
|
if (envelope.kind !== "request") return;
|
|
420
678
|
void this.handleIncomingRequest(socket, envelope);
|
|
421
679
|
}));
|
|
@@ -518,6 +776,8 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
518
776
|
}
|
|
519
777
|
case "get_snapshot":
|
|
520
778
|
return { success: true, result: this.getSnapshot(request.payload.sessionId, request.payload.sinceSeq) };
|
|
779
|
+
case "get_terminal_snapshot":
|
|
780
|
+
return { success: true, result: this.requireRuntime(request.payload.sessionId).getTerminalSnapshot() };
|
|
521
781
|
case "get_host_diagnostics":
|
|
522
782
|
return { success: true, result: this.getHostDiagnostics(request.payload) };
|
|
523
783
|
case "clear_session_buffer": {
|
|
@@ -618,7 +878,7 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
618
878
|
if (this.runtimes.has(request.payload.sessionId)) {
|
|
619
879
|
return { success: true, result: existing };
|
|
620
880
|
}
|
|
621
|
-
const resumed = this.startRuntime(existing,
|
|
881
|
+
const resumed = this.startRuntime(existing, buildPayloadFromRecord(existing), "session_resumed");
|
|
622
882
|
this.recordRuntimeTransition(request.payload.sessionId, "resume_session", resumed.lifecycle, void 0, true);
|
|
623
883
|
return { success: true, result: resumed };
|
|
624
884
|
}
|
|
@@ -700,7 +960,7 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
700
960
|
sessions.add(sessionId);
|
|
701
961
|
}
|
|
702
962
|
async handleIncomingRequest(socket, envelope) {
|
|
703
|
-
const sessionId =
|
|
963
|
+
const sessionId = getRequestSessionId(envelope.request);
|
|
704
964
|
if (sessionId && (envelope.request.type === "create_session" || envelope.request.type === "attach_session")) {
|
|
705
965
|
this.subscribeSocketToSession(socket, sessionId);
|
|
706
966
|
}
|
|
@@ -714,13 +974,13 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
714
974
|
timestamp: startedAt,
|
|
715
975
|
requestId: envelope.requestId,
|
|
716
976
|
type: envelope.request.type,
|
|
717
|
-
sessionId:
|
|
718
|
-
clientId:
|
|
977
|
+
sessionId: getRequestSessionId(envelope.request),
|
|
978
|
+
clientId: getRequestClientId(envelope.request),
|
|
719
979
|
success: response.success,
|
|
720
980
|
durationMs: Math.max(0, Date.now() - startedAt),
|
|
721
981
|
error: response.success ? void 0 : response.error
|
|
722
982
|
});
|
|
723
|
-
this.writeEnvelopeSafely(socket, (0,
|
|
983
|
+
this.writeEnvelopeSafely(socket, (0, import_session_host_core4.createResponseEnvelope)(envelope.requestId, response));
|
|
724
984
|
}
|
|
725
985
|
writeEnvelopeSafely(socket, envelope) {
|
|
726
986
|
if (socket.destroyed || !socket.writable || socket.writableEnded) {
|
|
@@ -758,79 +1018,24 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
758
1018
|
const record = this.registry.getSession(sessionId);
|
|
759
1019
|
if (!record) return;
|
|
760
1020
|
const snapshot = this.getSnapshot(sessionId);
|
|
761
|
-
|
|
762
|
-
|
|
763
|
-
|
|
764
|
-
|
|
765
|
-
|
|
766
|
-
if (recoveryState === "auto_resumed") return "restored after restart";
|
|
767
|
-
if (recoveryState === "resume_failed") return "restore failed";
|
|
768
|
-
if (recoveryState === "host_restart_interrupted") return "host restart interrupted";
|
|
769
|
-
if (recoveryState === "orphan_snapshot") return "snapshot recovered";
|
|
770
|
-
return recoveryState.replace(/_/g, " ");
|
|
771
|
-
}
|
|
772
|
-
getSessionSurfaceKind(record) {
|
|
773
|
-
if (["starting", "running", "stopping", "interrupted"].includes(record.lifecycle)) {
|
|
774
|
-
return "live_runtime";
|
|
775
|
-
}
|
|
776
|
-
if ((record.lifecycle === "stopped" || record.lifecycle === "failed") && (record.meta?.restoredFromStorage === true || this.getSessionHostRecoveryLabel(record))) {
|
|
777
|
-
return "recovery_snapshot";
|
|
1021
|
+
try {
|
|
1022
|
+
this.storage.save(record, snapshot);
|
|
1023
|
+
} catch (error) {
|
|
1024
|
+
const code = typeof error?.code === "string" ? error.code : "persist_failed";
|
|
1025
|
+
console.error(`[session-host] Persist failed for ${sessionId}: ${code}: ${error?.message || error}`);
|
|
778
1026
|
}
|
|
779
|
-
return "inactive_record";
|
|
780
|
-
}
|
|
781
|
-
annotateSessionSurface(record) {
|
|
782
|
-
return {
|
|
783
|
-
...record,
|
|
784
|
-
surfaceKind: this.getSessionSurfaceKind(record)
|
|
785
|
-
};
|
|
786
|
-
}
|
|
787
|
-
sanitizeDiagnosticsRecord(record) {
|
|
788
|
-
return {
|
|
789
|
-
...record,
|
|
790
|
-
launchCommand: {
|
|
791
|
-
command: record.launchCommand.command,
|
|
792
|
-
args: Array.isArray(record.launchCommand.args) ? [...record.launchCommand.args] : []
|
|
793
|
-
}
|
|
794
|
-
};
|
|
795
1027
|
}
|
|
796
1028
|
getHostDiagnostics(payload) {
|
|
797
|
-
|
|
798
|
-
|
|
799
|
-
const liveRuntimes = allSessions?.filter((record) => record.surfaceKind === "live_runtime");
|
|
800
|
-
const recoverySnapshots = allSessions?.filter((record) => record.surfaceKind === "recovery_snapshot").slice(0, limit);
|
|
801
|
-
const inactiveRecords = allSessions?.filter((record) => record.surfaceKind === "inactive_record").slice(0, limit);
|
|
802
|
-
const sessions = allSessions ? [
|
|
803
|
-
...liveRuntimes || [],
|
|
804
|
-
...recoverySnapshots || [],
|
|
805
|
-
...inactiveRecords || []
|
|
806
|
-
] : void 0;
|
|
807
|
-
return {
|
|
1029
|
+
return buildHostDiagnostics({
|
|
1030
|
+
payload,
|
|
808
1031
|
hostStartedAt: this.startedAt,
|
|
809
|
-
|
|
1032
|
+
endpointPath: this.endpoint.path,
|
|
810
1033
|
runtimeCount: this.runtimes.size,
|
|
811
|
-
|
|
812
|
-
|
|
813
|
-
|
|
814
|
-
|
|
815
|
-
|
|
816
|
-
recentLogs: this.recentLogs.slice(-limit),
|
|
817
|
-
recentRequests: this.recentRequests.slice(-limit),
|
|
818
|
-
recentTransitions: this.recentTransitions.slice(-limit)
|
|
819
|
-
};
|
|
820
|
-
}
|
|
821
|
-
getRequestSessionId(request) {
|
|
822
|
-
const payload = request.payload;
|
|
823
|
-
return typeof payload?.sessionId === "string" ? payload.sessionId : void 0;
|
|
824
|
-
}
|
|
825
|
-
getRequestClientId(request) {
|
|
826
|
-
const payload = request.payload;
|
|
827
|
-
return typeof payload?.clientId === "string" ? payload.clientId : void 0;
|
|
828
|
-
}
|
|
829
|
-
pushRecent(bucket, entry) {
|
|
830
|
-
bucket.push(entry);
|
|
831
|
-
if (bucket.length > _SessionHostServer.MAX_RECENT_DIAGNOSTICS) {
|
|
832
|
-
bucket.splice(0, bucket.length - _SessionHostServer.MAX_RECENT_DIAGNOSTICS);
|
|
833
|
-
}
|
|
1034
|
+
sessions: this.registry.listSessions(),
|
|
1035
|
+
recentLogs: this.recentLogs,
|
|
1036
|
+
recentRequests: this.recentRequests,
|
|
1037
|
+
recentTransitions: this.recentTransitions
|
|
1038
|
+
});
|
|
834
1039
|
}
|
|
835
1040
|
recordHostLog(level, message, sessionId, data) {
|
|
836
1041
|
const entry = {
|
|
@@ -840,12 +1045,12 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
840
1045
|
sessionId,
|
|
841
1046
|
data
|
|
842
1047
|
};
|
|
843
|
-
|
|
1048
|
+
pushRecent(this.recentLogs, entry);
|
|
844
1049
|
this.emitEvent({ type: "host_log", entry });
|
|
845
1050
|
this.emit("log", `[${level}] ${message}`);
|
|
846
1051
|
}
|
|
847
1052
|
recordRequestTrace(trace) {
|
|
848
|
-
|
|
1053
|
+
pushRecent(this.recentRequests, trace);
|
|
849
1054
|
this.emitEvent({ type: "request_trace", trace });
|
|
850
1055
|
if (!trace.success) {
|
|
851
1056
|
this.recordHostLog(
|
|
@@ -915,7 +1120,7 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
915
1120
|
success,
|
|
916
1121
|
error
|
|
917
1122
|
};
|
|
918
|
-
|
|
1123
|
+
pushRecent(this.recentTransitions, transition);
|
|
919
1124
|
this.emitEvent({ type: "runtime_transition", transition });
|
|
920
1125
|
}
|
|
921
1126
|
waitForRuntimeExit(sessionId, timeoutMs = 5e3) {
|
|
@@ -951,29 +1156,8 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
951
1156
|
getSnapshot(sessionId, sinceSeq) {
|
|
952
1157
|
const snapshot = this.registry.getSnapshot(sessionId, sinceSeq);
|
|
953
1158
|
const record = this.registry.getSession(sessionId);
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
...snapshot,
|
|
957
|
-
cols: typeof record?.meta?.sessionHostCols === "number" ? record.meta.sessionHostCols : 80,
|
|
958
|
-
rows: typeof record?.meta?.sessionHostRows === "number" ? record.meta.sessionHostRows : 24
|
|
959
|
-
};
|
|
960
|
-
}
|
|
961
|
-
const runtime = this.runtimes.get(sessionId);
|
|
962
|
-
const runtimeText = runtime?.getSnapshotText?.() || "";
|
|
963
|
-
if (!runtimeText) {
|
|
964
|
-
return {
|
|
965
|
-
...snapshot,
|
|
966
|
-
cols: typeof record?.meta?.sessionHostCols === "number" ? record.meta.sessionHostCols : 80,
|
|
967
|
-
rows: typeof record?.meta?.sessionHostRows === "number" ? record.meta.sessionHostRows : 24
|
|
968
|
-
};
|
|
969
|
-
}
|
|
970
|
-
return {
|
|
971
|
-
...snapshot,
|
|
972
|
-
text: runtimeText,
|
|
973
|
-
truncated: false,
|
|
974
|
-
cols: typeof record?.meta?.sessionHostCols === "number" ? record.meta.sessionHostCols : 80,
|
|
975
|
-
rows: typeof record?.meta?.sessionHostRows === "number" ? record.meta.sessionHostRows : 24
|
|
976
|
-
};
|
|
1159
|
+
const runtimeText = typeof sinceSeq === "number" ? "" : this.runtimes.get(sessionId)?.getSnapshotText?.() || "";
|
|
1160
|
+
return mergeRuntimeSnapshot(snapshot, record, { sinceSeq, runtimeText });
|
|
977
1161
|
}
|
|
978
1162
|
flushAllPersistence() {
|
|
979
1163
|
for (const sessionId of this.runtimes.keys()) {
|
|
@@ -996,7 +1180,7 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
996
1180
|
await this.waitForRuntimeExit(sessionId);
|
|
997
1181
|
}
|
|
998
1182
|
const latest = this.registry.getSession(sessionId) || existing;
|
|
999
|
-
const restarted = this.startRuntime(latest,
|
|
1183
|
+
const restarted = this.startRuntime(latest, buildPayloadFromRecord(latest), "session_resumed");
|
|
1000
1184
|
this.recordRuntimeTransition(sessionId, "restart_completed", restarted.lifecycle, void 0, true);
|
|
1001
1185
|
return restarted;
|
|
1002
1186
|
}
|
|
@@ -1004,36 +1188,13 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
1004
1188
|
const providerFilter = typeof payload?.providerType === "string" ? payload.providerType.trim() : "";
|
|
1005
1189
|
const workspaceFilter = typeof payload?.workspace === "string" ? payload.workspace.trim() : "";
|
|
1006
1190
|
const dryRun = payload?.dryRun === true;
|
|
1007
|
-
const
|
|
1008
|
-
|
|
1009
|
-
|
|
1010
|
-
|
|
1011
|
-
if (!providerSessionId) continue;
|
|
1012
|
-
const bindingKey = `${record.providerType}::${record.workspace}::${providerSessionId}`;
|
|
1013
|
-
const bucket = groups.get(bindingKey) || [];
|
|
1014
|
-
bucket.push(record);
|
|
1015
|
-
groups.set(bindingKey, bucket);
|
|
1016
|
-
}
|
|
1017
|
-
const duplicateGroups = [];
|
|
1018
|
-
const keptSessionIds = [];
|
|
1191
|
+
const { duplicateGroups, keptSessionIds, duplicateRecords } = planDuplicatePrune(
|
|
1192
|
+
this.registry.listSessions(),
|
|
1193
|
+
{ providerFilter, workspaceFilter }
|
|
1194
|
+
);
|
|
1019
1195
|
const prunedSessionIds = [];
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
const sorted = [...records].sort((a, b) => this.compareDuplicateCandidates(a, b));
|
|
1023
|
-
const kept = sorted[0];
|
|
1024
|
-
const duplicates = sorted.slice(1);
|
|
1025
|
-
const providerSessionId = typeof kept.meta?.providerSessionId === "string" ? String(kept.meta.providerSessionId) : "";
|
|
1026
|
-
duplicateGroups.push({
|
|
1027
|
-
bindingKey,
|
|
1028
|
-
providerType: kept.providerType,
|
|
1029
|
-
workspace: kept.workspace,
|
|
1030
|
-
providerSessionId,
|
|
1031
|
-
keptSessionId: kept.sessionId,
|
|
1032
|
-
prunedSessionIds: duplicates.map((record) => record.sessionId)
|
|
1033
|
-
});
|
|
1034
|
-
keptSessionIds.push(kept.sessionId);
|
|
1035
|
-
if (dryRun) continue;
|
|
1036
|
-
for (const duplicate of duplicates) {
|
|
1196
|
+
if (!dryRun) {
|
|
1197
|
+
for (const duplicate of duplicateRecords) {
|
|
1037
1198
|
await this.pruneDuplicateRuntime(duplicate);
|
|
1038
1199
|
prunedSessionIds.push(duplicate.sessionId);
|
|
1039
1200
|
}
|
|
@@ -1061,25 +1222,7 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
1061
1222
|
const states = this.storage.loadAll();
|
|
1062
1223
|
let skippedAutoResumeSessions = 0;
|
|
1063
1224
|
for (const persisted of states) {
|
|
1064
|
-
const wasLiveRuntime =
|
|
1065
|
-
const hadAttachedClients = Array.isArray(persisted.record.attachedClients) && persisted.record.attachedClients.length > 0;
|
|
1066
|
-
const hadWriteOwner = !!persisted.record.writeOwner;
|
|
1067
|
-
const hadRecoveryInterest = hadAttachedClients || hadWriteOwner;
|
|
1068
|
-
const recoveredRecord = {
|
|
1069
|
-
...persisted.record,
|
|
1070
|
-
attachedClients: [],
|
|
1071
|
-
writeOwner: null,
|
|
1072
|
-
lifecycle: wasLiveRuntime ? "stopped" : persisted.record.lifecycle,
|
|
1073
|
-
lastActivityAt: Date.now(),
|
|
1074
|
-
meta: {
|
|
1075
|
-
...persisted.record.meta || {},
|
|
1076
|
-
restoredFromStorage: true,
|
|
1077
|
-
runtimeRecoveryState: wasLiveRuntime ? "orphan_snapshot" : "snapshot",
|
|
1078
|
-
runtimeHadAttachedClientsAtCrash: hadAttachedClients,
|
|
1079
|
-
runtimeHadWriteOwnerAtCrash: hadWriteOwner,
|
|
1080
|
-
runtimeAutoResumeSkipped: wasLiveRuntime && hadRecoveryInterest
|
|
1081
|
-
}
|
|
1082
|
-
};
|
|
1225
|
+
const { recoveredRecord, wasLiveRuntime, hadRecoveryInterest } = buildRecoveredRecord(persisted);
|
|
1083
1226
|
this.registry.restoreSession(recoveredRecord, persisted.snapshot);
|
|
1084
1227
|
this.storage.save(recoveredRecord, persisted.snapshot);
|
|
1085
1228
|
if (wasLiveRuntime && hadRecoveryInterest) {
|
|
@@ -1090,26 +1233,6 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
1090
1233
|
this.recordHostLog("warn", `session host restored ${skippedAutoResumeSessions} live runtime snapshot(s) without auto-resume`);
|
|
1091
1234
|
}
|
|
1092
1235
|
}
|
|
1093
|
-
compareDuplicateCandidates(a, b) {
|
|
1094
|
-
const score = (record) => {
|
|
1095
|
-
const lifecycleScore = record.lifecycle === "running" ? 4 : record.lifecycle === "starting" ? 3 : record.lifecycle === "stopping" ? 2 : record.lifecycle === "interrupted" ? 1 : 0;
|
|
1096
|
-
return [
|
|
1097
|
-
lifecycleScore,
|
|
1098
|
-
record.writeOwner ? 1 : 0,
|
|
1099
|
-
Array.isArray(record.attachedClients) ? record.attachedClients.length : 0,
|
|
1100
|
-
record.lastActivityAt || 0,
|
|
1101
|
-
record.startedAt || 0,
|
|
1102
|
-
record.createdAt || 0
|
|
1103
|
-
];
|
|
1104
|
-
};
|
|
1105
|
-
const aScore = score(a);
|
|
1106
|
-
const bScore = score(b);
|
|
1107
|
-
for (let i = 0; i < aScore.length; i += 1) {
|
|
1108
|
-
if (aScore[i] === bScore[i]) continue;
|
|
1109
|
-
return bScore[i] - aScore[i];
|
|
1110
|
-
}
|
|
1111
|
-
return 0;
|
|
1112
|
-
}
|
|
1113
1236
|
async pruneDuplicateRuntime(record) {
|
|
1114
1237
|
const providerSessionId = typeof record.meta?.providerSessionId === "string" ? String(record.meta.providerSessionId) : void 0;
|
|
1115
1238
|
this.recordRuntimeTransition(
|
|
@@ -1130,20 +1253,6 @@ var SessionHostServer = class _SessionHostServer extends import_events.EventEmit
|
|
|
1130
1253
|
this.registry.deleteSession(record.sessionId);
|
|
1131
1254
|
this.storage.remove(record.sessionId);
|
|
1132
1255
|
}
|
|
1133
|
-
buildPayloadFromRecord(record) {
|
|
1134
|
-
return {
|
|
1135
|
-
sessionId: record.sessionId,
|
|
1136
|
-
runtimeKey: record.runtimeKey,
|
|
1137
|
-
displayName: record.displayName,
|
|
1138
|
-
providerType: record.providerType,
|
|
1139
|
-
category: record.category,
|
|
1140
|
-
workspace: record.workspace,
|
|
1141
|
-
launchCommand: record.launchCommand,
|
|
1142
|
-
cols: (0, import_session_host_core2.resolveSessionHostCols)(typeof record.meta?.sessionHostCols === "number" ? record.meta.sessionHostCols : void 0),
|
|
1143
|
-
rows: (0, import_session_host_core2.resolveSessionHostRows)(typeof record.meta?.sessionHostRows === "number" ? record.meta.sessionHostRows : void 0),
|
|
1144
|
-
meta: record.meta
|
|
1145
|
-
};
|
|
1146
|
-
}
|
|
1147
1256
|
startRuntime(record, payload, startEventType) {
|
|
1148
1257
|
const runtime = new PtySessionRuntime({
|
|
1149
1258
|
sessionId: record.sessionId,
|
|
@@ -1233,7 +1342,7 @@ async function runServer() {
|
|
|
1233
1342
|
});
|
|
1234
1343
|
}
|
|
1235
1344
|
async function listRuntimes(showAll = false) {
|
|
1236
|
-
const client = new
|
|
1345
|
+
const client = new import_session_host_core5.SessionHostClient({ endpoint: (0, import_session_host_core5.getDefaultSessionHostEndpoint)(SESSION_HOST_APP_NAME) });
|
|
1237
1346
|
try {
|
|
1238
1347
|
const response = await client.request({
|
|
1239
1348
|
type: "list_sessions",
|
|
@@ -1252,7 +1361,7 @@ async function listRuntimes(showAll = false) {
|
|
|
1252
1361
|
console.log([
|
|
1253
1362
|
runtime.runtimeKey,
|
|
1254
1363
|
runtime.lifecycle,
|
|
1255
|
-
(0,
|
|
1364
|
+
(0, import_session_host_core5.formatRuntimeOwner)(runtime),
|
|
1256
1365
|
runtime.workspaceLabel,
|
|
1257
1366
|
runtime.sessionId,
|
|
1258
1367
|
runtime.displayName
|
|
@@ -1264,7 +1373,7 @@ async function listRuntimes(showAll = false) {
|
|
|
1264
1373
|
}
|
|
1265
1374
|
}
|
|
1266
1375
|
async function attachRuntime(target, readOnly = false, takeover = false) {
|
|
1267
|
-
const client = new
|
|
1376
|
+
const client = new import_session_host_core5.SessionHostClient({ endpoint: (0, import_session_host_core5.getDefaultSessionHostEndpoint)(SESSION_HOST_APP_NAME) });
|
|
1268
1377
|
const clientId = `local-terminal-${process.pid}-${(0, import_crypto.randomUUID)().slice(0, 8)}`;
|
|
1269
1378
|
let lastSeq = 0;
|
|
1270
1379
|
let restoredRawMode = false;
|
|
@@ -1359,7 +1468,7 @@ async function attachRuntime(target, readOnly = false, takeover = false) {
|
|
|
1359
1468
|
if (!listResponse.success || !listResponse.result) {
|
|
1360
1469
|
throw new Error(listResponse.error || "Failed to list runtimes");
|
|
1361
1470
|
}
|
|
1362
|
-
let runtimeRecord = (0,
|
|
1471
|
+
let runtimeRecord = (0, import_session_host_core5.resolveAttachableRuntimeRecord)(listResponse.result, target);
|
|
1363
1472
|
runtimeId = runtimeRecord.sessionId;
|
|
1364
1473
|
if (runtimeRecord.lifecycle === "interrupted" && !readOnly) {
|
|
1365
1474
|
const resumeResponse = await client.request({
|
|
@@ -1502,13 +1611,13 @@ async function main() {
|
|
|
1502
1611
|
if (!target) {
|
|
1503
1612
|
throw new Error("runtime target is required: adhdev-sessiond resume <runtimeId|runtimeKey>");
|
|
1504
1613
|
}
|
|
1505
|
-
const client = new
|
|
1614
|
+
const client = new import_session_host_core5.SessionHostClient({ endpoint: (0, import_session_host_core5.getDefaultSessionHostEndpoint)(SESSION_HOST_APP_NAME) });
|
|
1506
1615
|
try {
|
|
1507
1616
|
const listResponse = await client.request({ type: "list_sessions", payload: {} });
|
|
1508
1617
|
if (!listResponse.success || !listResponse.result) {
|
|
1509
1618
|
throw new Error(listResponse.error || "Failed to list runtimes");
|
|
1510
1619
|
}
|
|
1511
|
-
const runtimeRecord = (0,
|
|
1620
|
+
const runtimeRecord = (0, import_session_host_core5.resolveRuntimeRecord)(listResponse.result, target);
|
|
1512
1621
|
const resumeResponse = await client.request({
|
|
1513
1622
|
type: "resume_session",
|
|
1514
1623
|
payload: {
|