@adhdev/daemon-core 0.8.25 → 0.8.27
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/agent-stream/provider-adapter.d.ts +1 -0
- package/dist/boot/daemon-lifecycle.d.ts +2 -0
- package/dist/cli-adapters/pty-transport.d.ts +3 -0
- package/dist/commands/router.d.ts +24 -0
- package/dist/index.js +221 -14
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +221 -14
- package/dist/index.mjs.map +1 -1
- package/dist/providers/cli-provider-instance.d.ts +1 -0
- package/dist/providers/extension-provider-instance.d.ts +7 -0
- package/dist/status/normalize.js +14 -2
- package/dist/status/normalize.js.map +1 -1
- package/dist/status/normalize.mjs +14 -2
- package/dist/status/normalize.mjs.map +1 -1
- package/dist/status/snapshot.d.ts +0 -2
- package/node_modules/@adhdev/session-host-core/dist/index.d.mts +72 -1
- package/node_modules/@adhdev/session-host-core/dist/index.d.ts +72 -1
- package/node_modules/@adhdev/session-host-core/dist/index.js.map +1 -1
- package/node_modules/@adhdev/session-host-core/package.json +1 -1
- package/package.json +1 -1
- package/src/agent-stream/provider-adapter.ts +30 -1
- package/src/boot/daemon-lifecycle.ts +3 -0
- package/src/cli-adapters/pty-transport.ts +3 -0
- package/src/cli-adapters/session-host-transport.ts +8 -0
- package/src/commands/chat-commands.ts +2 -2
- package/src/commands/handler.ts +25 -3
- package/src/commands/router.ts +132 -0
- package/src/providers/cli-provider-instance.ts +29 -1
- package/src/providers/extension-provider-instance.ts +24 -1
- package/src/status/normalize.ts +19 -2
- package/src/status/snapshot.ts +6 -13
package/dist/index.mjs
CHANGED
|
@@ -5116,6 +5116,7 @@ var ExtensionProviderInstance = class {
|
|
|
5116
5116
|
currentStatus = "idle";
|
|
5117
5117
|
agentStreams = [];
|
|
5118
5118
|
messages = [];
|
|
5119
|
+
prevMessageHashes = /* @__PURE__ */ new Map();
|
|
5119
5120
|
activeModal = null;
|
|
5120
5121
|
currentModel = "";
|
|
5121
5122
|
currentMode = "";
|
|
@@ -5181,7 +5182,7 @@ var ExtensionProviderInstance = class {
|
|
|
5181
5182
|
onEvent(event, data) {
|
|
5182
5183
|
if (event === "stream_update") {
|
|
5183
5184
|
if (data?.streams) this.agentStreams = data.streams;
|
|
5184
|
-
if (data?.messages) this.messages = data.messages;
|
|
5185
|
+
if (data?.messages) this.messages = this.assignReceivedAt(data.messages);
|
|
5185
5186
|
if (data?.activeModal !== void 0) this.activeModal = data.activeModal;
|
|
5186
5187
|
if (data?.model) this.currentModel = data.model;
|
|
5187
5188
|
if (data?.mode) this.currentMode = data.mode;
|
|
@@ -5207,6 +5208,7 @@ var ExtensionProviderInstance = class {
|
|
|
5207
5208
|
dispose() {
|
|
5208
5209
|
this.agentStreams = [];
|
|
5209
5210
|
this.messages = [];
|
|
5211
|
+
this.prevMessageHashes.clear();
|
|
5210
5212
|
this.monitor.reset();
|
|
5211
5213
|
this.appliedEffectKeys.clear();
|
|
5212
5214
|
this.runtimeMessages = [];
|
|
@@ -5362,6 +5364,23 @@ var ExtensionProviderInstance = class {
|
|
|
5362
5364
|
this.chatId || this.instanceId
|
|
5363
5365
|
);
|
|
5364
5366
|
}
|
|
5367
|
+
/**
|
|
5368
|
+
* Assign stable receivedAt to extension messages.
|
|
5369
|
+
* Same pattern as IdeProviderInstance.readChat() prevByHash —
|
|
5370
|
+
* preserves first-seen timestamp across polling cycles.
|
|
5371
|
+
*/
|
|
5372
|
+
assignReceivedAt(messages) {
|
|
5373
|
+
const now = Date.now();
|
|
5374
|
+
const nextHashes = /* @__PURE__ */ new Map();
|
|
5375
|
+
for (const msg of messages) {
|
|
5376
|
+
const hash = `${msg.role}:${(msg.content || "").slice(0, 100)}`;
|
|
5377
|
+
const prevTime = this.prevMessageHashes.get(hash);
|
|
5378
|
+
msg.receivedAt = prevTime || now;
|
|
5379
|
+
nextHashes.set(hash, msg.receivedAt);
|
|
5380
|
+
}
|
|
5381
|
+
this.prevMessageHashes = nextHashes;
|
|
5382
|
+
return messages;
|
|
5383
|
+
}
|
|
5365
5384
|
mergeConversationMessages(messages) {
|
|
5366
5385
|
if (this.runtimeMessages.length === 0) return messages;
|
|
5367
5386
|
return [...messages, ...this.runtimeMessages.map((entry) => entry.message)].map((message, index) => ({ message, index })).sort((a, b) => {
|
|
@@ -5418,6 +5437,7 @@ ${effect.notification.body || ""}`.trim();
|
|
|
5418
5437
|
}
|
|
5419
5438
|
this.agentStreams = [];
|
|
5420
5439
|
this.messages = [];
|
|
5440
|
+
this.prevMessageHashes.clear();
|
|
5421
5441
|
this.activeModal = null;
|
|
5422
5442
|
this.currentModel = "";
|
|
5423
5443
|
this.currentMode = "";
|
|
@@ -6403,16 +6423,28 @@ function trimMessageForStatus(message, stringLimit) {
|
|
|
6403
6423
|
if (!message || typeof message !== "object") return message;
|
|
6404
6424
|
return trimStructuredStrings(message, stringLimit);
|
|
6405
6425
|
}
|
|
6426
|
+
function normalizeMessageTime(message) {
|
|
6427
|
+
if (!message || typeof message !== "object") return message;
|
|
6428
|
+
const msg = message;
|
|
6429
|
+
if (msg.receivedAt == null) {
|
|
6430
|
+
const fallback = msg.timestamp ?? msg.createdAt;
|
|
6431
|
+
if (fallback != null) {
|
|
6432
|
+
const ts2 = typeof fallback === "string" ? Date.parse(fallback) : Number(fallback);
|
|
6433
|
+
if (Number.isFinite(ts2) && ts2 > 0) msg.receivedAt = ts2;
|
|
6434
|
+
}
|
|
6435
|
+
}
|
|
6436
|
+
return msg;
|
|
6437
|
+
}
|
|
6406
6438
|
function trimMessagesForStatus(messages) {
|
|
6407
6439
|
if (!Array.isArray(messages) || messages.length === 0) return [];
|
|
6408
6440
|
const recent = messages.slice(-STATUS_ACTIVE_CHAT_MESSAGE_LIMIT);
|
|
6409
6441
|
const kept = [];
|
|
6410
6442
|
let totalBytes = 0;
|
|
6411
6443
|
for (let i = recent.length - 1; i >= 0; i -= 1) {
|
|
6412
|
-
let normalized = trimMessageForStatus(recent[i], STATUS_ACTIVE_CHAT_STRING_LIMIT);
|
|
6444
|
+
let normalized = normalizeMessageTime(trimMessageForStatus(recent[i], STATUS_ACTIVE_CHAT_STRING_LIMIT));
|
|
6413
6445
|
let size = estimateBytes(normalized);
|
|
6414
6446
|
if (size > STATUS_ACTIVE_CHAT_TOTAL_BYTES_LIMIT) {
|
|
6415
|
-
normalized = trimMessageForStatus(recent[i], STATUS_ACTIVE_CHAT_FALLBACK_STRING_LIMIT);
|
|
6447
|
+
normalized = normalizeMessageTime(trimMessageForStatus(recent[i], STATUS_ACTIVE_CHAT_FALLBACK_STRING_LIMIT));
|
|
6416
6448
|
size = estimateBytes(normalized);
|
|
6417
6449
|
}
|
|
6418
6450
|
if (kept.length > 0 && totalBytes + size > STATUS_ACTIVE_CHAT_TOTAL_BYTES_LIMIT) {
|
|
@@ -7035,7 +7067,7 @@ async function handleSendChat(h, args) {
|
|
|
7035
7067
|
if (isExtensionTransport(transport)) {
|
|
7036
7068
|
_log(`Extension: ${provider?.type || "unknown_extension"}`);
|
|
7037
7069
|
try {
|
|
7038
|
-
const evalResult = await h.evaluateProviderScript("sendMessage", {
|
|
7070
|
+
const evalResult = await h.evaluateProviderScript("sendMessage", { message: text }, 3e4);
|
|
7039
7071
|
if (evalResult?.result) {
|
|
7040
7072
|
const parsed = parseMaybeJson(evalResult.result);
|
|
7041
7073
|
if (didProviderConfirmSend(parsed)) {
|
|
@@ -7066,7 +7098,7 @@ async function handleSendChat(h, args) {
|
|
|
7066
7098
|
return { success: false, error: `CDP for ${managerKey || "unknown"} not connected` };
|
|
7067
7099
|
}
|
|
7068
7100
|
_log(`Targeting IDE: ${getCurrentManagerKey(h)}`);
|
|
7069
|
-
const sendScript = h.getProviderScript("sendMessage", {
|
|
7101
|
+
const sendScript = h.getProviderScript("sendMessage", { message: text });
|
|
7070
7102
|
if (sendScript) {
|
|
7071
7103
|
try {
|
|
7072
7104
|
const result = await targetCdp.evaluate(sendScript, 3e4);
|
|
@@ -8468,9 +8500,26 @@ var DaemonCommandHandler = class {
|
|
|
8468
8500
|
if (provider?.scripts) {
|
|
8469
8501
|
const fn = provider.scripts[scriptName];
|
|
8470
8502
|
if (typeof fn === "function") {
|
|
8471
|
-
|
|
8472
|
-
|
|
8473
|
-
|
|
8503
|
+
if (params && Object.keys(params).length > 0) {
|
|
8504
|
+
const firstVal = Object.values(params)[0];
|
|
8505
|
+
if (scriptName === "sendMessage" && typeof firstVal === "string") {
|
|
8506
|
+
const legacyScript = fn(firstVal);
|
|
8507
|
+
if (legacyScript) return legacyScript;
|
|
8508
|
+
}
|
|
8509
|
+
const script = fn(params);
|
|
8510
|
+
if (script) {
|
|
8511
|
+
const likelyLegacyObjectLeak = typeof script === "string" && script.includes("[object Object]") && typeof firstVal === "string";
|
|
8512
|
+
if (!likelyLegacyObjectLeak) return script;
|
|
8513
|
+
}
|
|
8514
|
+
if (firstVal !== void 0) {
|
|
8515
|
+
const legacyScript = fn(firstVal);
|
|
8516
|
+
if (legacyScript) return legacyScript;
|
|
8517
|
+
}
|
|
8518
|
+
if (script) return script;
|
|
8519
|
+
} else {
|
|
8520
|
+
const script = fn();
|
|
8521
|
+
if (script) return script;
|
|
8522
|
+
}
|
|
8474
8523
|
}
|
|
8475
8524
|
}
|
|
8476
8525
|
return null;
|
|
@@ -8931,6 +8980,7 @@ var CliProviderInstance = class {
|
|
|
8931
8980
|
this.detectStatusTransition();
|
|
8932
8981
|
});
|
|
8933
8982
|
await this.adapter.spawn();
|
|
8983
|
+
this.maybeAppendRuntimeRecoveryMessage(this.adapter.getRuntimeMetadata());
|
|
8934
8984
|
if (this.providerSessionId) {
|
|
8935
8985
|
const restoredHistory = readChatHistory(this.type, 0, 200, this.providerSessionId);
|
|
8936
8986
|
if (restoredHistory.messages.length > 0) {
|
|
@@ -9025,6 +9075,7 @@ var CliProviderInstance = class {
|
|
|
9025
9075
|
this.promoteProviderSessionId(parsedProviderSessionId);
|
|
9026
9076
|
}
|
|
9027
9077
|
const runtime = this.adapter.getRuntimeMetadata();
|
|
9078
|
+
this.maybeAppendRuntimeRecoveryMessage(runtime);
|
|
9028
9079
|
const parsedMessages = Array.isArray(parsedStatus?.messages) ? parsedStatus.messages : [];
|
|
9029
9080
|
const controlValues = extractProviderControlValues(this.provider.controls, parsedStatus);
|
|
9030
9081
|
if (controlValues) {
|
|
@@ -9351,6 +9402,28 @@ ${effect.notification.body || ""}`.trim();
|
|
|
9351
9402
|
const pad = (value) => String(value).padStart(2, "0");
|
|
9352
9403
|
return `${date.getFullYear()}-${pad(date.getMonth() + 1)}-${pad(date.getDate())} ${pad(date.getHours())}:${pad(date.getMinutes())}:${pad(date.getSeconds())}`;
|
|
9353
9404
|
}
|
|
9405
|
+
maybeAppendRuntimeRecoveryMessage(runtime) {
|
|
9406
|
+
if (!runtime?.restoredFromStorage || !runtime.runtimeId) return;
|
|
9407
|
+
const recoveryState = String(runtime.recoveryState || "").trim();
|
|
9408
|
+
if (!recoveryState) return;
|
|
9409
|
+
let content = "";
|
|
9410
|
+
if (recoveryState === "auto_resumed") {
|
|
9411
|
+
content = "Session host restored this CLI after restart and reattached it from a saved snapshot.";
|
|
9412
|
+
} else if (recoveryState === "resume_failed") {
|
|
9413
|
+
const errorSuffix = runtime.recoveryError ? ` Resume failed: ${runtime.recoveryError}` : "";
|
|
9414
|
+
content = `Session host found this CLI after restart, but automatic resume failed.${errorSuffix}`;
|
|
9415
|
+
} else if (recoveryState === "host_restart_interrupted") {
|
|
9416
|
+
content = "Session host found this CLI in interrupted state after restart and is attempting to resume it.";
|
|
9417
|
+
} else if (recoveryState === "orphan_snapshot") {
|
|
9418
|
+
content = "Session host restored the last snapshot for this CLI, but the original runtime was not resumed automatically.";
|
|
9419
|
+
} else {
|
|
9420
|
+
content = `Session host restored this CLI after restart (${recoveryState}).`;
|
|
9421
|
+
}
|
|
9422
|
+
this.appendRuntimeSystemMessage(
|
|
9423
|
+
content,
|
|
9424
|
+
`runtime_recovery:${runtime.runtimeId}:${recoveryState}`
|
|
9425
|
+
);
|
|
9426
|
+
}
|
|
9354
9427
|
appendRuntimeSystemMessage(content, dedupKey, receivedAt = Date.now()) {
|
|
9355
9428
|
const normalizedContent = String(content || "").trim();
|
|
9356
9429
|
if (!normalizedContent) return;
|
|
@@ -12644,17 +12717,17 @@ function parseMessageTime(value) {
|
|
|
12644
12717
|
function getSessionMessageUpdatedAt(session) {
|
|
12645
12718
|
const lastMessage = session.activeChat?.messages?.at?.(-1);
|
|
12646
12719
|
if (!lastMessage) return 0;
|
|
12647
|
-
return parseMessageTime(lastMessage.
|
|
12720
|
+
return parseMessageTime(lastMessage.receivedAt) || 0;
|
|
12648
12721
|
}
|
|
12649
12722
|
function getSessionCompletionMarker(session) {
|
|
12650
12723
|
const lastMessage = session.activeChat?.messages?.at?.(-1);
|
|
12651
12724
|
if (!lastMessage) return "";
|
|
12652
12725
|
const role = typeof lastMessage.role === "string" ? lastMessage.role : "";
|
|
12653
|
-
if (role === "user" || role === "human") return "";
|
|
12726
|
+
if (role === "user" || role === "human" || role === "system") return "";
|
|
12654
12727
|
if (typeof lastMessage._turnKey === "string" && lastMessage._turnKey) return `turn:${lastMessage._turnKey}`;
|
|
12655
12728
|
if (typeof lastMessage.id === "string" && lastMessage.id) return `id:${lastMessage.id}`;
|
|
12656
12729
|
if (typeof lastMessage.index === "number" && Number.isFinite(lastMessage.index)) return `idx:${lastMessage.index}`;
|
|
12657
|
-
const timestamp = parseMessageTime(lastMessage.
|
|
12730
|
+
const timestamp = parseMessageTime(lastMessage.receivedAt);
|
|
12658
12731
|
return timestamp > 0 ? `ts:${timestamp}` : "";
|
|
12659
12732
|
}
|
|
12660
12733
|
function getSessionLastUsedAt(session) {
|
|
@@ -12671,7 +12744,7 @@ function getUnreadState(hasContentChange, status, lastUsedAt, lastSeenAt, lastRo
|
|
|
12671
12744
|
if (status === "generating" || status === "starting") {
|
|
12672
12745
|
return { unread: false, inboxBucket: "working" };
|
|
12673
12746
|
}
|
|
12674
|
-
const unread = completionMarker ? completionMarker !== seenCompletionMarker : hasContentChange && lastUsedAt > lastSeenAt && lastRole !== "user" && lastRole !== "human";
|
|
12747
|
+
const unread = completionMarker ? completionMarker !== seenCompletionMarker : hasContentChange && lastUsedAt > lastSeenAt && lastRole !== "user" && lastRole !== "human" && lastRole !== "system";
|
|
12675
12748
|
return { unread, inboxBucket: unread ? "task_complete" : "idle" };
|
|
12676
12749
|
}
|
|
12677
12750
|
function buildRecentLaunches(recentActivity) {
|
|
@@ -12956,6 +13029,25 @@ var CHAT_COMMANDS = [
|
|
|
12956
13029
|
"change_model"
|
|
12957
13030
|
];
|
|
12958
13031
|
var READ_DEBUG_ENABLED2 = process.argv.includes("--dev") || process.env.ADHDEV_READ_DEBUG === "1";
|
|
13032
|
+
function toHostedCliRuntimeDescriptor(record) {
|
|
13033
|
+
if (!record || typeof record !== "object") return null;
|
|
13034
|
+
const runtimeId = typeof record.sessionId === "string" ? record.sessionId : "";
|
|
13035
|
+
const cliType = typeof record.providerType === "string" ? record.providerType : "";
|
|
13036
|
+
const workspace = typeof record.workspace === "string" ? record.workspace : "";
|
|
13037
|
+
if (!runtimeId || !cliType || !workspace) return null;
|
|
13038
|
+
return {
|
|
13039
|
+
runtimeId,
|
|
13040
|
+
runtimeKey: typeof record.runtimeKey === "string" ? record.runtimeKey : void 0,
|
|
13041
|
+
displayName: typeof record.displayName === "string" ? record.displayName : void 0,
|
|
13042
|
+
workspaceLabel: typeof record.workspaceLabel === "string" ? record.workspaceLabel : void 0,
|
|
13043
|
+
lifecycle: typeof record.lifecycle === "string" ? record.lifecycle : void 0,
|
|
13044
|
+
recoveryState: typeof record.meta?.runtimeRecoveryState === "string" ? String(record.meta.runtimeRecoveryState) : null,
|
|
13045
|
+
cliType,
|
|
13046
|
+
workspace,
|
|
13047
|
+
cliArgs: Array.isArray(record.meta?.cliArgs) ? record.meta.cliArgs : [],
|
|
13048
|
+
providerSessionId: typeof record.meta?.providerSessionId === "string" ? String(record.meta.providerSessionId) : void 0
|
|
13049
|
+
};
|
|
13050
|
+
}
|
|
12959
13051
|
var DaemonCommandRouter = class {
|
|
12960
13052
|
deps;
|
|
12961
13053
|
constructor(deps) {
|
|
@@ -13029,6 +13121,90 @@ var DaemonCommandRouter = class {
|
|
|
13029
13121
|
return { success: false, error: e.message };
|
|
13030
13122
|
}
|
|
13031
13123
|
}
|
|
13124
|
+
case "session_host_get_diagnostics": {
|
|
13125
|
+
if (!this.deps.sessionHostControl) return { success: false, error: "Session host control unavailable" };
|
|
13126
|
+
const diagnostics = await this.deps.sessionHostControl.getDiagnostics({
|
|
13127
|
+
includeSessions: args?.includeSessions !== false,
|
|
13128
|
+
limit: Number(args?.limit) || void 0
|
|
13129
|
+
});
|
|
13130
|
+
return { success: true, diagnostics };
|
|
13131
|
+
}
|
|
13132
|
+
case "session_host_list_sessions": {
|
|
13133
|
+
if (!this.deps.sessionHostControl) return { success: false, error: "Session host control unavailable" };
|
|
13134
|
+
const sessions = await this.deps.sessionHostControl.listSessions();
|
|
13135
|
+
return { success: true, sessions };
|
|
13136
|
+
}
|
|
13137
|
+
case "session_host_stop_session": {
|
|
13138
|
+
if (!this.deps.sessionHostControl) return { success: false, error: "Session host control unavailable" };
|
|
13139
|
+
const sessionId = typeof args?.sessionId === "string" ? args.sessionId : "";
|
|
13140
|
+
if (!sessionId) return { success: false, error: "sessionId required" };
|
|
13141
|
+
const record = await this.deps.sessionHostControl.stopSession(sessionId);
|
|
13142
|
+
return { success: true, record };
|
|
13143
|
+
}
|
|
13144
|
+
case "session_host_resume_session": {
|
|
13145
|
+
if (!this.deps.sessionHostControl) return { success: false, error: "Session host control unavailable" };
|
|
13146
|
+
const sessionId = typeof args?.sessionId === "string" ? args.sessionId : "";
|
|
13147
|
+
if (!sessionId) return { success: false, error: "sessionId required" };
|
|
13148
|
+
const record = await this.deps.sessionHostControl.resumeSession(sessionId);
|
|
13149
|
+
const hosted = toHostedCliRuntimeDescriptor(record);
|
|
13150
|
+
if (hosted) {
|
|
13151
|
+
await this.deps.cliManager.restoreHostedSessions([hosted]);
|
|
13152
|
+
}
|
|
13153
|
+
return { success: true, record };
|
|
13154
|
+
}
|
|
13155
|
+
case "session_host_restart_session": {
|
|
13156
|
+
if (!this.deps.sessionHostControl) return { success: false, error: "Session host control unavailable" };
|
|
13157
|
+
const sessionId = typeof args?.sessionId === "string" ? args.sessionId : "";
|
|
13158
|
+
if (!sessionId) return { success: false, error: "sessionId required" };
|
|
13159
|
+
const record = await this.deps.sessionHostControl.restartSession(sessionId);
|
|
13160
|
+
const hosted = toHostedCliRuntimeDescriptor(record);
|
|
13161
|
+
if (hosted) {
|
|
13162
|
+
await this.deps.cliManager.restoreHostedSessions([hosted]);
|
|
13163
|
+
}
|
|
13164
|
+
return { success: true, record };
|
|
13165
|
+
}
|
|
13166
|
+
case "session_host_send_signal": {
|
|
13167
|
+
if (!this.deps.sessionHostControl) return { success: false, error: "Session host control unavailable" };
|
|
13168
|
+
const sessionId = typeof args?.sessionId === "string" ? args.sessionId : "";
|
|
13169
|
+
const signal = typeof args?.signal === "string" ? args.signal : "";
|
|
13170
|
+
if (!sessionId) return { success: false, error: "sessionId required" };
|
|
13171
|
+
if (!signal) return { success: false, error: "signal required" };
|
|
13172
|
+
const record = await this.deps.sessionHostControl.sendSignal(sessionId, signal);
|
|
13173
|
+
return { success: true, record };
|
|
13174
|
+
}
|
|
13175
|
+
case "session_host_force_detach_client": {
|
|
13176
|
+
if (!this.deps.sessionHostControl) return { success: false, error: "Session host control unavailable" };
|
|
13177
|
+
const sessionId = typeof args?.sessionId === "string" ? args.sessionId : "";
|
|
13178
|
+
const clientId = typeof args?.clientId === "string" ? args.clientId : "";
|
|
13179
|
+
if (!sessionId) return { success: false, error: "sessionId required" };
|
|
13180
|
+
if (!clientId) return { success: false, error: "clientId required" };
|
|
13181
|
+
const record = await this.deps.sessionHostControl.forceDetachClient(sessionId, clientId);
|
|
13182
|
+
return { success: true, record };
|
|
13183
|
+
}
|
|
13184
|
+
case "session_host_acquire_write": {
|
|
13185
|
+
if (!this.deps.sessionHostControl) return { success: false, error: "Session host control unavailable" };
|
|
13186
|
+
const sessionId = typeof args?.sessionId === "string" ? args.sessionId : "";
|
|
13187
|
+
const clientId = typeof args?.clientId === "string" ? args.clientId : "";
|
|
13188
|
+
const ownerType = args?.ownerType === "agent" ? "agent" : "user";
|
|
13189
|
+
if (!sessionId) return { success: false, error: "sessionId required" };
|
|
13190
|
+
if (!clientId) return { success: false, error: "clientId required" };
|
|
13191
|
+
const record = await this.deps.sessionHostControl.acquireWrite({
|
|
13192
|
+
sessionId,
|
|
13193
|
+
clientId,
|
|
13194
|
+
ownerType,
|
|
13195
|
+
force: args?.force !== false
|
|
13196
|
+
});
|
|
13197
|
+
return { success: true, record };
|
|
13198
|
+
}
|
|
13199
|
+
case "session_host_release_write": {
|
|
13200
|
+
if (!this.deps.sessionHostControl) return { success: false, error: "Session host control unavailable" };
|
|
13201
|
+
const sessionId = typeof args?.sessionId === "string" ? args.sessionId : "";
|
|
13202
|
+
const clientId = typeof args?.clientId === "string" ? args.clientId : "";
|
|
13203
|
+
if (!sessionId) return { success: false, error: "sessionId required" };
|
|
13204
|
+
if (!clientId) return { success: false, error: "clientId required" };
|
|
13205
|
+
const record = await this.deps.sessionHostControl.releaseWrite({ sessionId, clientId });
|
|
13206
|
+
return { success: true, record };
|
|
13207
|
+
}
|
|
13032
13208
|
case "list_saved_sessions": {
|
|
13033
13209
|
const providerType = typeof args?.providerType === "string" ? args.providerType.trim() : typeof args?.agentType === "string" ? args.agentType.trim() : "";
|
|
13034
13210
|
const kind = args?.kind === "acp" ? "acp" : "cli";
|
|
@@ -13557,6 +13733,14 @@ var ProviderStreamAdapter = class {
|
|
|
13557
13733
|
hasScript(name) {
|
|
13558
13734
|
return typeof this.provider.scripts?.[name] === "function";
|
|
13559
13735
|
}
|
|
13736
|
+
parseMaybeJson(raw) {
|
|
13737
|
+
if (typeof raw !== "string") return raw;
|
|
13738
|
+
try {
|
|
13739
|
+
return JSON.parse(raw);
|
|
13740
|
+
} catch {
|
|
13741
|
+
return raw;
|
|
13742
|
+
}
|
|
13743
|
+
}
|
|
13560
13744
|
summarizeRaw(raw) {
|
|
13561
13745
|
try {
|
|
13562
13746
|
if (typeof raw === "string") return raw.replace(/\s+/g, " ").trim().slice(0, 240);
|
|
@@ -13617,12 +13801,30 @@ var ProviderStreamAdapter = class {
|
|
|
13617
13801
|
}
|
|
13618
13802
|
}
|
|
13619
13803
|
async sendMessage(evaluate, text) {
|
|
13620
|
-
const
|
|
13804
|
+
const params = { message: text };
|
|
13805
|
+
const script = this.callScript("sendMessage", params) || this.callScript("sendMessage", text);
|
|
13621
13806
|
if (!script) throw new Error(`[${this.agentName}] sendMessage script not available`);
|
|
13622
13807
|
const result = await evaluate(script);
|
|
13623
13808
|
if (result && typeof result === "string" && result.startsWith("error:")) {
|
|
13624
13809
|
throw new Error(`[${this.agentName}] sendMessage failed: ${result}`);
|
|
13625
13810
|
}
|
|
13811
|
+
const parsed = this.parseMaybeJson(result);
|
|
13812
|
+
if (parsed === true) return;
|
|
13813
|
+
if (typeof parsed === "string") {
|
|
13814
|
+
const normalized = parsed.trim().toLowerCase();
|
|
13815
|
+
if (normalized === "ok" || normalized === "sent" || normalized === "success" || normalized === "true") {
|
|
13816
|
+
return;
|
|
13817
|
+
}
|
|
13818
|
+
}
|
|
13819
|
+
if (parsed && typeof parsed === "object") {
|
|
13820
|
+
if (parsed.sent === true || parsed.success === true || parsed.ok === true || parsed.submitted === true || parsed.dispatched === true) {
|
|
13821
|
+
return;
|
|
13822
|
+
}
|
|
13823
|
+
if (typeof parsed.error === "string" && parsed.error.trim()) {
|
|
13824
|
+
throw new Error(`[${this.agentName}] sendMessage failed: ${parsed.error}`);
|
|
13825
|
+
}
|
|
13826
|
+
}
|
|
13827
|
+
throw new Error(`[${this.agentName}] sendMessage was not confirmed`);
|
|
13626
13828
|
}
|
|
13627
13829
|
async resolveAction(evaluate, action, button) {
|
|
13628
13830
|
const script = this.callScript("resolveAction", { action, button });
|
|
@@ -19875,6 +20077,7 @@ var SessionHostRuntimeTransport = class {
|
|
|
19875
20077
|
}
|
|
19876
20078
|
}
|
|
19877
20079
|
handleEvent(event) {
|
|
20080
|
+
if (!("sessionId" in event)) return;
|
|
19878
20081
|
if (event.sessionId !== this.options.runtimeId) return;
|
|
19879
20082
|
if ((event.type === "session_started" || event.type === "session_resumed") && typeof event.pid === "number") {
|
|
19880
20083
|
this.currentPid = event.pid;
|
|
@@ -19950,7 +20153,10 @@ var SessionHostRuntimeTransport = class {
|
|
|
19950
20153
|
clientId: client.clientId,
|
|
19951
20154
|
type: client.type,
|
|
19952
20155
|
readOnly: client.readOnly
|
|
19953
|
-
}))
|
|
20156
|
+
})),
|
|
20157
|
+
restoredFromStorage: record.meta?.restoredFromStorage === true,
|
|
20158
|
+
recoveryState: typeof record.meta?.runtimeRecoveryState === "string" ? String(record.meta.runtimeRecoveryState) : null,
|
|
20159
|
+
recoveryError: typeof record.meta?.runtimeRecoveryError === "string" ? String(record.meta.runtimeRecoveryError) : null
|
|
19954
20160
|
};
|
|
19955
20161
|
}
|
|
19956
20162
|
enqueue(action) {
|
|
@@ -20397,6 +20603,7 @@ async function initDaemonComponents(config) {
|
|
|
20397
20603
|
onIdeConnected: () => poller?.start(),
|
|
20398
20604
|
onStatusChange: config.onStatusChange,
|
|
20399
20605
|
onPostChatCommand: config.onPostChatCommand,
|
|
20606
|
+
sessionHostControl: config.sessionHostControl,
|
|
20400
20607
|
getCdpLogFn: config.getCdpLogFn || ((ideType) => LOG.forComponent(`CDP:${ideType}`).asLogFn())
|
|
20401
20608
|
});
|
|
20402
20609
|
poller = new AgentStreamPoller({
|