@assistant-ui/react-ag-ui 0.1.5 → 0.1.6
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/runtime/AgUiThreadController.d.ts.map +1 -1
- package/dist/runtime/AgUiThreadController.js +80 -13
- package/dist/runtime/AgUiThreadController.js.map +1 -1
- package/dist/runtime/adapter/run-aggregator.d.ts +37 -31
- package/dist/runtime/adapter/run-aggregator.d.ts.map +1 -1
- package/dist/runtime/adapter/run-aggregator.js +363 -218
- package/dist/runtime/adapter/run-aggregator.js.map +1 -1
- package/package.json +1 -1
- package/src/runtime/AgUiThreadController.disconnect.test.ts +198 -3
- package/src/runtime/AgUiThreadController.replay.test.ts +57 -0
- package/src/runtime/AgUiThreadController.snapshot-head-history.test.ts +34 -2
- package/src/runtime/AgUiThreadController.snapshot-head-move.test.ts +510 -0
- package/src/runtime/AgUiThreadController.ts +179 -28
- package/src/runtime/adapter/run-aggregator.routing.test.ts +359 -0
- package/src/runtime/adapter/run-aggregator.ts +539 -258
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AgUiThreadController.d.ts","sourceRoot":"","sources":["../../src/runtime/AgUiThreadController.ts"],"names":[],"mappings":"AAOA,OAAO,KAAK,EACV,oBAAoB,EACpB,aAAa,EACb,mBAAmB,EACnB,gBAAgB,EAChB,mBAAmB,EACnB,kBAAkB,EAClB,yBAAyB,EAEzB,4BAA4B,EAC5B,SAAS,EAET,oBAAoB,EACpB,aAAa,EAEb,wBAAwB,EACzB,MAAM,oBAAoB,CAAC;AAS5B,OAAO,KAAK,EACV,aAAa,EAKd,MAAM,eAAe,CAAC;AAQvB,OAAO,KAAK,EAAE,MAAM,EAAE,oBAAiB;AAEvC,OAAO,KAAK,EAGV,aAAa,EACb,eAAe,EACf,oBAAoB,EACpB,qBAAqB,EACtB,mBAAgB;AAEjB,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC;
|
|
1
|
+
{"version":3,"file":"AgUiThreadController.d.ts","sourceRoot":"","sources":["../../src/runtime/AgUiThreadController.ts"],"names":[],"mappings":"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"}
|
|
@@ -65,6 +65,10 @@ const FALLBACK_USER_STATUS = {
|
|
|
65
65
|
type: "complete",
|
|
66
66
|
reason: "unknown"
|
|
67
67
|
};
|
|
68
|
+
const snapshotRecordToolCallIds = (record) => {
|
|
69
|
+
const toolCalls = record?.toolCalls;
|
|
70
|
+
return new Set(Array.isArray(toolCalls) ? toolCalls.map((call) => call?.id).filter((id) => typeof id === "string") : []);
|
|
71
|
+
};
|
|
68
72
|
const textOf = (content) => content.flatMap((part) => part.type === "text" ? [part.text] : []).join("");
|
|
69
73
|
/**
|
|
70
74
|
* Swaps `content`'s text parts, in order, for `source`'s. A text part `source`
|
|
@@ -1017,6 +1021,9 @@ var AgUiThreadController = class {
|
|
|
1017
1021
|
let settlingRun = false;
|
|
1018
1022
|
let latestSnapshot;
|
|
1019
1023
|
let snapshotToolCallIds = /* @__PURE__ */ new Set();
|
|
1024
|
+
const snapshotResultIds = /* @__PURE__ */ new Set();
|
|
1025
|
+
let announcingMove = false;
|
|
1026
|
+
const retainedSnapshots = /* @__PURE__ */ new Map();
|
|
1020
1027
|
const ensureAssistant = (allowRecreate = false) => {
|
|
1021
1028
|
const cached = assistantMessageId;
|
|
1022
1029
|
if (cached !== void 0 && this.session.tryGetMessage(cached)) return cached;
|
|
@@ -1040,6 +1047,7 @@ var AgUiThreadController = class {
|
|
|
1040
1047
|
}
|
|
1041
1048
|
for (const [messageId, openToolCallIds] of heldMessages) {
|
|
1042
1049
|
const existing = this.session.tryGetMessage(messageId);
|
|
1050
|
+
if (!canWaitForTools && this.isTerminalStatus(existing?.message.status)) continue;
|
|
1043
1051
|
if (existing) this.markPendingAssistantHistory(messageId, existing.parentId);
|
|
1044
1052
|
let requiresToolResult = false;
|
|
1045
1053
|
if (this.session.updateMessage(messageId, (message) => {
|
|
@@ -1216,6 +1224,39 @@ var AgUiThreadController = class {
|
|
|
1216
1224
|
}
|
|
1217
1225
|
} else assistantCollided = true;
|
|
1218
1226
|
};
|
|
1227
|
+
const applyRetainedUpdate = (update, { messageId, streaming, openToolCallIds }) => {
|
|
1228
|
+
const item = this.session.tryGetMessage(messageId);
|
|
1229
|
+
if (item?.message.role !== "assistant") return;
|
|
1230
|
+
this.markPendingAssistantHistory(messageId, item.parentId);
|
|
1231
|
+
let snapshot = retainedSnapshots.get(messageId);
|
|
1232
|
+
if (!snapshot) {
|
|
1233
|
+
snapshot = {
|
|
1234
|
+
message: item.message,
|
|
1235
|
+
toolCallIds: new Set(Array.from(iterateToolCallParts(item.message.content), (part) => part.toolCallId))
|
|
1236
|
+
};
|
|
1237
|
+
retainedSnapshots.set(messageId, snapshot);
|
|
1238
|
+
}
|
|
1239
|
+
const content = update.content !== void 0 ? this.mergeSnapshotAssistantContent(snapshot.message.content, update.content, update.content.some((part) => part.type === "reasoning"), update.content.some(isActivityPart), snapshot.toolCallIds) : update.content;
|
|
1240
|
+
const unresolved = [.../* @__PURE__ */ new Set([...openToolCallIds, ...Array.from(iterateToolCallParts(content ?? item.message.content)).filter((part) => snapshot.toolCallIds.has(part.toolCallId) && !isResolvedToolCall(part)).map((part) => part.toolCallId)])].filter((id) => !snapshotResultIds.has(id));
|
|
1241
|
+
const held = streaming || unresolved.length > 0 || settlingRun && heldMessages.has(messageId);
|
|
1242
|
+
if (held) heldMessages.set(messageId, new Set(unresolved));
|
|
1243
|
+
else heldMessages.delete(messageId);
|
|
1244
|
+
this.updateAssistantMessage(messageId, {
|
|
1245
|
+
...update,
|
|
1246
|
+
...content !== void 0 ? { content } : {},
|
|
1247
|
+
status: held ? { type: "running" } : {
|
|
1248
|
+
type: "complete",
|
|
1249
|
+
reason: "unknown"
|
|
1250
|
+
}
|
|
1251
|
+
});
|
|
1252
|
+
const current = this.session.tryGetMessage(messageId)?.message;
|
|
1253
|
+
if (current?.role === "assistant") retainedSnapshots.set(messageId, {
|
|
1254
|
+
...snapshot,
|
|
1255
|
+
message: current
|
|
1256
|
+
});
|
|
1257
|
+
const head = assistantMessageId === void 0 ? void 0 : this.session.tryGetMessage(assistantMessageId)?.message;
|
|
1258
|
+
if (!settlingRun && !announcingMove && head?.role === "assistant" && head.status?.type !== "running" && !runStartMessageIds.has(head.id) && !aggregator.isRetained(head.id)) this.updateAssistantMessage(head.id, { status: { type: "running" } });
|
|
1259
|
+
};
|
|
1219
1260
|
const abortController = new AbortController();
|
|
1220
1261
|
const abortSignal = abortController.signal;
|
|
1221
1262
|
const aggregator = new RunAggregator({
|
|
@@ -1261,10 +1302,13 @@ var AgUiThreadController = class {
|
|
|
1261
1302
|
const current = assistantMessageId ? this.session.tryGetMessage(assistantMessageId)?.message : void 0;
|
|
1262
1303
|
latestSnapshot = !settlingRun && current?.role === "assistant" && current.id === latestSnapshot?.id ? current : void 0;
|
|
1263
1304
|
},
|
|
1305
|
+
onRetainedMessage: applyRetainedUpdate,
|
|
1306
|
+
canRetainMessage: (messageId) => messageId !== assistantMessageId && messageId !== this.session.headId && !runStartMessageIds.has(messageId) && this.session.tryGetMessage(messageId)?.message.role === "assistant",
|
|
1264
1307
|
onServerMessageId: (serverId) => {
|
|
1265
1308
|
adoptServerMessageId(serverId, false);
|
|
1266
1309
|
},
|
|
1267
1310
|
onTextMessageStart: (serverId, openToolCallIds) => {
|
|
1311
|
+
const outgoingId = assistantMessageId !== void 0 && !assistantCollided && !runStartMessageIds.has(assistantMessageId) && !replayContexts.has(assistantMessageId) && this.session.hasMessage(assistantMessageId) ? assistantMessageId : void 0;
|
|
1268
1312
|
const owners = this.getTrailingAssistantTurn().filter((message) => replayContexts.has(message.id));
|
|
1269
1313
|
const toolOwners = indexReplayToolOwners(owners);
|
|
1270
1314
|
const frameOpenIds = openToolCallIds.filter((id) => {
|
|
@@ -1281,6 +1325,7 @@ var AgUiThreadController = class {
|
|
|
1281
1325
|
}
|
|
1282
1326
|
frameOwnerIds.clear();
|
|
1283
1327
|
adoptServerMessageId(serverId, true, frameOpenIds);
|
|
1328
|
+
return outgoingId;
|
|
1284
1329
|
}
|
|
1285
1330
|
});
|
|
1286
1331
|
const settleRunSubagents = (status) => {
|
|
@@ -1316,11 +1361,16 @@ var AgUiThreadController = class {
|
|
|
1316
1361
|
if (!assistantCollided && candidateContexts.size) accountedResultIds.add(event.toolCallId);
|
|
1317
1362
|
for (const openToolCallIds of heldMessages.values()) openToolCallIds.delete(event.toolCallId);
|
|
1318
1363
|
}
|
|
1364
|
+
if (event.type === "MESSAGES_SNAPSHOT") for (const record of event.messages) {
|
|
1365
|
+
if (record?.role !== "tool" || typeof record.toolCallId !== "string") continue;
|
|
1366
|
+
snapshotResultIds.add(record.toolCallId);
|
|
1367
|
+
for (const openToolCallIds of heldMessages.values()) openToolCallIds.delete(record.toolCallId);
|
|
1368
|
+
}
|
|
1319
1369
|
settlingRun = event.type === "RUN_FINISHED" || event.type === "RUN_ERROR" || event.type === "RUN_CANCELLED";
|
|
1320
1370
|
if (settlingRun) persistRunAssistants(true);
|
|
1321
1371
|
const beforeSnapshot = event.type === "MESSAGES_SNAPSHOT" ? this.session.getMessages() : [];
|
|
1322
1372
|
try {
|
|
1323
|
-
const nextAssistantMessageId = this.handleEvent(aggregator, event, assistantMessageId, joinStrategy, runStartMessageIds, hasRunUserBoundary, candidateContexts.size ? reconcileReplaySnapshot : void 0);
|
|
1373
|
+
const nextAssistantMessageId = this.handleEvent(aggregator, event, assistantMessageId, joinStrategy, runStartMessageIds, hasRunUserBoundary, heldMessages, candidateContexts.size ? reconcileReplaySnapshot : void 0);
|
|
1324
1374
|
if (event.type === "MESSAGES_SNAPSHOT") {
|
|
1325
1375
|
const previousIds = new Set(beforeSnapshot.map(({ id }) => id));
|
|
1326
1376
|
for (const message of this.session.getMessages()) {
|
|
@@ -1344,11 +1394,26 @@ var AgUiThreadController = class {
|
|
|
1344
1394
|
const imported = assistantMessageId ? this.session.tryGetMessage(assistantMessageId)?.message : void 0;
|
|
1345
1395
|
const source = event.messages.find((message) => message?.role === "assistant" && message.id === imported?.id);
|
|
1346
1396
|
latestSnapshot = imported?.role === "assistant" && source ? imported : void 0;
|
|
1347
|
-
snapshotToolCallIds =
|
|
1397
|
+
snapshotToolCallIds = snapshotRecordToolCallIds(source);
|
|
1348
1398
|
if (!replayEnded && assistantMessageId === void 0) {
|
|
1349
1399
|
const tail = this.session.getMessages().at(-1);
|
|
1350
1400
|
snapshotAssistantId = tail?.role === "assistant" ? tail.id : void 0;
|
|
1351
1401
|
}
|
|
1402
|
+
for (const record of event.messages) {
|
|
1403
|
+
if (record?.role !== "assistant" || !aggregator.isRetained(record.id)) continue;
|
|
1404
|
+
const message = this.session.tryGetMessage(record.id)?.message;
|
|
1405
|
+
if (message?.role !== "assistant") continue;
|
|
1406
|
+
retainedSnapshots.set(record.id, {
|
|
1407
|
+
message,
|
|
1408
|
+
toolCallIds: snapshotRecordToolCallIds(record)
|
|
1409
|
+
});
|
|
1410
|
+
}
|
|
1411
|
+
announcingMove = true;
|
|
1412
|
+
try {
|
|
1413
|
+
aggregator.announceRetained();
|
|
1414
|
+
} finally {
|
|
1415
|
+
announcingMove = false;
|
|
1416
|
+
}
|
|
1352
1417
|
}
|
|
1353
1418
|
if (event.type === "RUN_ERROR") settleRunSubagents({
|
|
1354
1419
|
type: "incomplete",
|
|
@@ -1429,7 +1494,8 @@ var AgUiThreadController = class {
|
|
|
1429
1494
|
}
|
|
1430
1495
|
} finally {
|
|
1431
1496
|
const current = assistantMessageId ? this.session.tryGetMessage(assistantMessageId)?.message : void 0;
|
|
1432
|
-
|
|
1497
|
+
const currentRunning = current?.role === "assistant" && current.status?.type === "running";
|
|
1498
|
+
if (this.abortController === abortController && (currentRunning || heldMessages.size > 0)) {
|
|
1433
1499
|
persistRunAssistants(true);
|
|
1434
1500
|
const status = {
|
|
1435
1501
|
type: "incomplete",
|
|
@@ -1437,7 +1503,7 @@ var AgUiThreadController = class {
|
|
|
1437
1503
|
error: "The connection ended before the answer finished."
|
|
1438
1504
|
};
|
|
1439
1505
|
settleHeldMessages(status);
|
|
1440
|
-
applyUpdate({
|
|
1506
|
+
if (currentRunning) applyUpdate({
|
|
1441
1507
|
status,
|
|
1442
1508
|
content: settleNestedContent(current.content, status)
|
|
1443
1509
|
});
|
|
@@ -1891,7 +1957,7 @@ var AgUiThreadController = class {
|
|
|
1891
1957
|
custom: incoming.custom ? mergeAgUiNamespace(current.custom, incoming.custom) : current.custom
|
|
1892
1958
|
};
|
|
1893
1959
|
}
|
|
1894
|
-
handleEvent(aggregator, event, activeAssistantId, joinStrategy, runStartMessageIds, hasRunUserBoundary, reconcileSnapshot) {
|
|
1960
|
+
handleEvent(aggregator, event, activeAssistantId, joinStrategy, runStartMessageIds, hasRunUserBoundary, heldMessages, reconcileSnapshot) {
|
|
1895
1961
|
if (event.type === "SUBAGENT_STARTED" && !this.subagentParentToolCallIds.has(event.subagentRunId)) this.subagentParentToolCallIds.set(event.subagentRunId, event.parentToolCallId);
|
|
1896
1962
|
switch (event.type) {
|
|
1897
1963
|
case "STATE_SNAPSHOT":
|
|
@@ -1919,23 +1985,24 @@ var AgUiThreadController = class {
|
|
|
1919
1985
|
const previousHeadId = this.session.headId;
|
|
1920
1986
|
const activeAssistant = activeAssistantId === void 0 ? void 0 : this.session.tryGetMessage(activeAssistantId)?.message;
|
|
1921
1987
|
const hasActiveText = activeAssistant?.role === "assistant" && activeAssistant.content.some((part) => part.type === "text");
|
|
1922
|
-
this.importMessagesSnapshot(event.messages, activeAssistantId, joinStrategy, runStartMessageIds, hasRunUserBoundary, reconcileSnapshot);
|
|
1988
|
+
this.importMessagesSnapshot(event.messages, activeAssistantId, joinStrategy, runStartMessageIds, hasRunUserBoundary, heldMessages, reconcileSnapshot);
|
|
1923
1989
|
const headId = this.session.headId;
|
|
1924
1990
|
const head = headId === null ? void 0 : this.session.tryGetMessage(headId)?.message;
|
|
1925
1991
|
const hasNewPendingToolCallAnswer = head?.role === "assistant" && !runStartMessageIds.has(head.id) && head.status?.type === "requires-action" && head.status.reason === "tool-calls";
|
|
1926
1992
|
if (headId !== previousHeadId && (hasActiveText || hasNewPendingToolCallAnswer)) {
|
|
1927
1993
|
const nextActiveAssistantId = head?.role === "assistant" ? headId ?? void 0 : void 0;
|
|
1928
|
-
|
|
1929
|
-
|
|
1930
|
-
|
|
1994
|
+
const previousActiveId = activeAssistantId !== nextActiveAssistantId ? activeAssistantId : void 0;
|
|
1995
|
+
const retained = nextActiveAssistantId !== void 0 && joinStrategy !== "concat-content" && aggregator.rebaseMessage(nextActiveAssistantId, previousActiveId);
|
|
1996
|
+
if (previousActiveId && !retained) {
|
|
1997
|
+
const previous = this.session.tryGetMessage(previousActiveId)?.message;
|
|
1998
|
+
if (previous?.role === "assistant" && previous.status?.type === "running") this.updateAssistantMessage(previousActiveId, {
|
|
1931
1999
|
status: FALLBACK_USER_STATUS,
|
|
1932
2000
|
content: settleNestedContent(previous.content, FALLBACK_USER_STATUS)
|
|
1933
2001
|
});
|
|
1934
2002
|
}
|
|
1935
2003
|
activeAssistantId = nextActiveAssistantId;
|
|
1936
|
-
if (activeAssistantId && joinStrategy !== "concat-content") aggregator.rebaseMessage(activeAssistantId);
|
|
1937
|
-
if (hasNewPendingToolCallAnswer && head) this.updateAssistantMessage(head.id, { status: { type: "running" } });
|
|
1938
2004
|
}
|
|
2005
|
+
if (hasNewPendingToolCallAnswer && head && head.id === activeAssistantId) this.updateAssistantMessage(head.id, { status: { type: "running" } });
|
|
1939
2006
|
this.updateActiveAssistantState(activeAssistantId);
|
|
1940
2007
|
break;
|
|
1941
2008
|
}
|
|
@@ -2064,7 +2131,7 @@ var AgUiThreadController = class {
|
|
|
2064
2131
|
if (this.maybeCompleteAfterToolResults(messageId)) return;
|
|
2065
2132
|
this.persistSettledAssistant(messageId);
|
|
2066
2133
|
}
|
|
2067
|
-
importMessagesSnapshot(rawMessages, activeAssistantId, joinStrategy, runStartMessageIds, hasRunUserBoundary, reconcileSnapshot) {
|
|
2134
|
+
importMessagesSnapshot(rawMessages, activeAssistantId, joinStrategy, runStartMessageIds, hasRunUserBoundary, heldMessages, reconcileSnapshot) {
|
|
2068
2135
|
try {
|
|
2069
2136
|
const activeAssistantItem = activeAssistantId ? this.session.tryGetMessage(activeAssistantId) : void 0;
|
|
2070
2137
|
const activeMessage = activeAssistantItem?.message;
|
|
@@ -2087,7 +2154,7 @@ var AgUiThreadController = class {
|
|
|
2087
2154
|
if (convertedMessage.role === "assistant") {
|
|
2088
2155
|
const previous = existing?.role === "assistant" ? existing : void 0;
|
|
2089
2156
|
const snapshot = reconcileSnapshot?.(convertedMessage, previous) ?? convertedMessage;
|
|
2090
|
-
const preservesRunningStatus = convertedMessage.id === activeAssistantId && previous?.status?.type === "running" && snapshot.status?.type === "requires-action" && snapshot.status.reason === "tool-calls";
|
|
2157
|
+
const preservesRunningStatus = (convertedMessage.id === activeAssistantId || heldMessages.has(convertedMessage.id)) && previous?.status?.type === "running" && snapshot.status?.type === "requires-action" && snapshot.status.reason === "tool-calls";
|
|
2091
2158
|
const previousToolCallIds = new Set(Array.from(iterateToolCallParts(previous?.content ?? []), (call) => call.toolCallId));
|
|
2092
2159
|
const preservesSettledStatus = convertedMessage.id !== activeAssistantId && this.isTerminalStatus(previous?.status) && snapshot.status?.type === "requires-action" && snapshot.status.reason === "tool-calls" && Array.from(iterateToolCallParts(snapshot.content)).every((call) => isResolvedToolCall(call) || previousToolCallIds.has(call.toolCallId));
|
|
2093
2160
|
converted[index] = previous ? {
|