chatroom-cli 1.106.0 → 1.107.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 +285 -103
- package/dist/index.js.map +12 -10
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -78981,6 +78981,9 @@ var init_machine_service = __esm(() => {
|
|
|
78981
78981
|
RegisterAgentMachineService = class RegisterAgentMachineService extends exports_Context.Tag("RegisterAgentMachineService")() {
|
|
78982
78982
|
};
|
|
78983
78983
|
});
|
|
78984
|
+
// ../../services/backend/convex/workspaceFileTree/access.ts
|
|
78985
|
+
var FILE_TREE_SYNC_DISABLED_CODE = "FILE_TREE_SYNC_DISABLED";
|
|
78986
|
+
var init_access = () => {};
|
|
78984
78987
|
|
|
78985
78988
|
// src/utils/convex-error.ts
|
|
78986
78989
|
function formatConvexErrorObject(data) {
|
|
@@ -79013,8 +79016,23 @@ function getErrorMessage(error) {
|
|
|
79013
79016
|
return formatServerError(error);
|
|
79014
79017
|
return String(error);
|
|
79015
79018
|
}
|
|
79019
|
+
function getConvexErrorCode(error) {
|
|
79020
|
+
if (!(error instanceof ConvexError))
|
|
79021
|
+
return;
|
|
79022
|
+
const data = error.data;
|
|
79023
|
+
if (data !== null && typeof data === "object" && "code" in data) {
|
|
79024
|
+
const code2 = data.code;
|
|
79025
|
+
if (typeof code2 === "string")
|
|
79026
|
+
return code2;
|
|
79027
|
+
}
|
|
79028
|
+
return;
|
|
79029
|
+
}
|
|
79030
|
+
function isFileTreeSyncDisabledError(error) {
|
|
79031
|
+
return getConvexErrorCode(error) === FILE_TREE_SYNC_DISABLED_CODE;
|
|
79032
|
+
}
|
|
79016
79033
|
var SERVER_ERROR_HINT;
|
|
79017
79034
|
var init_convex_error = __esm(() => {
|
|
79035
|
+
init_access();
|
|
79018
79036
|
init_values();
|
|
79019
79037
|
SERVER_ERROR_HINT = "This is a generic server error — likely a backend arg-validator rejection or a CLI/backend version mismatch." + " Verify the CLI and backend are on the same commit (run `pnpm install` and check `git log -1 origin/master`).";
|
|
79020
79038
|
});
|
|
@@ -116251,11 +116269,20 @@ async function publishCheckpointUntilPruned(session2, normalizedWorkingDir, snap
|
|
|
116251
116269
|
assertCheckpointAccepted(result);
|
|
116252
116270
|
return checkpointRevision;
|
|
116253
116271
|
}
|
|
116254
|
-
function createWorkspaceFileTreeCheckpointSend(session2, normalizedWorkingDir) {
|
|
116272
|
+
function createWorkspaceFileTreeCheckpointSend(session2, normalizedWorkingDir, options) {
|
|
116255
116273
|
return async (state) => {
|
|
116256
|
-
|
|
116257
|
-
|
|
116258
|
-
|
|
116274
|
+
try {
|
|
116275
|
+
const snapshot = await syncScannedFileTree(session2, normalizedWorkingDir, state.tree, computeFileTreeDataHash(state.tree), randomUUID11());
|
|
116276
|
+
const revision = await publishCheckpointUntilPruned(session2, normalizedWorkingDir, snapshot, state.revision);
|
|
116277
|
+
return { revision };
|
|
116278
|
+
} catch (error51) {
|
|
116279
|
+
if (!isFileTreeSyncDisabledError(error51))
|
|
116280
|
+
throw error51;
|
|
116281
|
+
(async () => options?.onSyncDisabled?.())().catch(() => {
|
|
116282
|
+
return;
|
|
116283
|
+
});
|
|
116284
|
+
return { revision: state.revision };
|
|
116285
|
+
}
|
|
116259
116286
|
};
|
|
116260
116287
|
}
|
|
116261
116288
|
var init_workspace_file_tree_checkpoint_send = __esm(() => {
|
|
@@ -116264,6 +116291,7 @@ var init_workspace_file_tree_checkpoint_send = __esm(() => {
|
|
|
116264
116291
|
init_file_tree_data_hash();
|
|
116265
116292
|
init_blob_snapshot_publish();
|
|
116266
116293
|
init_sharded_snapshot_publish();
|
|
116294
|
+
init_convex_error();
|
|
116267
116295
|
});
|
|
116268
116296
|
|
|
116269
116297
|
// src/daemon/infrastructure/outbox/workspace-file-tree-delta-send.ts
|
|
@@ -116285,52 +116313,81 @@ function toDeltaOperations(delta) {
|
|
|
116285
116313
|
}))
|
|
116286
116314
|
];
|
|
116287
116315
|
}
|
|
116288
|
-
function createWorkspaceFileTreeDeltaSend(session2, normalizedWorkingDir) {
|
|
116316
|
+
function createWorkspaceFileTreeDeltaSend(session2, normalizedWorkingDir, options) {
|
|
116289
116317
|
return async (unit) => {
|
|
116290
|
-
|
|
116291
|
-
|
|
116292
|
-
|
|
116293
|
-
|
|
116294
|
-
|
|
116295
|
-
|
|
116296
|
-
|
|
116297
|
-
|
|
116298
|
-
|
|
116299
|
-
|
|
116318
|
+
try {
|
|
116319
|
+
const result = await session2.backend.mutation(api.workspaceFiles.applyFileTreeDeltaBatch, {
|
|
116320
|
+
sessionId: session2.sessionId,
|
|
116321
|
+
machineId: session2.machineId,
|
|
116322
|
+
workingDir: normalizedWorkingDir,
|
|
116323
|
+
operationId: unit.delta.operationId,
|
|
116324
|
+
baseRevision: unit.baseRevision,
|
|
116325
|
+
operations: toDeltaOperations(unit.delta)
|
|
116326
|
+
});
|
|
116327
|
+
if (result.status === "resync-required") {
|
|
116328
|
+
return { status: "conflict", revision: result.expectedRevision };
|
|
116329
|
+
}
|
|
116330
|
+
return result;
|
|
116331
|
+
} catch (error51) {
|
|
116332
|
+
if (!isFileTreeSyncDisabledError(error51))
|
|
116333
|
+
throw error51;
|
|
116334
|
+
(async () => options?.onSyncDisabled?.())().catch(() => {
|
|
116335
|
+
return;
|
|
116336
|
+
});
|
|
116337
|
+
return { status: "applied", revision: unit.baseRevision };
|
|
116300
116338
|
}
|
|
116301
|
-
return result;
|
|
116302
116339
|
};
|
|
116303
116340
|
}
|
|
116304
116341
|
var init_workspace_file_tree_delta_send = __esm(() => {
|
|
116305
116342
|
init_api3();
|
|
116343
|
+
init_convex_error();
|
|
116306
116344
|
});
|
|
116307
116345
|
|
|
116308
116346
|
// src/daemon/entry/files/file-tree-subscription.ts
|
|
116309
116347
|
function logSubscriptionWarn(label, err) {
|
|
116310
116348
|
console.warn(`[${formatTimestamp()}] ⚠️ ${label}: ${getErrorMessage(err)}`);
|
|
116311
116349
|
}
|
|
116312
|
-
async function runOneShotFileTreeSync(session2, workingDir) {
|
|
116350
|
+
async function runOneShotFileTreeSync(session2, workingDir, coordinators, checkpointOutboxRegistry, deltaOutboxRegistry) {
|
|
116313
116351
|
const normalized = normalizeWorkingDirForLookup(workingDir);
|
|
116314
|
-
|
|
116315
|
-
|
|
116316
|
-
|
|
116317
|
-
|
|
116318
|
-
|
|
116319
|
-
|
|
116320
|
-
|
|
116321
|
-
|
|
116352
|
+
let syncDisabled = false;
|
|
116353
|
+
try {
|
|
116354
|
+
const tree = await scanFileTree(normalized);
|
|
116355
|
+
const send = createWorkspaceFileTreeCheckpointSend(session2, normalized, {
|
|
116356
|
+
onSyncDisabled: () => {
|
|
116357
|
+
syncDisabled = true;
|
|
116358
|
+
}
|
|
116359
|
+
});
|
|
116360
|
+
await send({ tree, revision: 0 });
|
|
116361
|
+
if (syncDisabled) {
|
|
116362
|
+
await stopFileTreeSyncForDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized);
|
|
116363
|
+
return;
|
|
116364
|
+
}
|
|
116365
|
+
await session2.backend.mutation(api.workspaceFiles.fulfillFileTreeRequest, {
|
|
116366
|
+
sessionId: session2.sessionId,
|
|
116367
|
+
machineId: session2.machineId,
|
|
116368
|
+
workingDir: normalized
|
|
116369
|
+
});
|
|
116370
|
+
} catch (error51) {
|
|
116371
|
+
if (!isFileTreeSyncDisabledError(error51))
|
|
116372
|
+
throw error51;
|
|
116373
|
+
await stopFileTreeSyncForDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized);
|
|
116374
|
+
}
|
|
116322
116375
|
}
|
|
116323
116376
|
async function stopCoordinatorForWorkingDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized) {
|
|
116324
116377
|
const coordinatorPromise = coordinators.get(normalized);
|
|
116325
|
-
if (
|
|
116326
|
-
|
|
116327
|
-
|
|
116328
|
-
|
|
116329
|
-
|
|
116330
|
-
}
|
|
116378
|
+
if (coordinatorPromise) {
|
|
116379
|
+
coordinators.delete(normalized);
|
|
116380
|
+
await coordinatorPromise.then((coordinator2) => coordinator2.stop()).catch(() => {
|
|
116381
|
+
return;
|
|
116382
|
+
});
|
|
116383
|
+
}
|
|
116331
116384
|
await checkpointOutboxRegistry?.stop(normalized);
|
|
116332
116385
|
await deltaOutboxRegistry?.stop(normalized);
|
|
116333
116386
|
}
|
|
116387
|
+
async function stopFileTreeSyncForDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized) {
|
|
116388
|
+
await stopCoordinatorForWorkingDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized);
|
|
116389
|
+
console.log(`[${formatTimestamp()}] \uD83C\uDF33 File tree sync disabled: ${normalized}`);
|
|
116390
|
+
}
|
|
116334
116391
|
async function drainPendingFileTreeReleaseRequests(session2, coordinators, checkpointOutboxRegistry, deltaOutboxRegistry) {
|
|
116335
116392
|
while (true) {
|
|
116336
116393
|
const releases = await session2.backend.query(api.workspaceFiles.getPendingFileTreeReleaseRequests, {
|
|
@@ -116346,13 +116403,12 @@ async function drainPendingFileTreeReleaseRequests(session2, coordinators, check
|
|
|
116346
116403
|
let successCount = 0;
|
|
116347
116404
|
for (const normalized of releasesByDir) {
|
|
116348
116405
|
try {
|
|
116349
|
-
await
|
|
116406
|
+
await stopFileTreeSyncForDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized);
|
|
116350
116407
|
await session2.backend.mutation(api.workspaceFiles.fulfillFileTreeReleaseRequest, {
|
|
116351
116408
|
sessionId: session2.sessionId,
|
|
116352
116409
|
machineId: session2.machineId,
|
|
116353
116410
|
workingDir: normalized
|
|
116354
116411
|
});
|
|
116355
|
-
console.log(`[${formatTimestamp()}] \uD83C\uDF33 File tree coordinator stopped: ${normalized}`);
|
|
116356
116412
|
successCount++;
|
|
116357
116413
|
} catch (err) {
|
|
116358
116414
|
logSubscriptionWarn(`File tree release failed for ${normalized}`, err);
|
|
@@ -116371,7 +116427,7 @@ async function processOnePendingFileTreeRequest(session2, coordinators, ensureCo
|
|
|
116371
116427
|
});
|
|
116372
116428
|
if (!lease?.leaseActive) {
|
|
116373
116429
|
await stopCoordinatorForWorkingDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized);
|
|
116374
|
-
await runOneShotFileTreeSync(session2, normalized);
|
|
116430
|
+
await runOneShotFileTreeSync(session2, normalized, coordinators, checkpointOutboxRegistry, deltaOutboxRegistry);
|
|
116375
116431
|
console.log(`[${formatTimestamp()}] \uD83C\uDF33 File tree ready: ${normalized} (${Date.now() - start3}ms, one-shot)`);
|
|
116376
116432
|
return;
|
|
116377
116433
|
}
|
|
@@ -116404,6 +116460,10 @@ async function processPendingFileTreeRequests(session2, coordinators, ensureCoor
|
|
|
116404
116460
|
try {
|
|
116405
116461
|
await processOnePendingFileTreeRequest(session2, coordinators, ensureCoordinator, normalized, force, checkpointOutboxRegistry, deltaOutboxRegistry);
|
|
116406
116462
|
} catch (err) {
|
|
116463
|
+
if (isFileTreeSyncDisabledError(err)) {
|
|
116464
|
+
await stopFileTreeSyncForDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized);
|
|
116465
|
+
return;
|
|
116466
|
+
}
|
|
116407
116467
|
logSubscriptionWarn(`File tree failed for ${normalized}`, err);
|
|
116408
116468
|
}
|
|
116409
116469
|
});
|
|
@@ -116420,16 +116480,40 @@ var startFileTreeSubscriptionEffect = () => exports_Effect.gen(function* () {
|
|
|
116420
116480
|
const session2 = yield* DaemonSessionService;
|
|
116421
116481
|
const coordinators = new Map;
|
|
116422
116482
|
const checkpointOutboxRegistry = createWorkspaceFileTreeCheckpointOutboxRegistry(session2.machineId, (normalized) => {
|
|
116423
|
-
const
|
|
116483
|
+
const onSyncDisabled = () => stopFileTreeSyncForDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized);
|
|
116484
|
+
const send = createWorkspaceFileTreeCheckpointSend(session2, normalized, {
|
|
116485
|
+
onSyncDisabled
|
|
116486
|
+
});
|
|
116424
116487
|
return async (state) => {
|
|
116425
116488
|
const result = await send(state);
|
|
116426
116489
|
console.log(`[${formatTimestamp()}] \uD83C\uDF33 File tree checkpoint: ${normalized} (${state.tree.entries.length} entries, revision ${result.revision})`);
|
|
116427
116490
|
return result;
|
|
116428
116491
|
};
|
|
116429
116492
|
}, {
|
|
116430
|
-
onError: (normalized, error51) =>
|
|
116493
|
+
onError: (normalized, error51) => {
|
|
116494
|
+
if (isFileTreeSyncDisabledError(error51)) {
|
|
116495
|
+
stopFileTreeSyncForDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized).catch(() => {
|
|
116496
|
+
return;
|
|
116497
|
+
});
|
|
116498
|
+
return;
|
|
116499
|
+
}
|
|
116500
|
+
logSubscriptionWarn(`File tree checkpoint outbox failed for ${normalized}`, error51);
|
|
116501
|
+
}
|
|
116502
|
+
});
|
|
116503
|
+
const deltaOutboxRegistry = createWorkspaceFileTreeDeltaOutboxRegistry(session2.machineId, (normalized) => {
|
|
116504
|
+
const onSyncDisabled = () => stopFileTreeSyncForDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized);
|
|
116505
|
+
return createWorkspaceFileTreeDeltaSend(session2, normalized, { onSyncDisabled });
|
|
116506
|
+
}, {
|
|
116507
|
+
onError: (normalized, error51) => {
|
|
116508
|
+
if (isFileTreeSyncDisabledError(error51)) {
|
|
116509
|
+
stopFileTreeSyncForDir(coordinators, checkpointOutboxRegistry, deltaOutboxRegistry, normalized).catch(() => {
|
|
116510
|
+
return;
|
|
116511
|
+
});
|
|
116512
|
+
return;
|
|
116513
|
+
}
|
|
116514
|
+
logSubscriptionWarn(`File tree delta outbox failed for ${normalized}`, error51);
|
|
116515
|
+
}
|
|
116431
116516
|
});
|
|
116432
|
-
const deltaOutboxRegistry = createWorkspaceFileTreeDeltaOutboxRegistry(session2.machineId, (normalized) => createWorkspaceFileTreeDeltaSend(session2, normalized));
|
|
116433
116517
|
const ensureCoordinator = (workingDir, forceReconcile) => {
|
|
116434
116518
|
const normalized = normalizeWorkingDirForLookup(workingDir);
|
|
116435
116519
|
let coordinatorPromise = coordinators.get(normalized);
|
|
@@ -117699,14 +117783,47 @@ var init_task_delivery_processor = __esm(() => {
|
|
|
117699
117783
|
init_task_delivery_logic();
|
|
117700
117784
|
});
|
|
117701
117785
|
|
|
117786
|
+
// src/daemon/infrastructure/agent-operational/operational-signal-contract.ts
|
|
117787
|
+
function asChatroomId(chatroomId) {
|
|
117788
|
+
return chatroomId;
|
|
117789
|
+
}
|
|
117790
|
+
function buildSubscribeMachineOperationalSignalsSinceArgs(input) {
|
|
117791
|
+
return {
|
|
117792
|
+
sessionId: input.sessionId,
|
|
117793
|
+
machineId: input.machineId,
|
|
117794
|
+
chatroomId: asChatroomId(input.chatroomId),
|
|
117795
|
+
afterKey: input.afterKey,
|
|
117796
|
+
...input.limit === undefined ? {} : { limit: input.limit }
|
|
117797
|
+
};
|
|
117798
|
+
}
|
|
117799
|
+
function buildListOperationalStatusForMachineSignalRangeArgs(input) {
|
|
117800
|
+
return {
|
|
117801
|
+
sessionId: input.sessionId,
|
|
117802
|
+
machineId: input.machineId,
|
|
117803
|
+
chatroomId: asChatroomId(input.chatroomId),
|
|
117804
|
+
afterSignalKey: input.afterSignalKey,
|
|
117805
|
+
throughSignalKey: input.throughSignalKey,
|
|
117806
|
+
...input.limit === undefined ? {} : { limit: input.limit }
|
|
117807
|
+
};
|
|
117808
|
+
}
|
|
117809
|
+
function buildAckMachineOperationalSignalsArgs(input) {
|
|
117810
|
+
return {
|
|
117811
|
+
sessionId: input.sessionId,
|
|
117812
|
+
machineId: input.machineId,
|
|
117813
|
+
chatroomId: asChatroomId(input.chatroomId),
|
|
117814
|
+
throughSignalKey: input.throughSignalKey
|
|
117815
|
+
};
|
|
117816
|
+
}
|
|
117817
|
+
|
|
117702
117818
|
// src/daemon/infrastructure/agent-operational/ack-machine-operational-signals.ts
|
|
117703
|
-
async function ackMachineOperationalSignals(sessionDeps, machineId, throughSignalKey) {
|
|
117819
|
+
async function ackMachineOperationalSignals(sessionDeps, machineId, chatroomId, throughSignalKey) {
|
|
117704
117820
|
while (true) {
|
|
117705
|
-
const result = await sessionDeps.backend.mutation(api.machines.ackMachineOperationalSignals, {
|
|
117821
|
+
const result = await sessionDeps.backend.mutation(api.machines.ackMachineOperationalSignals, buildAckMachineOperationalSignalsArgs({
|
|
117706
117822
|
sessionId: sessionDeps.sessionId,
|
|
117707
117823
|
machineId,
|
|
117824
|
+
chatroomId,
|
|
117708
117825
|
throughSignalKey
|
|
117709
|
-
});
|
|
117826
|
+
}));
|
|
117710
117827
|
if (!result.hasMore)
|
|
117711
117828
|
return;
|
|
117712
117829
|
if (result.deletedCount === 0) {
|
|
@@ -117789,12 +117906,13 @@ function waitForOperationalSignalPage(options, afterSignalKey) {
|
|
|
117789
117906
|
settle2(() => reject(error51));
|
|
117790
117907
|
return;
|
|
117791
117908
|
}
|
|
117792
|
-
unsubscribe = options.client.onUpdate(api.machines.subscribeMachineOperationalSignalsSince, {
|
|
117909
|
+
unsubscribe = options.client.onUpdate(api.machines.subscribeMachineOperationalSignalsSince, buildSubscribeMachineOperationalSignalsSinceArgs({
|
|
117793
117910
|
sessionId: options.sessionId,
|
|
117794
117911
|
machineId: options.machineId,
|
|
117912
|
+
chatroomId: options.chatroomId,
|
|
117795
117913
|
afterKey: afterSignalKey,
|
|
117796
117914
|
limit: options.signalPageLimit ?? DEFAULT_SIGNAL_PAGE_LIMIT
|
|
117797
|
-
}, (result) => {
|
|
117915
|
+
}), (result) => {
|
|
117798
117916
|
if (!result || typeof result !== "object")
|
|
117799
117917
|
return;
|
|
117800
117918
|
const page = result;
|
|
@@ -117826,13 +117944,14 @@ async function fetchRowsForSignalPage(options, page) {
|
|
|
117826
117944
|
let afterSignalKey = page.afterSignalKey;
|
|
117827
117945
|
while (true) {
|
|
117828
117946
|
throwIfAborted(options.signal);
|
|
117829
|
-
const result = await options.client.query(api.machines.listOperationalStatusForMachineSignalRange, {
|
|
117947
|
+
const result = await options.client.query(api.machines.listOperationalStatusForMachineSignalRange, buildListOperationalStatusForMachineSignalRangeArgs({
|
|
117830
117948
|
sessionId: options.sessionId,
|
|
117831
117949
|
machineId: options.machineId,
|
|
117950
|
+
chatroomId: options.chatroomId,
|
|
117832
117951
|
afterSignalKey,
|
|
117833
117952
|
throughSignalKey: page.highSignalKey,
|
|
117834
117953
|
limit: options.operationalPageLimit ?? DEFAULT_OPERATIONAL_PAGE_LIMIT
|
|
117835
|
-
});
|
|
117954
|
+
}));
|
|
117836
117955
|
rows.push(...result.rows);
|
|
117837
117956
|
removed.push(...result.removed);
|
|
117838
117957
|
if (!result.hasMore || !result.nextSignalKey)
|
|
@@ -117845,6 +117964,7 @@ async function runOperationalInbox(options, onUpdate) {
|
|
|
117845
117964
|
for await (const page of createOperationalSignalIterator(options)) {
|
|
117846
117965
|
const hydrated = await fetchRowsForSignalPage(options, page);
|
|
117847
117966
|
await onUpdate({
|
|
117967
|
+
chatroomId: options.chatroomId,
|
|
117848
117968
|
signals: page.items,
|
|
117849
117969
|
rows: hydrated.rows,
|
|
117850
117970
|
removed: hydrated.removed,
|
|
@@ -118152,6 +118272,10 @@ async function bootstrapMachineAssignedTaskSnapshots(deps) {
|
|
|
118152
118272
|
});
|
|
118153
118273
|
const tasks = await fetchMachineAssignedTaskSnapshots(deps.sessionDeps, deps.machineId);
|
|
118154
118274
|
deps.taskSnapshotState?.replace(tasks);
|
|
118275
|
+
const chatroomIds = [...new Set(tasks.map((task) => task.chatroomId))];
|
|
118276
|
+
if (chatroomIds.length > 0) {
|
|
118277
|
+
await deps.onDiscoveredChatrooms?.(chatroomIds);
|
|
118278
|
+
}
|
|
118155
118279
|
if (!tasks.length)
|
|
118156
118280
|
return;
|
|
118157
118281
|
await processTasksUpdate(deps.runtime, deps.effectContext, deps.cooldown, deps.agentMgr, deps.sessionDeps, deps.machineId, "bootstrap", { snapshots: enrichSnapshotsWithOperational(tasks) });
|
|
@@ -118159,6 +118283,9 @@ async function bootstrapMachineAssignedTaskSnapshots(deps) {
|
|
|
118159
118283
|
function isAbortError2(error51) {
|
|
118160
118284
|
return error51 instanceof Error && error51.name === "AbortError";
|
|
118161
118285
|
}
|
|
118286
|
+
function operationalScopeKey(machineId, chatroomId) {
|
|
118287
|
+
return JSON.stringify([machineId, chatroomId]);
|
|
118288
|
+
}
|
|
118162
118289
|
async function runInboxLoopWithRestart(options, onUpdate, isStopped) {
|
|
118163
118290
|
let backoffMs = INBOX_RESTART_INITIAL_MS;
|
|
118164
118291
|
while (!isStopped()) {
|
|
@@ -118183,7 +118310,7 @@ async function runOperationalInboxLoopWithRestart(options, onUpdate, isStopped)
|
|
|
118183
118310
|
} catch (error51) {
|
|
118184
118311
|
if (isStopped() || isAbortError2(error51))
|
|
118185
118312
|
return;
|
|
118186
|
-
console.warn(`[OperationalInbox] loop error, restarting in ${backoffMs}ms:`, error51);
|
|
118313
|
+
console.warn(`[OperationalInbox room=${options.chatroomId}] loop error, restarting in ${backoffMs}ms:`, error51);
|
|
118187
118314
|
await new Promise((resolve8) => setTimeout(resolve8, backoffMs));
|
|
118188
118315
|
backoffMs = Math.min(backoffMs * 2, INBOX_RESTART_MAX_MS);
|
|
118189
118316
|
}
|
|
@@ -118208,23 +118335,19 @@ var NATIVE_DELIVERY_RECONCILE_MS = 1e4, INBOX_RESTART_INITIAL_MS = 1000, INBOX_R
|
|
|
118208
118335
|
query: (fn2, args2) => session2.backend.query(fn2, args2)
|
|
118209
118336
|
}
|
|
118210
118337
|
};
|
|
118211
|
-
console.log(`[${formatTimestamp()}] \uD83D\uDCEC Starting task-inbox (
|
|
118338
|
+
console.log(`[${formatTimestamp()}] \uD83D\uDCEC Starting task-inbox (chatroom-scoped operational signals)`);
|
|
118212
118339
|
const inboxStore = createInboxStateStore(resolveInboxDbPath(session2.machineId));
|
|
118213
118340
|
const persisted = inboxStore.get({
|
|
118214
118341
|
inboxType: "task",
|
|
118215
118342
|
scopeKey: session2.machineId
|
|
118216
118343
|
});
|
|
118217
|
-
const persistedOperational = inboxStore.get({
|
|
118218
|
-
inboxType: "operational",
|
|
118219
|
-
scopeKey: session2.machineId
|
|
118220
|
-
});
|
|
118221
118344
|
const serviceStartedAt = Date.now();
|
|
118222
|
-
const persistedOperationalKey = persistedOperational?.state.afterSignalKey;
|
|
118223
|
-
const initialOperationalKey = persistedOperationalKey ?? operationalSignalCursorAt(serviceStartedAt);
|
|
118224
118345
|
const abort = new AbortController;
|
|
118225
118346
|
let stopped = false;
|
|
118226
118347
|
const taskSnapshotState = new MachineTaskSnapshotState;
|
|
118227
118348
|
const agentOperationalReadModel = new AgentOperationalReadModel;
|
|
118349
|
+
const knownRoomIds = new Set;
|
|
118350
|
+
const roomWatchers = new Map;
|
|
118228
118351
|
registerNativeDeliverySession({
|
|
118229
118352
|
runtime: runtime4,
|
|
118230
118353
|
effectContext: effectContext2,
|
|
@@ -118236,7 +118359,7 @@ var NATIVE_DELIVERY_RECONCILE_MS = 1e4, INBOX_RESTART_INITIAL_MS = 1000, INBOX_R
|
|
|
118236
118359
|
lifecycleOutbox
|
|
118237
118360
|
});
|
|
118238
118361
|
const cooldown = new RecoveryCooldown;
|
|
118239
|
-
let
|
|
118362
|
+
let inboxUpdatesInFlight = 0;
|
|
118240
118363
|
let reconcileInFlight = false;
|
|
118241
118364
|
const inboxOptions = {
|
|
118242
118365
|
client: wsClient2,
|
|
@@ -118246,41 +118369,95 @@ var NATIVE_DELIVERY_RECONCILE_MS = 1e4, INBOX_RESTART_INITIAL_MS = 1000, INBOX_R
|
|
|
118246
118369
|
initialAfterSignalKey: persisted?.state.afterSignalKey,
|
|
118247
118370
|
signal: abort.signal
|
|
118248
118371
|
};
|
|
118249
|
-
const inboxHandler = async (update6) => {
|
|
118250
|
-
inboxUpdateInFlight = true;
|
|
118251
|
-
try {
|
|
118252
|
-
await handleTaskInboxUpdate(update6, {
|
|
118253
|
-
runtime: runtime4,
|
|
118254
|
-
effectContext: effectContext2,
|
|
118255
|
-
cooldown,
|
|
118256
|
-
agentMgr,
|
|
118257
|
-
sessionDeps,
|
|
118258
|
-
machineId: session2.machineId,
|
|
118259
|
-
taskSnapshotState
|
|
118260
|
-
});
|
|
118261
|
-
inboxStore.save({ inboxType: "task", scopeKey: session2.machineId }, { afterSignalKey: update6.throughSignalKey });
|
|
118262
|
-
} finally {
|
|
118263
|
-
inboxUpdateInFlight = false;
|
|
118264
|
-
}
|
|
118265
|
-
};
|
|
118266
118372
|
const bootstrapSucceeded = yield* exports_Effect.tryPromise(async () => {
|
|
118267
118373
|
const rows = await fetchMachineAgentOperationalStatus(sessionDeps, session2.machineId);
|
|
118268
118374
|
agentOperationalReadModel.replace(rows);
|
|
118375
|
+
for (const row of rows)
|
|
118376
|
+
knownRoomIds.add(row.chatroomId);
|
|
118269
118377
|
return true;
|
|
118270
118378
|
}).pipe(exports_Effect.catchAll((error51) => {
|
|
118271
118379
|
console.warn("[OperationalInbox] bootstrap failed:", error51);
|
|
118272
118380
|
return exports_Effect.succeed(false);
|
|
118273
118381
|
}));
|
|
118274
|
-
|
|
118275
|
-
|
|
118276
|
-
|
|
118382
|
+
const operationalHandler = async (update6) => {
|
|
118383
|
+
const chatroomId = update6.chatroomId;
|
|
118384
|
+
inboxUpdatesInFlight += 1;
|
|
118277
118385
|
try {
|
|
118278
|
-
|
|
118279
|
-
|
|
118280
|
-
|
|
118281
|
-
|
|
118386
|
+
const changed = agentOperationalReadModel.applySignalPage(update6.rows, update6.removed);
|
|
118387
|
+
const snapshots = changed.flatMap(({ chatroomId: roomId, role }) => taskSnapshotState.listForRole(roomId, role));
|
|
118388
|
+
if (snapshots.length > 0) {
|
|
118389
|
+
await processTasksUpdate(runtime4, effectContext2, cooldown, agentMgr, sessionDeps, session2.machineId, "operational-status", { snapshots: enrichSnapshotsWithOperational(snapshots) });
|
|
118390
|
+
}
|
|
118391
|
+
inboxStore.save({
|
|
118392
|
+
inboxType: "operational",
|
|
118393
|
+
scopeKey: operationalScopeKey(session2.machineId, chatroomId)
|
|
118394
|
+
}, { afterSignalKey: update6.throughSignalKey });
|
|
118395
|
+
try {
|
|
118396
|
+
await ackMachineOperationalSignals(sessionDeps, session2.machineId, chatroomId, update6.throughSignalKey);
|
|
118397
|
+
} catch (error51) {
|
|
118398
|
+
console.warn(`[OperationalInbox room=${chatroomId}] signal cleanup failed:`, error51);
|
|
118399
|
+
}
|
|
118400
|
+
} finally {
|
|
118401
|
+
inboxUpdatesInFlight -= 1;
|
|
118282
118402
|
}
|
|
118283
|
-
}
|
|
118403
|
+
};
|
|
118404
|
+
const ensureOperationalInbox = (chatroomId) => {
|
|
118405
|
+
const existing = roomWatchers.get(chatroomId);
|
|
118406
|
+
if (existing)
|
|
118407
|
+
return existing.startPromise;
|
|
118408
|
+
const controller = new AbortController;
|
|
118409
|
+
const entry = {
|
|
118410
|
+
controller,
|
|
118411
|
+
startPromise: Promise.resolve()
|
|
118412
|
+
};
|
|
118413
|
+
roomWatchers.set(chatroomId, entry);
|
|
118414
|
+
entry.startPromise = (async () => {
|
|
118415
|
+
if (!knownRoomIds.has(chatroomId)) {
|
|
118416
|
+
try {
|
|
118417
|
+
const current = await fetchMachineAgentOperationalStatus(sessionDeps, session2.machineId);
|
|
118418
|
+
agentOperationalReadModel.replace(current);
|
|
118419
|
+
for (const row of current)
|
|
118420
|
+
knownRoomIds.add(row.chatroomId);
|
|
118421
|
+
} catch (error51) {
|
|
118422
|
+
console.warn(`[OperationalInbox room=${chatroomId}] operational hydration failed:`, error51);
|
|
118423
|
+
}
|
|
118424
|
+
}
|
|
118425
|
+
const roomKey = {
|
|
118426
|
+
inboxType: "operational",
|
|
118427
|
+
scopeKey: operationalScopeKey(session2.machineId, chatroomId)
|
|
118428
|
+
};
|
|
118429
|
+
const persistedRoom = inboxStore.get(roomKey);
|
|
118430
|
+
let initialCursor;
|
|
118431
|
+
if (persistedRoom) {
|
|
118432
|
+
initialCursor = persistedRoom.state.afterSignalKey;
|
|
118433
|
+
ackMachineOperationalSignals(sessionDeps, session2.machineId, chatroomId, initialCursor).catch((error51) => console.warn(`[OperationalInbox room=${chatroomId}] startup signal cleanup failed:`, error51));
|
|
118434
|
+
} else if (bootstrapSucceeded) {
|
|
118435
|
+
initialCursor = operationalSignalCursorAt(serviceStartedAt);
|
|
118436
|
+
try {
|
|
118437
|
+
inboxStore.save(roomKey, { afterSignalKey: initialCursor });
|
|
118438
|
+
ackMachineOperationalSignals(sessionDeps, session2.machineId, chatroomId, initialCursor).catch((error51) => console.warn(`[OperationalInbox room=${chatroomId}] startup signal cleanup failed:`, error51));
|
|
118439
|
+
} catch (error51) {
|
|
118440
|
+
console.warn(`[OperationalInbox room=${chatroomId}] failed to persist bootstrap baseline:`, error51);
|
|
118441
|
+
}
|
|
118442
|
+
} else {
|
|
118443
|
+
initialCursor = operationalSignalCursorAt(serviceStartedAt);
|
|
118444
|
+
}
|
|
118445
|
+
runOperationalInboxLoopWithRestart({
|
|
118446
|
+
client: wsClient2,
|
|
118447
|
+
sessionId: session2.sessionId,
|
|
118448
|
+
machineId: session2.machineId,
|
|
118449
|
+
chatroomId,
|
|
118450
|
+
serviceStartedAt,
|
|
118451
|
+
initialAfterSignalKey: initialCursor,
|
|
118452
|
+
signal: controller.signal
|
|
118453
|
+
}, operationalHandler, () => stopped);
|
|
118454
|
+
})();
|
|
118455
|
+
return entry.startPromise;
|
|
118456
|
+
};
|
|
118457
|
+
yield* exports_Effect.tryPromise(() => Promise.all([...knownRoomIds].map((chatroomId) => ensureOperationalInbox(chatroomId)))).pipe(exports_Effect.catchAll((error51) => {
|
|
118458
|
+
console.warn("[OperationalInbox] initial watcher start failed:", error51);
|
|
118459
|
+
return exports_Effect.void;
|
|
118460
|
+
}));
|
|
118284
118461
|
yield* exports_Effect.tryPromise(() => bootstrapMachineAssignedTaskSnapshots({
|
|
118285
118462
|
sessionDeps,
|
|
118286
118463
|
runtime: runtime4,
|
|
@@ -118288,39 +118465,42 @@ var NATIVE_DELIVERY_RECONCILE_MS = 1e4, INBOX_RESTART_INITIAL_MS = 1000, INBOX_R
|
|
|
118288
118465
|
cooldown,
|
|
118289
118466
|
agentMgr,
|
|
118290
118467
|
machineId: session2.machineId,
|
|
118291
|
-
taskSnapshotState
|
|
118468
|
+
taskSnapshotState,
|
|
118469
|
+
onDiscoveredChatrooms: async (chatroomIds) => {
|
|
118470
|
+
await Promise.all(chatroomIds.map((chatroomId) => ensureOperationalInbox(chatroomId)));
|
|
118471
|
+
}
|
|
118292
118472
|
})).pipe(exports_Effect.catchAll((error51) => {
|
|
118293
118473
|
console.warn("[TaskInbox] bootstrap failed:", error51);
|
|
118294
118474
|
return exports_Effect.void;
|
|
118295
118475
|
}));
|
|
118296
|
-
const
|
|
118297
|
-
|
|
118298
|
-
sessionId: session2.sessionId,
|
|
118299
|
-
machineId: session2.machineId,
|
|
118300
|
-
serviceStartedAt,
|
|
118301
|
-
initialAfterSignalKey: initialOperationalKey,
|
|
118302
|
-
signal: abort.signal
|
|
118303
|
-
};
|
|
118304
|
-
const operationalInboxHandler = async (update6) => {
|
|
118305
|
-
inboxUpdateInFlight = true;
|
|
118476
|
+
const inboxHandler = async (update6) => {
|
|
118477
|
+
inboxUpdatesInFlight += 1;
|
|
118306
118478
|
try {
|
|
118307
|
-
const
|
|
118308
|
-
|
|
118309
|
-
|
|
118310
|
-
|
|
118311
|
-
|
|
118312
|
-
|
|
118313
|
-
|
|
118314
|
-
await
|
|
118315
|
-
} catch (error51) {
|
|
118316
|
-
console.warn("[OperationalInbox] signal cleanup failed:", error51);
|
|
118479
|
+
const chatroomIds = [
|
|
118480
|
+
...new Set([
|
|
118481
|
+
...update6.snapshots.map((snapshot) => snapshot.chatroomId),
|
|
118482
|
+
...update6.signals.map((signal) => signal.chatroomId)
|
|
118483
|
+
])
|
|
118484
|
+
];
|
|
118485
|
+
if (chatroomIds.length > 0) {
|
|
118486
|
+
await Promise.all(chatroomIds.map((chatroomId) => ensureOperationalInbox(chatroomId)));
|
|
118317
118487
|
}
|
|
118488
|
+
await handleTaskInboxUpdate(update6, {
|
|
118489
|
+
runtime: runtime4,
|
|
118490
|
+
effectContext: effectContext2,
|
|
118491
|
+
cooldown,
|
|
118492
|
+
agentMgr,
|
|
118493
|
+
sessionDeps,
|
|
118494
|
+
machineId: session2.machineId,
|
|
118495
|
+
taskSnapshotState
|
|
118496
|
+
});
|
|
118497
|
+
inboxStore.save({ inboxType: "task", scopeKey: session2.machineId }, { afterSignalKey: update6.throughSignalKey });
|
|
118318
118498
|
} finally {
|
|
118319
|
-
|
|
118499
|
+
inboxUpdatesInFlight -= 1;
|
|
118320
118500
|
}
|
|
118321
118501
|
};
|
|
118322
118502
|
const reconcileTimer = setInterval(() => {
|
|
118323
|
-
if (stopped ||
|
|
118503
|
+
if (stopped || inboxUpdatesInFlight > 0 || reconcileInFlight)
|
|
118324
118504
|
return;
|
|
118325
118505
|
reconcileInFlight = true;
|
|
118326
118506
|
processTasksUpdate(runtime4, effectContext2, cooldown, agentMgr, sessionDeps, session2.machineId, "periodic-reconcile", { snapshots: enrichSnapshotsWithOperational(taskSnapshotState.listAll()) }).catch((error51) => {
|
|
@@ -118330,11 +118510,13 @@ var NATIVE_DELIVERY_RECONCILE_MS = 1e4, INBOX_RESTART_INITIAL_MS = 1000, INBOX_R
|
|
|
118330
118510
|
});
|
|
118331
118511
|
}, NATIVE_DELIVERY_RECONCILE_MS);
|
|
118332
118512
|
runInboxLoopWithRestart(inboxOptions, inboxHandler, () => stopped);
|
|
118333
|
-
runOperationalInboxLoopWithRestart(operationalInboxOptions, operationalInboxHandler, () => stopped);
|
|
118334
118513
|
return {
|
|
118335
118514
|
stop() {
|
|
118336
118515
|
stopped = true;
|
|
118337
118516
|
abort.abort();
|
|
118517
|
+
for (const watcher of roomWatchers.values()) {
|
|
118518
|
+
watcher.controller.abort();
|
|
118519
|
+
}
|
|
118338
118520
|
clearInterval(reconcileTimer);
|
|
118339
118521
|
unregisterNativeDeliverySession();
|
|
118340
118522
|
inboxStore.close();
|
|
@@ -135552,4 +135734,4 @@ program2.hook("preAction", async (_thisCommand, actionCommand) => {
|
|
|
135552
135734
|
});
|
|
135553
135735
|
program2.parse();
|
|
135554
135736
|
|
|
135555
|
-
//# debugId=
|
|
135737
|
+
//# debugId=962BD51641BEFD4F64756E2164756E21
|