@staff0rd/assist 0.359.0 → 0.360.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/commands/sessions/web/bundle.js +86 -86
- package/dist/index.js +230 -142
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -6,7 +6,7 @@ import { Command } from "commander";
|
|
|
6
6
|
// package.json
|
|
7
7
|
var package_default = {
|
|
8
8
|
name: "@staff0rd/assist",
|
|
9
|
-
version: "0.
|
|
9
|
+
version: "0.360.1",
|
|
10
10
|
type: "module",
|
|
11
11
|
main: "dist/index.js",
|
|
12
12
|
bin: {
|
|
@@ -21975,6 +21975,228 @@ function recordSessionUsage(sessions, claudeSessionId, totalIn, totalOut) {
|
|
|
21975
21975
|
}
|
|
21976
21976
|
}
|
|
21977
21977
|
|
|
21978
|
+
// src/commands/sessions/daemon/watchActivity.ts
|
|
21979
|
+
import { existsSync as existsSync53, mkdirSync as mkdirSync23, watch } from "fs";
|
|
21980
|
+
import { dirname as dirname26 } from "path";
|
|
21981
|
+
|
|
21982
|
+
// src/commands/sessions/daemon/applyReviewPause.ts
|
|
21983
|
+
function applyReviewPause(session, activity2) {
|
|
21984
|
+
const inReview = activity2.kind === "backlog" && activity2.phase !== void 0 && activity2.phase === activity2.totalPhases;
|
|
21985
|
+
if (inReview && !session.reviewStarted) {
|
|
21986
|
+
session.autoAdvance = false;
|
|
21987
|
+
session.reviewStarted = true;
|
|
21988
|
+
} else if (!inReview && session.reviewStarted) {
|
|
21989
|
+
session.reviewStarted = false;
|
|
21990
|
+
}
|
|
21991
|
+
}
|
|
21992
|
+
|
|
21993
|
+
// src/shared/db/getPhaseActiveMs.ts
|
|
21994
|
+
import { and as and17, eq as eq36 } from "drizzle-orm";
|
|
21995
|
+
async function getPhaseActiveMs(db, itemId, phaseIdx) {
|
|
21996
|
+
const [row] = await db.select({ activeMs: phaseUsage.activeMs }).from(phaseUsage).where(
|
|
21997
|
+
and17(eq36(phaseUsage.itemId, itemId), eq36(phaseUsage.phaseIdx, phaseIdx))
|
|
21998
|
+
);
|
|
21999
|
+
return row?.activeMs ?? 0;
|
|
22000
|
+
}
|
|
22001
|
+
|
|
22002
|
+
// src/commands/sessions/daemon/loadPhaseActiveMs.ts
|
|
22003
|
+
async function loadPhaseActiveMs(itemId, phaseIdx) {
|
|
22004
|
+
try {
|
|
22005
|
+
if (!process.env.ASSIST_DATABASE_URL && !loadConfig().database.url)
|
|
22006
|
+
return null;
|
|
22007
|
+
return await getPhaseActiveMs(await getDb(), itemId, phaseIdx);
|
|
22008
|
+
} catch (error) {
|
|
22009
|
+
daemonLog(`phase-active-ms load failed: ${String(error)}`);
|
|
22010
|
+
return null;
|
|
22011
|
+
}
|
|
22012
|
+
}
|
|
22013
|
+
|
|
22014
|
+
// src/commands/sessions/daemon/seedRunningMsFromUsage.ts
|
|
22015
|
+
async function seedRunningMsFromUsage(session, notify2) {
|
|
22016
|
+
if (session.usageSeeded) return;
|
|
22017
|
+
const phase = sessionBacklogPhase(session);
|
|
22018
|
+
if (!phase) return;
|
|
22019
|
+
session.usageSeeded = true;
|
|
22020
|
+
const priorMs = await loadPhaseActiveMs(phase.itemId, phase.phaseIdx);
|
|
22021
|
+
if (priorMs == null || priorMs <= session.runningMs) return;
|
|
22022
|
+
session.runningMs = priorMs;
|
|
22023
|
+
daemonLog(
|
|
22024
|
+
`session ${session.id} seeded runningMs=${priorMs} from item ${phase.itemId} phase ${phase.phaseIdx} recorded usage`
|
|
22025
|
+
);
|
|
22026
|
+
notify2();
|
|
22027
|
+
}
|
|
22028
|
+
|
|
22029
|
+
// src/commands/sessions/daemon/watchActivity.ts
|
|
22030
|
+
var DEBOUNCE_MS = 50;
|
|
22031
|
+
function watchActivity(session, notify2) {
|
|
22032
|
+
if (session.commandType !== "assist" || !session.cwd) return;
|
|
22033
|
+
const path57 = activityPath(session.id);
|
|
22034
|
+
const dir = dirname26(path57);
|
|
22035
|
+
try {
|
|
22036
|
+
mkdirSync23(dir, { recursive: true });
|
|
22037
|
+
} catch {
|
|
22038
|
+
return;
|
|
22039
|
+
}
|
|
22040
|
+
reconcileActivity(session.id, session.activity);
|
|
22041
|
+
let timer = null;
|
|
22042
|
+
const read = () => {
|
|
22043
|
+
timer = null;
|
|
22044
|
+
const activity2 = readActivity(path57);
|
|
22045
|
+
if (!activity2) return;
|
|
22046
|
+
session.activity = activity2;
|
|
22047
|
+
if (activity2.claudeSessionId)
|
|
22048
|
+
session.claudeSessionId = activity2.claudeSessionId;
|
|
22049
|
+
applyReviewPause(session, activity2);
|
|
22050
|
+
void seedRunningMsFromUsage(session, notify2);
|
|
22051
|
+
notify2();
|
|
22052
|
+
};
|
|
22053
|
+
session.activityWatcher = watch(dir, (_event, filename) => {
|
|
22054
|
+
if (filename && !path57.endsWith(filename)) return;
|
|
22055
|
+
if (timer) clearTimeout(timer);
|
|
22056
|
+
timer = setTimeout(read, DEBOUNCE_MS);
|
|
22057
|
+
});
|
|
22058
|
+
if (existsSync53(path57)) read();
|
|
22059
|
+
}
|
|
22060
|
+
function refreshActivity(session) {
|
|
22061
|
+
if (session.commandType !== "assist" || !session.cwd) return;
|
|
22062
|
+
const activity2 = readActivity(activityPath(session.id));
|
|
22063
|
+
if (!activity2) return;
|
|
22064
|
+
session.activity = activity2;
|
|
22065
|
+
if (activity2.claudeSessionId)
|
|
22066
|
+
session.claudeSessionId = activity2.claudeSessionId;
|
|
22067
|
+
}
|
|
22068
|
+
|
|
22069
|
+
// src/commands/sessions/daemon/handlePtyExit.ts
|
|
22070
|
+
function handlePtyExit(session, exitCode, onStatusChange) {
|
|
22071
|
+
if (session.pendingRestart) {
|
|
22072
|
+
const resume = session.pendingRestart;
|
|
22073
|
+
session.pendingRestart = void 0;
|
|
22074
|
+
daemonLog(
|
|
22075
|
+
`session ${session.id} ("${session.name}") pty exited (code ${exitCode}) for restart; resuming now the process is gone`
|
|
22076
|
+
);
|
|
22077
|
+
resume();
|
|
22078
|
+
return;
|
|
22079
|
+
}
|
|
22080
|
+
refreshActivity(session);
|
|
22081
|
+
const failedResume = session.restored === true && exitCode !== 0 && session.scrollback.length === 0;
|
|
22082
|
+
if (failedResume) {
|
|
22083
|
+
session.error = `resume process exited with code ${exitCode} before producing any output`;
|
|
22084
|
+
daemonLog(
|
|
22085
|
+
`could not resume restored session "${session.name}" (id ${session.id}): ${session.error}`
|
|
22086
|
+
);
|
|
22087
|
+
onStatusChange(session, "error", exitCode);
|
|
22088
|
+
return;
|
|
22089
|
+
}
|
|
22090
|
+
const priorStatus = session.status;
|
|
22091
|
+
const unexpected = priorStatus === "waiting" || exitCode !== 0;
|
|
22092
|
+
daemonLog(
|
|
22093
|
+
`session ${session.id} ("${session.name}") pty exited with code ${exitCode} from status "${priorStatus}" (${session.scrollback.length} bytes of output) \u2014 ${unexpected ? "unexpected exit, process died mid-session" : "expected completion"}; marking done`
|
|
22094
|
+
);
|
|
22095
|
+
onStatusChange(session, "done", exitCode);
|
|
22096
|
+
}
|
|
22097
|
+
|
|
22098
|
+
// src/commands/sessions/daemon/wirePtyEvents.ts
|
|
22099
|
+
var MAX_SCROLLBACK = 256 * 1024;
|
|
22100
|
+
function appendScrollback(session, data) {
|
|
22101
|
+
session.scrollback += data;
|
|
22102
|
+
if (session.scrollback.length > MAX_SCROLLBACK) {
|
|
22103
|
+
session.scrollback = session.scrollback.slice(-MAX_SCROLLBACK);
|
|
22104
|
+
}
|
|
22105
|
+
}
|
|
22106
|
+
function wirePtyEvents(session, clients, onStatusChange) {
|
|
22107
|
+
if (!session.pty) return;
|
|
22108
|
+
session.pty.onData((data) => {
|
|
22109
|
+
appendScrollback(session, data);
|
|
22110
|
+
noteOutputForEscInterrupt(session, onStatusChange);
|
|
22111
|
+
broadcast(clients, { type: "output", sessionId: session.id, data });
|
|
22112
|
+
});
|
|
22113
|
+
session.pty.onExit(
|
|
22114
|
+
({ exitCode }) => handlePtyExit(session, exitCode, onStatusChange)
|
|
22115
|
+
);
|
|
22116
|
+
}
|
|
22117
|
+
|
|
22118
|
+
// src/commands/sessions/daemon/respawnSession.ts
|
|
22119
|
+
function respawnSession(session, respawn, status2, clients, onStatusChange) {
|
|
22120
|
+
session.scrollback = "";
|
|
22121
|
+
session.startedAt = Date.now();
|
|
22122
|
+
session.runningMs = 0;
|
|
22123
|
+
session.runningSince = null;
|
|
22124
|
+
setStatus2(session, status2);
|
|
22125
|
+
session.restored = void 0;
|
|
22126
|
+
session.pty = respawn();
|
|
22127
|
+
broadcast(clients, { type: "clear", sessionId: session.id });
|
|
22128
|
+
wirePtyEvents(session, clients, onStatusChange);
|
|
22129
|
+
}
|
|
22130
|
+
|
|
22131
|
+
// src/commands/sessions/daemon/assistResumeArgs.ts
|
|
22132
|
+
function assistResumeArgs(session) {
|
|
22133
|
+
const args = ["assist", ...session.assistArgs];
|
|
22134
|
+
return session.claudeSessionId ? [...args, "--resume-session", session.claudeSessionId] : args;
|
|
22135
|
+
}
|
|
22136
|
+
|
|
22137
|
+
// src/commands/sessions/daemon/respawnPlan.ts
|
|
22138
|
+
function respawnPlan(session) {
|
|
22139
|
+
const { commandType, claudeSessionId, cwd, assistArgs } = session;
|
|
22140
|
+
if (commandType === "claude")
|
|
22141
|
+
return claudeSessionId ? {
|
|
22142
|
+
spawn: () => spawnClaude2({
|
|
22143
|
+
resumeSessionId: claudeSessionId,
|
|
22144
|
+
cwd,
|
|
22145
|
+
sessionId: session.id
|
|
22146
|
+
}),
|
|
22147
|
+
status: "waiting"
|
|
22148
|
+
} : null;
|
|
22149
|
+
if (commandType === "assist" && assistArgs) {
|
|
22150
|
+
const idle = session.status === "waiting";
|
|
22151
|
+
return {
|
|
22152
|
+
spawn: () => spawnPty(
|
|
22153
|
+
assistResumeArgs({ assistArgs, claudeSessionId }),
|
|
22154
|
+
cwd,
|
|
22155
|
+
session.id,
|
|
22156
|
+
idle ? { ASSIST_RESUME_IDLE: "1" } : void 0
|
|
22157
|
+
),
|
|
22158
|
+
status: idle ? "waiting" : "running"
|
|
22159
|
+
};
|
|
22160
|
+
}
|
|
22161
|
+
return null;
|
|
22162
|
+
}
|
|
22163
|
+
|
|
22164
|
+
// src/commands/sessions/daemon/restartSession.ts
|
|
22165
|
+
function restartSession(session, clients, onStatusChange) {
|
|
22166
|
+
const plan2 = respawnPlan(session);
|
|
22167
|
+
if (!plan2) return false;
|
|
22168
|
+
const via = session.claudeSessionId ? `resume ${session.claudeSessionId}` : "fresh";
|
|
22169
|
+
const respawn = () => {
|
|
22170
|
+
respawnSession(session, plan2.spawn, plan2.status, clients, onStatusChange);
|
|
22171
|
+
daemonLog(`session ${session.id} restarted (${via}): ${session.name}`);
|
|
22172
|
+
};
|
|
22173
|
+
const pty2 = session.pty;
|
|
22174
|
+
if (pty2 && session.status !== "done") {
|
|
22175
|
+
daemonLog(
|
|
22176
|
+
`session ${session.id} restart requested: killing running process, will resume on exit`
|
|
22177
|
+
);
|
|
22178
|
+
session.pendingRestart = respawn;
|
|
22179
|
+
killPtyTree(pty2);
|
|
22180
|
+
} else {
|
|
22181
|
+
respawn();
|
|
22182
|
+
}
|
|
22183
|
+
return true;
|
|
22184
|
+
}
|
|
22185
|
+
function killPtyTree(pty2) {
|
|
22186
|
+
if (process.platform === "win32") {
|
|
22187
|
+
pty2.kill();
|
|
22188
|
+
return;
|
|
22189
|
+
}
|
|
22190
|
+
try {
|
|
22191
|
+
process.kill(-pty2.pid, "SIGHUP");
|
|
22192
|
+
} catch {
|
|
22193
|
+
try {
|
|
22194
|
+
pty2.kill();
|
|
22195
|
+
} catch {
|
|
22196
|
+
}
|
|
22197
|
+
}
|
|
22198
|
+
}
|
|
22199
|
+
|
|
21978
22200
|
// src/commands/sessions/daemon/restoreBase.ts
|
|
21979
22201
|
function restoreBase(id2, persisted) {
|
|
21980
22202
|
return {
|
|
@@ -22005,12 +22227,6 @@ function errorSession(id2, persisted, error) {
|
|
|
22005
22227
|
};
|
|
22006
22228
|
}
|
|
22007
22229
|
|
|
22008
|
-
// src/commands/sessions/daemon/assistResumeArgs.ts
|
|
22009
|
-
function assistResumeArgs(persisted) {
|
|
22010
|
-
const args = ["assist", ...persisted.assistArgs];
|
|
22011
|
-
return persisted.claudeSessionId ? [...args, "--resume-session", persisted.claudeSessionId] : args;
|
|
22012
|
-
}
|
|
22013
|
-
|
|
22014
22230
|
// src/commands/sessions/daemon/runningSession.ts
|
|
22015
22231
|
function runningSession(base, persisted, pty2) {
|
|
22016
22232
|
return restoredSession(base, persisted, pty2, "running");
|
|
@@ -22194,146 +22410,12 @@ function resumeSession(id2, sessionId, cwd, name) {
|
|
|
22194
22410
|
};
|
|
22195
22411
|
}
|
|
22196
22412
|
|
|
22197
|
-
// src/commands/sessions/daemon/watchActivity.ts
|
|
22198
|
-
import { existsSync as existsSync53, mkdirSync as mkdirSync23, watch } from "fs";
|
|
22199
|
-
import { dirname as dirname26 } from "path";
|
|
22200
|
-
|
|
22201
|
-
// src/commands/sessions/daemon/applyReviewPause.ts
|
|
22202
|
-
function applyReviewPause(session, activity2) {
|
|
22203
|
-
const inReview = activity2.kind === "backlog" && activity2.phase !== void 0 && activity2.phase === activity2.totalPhases;
|
|
22204
|
-
if (inReview && !session.reviewStarted) {
|
|
22205
|
-
session.autoAdvance = false;
|
|
22206
|
-
session.reviewStarted = true;
|
|
22207
|
-
} else if (!inReview && session.reviewStarted) {
|
|
22208
|
-
session.reviewStarted = false;
|
|
22209
|
-
}
|
|
22210
|
-
}
|
|
22211
|
-
|
|
22212
|
-
// src/shared/db/getPhaseActiveMs.ts
|
|
22213
|
-
import { and as and17, eq as eq36 } from "drizzle-orm";
|
|
22214
|
-
async function getPhaseActiveMs(db, itemId, phaseIdx) {
|
|
22215
|
-
const [row] = await db.select({ activeMs: phaseUsage.activeMs }).from(phaseUsage).where(
|
|
22216
|
-
and17(eq36(phaseUsage.itemId, itemId), eq36(phaseUsage.phaseIdx, phaseIdx))
|
|
22217
|
-
);
|
|
22218
|
-
return row?.activeMs ?? 0;
|
|
22219
|
-
}
|
|
22220
|
-
|
|
22221
|
-
// src/commands/sessions/daemon/loadPhaseActiveMs.ts
|
|
22222
|
-
async function loadPhaseActiveMs(itemId, phaseIdx) {
|
|
22223
|
-
try {
|
|
22224
|
-
if (!process.env.ASSIST_DATABASE_URL && !loadConfig().database.url)
|
|
22225
|
-
return null;
|
|
22226
|
-
return await getPhaseActiveMs(await getDb(), itemId, phaseIdx);
|
|
22227
|
-
} catch (error) {
|
|
22228
|
-
daemonLog(`phase-active-ms load failed: ${String(error)}`);
|
|
22229
|
-
return null;
|
|
22230
|
-
}
|
|
22231
|
-
}
|
|
22232
|
-
|
|
22233
|
-
// src/commands/sessions/daemon/seedRunningMsFromUsage.ts
|
|
22234
|
-
async function seedRunningMsFromUsage(session, notify2) {
|
|
22235
|
-
if (session.usageSeeded) return;
|
|
22236
|
-
const phase = sessionBacklogPhase(session);
|
|
22237
|
-
if (!phase) return;
|
|
22238
|
-
session.usageSeeded = true;
|
|
22239
|
-
const priorMs = await loadPhaseActiveMs(phase.itemId, phase.phaseIdx);
|
|
22240
|
-
if (priorMs == null || priorMs <= session.runningMs) return;
|
|
22241
|
-
session.runningMs = priorMs;
|
|
22242
|
-
daemonLog(
|
|
22243
|
-
`session ${session.id} seeded runningMs=${priorMs} from item ${phase.itemId} phase ${phase.phaseIdx} recorded usage`
|
|
22244
|
-
);
|
|
22245
|
-
notify2();
|
|
22246
|
-
}
|
|
22247
|
-
|
|
22248
|
-
// src/commands/sessions/daemon/watchActivity.ts
|
|
22249
|
-
var DEBOUNCE_MS = 50;
|
|
22250
|
-
function watchActivity(session, notify2) {
|
|
22251
|
-
if (session.commandType !== "assist" || !session.cwd) return;
|
|
22252
|
-
const path57 = activityPath(session.id);
|
|
22253
|
-
const dir = dirname26(path57);
|
|
22254
|
-
try {
|
|
22255
|
-
mkdirSync23(dir, { recursive: true });
|
|
22256
|
-
} catch {
|
|
22257
|
-
return;
|
|
22258
|
-
}
|
|
22259
|
-
reconcileActivity(session.id, session.activity);
|
|
22260
|
-
let timer = null;
|
|
22261
|
-
const read = () => {
|
|
22262
|
-
timer = null;
|
|
22263
|
-
const activity2 = readActivity(path57);
|
|
22264
|
-
if (!activity2) return;
|
|
22265
|
-
session.activity = activity2;
|
|
22266
|
-
if (activity2.claudeSessionId)
|
|
22267
|
-
session.claudeSessionId = activity2.claudeSessionId;
|
|
22268
|
-
applyReviewPause(session, activity2);
|
|
22269
|
-
void seedRunningMsFromUsage(session, notify2);
|
|
22270
|
-
notify2();
|
|
22271
|
-
};
|
|
22272
|
-
session.activityWatcher = watch(dir, (_event, filename) => {
|
|
22273
|
-
if (filename && !path57.endsWith(filename)) return;
|
|
22274
|
-
if (timer) clearTimeout(timer);
|
|
22275
|
-
timer = setTimeout(read, DEBOUNCE_MS);
|
|
22276
|
-
});
|
|
22277
|
-
if (existsSync53(path57)) read();
|
|
22278
|
-
}
|
|
22279
|
-
function refreshActivity(session) {
|
|
22280
|
-
if (session.commandType !== "assist" || !session.cwd) return;
|
|
22281
|
-
const activity2 = readActivity(activityPath(session.id));
|
|
22282
|
-
if (!activity2) return;
|
|
22283
|
-
session.activity = activity2;
|
|
22284
|
-
if (activity2.claudeSessionId)
|
|
22285
|
-
session.claudeSessionId = activity2.claudeSessionId;
|
|
22286
|
-
}
|
|
22287
|
-
|
|
22288
|
-
// src/commands/sessions/daemon/wirePtyEvents.ts
|
|
22289
|
-
var MAX_SCROLLBACK = 256 * 1024;
|
|
22290
|
-
function appendScrollback(session, data) {
|
|
22291
|
-
session.scrollback += data;
|
|
22292
|
-
if (session.scrollback.length > MAX_SCROLLBACK) {
|
|
22293
|
-
session.scrollback = session.scrollback.slice(-MAX_SCROLLBACK);
|
|
22294
|
-
}
|
|
22295
|
-
}
|
|
22296
|
-
function wirePtyEvents(session, clients, onStatusChange) {
|
|
22297
|
-
if (!session.pty) return;
|
|
22298
|
-
session.pty.onData((data) => {
|
|
22299
|
-
appendScrollback(session, data);
|
|
22300
|
-
noteOutputForEscInterrupt(session, onStatusChange);
|
|
22301
|
-
broadcast(clients, { type: "output", sessionId: session.id, data });
|
|
22302
|
-
});
|
|
22303
|
-
session.pty.onExit(({ exitCode }) => {
|
|
22304
|
-
refreshActivity(session);
|
|
22305
|
-
const failedResume = session.restored === true && exitCode !== 0 && session.scrollback.length === 0;
|
|
22306
|
-
if (failedResume) {
|
|
22307
|
-
session.error = `resume process exited with code ${exitCode} before producing any output`;
|
|
22308
|
-
daemonLog(
|
|
22309
|
-
`could not resume restored session "${session.name}" (id ${session.id}): ${session.error}`
|
|
22310
|
-
);
|
|
22311
|
-
onStatusChange(session, "error", exitCode);
|
|
22312
|
-
return;
|
|
22313
|
-
}
|
|
22314
|
-
const priorStatus = session.status;
|
|
22315
|
-
const unexpected = priorStatus === "waiting" || exitCode !== 0;
|
|
22316
|
-
daemonLog(
|
|
22317
|
-
`session ${session.id} ("${session.name}") pty exited with code ${exitCode} from status "${priorStatus}" (${session.scrollback.length} bytes of output) \u2014 ${unexpected ? "unexpected exit, process died mid-session" : "expected completion"}; marking done`
|
|
22318
|
-
);
|
|
22319
|
-
onStatusChange(session, "done", exitCode);
|
|
22320
|
-
});
|
|
22321
|
-
}
|
|
22322
|
-
|
|
22323
22413
|
// src/commands/sessions/daemon/retrySession.ts
|
|
22324
22414
|
function retrySession(session, clients, onStatusChange) {
|
|
22325
22415
|
const respawn = respawnThunk(session);
|
|
22326
22416
|
if (!respawn) return false;
|
|
22327
22417
|
if (session.status !== "done") session.pty?.kill();
|
|
22328
|
-
session
|
|
22329
|
-
session.startedAt = Date.now();
|
|
22330
|
-
session.runningMs = 0;
|
|
22331
|
-
session.runningSince = null;
|
|
22332
|
-
setStatus2(session, "running");
|
|
22333
|
-
session.restored = void 0;
|
|
22334
|
-
session.pty = respawn();
|
|
22335
|
-
broadcast(clients, { type: "clear", sessionId: session.id });
|
|
22336
|
-
wirePtyEvents(session, clients, onStatusChange);
|
|
22418
|
+
respawnSession(session, respawn, "running", clients, onStatusChange);
|
|
22337
22419
|
daemonLog(`session ${session.id} retried: ${session.name}`);
|
|
22338
22420
|
return true;
|
|
22339
22421
|
}
|
|
@@ -23116,6 +23198,11 @@ var SessionManager = class {
|
|
|
23116
23198
|
const s = this.sessions.get(id2);
|
|
23117
23199
|
if (s && retrySession(s, this.clients, this.onStatusChange)) this.notify();
|
|
23118
23200
|
}
|
|
23201
|
+
restart(id2) {
|
|
23202
|
+
const s = this.sessions.get(id2);
|
|
23203
|
+
if (s && restartSession(s, this.clients, this.onStatusChange))
|
|
23204
|
+
this.notify();
|
|
23205
|
+
}
|
|
23119
23206
|
dismissSession = (id2) => {
|
|
23120
23207
|
if (dismissSession(this.sessions, id2)) this.notify();
|
|
23121
23208
|
};
|
|
@@ -23534,6 +23621,7 @@ var messageHandlers = {
|
|
|
23534
23621
|
(_client, m, d) => m.resizeSession(d.sessionId, d.cols, d.rows)
|
|
23535
23622
|
),
|
|
23536
23623
|
retry: routed((_client, m, d) => m.retrySession(d.sessionId)),
|
|
23624
|
+
restart: routed((_client, m, d) => m.restart(d.sessionId)),
|
|
23537
23625
|
dismiss: routed((_client, m, d) => m.dismissSession(d.sessionId)),
|
|
23538
23626
|
"set-autorun": routed(
|
|
23539
23627
|
(_client, m, d) => m.setAutoRun(d.sessionId, d.enabled)
|