@vibedeckx/linux-x64 0.3.4 → 0.3.5
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/bin.js +109 -43
- package/package.json +1 -1
package/dist/bin.js
CHANGED
|
@@ -205180,6 +205180,13 @@ function findTurnOpeningUserEntry(entries, beforeIndex) {
|
|
|
205180
205180
|
}
|
|
205181
205181
|
return opening;
|
|
205182
205182
|
}
|
|
205183
|
+
function findLatestUserEntry(entries) {
|
|
205184
|
+
for (let i = entries.length - 1; i >= 0; i--) {
|
|
205185
|
+
const entry = entries[i];
|
|
205186
|
+
if (entry?.type === "user") return entry;
|
|
205187
|
+
}
|
|
205188
|
+
return void 0;
|
|
205189
|
+
}
|
|
205183
205190
|
function resolveNotificationDisposition(openingUserEntry) {
|
|
205184
205191
|
if (openingUserEntry?.type !== "user") return "result";
|
|
205185
205192
|
if (openingUserEntry.notificationDisposition) return openingUserEntry.notificationDisposition;
|
|
@@ -228169,6 +228176,10 @@ var AgentSessionManager = class {
|
|
|
228169
228176
|
if (event.type === "turn_started" || event.type === "text" || event.type === "thinking" || event.type === "tool_use" || event.type === "tool_result" || event.type === "approval_request") {
|
|
228170
228177
|
this.applyCompletionTimerAction(session, session.completion.noteTurnActivity());
|
|
228171
228178
|
}
|
|
228179
|
+
if (session.turnOpenSince === null && (event.type === "turn_started" || event.type === "text" || event.type === "thinking" || event.type === "tool_use" || event.type === "tool_result" || event.type === "approval_request")) {
|
|
228180
|
+
session.turnOpenSince = timestamp;
|
|
228181
|
+
session.turnDisposition = resolveNotificationDisposition(findLatestUserEntry(session.store.entries));
|
|
228182
|
+
}
|
|
228172
228183
|
if (session.status !== "running" && (event.type === "text" || event.type === "thinking" || event.type === "tool_use" || event.type === "tool_result" || event.type === "approval_request")) {
|
|
228173
228184
|
session.status = "running";
|
|
228174
228185
|
if (!session.skipDb) await this.storage.agentSessions.updateStatus(sessionId, "running");
|
|
@@ -230244,6 +230255,26 @@ function tryParseWsMessage(raw) {
|
|
|
230244
230255
|
return void 0;
|
|
230245
230256
|
}
|
|
230246
230257
|
}
|
|
230258
|
+
function isEntryPatchFrame(parsed) {
|
|
230259
|
+
if (!parsed || !("JsonPatch" in parsed)) return false;
|
|
230260
|
+
const ops = parsed.JsonPatch;
|
|
230261
|
+
if (!Array.isArray(ops)) return false;
|
|
230262
|
+
return ops.some((op) => typeof op?.path === "string" && op.path.startsWith("/entries/"));
|
|
230263
|
+
}
|
|
230264
|
+
function entryPatchFrames(messages) {
|
|
230265
|
+
const frames = [];
|
|
230266
|
+
for (const raw of messages) {
|
|
230267
|
+
if (isEntryPatchFrame(tryParseWsMessage(raw))) frames.push(raw);
|
|
230268
|
+
}
|
|
230269
|
+
return frames;
|
|
230270
|
+
}
|
|
230271
|
+
function isSequencePrefix(cached2, replay) {
|
|
230272
|
+
if (cached2.length > replay.length) return false;
|
|
230273
|
+
for (let i = 0; i < cached2.length; i++) {
|
|
230274
|
+
if (cached2[i] !== replay[i]) return false;
|
|
230275
|
+
}
|
|
230276
|
+
return true;
|
|
230277
|
+
}
|
|
230247
230278
|
async function persistRemoteSessionActivityFrame(storage, sessionId, remoteInfo, parsed, activityAt = Date.now()) {
|
|
230248
230279
|
const projectId = projectIdFromRemoteSessionId(sessionId, remoteInfo);
|
|
230249
230280
|
const statusEvent = statusEventFromRemotePatch(parsed, sessionId, remoteInfo);
|
|
@@ -230307,6 +230338,7 @@ function connectPersistentRemoteWs(sessionId, remoteInfo, cache2, reverseConnect
|
|
|
230307
230338
|
const raw = data.toString();
|
|
230308
230339
|
const parsed = tryParseWsMessage(raw);
|
|
230309
230340
|
if (!parsed) return;
|
|
230341
|
+
if ("keepalive" in parsed) return;
|
|
230310
230342
|
const kind = "JsonPatch" in parsed ? "JsonPatch" : "finished" in parsed ? "finished" : "taskCompleted" in parsed ? "taskCompleted" : "workflowRunUpdated" in parsed ? "workflowRunUpdated" : "processAlive" in parsed ? "processAlive" : "branchActivity" in parsed ? "branchActivity" : "Ready" in parsed ? "Ready" : "error" in parsed ? "error" : "other";
|
|
230311
230343
|
if (kind === "JsonPatch") {
|
|
230312
230344
|
const ops = parsed.JsonPatch;
|
|
@@ -230454,23 +230486,18 @@ function connectPersistentRemoteWs(sessionId, remoteInfo, cache2, reverseConnect
|
|
|
230454
230486
|
if ("Ready" in parsed) {
|
|
230455
230487
|
syncing = false;
|
|
230456
230488
|
const currentEntry = cache2.get(sessionId);
|
|
230457
|
-
const
|
|
230458
|
-
|
|
230459
|
-
|
|
230460
|
-
|
|
230489
|
+
const cachedSeq = entryPatchFrames(currentEntry.messages);
|
|
230490
|
+
const extendsCache = isSequencePrefix(cachedSeq, replayBuffer);
|
|
230491
|
+
if (extendsCache && replayBuffer.length > cachedSeq.length) {
|
|
230492
|
+
const delta = replayBuffer.slice(cachedSeq.length);
|
|
230493
|
+
console.log(`[AgentWS] Sync delta: ${delta.length} new entry patches for ${sessionId} (remote=${replayBuffer.length}, cached=${cachedSeq.length})`);
|
|
230461
230494
|
for (const msg of delta) {
|
|
230462
|
-
|
|
230463
|
-
cache2.appendMessage(sessionId, msg, !!(p2 && "JsonPatch" in p2));
|
|
230495
|
+
cache2.appendMessage(sessionId, msg, true);
|
|
230464
230496
|
cache2.broadcast(sessionId, msg);
|
|
230465
230497
|
}
|
|
230466
|
-
} else if (
|
|
230467
|
-
console.log(`[AgentWS] Sync
|
|
230468
|
-
|
|
230469
|
-
for (const msg of replayBuffer) {
|
|
230470
|
-
const p2 = tryParseWsMessage(msg);
|
|
230471
|
-
if (p2 && "JsonPatch" in p2) newPatchCount++;
|
|
230472
|
-
}
|
|
230473
|
-
cache2.replaceAll(sessionId, [...replayBuffer], newPatchCount);
|
|
230498
|
+
} else if (!extendsCache) {
|
|
230499
|
+
console.log(`[AgentWS] Sync replace for ${sessionId}: remote=${replayBuffer.length}, cached=${cachedSeq.length} (sequence diverged or shrank)`);
|
|
230500
|
+
cache2.replaceAll(sessionId, [...replayBuffer], replayBuffer.length);
|
|
230474
230501
|
const clearPatch = {
|
|
230475
230502
|
JsonPatch: [{
|
|
230476
230503
|
op: "replace",
|
|
@@ -230488,12 +230515,15 @@ function connectPersistentRemoteWs(sessionId, remoteInfo, cache2, reverseConnect
|
|
|
230488
230515
|
remoteWs.on("message", handleLiveMessage);
|
|
230489
230516
|
return;
|
|
230490
230517
|
}
|
|
230491
|
-
if (
|
|
230518
|
+
if (isEntryPatchFrame(parsed)) {
|
|
230492
230519
|
replayBuffer.push(raw);
|
|
230520
|
+
return;
|
|
230493
230521
|
}
|
|
230494
230522
|
if ("finished" in parsed) {
|
|
230495
230523
|
cache2.setFinished(sessionId);
|
|
230524
|
+
return;
|
|
230496
230525
|
}
|
|
230526
|
+
handleLiveMessage(data);
|
|
230497
230527
|
});
|
|
230498
230528
|
}
|
|
230499
230529
|
remoteWs.on("error", (error48) => {
|
|
@@ -245476,6 +245506,7 @@ function attachRemoteProcessStream(fastify2, processId, send, onTerminal) {
|
|
|
245476
245506
|
} catch {
|
|
245477
245507
|
}
|
|
245478
245508
|
if (!parsed) return;
|
|
245509
|
+
if ("keepalive" in parsed) return;
|
|
245479
245510
|
send(parsed);
|
|
245480
245511
|
if (parsed.type === "finished" || parsed.type === "error") terminalSignalSent = true;
|
|
245481
245512
|
if (parsed.type === "finished" || parsed.type === "error") {
|
|
@@ -245630,6 +245661,47 @@ async function userOwnsSession(fastify2, sessionId, userId) {
|
|
|
245630
245661
|
return !!await fastify2.storage.projects.getById(session.project_id, userId);
|
|
245631
245662
|
}
|
|
245632
245663
|
|
|
245664
|
+
// src/utils/ws-heartbeat.ts
|
|
245665
|
+
var DEFAULT_INTERVAL_MS = 3e4;
|
|
245666
|
+
function attachWsHeartbeat(socket, { label, intervalMs = DEFAULT_INTERVAL_MS, keepalive = false }) {
|
|
245667
|
+
let awaitingPong = false;
|
|
245668
|
+
const markAlive = () => {
|
|
245669
|
+
awaitingPong = false;
|
|
245670
|
+
};
|
|
245671
|
+
socket.on("pong", markAlive);
|
|
245672
|
+
socket.on("message", markAlive);
|
|
245673
|
+
const timer = setInterval(() => {
|
|
245674
|
+
if (socket.readyState !== wrapper_default.OPEN) return;
|
|
245675
|
+
if (awaitingPong) {
|
|
245676
|
+
console.log(`[WsHeartbeat] ${label}: no pong within ${intervalMs * 2}ms \u2014 terminating dead socket`);
|
|
245677
|
+
try {
|
|
245678
|
+
socket.terminate();
|
|
245679
|
+
} catch {
|
|
245680
|
+
}
|
|
245681
|
+
return;
|
|
245682
|
+
}
|
|
245683
|
+
awaitingPong = true;
|
|
245684
|
+
try {
|
|
245685
|
+
socket.ping();
|
|
245686
|
+
} catch {
|
|
245687
|
+
}
|
|
245688
|
+
if (keepalive) {
|
|
245689
|
+
try {
|
|
245690
|
+
socket.send(JSON.stringify({ keepalive: Date.now() }));
|
|
245691
|
+
} catch {
|
|
245692
|
+
}
|
|
245693
|
+
}
|
|
245694
|
+
}, intervalMs);
|
|
245695
|
+
let cleaned = false;
|
|
245696
|
+
return () => {
|
|
245697
|
+
if (cleaned) return;
|
|
245698
|
+
cleaned = true;
|
|
245699
|
+
clearInterval(timer);
|
|
245700
|
+
socket.off("pong", markAlive);
|
|
245701
|
+
socket.off("message", markAlive);
|
|
245702
|
+
};
|
|
245703
|
+
}
|
|
245704
|
+
|
|
245633
245705
|
// src/routes/websocket-routes.ts
|
|
245634
245706
|
var routes24 = async (fastify2) => {
|
|
245635
245707
|
fastify2.reverseConnectManager.setStatusChangeHandler((remoteServerId, status) => {
|
|
@@ -245688,10 +245760,14 @@ var routes24 = async (fastify2) => {
|
|
|
245688
245760
|
}
|
|
245689
245761
|
return;
|
|
245690
245762
|
}
|
|
245763
|
+
const stopHeartbeat = attachWsHeartbeat(socket, {
|
|
245764
|
+
label: `ProjectChatWS thread=${req.params.threadId}`
|
|
245765
|
+
});
|
|
245691
245766
|
let cleaned = false;
|
|
245692
245767
|
const cleanup = () => {
|
|
245693
245768
|
if (cleaned) return;
|
|
245694
245769
|
cleaned = true;
|
|
245770
|
+
stopHeartbeat();
|
|
245695
245771
|
unsubscribe();
|
|
245696
245772
|
};
|
|
245697
245773
|
socket.on("close", cleanup);
|
|
@@ -245723,11 +245799,9 @@ var routes24 = async (fastify2) => {
|
|
|
245723
245799
|
return;
|
|
245724
245800
|
}
|
|
245725
245801
|
console.log(`[WebSocket] Client connected for process ${processId}`);
|
|
245726
|
-
const
|
|
245727
|
-
|
|
245728
|
-
|
|
245729
|
-
}
|
|
245730
|
-
}, 3e4);
|
|
245802
|
+
const stopHeartbeat = attachWsHeartbeat(socket, {
|
|
245803
|
+
label: `ExecutorWS process=${processId}`
|
|
245804
|
+
});
|
|
245731
245805
|
const send = (msg) => {
|
|
245732
245806
|
try {
|
|
245733
245807
|
socket.send(JSON.stringify(msg));
|
|
@@ -245753,7 +245827,7 @@ var routes24 = async (fastify2) => {
|
|
|
245753
245827
|
});
|
|
245754
245828
|
socket.on("close", () => {
|
|
245755
245829
|
console.log(`[WebSocket] Client disconnected from process ${processId}`);
|
|
245756
|
-
|
|
245830
|
+
stopHeartbeat();
|
|
245757
245831
|
handle.cleanup();
|
|
245758
245832
|
});
|
|
245759
245833
|
}
|
|
@@ -245769,11 +245843,7 @@ var routes24 = async (fastify2) => {
|
|
|
245769
245843
|
return;
|
|
245770
245844
|
}
|
|
245771
245845
|
console.log(`[ExecutorMux] Client connected`);
|
|
245772
|
-
const
|
|
245773
|
-
if (socket.readyState === wrapper_default.OPEN) {
|
|
245774
|
-
socket.ping();
|
|
245775
|
-
}
|
|
245776
|
-
}, 3e4);
|
|
245846
|
+
const stopHeartbeat = attachWsHeartbeat(socket, { label: "ExecutorMux" });
|
|
245777
245847
|
const subs = /* @__PURE__ */ new Map();
|
|
245778
245848
|
const handleInputMap = /* @__PURE__ */ new Map();
|
|
245779
245849
|
const subscribeProcess = async (processId) => {
|
|
@@ -245832,7 +245902,7 @@ var routes24 = async (fastify2) => {
|
|
|
245832
245902
|
});
|
|
245833
245903
|
socket.on("close", () => {
|
|
245834
245904
|
console.log(`[ExecutorMux] Client disconnected; cleaning ${subs.size} subscriptions`);
|
|
245835
|
-
|
|
245905
|
+
stopHeartbeat();
|
|
245836
245906
|
for (const cleanup of subs.values()) cleanup();
|
|
245837
245907
|
subs.clear();
|
|
245838
245908
|
handleInputMap.clear();
|
|
@@ -245876,15 +245946,15 @@ var routes24 = async (fastify2) => {
|
|
|
245876
245946
|
return;
|
|
245877
245947
|
}
|
|
245878
245948
|
console.log(`[AgentWS] Client connected for session ${sessionId}`);
|
|
245879
|
-
const
|
|
245880
|
-
|
|
245881
|
-
|
|
245882
|
-
|
|
245883
|
-
}, 3e4);
|
|
245949
|
+
const stopHeartbeat = attachWsHeartbeat(socket, {
|
|
245950
|
+
label: `AgentWS session=${sessionId}`,
|
|
245951
|
+
keepalive: true
|
|
245952
|
+
});
|
|
245884
245953
|
if (sessionId.startsWith("remote-")) {
|
|
245885
245954
|
const remoteInfo = fastify2.remoteSessionMap.get(sessionId);
|
|
245886
245955
|
if (!remoteInfo) {
|
|
245887
245956
|
console.log(`[AgentWS] Remote session ${sessionId} not found in map`);
|
|
245957
|
+
stopHeartbeat();
|
|
245888
245958
|
socket.send(JSON.stringify({ type: "error", message: "Remote session not found" }));
|
|
245889
245959
|
socket.close();
|
|
245890
245960
|
return;
|
|
@@ -245911,7 +245981,7 @@ var routes24 = async (fastify2) => {
|
|
|
245911
245981
|
}
|
|
245912
245982
|
cache2.addSubscriber(sessionId, socket);
|
|
245913
245983
|
socket.on("close", () => {
|
|
245914
|
-
|
|
245984
|
+
stopHeartbeat();
|
|
245915
245985
|
cache2.removeSubscriber(sessionId, socket);
|
|
245916
245986
|
});
|
|
245917
245987
|
return;
|
|
@@ -245952,7 +246022,7 @@ var routes24 = async (fastify2) => {
|
|
|
245952
246022
|
});
|
|
245953
246023
|
socket.on("close", () => {
|
|
245954
246024
|
console.log(`[AgentWS] Client disconnected from remote session ${sessionId}`);
|
|
245955
|
-
|
|
246025
|
+
stopHeartbeat();
|
|
245956
246026
|
cache2.removeSubscriber(sessionId, socket);
|
|
245957
246027
|
});
|
|
245958
246028
|
return;
|
|
@@ -245960,7 +246030,7 @@ var routes24 = async (fastify2) => {
|
|
|
245960
246030
|
const unsubscribe = fastify2.agentSessionManager.subscribe(sessionId, socket);
|
|
245961
246031
|
if (!unsubscribe) {
|
|
245962
246032
|
console.log(`[AgentWS] Session ${sessionId} not found`);
|
|
245963
|
-
|
|
246033
|
+
stopHeartbeat();
|
|
245964
246034
|
socket.send(JSON.stringify({ error: "Session not found" }));
|
|
245965
246035
|
socket.close();
|
|
245966
246036
|
return;
|
|
@@ -245979,7 +246049,7 @@ var routes24 = async (fastify2) => {
|
|
|
245979
246049
|
});
|
|
245980
246050
|
socket.on("close", () => {
|
|
245981
246051
|
console.log(`[AgentWS] Client disconnected from session ${sessionId}`);
|
|
245982
|
-
|
|
246052
|
+
stopHeartbeat();
|
|
245983
246053
|
unsubscribe?.();
|
|
245984
246054
|
});
|
|
245985
246055
|
}
|
|
@@ -246035,15 +246105,11 @@ var routes24 = async (fastify2) => {
|
|
|
246035
246105
|
}
|
|
246036
246106
|
}
|
|
246037
246107
|
console.log(`[ChatWS] Client connected for session ${sessionId}`);
|
|
246038
|
-
const
|
|
246039
|
-
if (socket.readyState === wrapper_default.OPEN) {
|
|
246040
|
-
socket.ping();
|
|
246041
|
-
}
|
|
246042
|
-
}, 3e4);
|
|
246108
|
+
const stopHeartbeat = attachWsHeartbeat(socket, { label: `ChatWS session=${sessionId}` });
|
|
246043
246109
|
const unsubscribe = fastify2.chatSessionManager.subscribe(sessionId, socket);
|
|
246044
246110
|
if (!unsubscribe) {
|
|
246045
246111
|
console.log(`[ChatWS] Session ${sessionId} not found`);
|
|
246046
|
-
|
|
246112
|
+
stopHeartbeat();
|
|
246047
246113
|
socket.send(JSON.stringify({ error: "Session not found" }));
|
|
246048
246114
|
socket.close();
|
|
246049
246115
|
return;
|
|
@@ -246063,7 +246129,7 @@ var routes24 = async (fastify2) => {
|
|
|
246063
246129
|
});
|
|
246064
246130
|
socket.on("close", () => {
|
|
246065
246131
|
console.log(`[ChatWS] Client disconnected from session ${sessionId}`);
|
|
246066
|
-
|
|
246132
|
+
stopHeartbeat();
|
|
246067
246133
|
unsubscribe?.();
|
|
246068
246134
|
});
|
|
246069
246135
|
}
|