@tanstack/ai-devtools-core 0.2.1 → 0.2.3
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/README.md +1 -0
- package/dist/esm/components/ConversationDetails.js +74 -1
- package/dist/esm/components/ConversationDetails.js.map +1 -1
- package/dist/esm/components/conversation/ActivityEventsTab.d.ts +8 -0
- package/dist/esm/components/conversation/ActivityEventsTab.js +72 -0
- package/dist/esm/components/conversation/ActivityEventsTab.js.map +1 -0
- package/dist/esm/components/conversation/ConversationHeader.js +109 -66
- package/dist/esm/components/conversation/ConversationHeader.js.map +1 -1
- package/dist/esm/components/conversation/ConversationTabs.d.ts +1 -1
- package/dist/esm/components/conversation/ConversationTabs.js +107 -3
- package/dist/esm/components/conversation/ConversationTabs.js.map +1 -1
- package/dist/esm/components/conversation/MessageCard.js +83 -28
- package/dist/esm/components/conversation/MessageCard.js.map +1 -1
- package/dist/esm/components/conversation/index.d.ts +1 -0
- package/dist/esm/store/ai-context.d.ts +19 -2
- package/dist/esm/store/ai-context.js +528 -262
- package/dist/esm/store/ai-context.js.map +1 -1
- package/dist/esm/styles/use-styles.d.ts +7 -0
- package/dist/esm/styles/use-styles.js +65 -1
- package/dist/esm/styles/use-styles.js.map +1 -1
- package/package.json +2 -2
- package/src/components/ConversationDetails.tsx +70 -1
- package/src/components/conversation/ActivityEventsTab.tsx +57 -0
- package/src/components/conversation/ConversationHeader.tsx +52 -36
- package/src/components/conversation/ConversationTabs.tsx +121 -2
- package/src/components/conversation/MessageCard.tsx +45 -10
- package/src/components/conversation/index.ts +1 -0
- package/src/store/ai-context.tsx +783 -418
- package/src/styles/use-styles.ts +65 -1
|
@@ -129,6 +129,10 @@ const AIProvider = (props) => {
|
|
|
129
129
|
label,
|
|
130
130
|
messages: [],
|
|
131
131
|
chunks: [],
|
|
132
|
+
imageEvents: [],
|
|
133
|
+
speechEvents: [],
|
|
134
|
+
transcriptionEvents: [],
|
|
135
|
+
videoEvents: [],
|
|
132
136
|
status: "active",
|
|
133
137
|
startedAt: Date.now()
|
|
134
138
|
});
|
|
@@ -170,6 +174,7 @@ const AIProvider = (props) => {
|
|
|
170
174
|
return;
|
|
171
175
|
}
|
|
172
176
|
}
|
|
177
|
+
addChunk(conversationId, chunk);
|
|
173
178
|
}
|
|
174
179
|
function updateMessageUsage(conversationId, messageId, cumulativeUsage) {
|
|
175
180
|
const conv = state.conversations[conversationId];
|
|
@@ -240,6 +245,21 @@ const AIProvider = (props) => {
|
|
|
240
245
|
if (!state.conversations[conversationId]) return;
|
|
241
246
|
queueChunk(conversationId, chunk);
|
|
242
247
|
}
|
|
248
|
+
function addActivityEvent(conversationId, activity, event) {
|
|
249
|
+
if (!state.conversations[conversationId]) return;
|
|
250
|
+
setState("conversations", conversationId, activity, produce((events) => {
|
|
251
|
+
if (!events) return [event];
|
|
252
|
+
events.push(event);
|
|
253
|
+
return events;
|
|
254
|
+
}));
|
|
255
|
+
const activityFlagMap = {
|
|
256
|
+
imageEvents: "hasImage",
|
|
257
|
+
speechEvents: "hasSpeech",
|
|
258
|
+
transcriptionEvents: "hasTranscription",
|
|
259
|
+
videoEvents: "hasVideo"
|
|
260
|
+
};
|
|
261
|
+
setState("conversations", conversationId, activityFlagMap[activity], true);
|
|
262
|
+
}
|
|
243
263
|
function ensureMessageForChunk(conversationId, messageId, timestamp) {
|
|
244
264
|
if (!messageId) return;
|
|
245
265
|
const conv = state.conversations[conversationId];
|
|
@@ -264,46 +284,115 @@ const AIProvider = (props) => {
|
|
|
264
284
|
provider: "Client"
|
|
265
285
|
});
|
|
266
286
|
}));
|
|
267
|
-
cleanupFns.push(aiEventClient.on("
|
|
268
|
-
const
|
|
269
|
-
|
|
270
|
-
|
|
287
|
+
cleanupFns.push(aiEventClient.on("text:message:created", (e) => {
|
|
288
|
+
const {
|
|
289
|
+
clientId,
|
|
290
|
+
streamId,
|
|
291
|
+
messageId,
|
|
292
|
+
role,
|
|
293
|
+
content,
|
|
294
|
+
timestamp
|
|
295
|
+
} = e.payload;
|
|
296
|
+
const conversationId = clientId || (streamId ? streamToConversation.get(streamId) : void 0);
|
|
297
|
+
if (!conversationId) return;
|
|
298
|
+
if (role === "tool" || role === "system") return;
|
|
299
|
+
if (!state.conversations[conversationId]) {
|
|
300
|
+
getOrCreateConversation(conversationId, clientId ? "client" : "server", clientId ? `Client Chat (${conversationId.substring(0, 8)})` : `Server Chat (${conversationId.substring(0, 8)})`);
|
|
271
301
|
}
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
302
|
+
const conv = state.conversations[conversationId];
|
|
303
|
+
if (!conv) return;
|
|
304
|
+
const existingIndex = conv.messages.findIndex((message) => message.id === messageId);
|
|
305
|
+
const parts = e.payload.parts?.map((part) => {
|
|
306
|
+
if (part.type === "text") {
|
|
307
|
+
return {
|
|
308
|
+
type: "text",
|
|
309
|
+
content: part.content
|
|
310
|
+
};
|
|
311
|
+
}
|
|
312
|
+
if (part.type === "tool-call") {
|
|
313
|
+
return {
|
|
314
|
+
type: "tool-call",
|
|
315
|
+
toolCallId: part.id,
|
|
316
|
+
toolName: part.name,
|
|
317
|
+
arguments: part.arguments,
|
|
318
|
+
state: part.state,
|
|
319
|
+
output: part.output,
|
|
320
|
+
content: part.approval ? JSON.stringify(part.approval) : void 0
|
|
321
|
+
};
|
|
322
|
+
}
|
|
323
|
+
if (part.type === "tool-result") {
|
|
324
|
+
return {
|
|
325
|
+
type: "tool-result",
|
|
326
|
+
toolCallId: part.toolCallId,
|
|
327
|
+
content: part.content,
|
|
328
|
+
state: part.state,
|
|
329
|
+
error: part.error
|
|
330
|
+
};
|
|
331
|
+
}
|
|
332
|
+
return {
|
|
333
|
+
type: "thinking",
|
|
334
|
+
content: part.content
|
|
335
|
+
};
|
|
278
336
|
});
|
|
279
|
-
|
|
280
|
-
|
|
337
|
+
const toolCalls = e.payload.toolCalls?.map((toolCall) => ({
|
|
338
|
+
id: toolCall.id,
|
|
339
|
+
name: toolCall.function.name,
|
|
340
|
+
arguments: toolCall.function.arguments,
|
|
341
|
+
state: "input-complete"
|
|
342
|
+
}));
|
|
343
|
+
const source = e.payload.source ?? (clientId ? "client" : "server");
|
|
344
|
+
if (role === "user" && conv.type === "client" && source === "server") {
|
|
345
|
+
return;
|
|
346
|
+
}
|
|
347
|
+
if (role === "assistant" && source === "client" && !content && (!toolCalls || toolCalls.length === 0)) {
|
|
348
|
+
return;
|
|
349
|
+
}
|
|
350
|
+
const messagePayload = {
|
|
351
|
+
id: messageId,
|
|
352
|
+
role,
|
|
353
|
+
content,
|
|
354
|
+
timestamp,
|
|
355
|
+
parts,
|
|
356
|
+
toolCalls,
|
|
357
|
+
source
|
|
358
|
+
};
|
|
359
|
+
if (existingIndex >= 0) {
|
|
360
|
+
updateMessage(conversationId, existingIndex, messagePayload);
|
|
361
|
+
} else {
|
|
362
|
+
addMessage(conversationId, messagePayload);
|
|
363
|
+
}
|
|
364
|
+
updateConversation(conversationId, {
|
|
365
|
+
status: "active",
|
|
366
|
+
hasChat: true
|
|
281
367
|
});
|
|
282
368
|
}));
|
|
283
|
-
cleanupFns.push(aiEventClient.on("
|
|
284
|
-
const
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
content: e.payload.contentPreview,
|
|
301
|
-
timestamp: e.payload.timestamp,
|
|
302
|
-
source: "client"
|
|
303
|
-
});
|
|
369
|
+
cleanupFns.push(aiEventClient.on("text:message:user", (e) => {
|
|
370
|
+
const {
|
|
371
|
+
clientId,
|
|
372
|
+
streamId,
|
|
373
|
+
messageId,
|
|
374
|
+
content,
|
|
375
|
+
timestamp
|
|
376
|
+
} = e.payload;
|
|
377
|
+
const conversationId = clientId || (streamId ? streamToConversation.get(streamId) : void 0);
|
|
378
|
+
if (!conversationId) return;
|
|
379
|
+
const conv = state.conversations[conversationId];
|
|
380
|
+
if (!conv) return;
|
|
381
|
+
const existingIndex = conv.messages.findIndex((message) => message.id === messageId);
|
|
382
|
+
if (existingIndex >= 0) return;
|
|
383
|
+
const source = e.payload.source ?? (clientId ? "client" : "server");
|
|
384
|
+
if (conv.type === "client" && source === "server") {
|
|
385
|
+
return;
|
|
304
386
|
}
|
|
387
|
+
addMessage(conversationId, {
|
|
388
|
+
id: messageId,
|
|
389
|
+
role: "user",
|
|
390
|
+
content,
|
|
391
|
+
timestamp,
|
|
392
|
+
source
|
|
393
|
+
});
|
|
305
394
|
}));
|
|
306
|
-
cleanupFns.push(aiEventClient.on("client:loading
|
|
395
|
+
cleanupFns.push(aiEventClient.on("client:loading:changed", (e) => {
|
|
307
396
|
const clientId = e.payload.clientId;
|
|
308
397
|
if (state.conversations[clientId]) {
|
|
309
398
|
updateConversation(clientId, {
|
|
@@ -320,7 +409,7 @@ const AIProvider = (props) => {
|
|
|
320
409
|
});
|
|
321
410
|
}
|
|
322
411
|
}));
|
|
323
|
-
cleanupFns.push(aiEventClient.on("client:messages
|
|
412
|
+
cleanupFns.push(aiEventClient.on("client:messages:cleared", (e) => {
|
|
324
413
|
const clientId = e.payload.clientId;
|
|
325
414
|
if (state.conversations[clientId]) {
|
|
326
415
|
updateConversation(clientId, {
|
|
@@ -340,7 +429,7 @@ const AIProvider = (props) => {
|
|
|
340
429
|
});
|
|
341
430
|
}
|
|
342
431
|
}));
|
|
343
|
-
cleanupFns.push(aiEventClient.on("client:error
|
|
432
|
+
cleanupFns.push(aiEventClient.on("client:error:changed", (e) => {
|
|
344
433
|
const clientId = e.payload.clientId;
|
|
345
434
|
if (state.conversations[clientId] && e.payload.error) {
|
|
346
435
|
updateConversation(clientId, {
|
|
@@ -348,31 +437,79 @@ const AIProvider = (props) => {
|
|
|
348
437
|
});
|
|
349
438
|
}
|
|
350
439
|
}));
|
|
351
|
-
cleanupFns.push(aiEventClient.on("
|
|
352
|
-
const
|
|
353
|
-
|
|
354
|
-
|
|
440
|
+
cleanupFns.push(aiEventClient.on("tools:result:added", (e) => {
|
|
441
|
+
const {
|
|
442
|
+
clientId,
|
|
443
|
+
toolCallId,
|
|
444
|
+
toolName,
|
|
445
|
+
output,
|
|
446
|
+
state: resultState,
|
|
447
|
+
timestamp
|
|
448
|
+
} = e.payload;
|
|
449
|
+
if (!clientId) return;
|
|
355
450
|
if (!state.conversations[clientId]) return;
|
|
356
451
|
const conv = state.conversations[clientId];
|
|
357
|
-
const
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
452
|
+
const chunk = {
|
|
453
|
+
id: `chunk-tool-result-${toolCallId}-${Date.now()}`,
|
|
454
|
+
type: "tool_result",
|
|
455
|
+
toolCallId,
|
|
456
|
+
toolName,
|
|
457
|
+
result: output,
|
|
458
|
+
timestamp,
|
|
459
|
+
chunkCount: 1,
|
|
460
|
+
isClientTool: true
|
|
461
|
+
};
|
|
462
|
+
for (let messageIndex = conv.messages.length - 1; messageIndex >= 0; messageIndex--) {
|
|
463
|
+
const message = conv.messages[messageIndex];
|
|
464
|
+
if (!message?.toolCalls) continue;
|
|
465
|
+
const toolCallIndex = message.toolCalls.findIndex((t) => t.id === toolCallId);
|
|
466
|
+
if (toolCallIndex >= 0) {
|
|
467
|
+
updateToolCall(clientId, messageIndex, toolCallIndex, {
|
|
468
|
+
result: output,
|
|
469
|
+
state: resultState === "output-error" ? "error" : "complete"
|
|
470
|
+
});
|
|
471
|
+
chunk.messageId = message.id;
|
|
472
|
+
addChunkToMessage(clientId, chunk);
|
|
473
|
+
return;
|
|
474
|
+
}
|
|
475
|
+
}
|
|
476
|
+
addChunkToMessage(clientId, chunk);
|
|
477
|
+
}));
|
|
478
|
+
cleanupFns.push(aiEventClient.on("tools:approval:responded", (e) => {
|
|
479
|
+
const {
|
|
480
|
+
clientId,
|
|
481
|
+
toolCallId,
|
|
482
|
+
approved
|
|
483
|
+
} = e.payload;
|
|
484
|
+
if (!clientId) return;
|
|
485
|
+
if (!state.conversations[clientId]) return;
|
|
486
|
+
const conv = state.conversations[clientId];
|
|
487
|
+
for (let messageIndex = conv.messages.length - 1; messageIndex >= 0; messageIndex--) {
|
|
488
|
+
const message = conv.messages[messageIndex];
|
|
489
|
+
if (!message?.toolCalls) continue;
|
|
490
|
+
const toolCallIndex = message.toolCalls.findIndex((t) => t.id === toolCallId);
|
|
491
|
+
if (toolCallIndex >= 0) {
|
|
492
|
+
updateToolCall(clientId, messageIndex, toolCallIndex, {
|
|
493
|
+
state: approved ? "approved" : "denied",
|
|
494
|
+
approvalRequired: false
|
|
495
|
+
});
|
|
496
|
+
return;
|
|
497
|
+
}
|
|
363
498
|
}
|
|
364
499
|
}));
|
|
365
|
-
cleanupFns.push(aiEventClient.on("
|
|
500
|
+
cleanupFns.push(aiEventClient.on("tools:call:updated", (e) => {
|
|
366
501
|
const {
|
|
367
502
|
clientId,
|
|
503
|
+
streamId,
|
|
368
504
|
messageId,
|
|
369
505
|
toolCallId,
|
|
370
506
|
toolName,
|
|
371
507
|
state: toolCallState,
|
|
372
508
|
arguments: args
|
|
373
509
|
} = e.payload;
|
|
374
|
-
|
|
375
|
-
|
|
510
|
+
const conversationId = clientId || (streamId ? streamToConversation.get(streamId) : void 0);
|
|
511
|
+
if (!conversationId || !state.conversations[conversationId]) return;
|
|
512
|
+
const conv = state.conversations[conversationId];
|
|
376
513
|
const messageIndex = conv.messages.findIndex((m) => m.id === messageId);
|
|
377
514
|
if (messageIndex === -1) return;
|
|
378
515
|
const message = conv.messages[messageIndex];
|
|
@@ -382,93 +519,98 @@ const AIProvider = (props) => {
|
|
|
382
519
|
const toolCall = {
|
|
383
520
|
id: toolCallId,
|
|
384
521
|
name: toolName,
|
|
385
|
-
arguments:
|
|
522
|
+
arguments: args,
|
|
386
523
|
state: toolCallState
|
|
387
524
|
};
|
|
388
525
|
if (existingToolIndex >= 0) {
|
|
389
|
-
updateToolCall(
|
|
526
|
+
updateToolCall(conversationId, messageIndex, existingToolIndex, toolCall);
|
|
390
527
|
} else {
|
|
391
|
-
setToolCalls(
|
|
528
|
+
setToolCalls(conversationId, messageIndex, [...toolCalls, toolCall]);
|
|
392
529
|
}
|
|
393
530
|
}));
|
|
394
|
-
cleanupFns.push(aiEventClient.on("
|
|
531
|
+
cleanupFns.push(aiEventClient.on("tools:input:available", (e) => {
|
|
395
532
|
const {
|
|
396
|
-
|
|
533
|
+
streamId,
|
|
397
534
|
messageId,
|
|
398
535
|
toolCallId,
|
|
399
|
-
|
|
536
|
+
toolName,
|
|
537
|
+
input,
|
|
538
|
+
timestamp,
|
|
539
|
+
clientId
|
|
400
540
|
} = e.payload;
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
const
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
const toolCallIndex = message.toolCalls.findIndex((t) => t.id === toolCallId);
|
|
408
|
-
if (toolCallIndex === -1) return;
|
|
409
|
-
updateToolCall(clientId, messageIndex, toolCallIndex, {
|
|
410
|
-
approvalRequired: true,
|
|
411
|
-
approvalId,
|
|
412
|
-
state: "approval-requested"
|
|
413
|
-
});
|
|
414
|
-
}));
|
|
415
|
-
cleanupFns.push(aiEventClient.on("tool:result-added", (e) => {
|
|
416
|
-
const {
|
|
417
|
-
clientId,
|
|
541
|
+
const conversationId = clientId || (streamId ? streamToConversation.get(streamId) : void 0);
|
|
542
|
+
if (!conversationId) return;
|
|
543
|
+
const chunk = {
|
|
544
|
+
id: `chunk-${Date.now()}-${Math.random()}`,
|
|
545
|
+
type: "tool_call",
|
|
546
|
+
messageId,
|
|
418
547
|
toolCallId,
|
|
419
548
|
toolName,
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
}
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
const toolCallIndex = message.toolCalls.findIndex((t) => t.id === toolCallId);
|
|
430
|
-
if (toolCallIndex >= 0) {
|
|
431
|
-
updateToolCall(clientId, messageIndex, toolCallIndex, {
|
|
432
|
-
result: output,
|
|
433
|
-
state: resultState === "output-error" ? "error" : "complete"
|
|
434
|
-
});
|
|
435
|
-
const chunk = {
|
|
436
|
-
id: `chunk-tool-result-${toolCallId}-${Date.now()}`,
|
|
437
|
-
type: "tool_result",
|
|
438
|
-
messageId: message.id,
|
|
439
|
-
toolCallId,
|
|
440
|
-
toolName,
|
|
441
|
-
result: output,
|
|
442
|
-
timestamp,
|
|
443
|
-
chunkCount: 1
|
|
444
|
-
};
|
|
445
|
-
addChunkToMessage(clientId, chunk);
|
|
446
|
-
return;
|
|
447
|
-
}
|
|
549
|
+
arguments: JSON.stringify(input),
|
|
550
|
+
timestamp,
|
|
551
|
+
chunkCount: 1
|
|
552
|
+
};
|
|
553
|
+
const conv = state.conversations[conversationId];
|
|
554
|
+
if (conv?.type === "client") {
|
|
555
|
+
addChunkToMessage(conversationId, chunk);
|
|
556
|
+
} else {
|
|
557
|
+
addChunk(conversationId, chunk);
|
|
448
558
|
}
|
|
449
559
|
}));
|
|
450
|
-
cleanupFns.push(aiEventClient.on("
|
|
560
|
+
cleanupFns.push(aiEventClient.on("tools:call:completed", (e) => {
|
|
451
561
|
const {
|
|
452
|
-
|
|
562
|
+
streamId,
|
|
453
563
|
toolCallId,
|
|
454
|
-
|
|
564
|
+
toolName,
|
|
565
|
+
result,
|
|
566
|
+
duration,
|
|
567
|
+
messageId,
|
|
568
|
+
timestamp,
|
|
569
|
+
clientId
|
|
455
570
|
} = e.payload;
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
571
|
+
const conversationId = clientId || (streamId ? streamToConversation.get(streamId) : void 0);
|
|
572
|
+
if (!conversationId || !state.conversations[conversationId]) return;
|
|
573
|
+
const conv = state.conversations[conversationId];
|
|
574
|
+
const chunk = {
|
|
575
|
+
id: `chunk-tool-result-${toolCallId}-${Date.now()}`,
|
|
576
|
+
type: "tool_result",
|
|
577
|
+
messageId,
|
|
578
|
+
toolCallId,
|
|
579
|
+
toolName,
|
|
580
|
+
result,
|
|
581
|
+
duration,
|
|
582
|
+
timestamp,
|
|
583
|
+
chunkCount: 1
|
|
584
|
+
};
|
|
585
|
+
if (conv.type === "client" && messageId) {
|
|
586
|
+
const messageIndex = conv.messages.findIndex((m) => m.id === messageId);
|
|
587
|
+
if (messageIndex !== -1) {
|
|
588
|
+
queueMessageChunk(conversationId, messageIndex, chunk);
|
|
589
|
+
} else {
|
|
590
|
+
for (let i = conv.messages.length - 1; i >= 0; i--) {
|
|
591
|
+
if (conv.messages[i]?.role === "assistant") {
|
|
592
|
+
queueMessageChunk(conversationId, i, chunk);
|
|
593
|
+
break;
|
|
594
|
+
}
|
|
595
|
+
}
|
|
596
|
+
}
|
|
597
|
+
} else {
|
|
598
|
+
addChunk(conversationId, chunk);
|
|
599
|
+
}
|
|
600
|
+
for (let i = conv.messages.length - 1; i >= 0; i--) {
|
|
601
|
+
const message = conv.messages[i];
|
|
460
602
|
if (!message?.toolCalls) continue;
|
|
461
603
|
const toolCallIndex = message.toolCalls.findIndex((t) => t.id === toolCallId);
|
|
462
604
|
if (toolCallIndex >= 0) {
|
|
463
|
-
updateToolCall(
|
|
464
|
-
|
|
465
|
-
|
|
605
|
+
updateToolCall(conversationId, i, toolCallIndex, {
|
|
606
|
+
duration,
|
|
607
|
+
result
|
|
466
608
|
});
|
|
467
609
|
return;
|
|
468
610
|
}
|
|
469
611
|
}
|
|
470
612
|
}));
|
|
471
|
-
cleanupFns.push(aiEventClient.on("
|
|
613
|
+
cleanupFns.push(aiEventClient.on("text:chunk:content", (e) => {
|
|
472
614
|
const streamId = e.payload.streamId;
|
|
473
615
|
const conversationId = streamToConversation.get(streamId);
|
|
474
616
|
if (!conversationId) return;
|
|
@@ -488,8 +630,16 @@ const AIProvider = (props) => {
|
|
|
488
630
|
ensureMessageForChunk(conversationId, e.payload.messageId, e.payload.timestamp);
|
|
489
631
|
addChunk(conversationId, chunk);
|
|
490
632
|
}
|
|
633
|
+
if (e.payload.messageId) {
|
|
634
|
+
const messageIndex = conv?.messages.findIndex((msg) => msg.id === e.payload.messageId);
|
|
635
|
+
if (messageIndex !== void 0 && messageIndex >= 0) {
|
|
636
|
+
updateMessage(conversationId, messageIndex, {
|
|
637
|
+
content: e.payload.content
|
|
638
|
+
});
|
|
639
|
+
}
|
|
640
|
+
}
|
|
491
641
|
}));
|
|
492
|
-
cleanupFns.push(aiEventClient.on("
|
|
642
|
+
cleanupFns.push(aiEventClient.on("text:chunk:tool-call", (e) => {
|
|
493
643
|
const streamId = e.payload.streamId;
|
|
494
644
|
const conversationId = streamToConversation.get(streamId);
|
|
495
645
|
if (!conversationId) return;
|
|
@@ -510,8 +660,28 @@ const AIProvider = (props) => {
|
|
|
510
660
|
ensureMessageForChunk(conversationId, e.payload.messageId, e.payload.timestamp);
|
|
511
661
|
addChunk(conversationId, chunk);
|
|
512
662
|
}
|
|
663
|
+
if (e.payload.messageId) {
|
|
664
|
+
const messageIndex = conv?.messages.findIndex((msg) => msg.id === e.payload.messageId);
|
|
665
|
+
if (messageIndex !== void 0 && messageIndex >= 0) {
|
|
666
|
+
const message = conv?.messages[messageIndex];
|
|
667
|
+
if (!message) return;
|
|
668
|
+
const toolCalls = message.toolCalls || [];
|
|
669
|
+
const existingToolIndex = toolCalls.findIndex((t) => t.id === e.payload.toolCallId);
|
|
670
|
+
const toolCall = {
|
|
671
|
+
id: e.payload.toolCallId,
|
|
672
|
+
name: e.payload.toolName,
|
|
673
|
+
arguments: e.payload.arguments,
|
|
674
|
+
state: "input-streaming"
|
|
675
|
+
};
|
|
676
|
+
if (existingToolIndex >= 0) {
|
|
677
|
+
updateToolCall(conversationId, messageIndex, existingToolIndex, toolCall);
|
|
678
|
+
} else {
|
|
679
|
+
setToolCalls(conversationId, messageIndex, [...toolCalls, toolCall]);
|
|
680
|
+
}
|
|
681
|
+
}
|
|
682
|
+
}
|
|
513
683
|
}));
|
|
514
|
-
cleanupFns.push(aiEventClient.on("
|
|
684
|
+
cleanupFns.push(aiEventClient.on("text:chunk:tool-result", (e) => {
|
|
515
685
|
const streamId = e.payload.streamId;
|
|
516
686
|
const conversationId = streamToConversation.get(streamId);
|
|
517
687
|
if (!conversationId) return;
|
|
@@ -520,7 +690,7 @@ const AIProvider = (props) => {
|
|
|
520
690
|
type: "tool_result",
|
|
521
691
|
messageId: e.payload.messageId,
|
|
522
692
|
toolCallId: e.payload.toolCallId,
|
|
523
|
-
|
|
693
|
+
result: e.payload.result,
|
|
524
694
|
timestamp: e.payload.timestamp,
|
|
525
695
|
chunkCount: 1
|
|
526
696
|
};
|
|
@@ -546,7 +716,7 @@ const AIProvider = (props) => {
|
|
|
546
716
|
}
|
|
547
717
|
}
|
|
548
718
|
}));
|
|
549
|
-
cleanupFns.push(aiEventClient.on("
|
|
719
|
+
cleanupFns.push(aiEventClient.on("text:chunk:thinking", (e) => {
|
|
550
720
|
const streamId = e.payload.streamId;
|
|
551
721
|
const conversationId = streamToConversation.get(streamId);
|
|
552
722
|
if (!conversationId) return;
|
|
@@ -575,7 +745,7 @@ const AIProvider = (props) => {
|
|
|
575
745
|
addChunk(conversationId, chunk);
|
|
576
746
|
}
|
|
577
747
|
}));
|
|
578
|
-
cleanupFns.push(aiEventClient.on("
|
|
748
|
+
cleanupFns.push(aiEventClient.on("text:chunk:done", (e) => {
|
|
579
749
|
const streamId = e.payload.streamId;
|
|
580
750
|
const conversationId = streamToConversation.get(streamId);
|
|
581
751
|
if (!conversationId) return;
|
|
@@ -605,7 +775,7 @@ const AIProvider = (props) => {
|
|
|
605
775
|
completedAt: e.payload.timestamp
|
|
606
776
|
});
|
|
607
777
|
}));
|
|
608
|
-
cleanupFns.push(aiEventClient.on("
|
|
778
|
+
cleanupFns.push(aiEventClient.on("text:chunk:error", (e) => {
|
|
609
779
|
const streamId = e.payload.streamId;
|
|
610
780
|
const conversationId = streamToConversation.get(streamId);
|
|
611
781
|
if (!conversationId) return;
|
|
@@ -629,16 +799,7 @@ const AIProvider = (props) => {
|
|
|
629
799
|
completedAt: e.payload.timestamp
|
|
630
800
|
});
|
|
631
801
|
}));
|
|
632
|
-
cleanupFns.push(aiEventClient.on("
|
|
633
|
-
const streamId = e.payload.streamId;
|
|
634
|
-
const conversationId = streamToConversation.get(streamId);
|
|
635
|
-
if (!conversationId) return;
|
|
636
|
-
updateConversation(conversationId, {
|
|
637
|
-
status: "completed",
|
|
638
|
-
completedAt: e.payload.timestamp
|
|
639
|
-
});
|
|
640
|
-
}));
|
|
641
|
-
cleanupFns.push(aiEventClient.on("stream:approval-requested", (e) => {
|
|
802
|
+
cleanupFns.push(aiEventClient.on("tools:approval:requested", (e) => {
|
|
642
803
|
const {
|
|
643
804
|
streamId,
|
|
644
805
|
messageId,
|
|
@@ -646,9 +807,10 @@ const AIProvider = (props) => {
|
|
|
646
807
|
toolName,
|
|
647
808
|
input,
|
|
648
809
|
approvalId,
|
|
649
|
-
timestamp
|
|
810
|
+
timestamp,
|
|
811
|
+
clientId
|
|
650
812
|
} = e.payload;
|
|
651
|
-
const conversationId = streamToConversation.get(streamId);
|
|
813
|
+
const conversationId = clientId || streamToConversation.get(streamId) || "";
|
|
652
814
|
if (!conversationId) return;
|
|
653
815
|
const conv = state.conversations[conversationId];
|
|
654
816
|
if (!conv) return;
|
|
@@ -684,104 +846,56 @@ const AIProvider = (props) => {
|
|
|
684
846
|
}
|
|
685
847
|
}
|
|
686
848
|
}));
|
|
687
|
-
cleanupFns.push(aiEventClient.on("
|
|
688
|
-
const streamId = e.payload.streamId;
|
|
689
|
-
let conversationId = streamToConversation.get(streamId);
|
|
690
|
-
if (!conversationId) {
|
|
691
|
-
const activeClients = Object.values(state.conversations).filter((c) => c.type === "client" && c.status === "active").sort((a, b) => b.startedAt - a.startedAt);
|
|
692
|
-
if (activeClients.length > 0 && activeClients[0]) {
|
|
693
|
-
conversationId = activeClients[0].id;
|
|
694
|
-
streamToConversation.set(streamId, conversationId);
|
|
695
|
-
}
|
|
696
|
-
}
|
|
697
|
-
if (!conversationId) return;
|
|
698
|
-
const conv = state.conversations[conversationId];
|
|
699
|
-
if (!conv) return;
|
|
700
|
-
const lastMessage = conv.messages[conv.messages.length - 1];
|
|
701
|
-
if (lastMessage && lastMessage.role === "assistant") {
|
|
702
|
-
updateMessage(conversationId, conv.messages.length - 1, {
|
|
703
|
-
content: e.payload.content
|
|
704
|
-
});
|
|
705
|
-
}
|
|
706
|
-
}));
|
|
707
|
-
cleanupFns.push(aiEventClient.on("processor:tool-call-state-changed", (e) => {
|
|
708
|
-
const streamId = e.payload.streamId;
|
|
709
|
-
const conversationId = streamToConversation.get(streamId);
|
|
710
|
-
if (!conversationId || !state.conversations[conversationId]) return;
|
|
711
|
-
const conv = state.conversations[conversationId];
|
|
712
|
-
const lastMessage = conv.messages[conv.messages.length - 1];
|
|
713
|
-
if (lastMessage && lastMessage.role === "assistant") {
|
|
714
|
-
const toolCalls = lastMessage.toolCalls || [];
|
|
715
|
-
const existingToolIndex = toolCalls.findIndex((t) => t.id === e.payload.toolCallId);
|
|
716
|
-
const toolCall = {
|
|
717
|
-
id: e.payload.toolCallId,
|
|
718
|
-
name: e.payload.toolName,
|
|
719
|
-
arguments: JSON.stringify(e.payload.arguments, null, 2),
|
|
720
|
-
state: e.payload.state
|
|
721
|
-
};
|
|
722
|
-
if (existingToolIndex >= 0) {
|
|
723
|
-
updateToolCall(conversationId, conv.messages.length - 1, existingToolIndex, toolCall);
|
|
724
|
-
} else {
|
|
725
|
-
setToolCalls(conversationId, conv.messages.length - 1, [...toolCalls, toolCall]);
|
|
726
|
-
}
|
|
727
|
-
}
|
|
728
|
-
}));
|
|
729
|
-
cleanupFns.push(aiEventClient.on("processor:tool-result-state-changed", (e) => {
|
|
730
|
-
const streamId = e.payload.streamId;
|
|
731
|
-
const conversationId = streamToConversation.get(streamId);
|
|
732
|
-
if (!conversationId || !state.conversations[conversationId]) return;
|
|
733
|
-
const conv = state.conversations[conversationId];
|
|
734
|
-
for (let i = conv.messages.length - 1; i >= 0; i--) {
|
|
735
|
-
const message = conv.messages[i];
|
|
736
|
-
if (!message?.toolCalls) continue;
|
|
737
|
-
const toolCallIndex = message.toolCalls.findIndex((t) => t.id === e.payload.toolCallId);
|
|
738
|
-
if (toolCallIndex >= 0) {
|
|
739
|
-
updateToolCall(conversationId, i, toolCallIndex, {
|
|
740
|
-
result: e.payload.content,
|
|
741
|
-
state: e.payload.error ? "error" : e.payload.state
|
|
742
|
-
});
|
|
743
|
-
return;
|
|
744
|
-
}
|
|
745
|
-
}
|
|
746
|
-
}));
|
|
747
|
-
cleanupFns.push(aiEventClient.on("text:started", (e) => {
|
|
849
|
+
cleanupFns.push(aiEventClient.on("text:request:started", (e) => {
|
|
748
850
|
const streamId = e.payload.streamId;
|
|
749
851
|
const model = e.payload.model;
|
|
750
852
|
e.payload.provider;
|
|
751
853
|
const clientId = e.payload.clientId;
|
|
752
854
|
if (clientId && state.conversations[clientId]) {
|
|
753
855
|
streamToConversation.set(streamId, clientId);
|
|
856
|
+
requestToConversation.set(e.payload.requestId, clientId);
|
|
754
857
|
updateConversation(clientId, {
|
|
755
858
|
status: "active",
|
|
756
|
-
...e.payload
|
|
859
|
+
...e.payload,
|
|
860
|
+
systemPrompts: e.payload.systemPrompts,
|
|
861
|
+
hasChat: true
|
|
757
862
|
});
|
|
758
863
|
return;
|
|
759
864
|
}
|
|
760
865
|
const activeClient = Object.values(state.conversations).find((c) => c.type === "client" && c.status === "active" && !c.model);
|
|
761
866
|
if (activeClient) {
|
|
762
867
|
streamToConversation.set(streamId, activeClient.id);
|
|
868
|
+
requestToConversation.set(e.payload.requestId, activeClient.id);
|
|
763
869
|
updateConversation(activeClient.id, {
|
|
764
|
-
...e.payload
|
|
870
|
+
...e.payload,
|
|
871
|
+
systemPrompts: e.payload.systemPrompts,
|
|
872
|
+
hasChat: true
|
|
765
873
|
});
|
|
766
874
|
} else {
|
|
767
875
|
const existingServerConv = Object.values(state.conversations).find((c) => c.type === "server" && c.model === model);
|
|
768
876
|
if (existingServerConv) {
|
|
769
877
|
streamToConversation.set(streamId, existingServerConv.id);
|
|
878
|
+
requestToConversation.set(e.payload.requestId, existingServerConv.id);
|
|
770
879
|
updateConversation(existingServerConv.id, {
|
|
771
880
|
status: "active",
|
|
772
|
-
...e.payload
|
|
881
|
+
...e.payload,
|
|
882
|
+
systemPrompts: e.payload.systemPrompts,
|
|
883
|
+
hasChat: true
|
|
773
884
|
});
|
|
774
885
|
} else {
|
|
775
886
|
const serverId = `server-${model}`;
|
|
776
887
|
getOrCreateConversation(serverId, "server", `${model} Server`);
|
|
777
888
|
streamToConversation.set(streamId, serverId);
|
|
889
|
+
requestToConversation.set(e.payload.requestId, serverId);
|
|
778
890
|
updateConversation(serverId, {
|
|
779
|
-
...e.payload
|
|
891
|
+
...e.payload,
|
|
892
|
+
systemPrompts: e.payload.systemPrompts,
|
|
893
|
+
hasChat: true
|
|
780
894
|
});
|
|
781
895
|
}
|
|
782
896
|
}
|
|
783
897
|
}));
|
|
784
|
-
cleanupFns.push(aiEventClient.on("text:completed", (e) => {
|
|
898
|
+
cleanupFns.push(aiEventClient.on("text:request:completed", (e) => {
|
|
785
899
|
const {
|
|
786
900
|
requestId,
|
|
787
901
|
usage
|
|
@@ -801,19 +915,7 @@ const AIProvider = (props) => {
|
|
|
801
915
|
}
|
|
802
916
|
}
|
|
803
917
|
}));
|
|
804
|
-
cleanupFns.push(aiEventClient.on("text:
|
|
805
|
-
const {
|
|
806
|
-
requestId,
|
|
807
|
-
iterationNumber
|
|
808
|
-
} = e.payload;
|
|
809
|
-
const conversationId = requestToConversation.get(requestId);
|
|
810
|
-
if (conversationId && state.conversations[conversationId]) {
|
|
811
|
-
updateConversation(conversationId, {
|
|
812
|
-
iterationCount: iterationNumber
|
|
813
|
-
});
|
|
814
|
-
}
|
|
815
|
-
}));
|
|
816
|
-
cleanupFns.push(aiEventClient.on("usage:tokens", (e) => {
|
|
918
|
+
cleanupFns.push(aiEventClient.on("text:usage", (e) => {
|
|
817
919
|
const {
|
|
818
920
|
requestId,
|
|
819
921
|
usage,
|
|
@@ -827,59 +929,7 @@ const AIProvider = (props) => {
|
|
|
827
929
|
updateMessageUsage(conversationId, messageId, usage);
|
|
828
930
|
}
|
|
829
931
|
}));
|
|
830
|
-
cleanupFns.push(aiEventClient.on("
|
|
831
|
-
const {
|
|
832
|
-
streamId,
|
|
833
|
-
toolCallId,
|
|
834
|
-
toolName,
|
|
835
|
-
result,
|
|
836
|
-
duration,
|
|
837
|
-
messageId,
|
|
838
|
-
timestamp
|
|
839
|
-
} = e.payload;
|
|
840
|
-
const conversationId = streamToConversation.get(streamId);
|
|
841
|
-
if (!conversationId || !state.conversations[conversationId]) return;
|
|
842
|
-
const conv = state.conversations[conversationId];
|
|
843
|
-
const chunk = {
|
|
844
|
-
id: `chunk-tool-result-${toolCallId}-${Date.now()}`,
|
|
845
|
-
type: "tool_result",
|
|
846
|
-
messageId,
|
|
847
|
-
toolCallId,
|
|
848
|
-
toolName,
|
|
849
|
-
result,
|
|
850
|
-
duration,
|
|
851
|
-
timestamp,
|
|
852
|
-
chunkCount: 1
|
|
853
|
-
};
|
|
854
|
-
if (conv.type === "client" && messageId) {
|
|
855
|
-
const messageIndex = conv.messages.findIndex((m) => m.id === messageId);
|
|
856
|
-
if (messageIndex !== -1) {
|
|
857
|
-
queueMessageChunk(conversationId, messageIndex, chunk);
|
|
858
|
-
} else {
|
|
859
|
-
for (let i = conv.messages.length - 1; i >= 0; i--) {
|
|
860
|
-
if (conv.messages[i]?.role === "assistant") {
|
|
861
|
-
queueMessageChunk(conversationId, i, chunk);
|
|
862
|
-
break;
|
|
863
|
-
}
|
|
864
|
-
}
|
|
865
|
-
}
|
|
866
|
-
} else {
|
|
867
|
-
addChunk(conversationId, chunk);
|
|
868
|
-
}
|
|
869
|
-
for (let i = conv.messages.length - 1; i >= 0; i--) {
|
|
870
|
-
const message = conv.messages[i];
|
|
871
|
-
if (!message?.toolCalls) continue;
|
|
872
|
-
const toolCallIndex = message.toolCalls.findIndex((t) => t.id === toolCallId);
|
|
873
|
-
if (toolCallIndex >= 0) {
|
|
874
|
-
updateToolCall(conversationId, i, toolCallIndex, {
|
|
875
|
-
duration,
|
|
876
|
-
result
|
|
877
|
-
});
|
|
878
|
-
return;
|
|
879
|
-
}
|
|
880
|
-
}
|
|
881
|
-
}));
|
|
882
|
-
cleanupFns.push(aiEventClient.on("summarize:started", (e) => {
|
|
932
|
+
cleanupFns.push(aiEventClient.on("summarize:request:started", (e) => {
|
|
883
933
|
const {
|
|
884
934
|
requestId,
|
|
885
935
|
model,
|
|
@@ -915,7 +965,7 @@ const AIProvider = (props) => {
|
|
|
915
965
|
setState("conversations", conversationId, "hasSummarize", true);
|
|
916
966
|
}
|
|
917
967
|
}));
|
|
918
|
-
cleanupFns.push(aiEventClient.on("summarize:completed", (e) => {
|
|
968
|
+
cleanupFns.push(aiEventClient.on("summarize:request:completed", (e) => {
|
|
919
969
|
const {
|
|
920
970
|
requestId,
|
|
921
971
|
outputLength,
|
|
@@ -934,6 +984,222 @@ const AIProvider = (props) => {
|
|
|
934
984
|
}));
|
|
935
985
|
}
|
|
936
986
|
}));
|
|
987
|
+
cleanupFns.push(aiEventClient.on("image:request:started", (e) => {
|
|
988
|
+
const {
|
|
989
|
+
requestId,
|
|
990
|
+
clientId,
|
|
991
|
+
timestamp
|
|
992
|
+
} = e.payload;
|
|
993
|
+
let conversationId = clientId;
|
|
994
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
995
|
+
conversationId = `image-${requestId}`;
|
|
996
|
+
getOrCreateConversation(conversationId, "server", `Image (${requestId.substring(0, 8)})`);
|
|
997
|
+
}
|
|
998
|
+
addActivityEvent(conversationId, "imageEvents", {
|
|
999
|
+
id: requestId,
|
|
1000
|
+
name: "image:request:started",
|
|
1001
|
+
timestamp,
|
|
1002
|
+
payload: e.payload
|
|
1003
|
+
});
|
|
1004
|
+
}));
|
|
1005
|
+
cleanupFns.push(aiEventClient.on("image:request:completed", (e) => {
|
|
1006
|
+
const {
|
|
1007
|
+
requestId,
|
|
1008
|
+
clientId,
|
|
1009
|
+
timestamp
|
|
1010
|
+
} = e.payload;
|
|
1011
|
+
let conversationId = clientId;
|
|
1012
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1013
|
+
conversationId = `image-${requestId}`;
|
|
1014
|
+
getOrCreateConversation(conversationId, "server", `Image (${requestId.substring(0, 8)})`);
|
|
1015
|
+
}
|
|
1016
|
+
addActivityEvent(conversationId, "imageEvents", {
|
|
1017
|
+
id: requestId,
|
|
1018
|
+
name: "image:request:completed",
|
|
1019
|
+
timestamp,
|
|
1020
|
+
payload: e.payload
|
|
1021
|
+
});
|
|
1022
|
+
}));
|
|
1023
|
+
cleanupFns.push(aiEventClient.on("image:usage", (e) => {
|
|
1024
|
+
const {
|
|
1025
|
+
requestId,
|
|
1026
|
+
clientId,
|
|
1027
|
+
timestamp
|
|
1028
|
+
} = e.payload;
|
|
1029
|
+
let conversationId = clientId;
|
|
1030
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1031
|
+
conversationId = `image-${requestId}`;
|
|
1032
|
+
getOrCreateConversation(conversationId, "server", `Image (${requestId.substring(0, 8)})`);
|
|
1033
|
+
}
|
|
1034
|
+
addActivityEvent(conversationId, "imageEvents", {
|
|
1035
|
+
id: requestId,
|
|
1036
|
+
name: "image:usage",
|
|
1037
|
+
timestamp,
|
|
1038
|
+
payload: e.payload
|
|
1039
|
+
});
|
|
1040
|
+
}));
|
|
1041
|
+
cleanupFns.push(aiEventClient.on("speech:request:started", (e) => {
|
|
1042
|
+
const {
|
|
1043
|
+
requestId,
|
|
1044
|
+
clientId,
|
|
1045
|
+
timestamp
|
|
1046
|
+
} = e.payload;
|
|
1047
|
+
let conversationId = clientId;
|
|
1048
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1049
|
+
conversationId = `speech-${requestId}`;
|
|
1050
|
+
getOrCreateConversation(conversationId, "server", `Speech (${requestId.substring(0, 8)})`);
|
|
1051
|
+
}
|
|
1052
|
+
addActivityEvent(conversationId, "speechEvents", {
|
|
1053
|
+
id: requestId,
|
|
1054
|
+
name: "speech:request:started",
|
|
1055
|
+
timestamp,
|
|
1056
|
+
payload: e.payload
|
|
1057
|
+
});
|
|
1058
|
+
}));
|
|
1059
|
+
cleanupFns.push(aiEventClient.on("speech:request:completed", (e) => {
|
|
1060
|
+
const {
|
|
1061
|
+
requestId,
|
|
1062
|
+
clientId,
|
|
1063
|
+
timestamp
|
|
1064
|
+
} = e.payload;
|
|
1065
|
+
let conversationId = clientId;
|
|
1066
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1067
|
+
conversationId = `speech-${requestId}`;
|
|
1068
|
+
getOrCreateConversation(conversationId, "server", `Speech (${requestId.substring(0, 8)})`);
|
|
1069
|
+
}
|
|
1070
|
+
addActivityEvent(conversationId, "speechEvents", {
|
|
1071
|
+
id: requestId,
|
|
1072
|
+
name: "speech:request:completed",
|
|
1073
|
+
timestamp,
|
|
1074
|
+
payload: e.payload
|
|
1075
|
+
});
|
|
1076
|
+
}));
|
|
1077
|
+
cleanupFns.push(aiEventClient.on("speech:usage", (e) => {
|
|
1078
|
+
const {
|
|
1079
|
+
requestId,
|
|
1080
|
+
clientId,
|
|
1081
|
+
timestamp
|
|
1082
|
+
} = e.payload;
|
|
1083
|
+
let conversationId = clientId;
|
|
1084
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1085
|
+
conversationId = `speech-${requestId}`;
|
|
1086
|
+
getOrCreateConversation(conversationId, "server", `Speech (${requestId.substring(0, 8)})`);
|
|
1087
|
+
}
|
|
1088
|
+
addActivityEvent(conversationId, "speechEvents", {
|
|
1089
|
+
id: requestId,
|
|
1090
|
+
name: "speech:usage",
|
|
1091
|
+
timestamp,
|
|
1092
|
+
payload: e.payload
|
|
1093
|
+
});
|
|
1094
|
+
}));
|
|
1095
|
+
cleanupFns.push(aiEventClient.on("transcription:request:started", (e) => {
|
|
1096
|
+
const {
|
|
1097
|
+
requestId,
|
|
1098
|
+
clientId,
|
|
1099
|
+
timestamp
|
|
1100
|
+
} = e.payload;
|
|
1101
|
+
let conversationId = clientId;
|
|
1102
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1103
|
+
conversationId = `transcription-${requestId}`;
|
|
1104
|
+
getOrCreateConversation(conversationId, "server", `Transcription (${requestId.substring(0, 8)})`);
|
|
1105
|
+
}
|
|
1106
|
+
addActivityEvent(conversationId, "transcriptionEvents", {
|
|
1107
|
+
id: requestId,
|
|
1108
|
+
name: "transcription:request:started",
|
|
1109
|
+
timestamp,
|
|
1110
|
+
payload: e.payload
|
|
1111
|
+
});
|
|
1112
|
+
}));
|
|
1113
|
+
cleanupFns.push(aiEventClient.on("transcription:request:completed", (e) => {
|
|
1114
|
+
const {
|
|
1115
|
+
requestId,
|
|
1116
|
+
clientId,
|
|
1117
|
+
timestamp
|
|
1118
|
+
} = e.payload;
|
|
1119
|
+
let conversationId = clientId;
|
|
1120
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1121
|
+
conversationId = `transcription-${requestId}`;
|
|
1122
|
+
getOrCreateConversation(conversationId, "server", `Transcription (${requestId.substring(0, 8)})`);
|
|
1123
|
+
}
|
|
1124
|
+
addActivityEvent(conversationId, "transcriptionEvents", {
|
|
1125
|
+
id: requestId,
|
|
1126
|
+
name: "transcription:request:completed",
|
|
1127
|
+
timestamp,
|
|
1128
|
+
payload: e.payload
|
|
1129
|
+
});
|
|
1130
|
+
}));
|
|
1131
|
+
cleanupFns.push(aiEventClient.on("transcription:usage", (e) => {
|
|
1132
|
+
const {
|
|
1133
|
+
requestId,
|
|
1134
|
+
clientId,
|
|
1135
|
+
timestamp
|
|
1136
|
+
} = e.payload;
|
|
1137
|
+
let conversationId = clientId;
|
|
1138
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1139
|
+
conversationId = `transcription-${requestId}`;
|
|
1140
|
+
getOrCreateConversation(conversationId, "server", `Transcription (${requestId.substring(0, 8)})`);
|
|
1141
|
+
}
|
|
1142
|
+
addActivityEvent(conversationId, "transcriptionEvents", {
|
|
1143
|
+
id: requestId,
|
|
1144
|
+
name: "transcription:usage",
|
|
1145
|
+
timestamp,
|
|
1146
|
+
payload: e.payload
|
|
1147
|
+
});
|
|
1148
|
+
}));
|
|
1149
|
+
cleanupFns.push(aiEventClient.on("video:request:started", (e) => {
|
|
1150
|
+
const {
|
|
1151
|
+
requestId,
|
|
1152
|
+
clientId,
|
|
1153
|
+
timestamp
|
|
1154
|
+
} = e.payload;
|
|
1155
|
+
let conversationId = clientId;
|
|
1156
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1157
|
+
conversationId = `video-${requestId}`;
|
|
1158
|
+
getOrCreateConversation(conversationId, "server", `Video (${requestId.substring(0, 8)})`);
|
|
1159
|
+
}
|
|
1160
|
+
addActivityEvent(conversationId, "videoEvents", {
|
|
1161
|
+
id: requestId,
|
|
1162
|
+
name: "video:request:started",
|
|
1163
|
+
timestamp,
|
|
1164
|
+
payload: e.payload
|
|
1165
|
+
});
|
|
1166
|
+
}));
|
|
1167
|
+
cleanupFns.push(aiEventClient.on("video:request:completed", (e) => {
|
|
1168
|
+
const {
|
|
1169
|
+
requestId,
|
|
1170
|
+
clientId,
|
|
1171
|
+
timestamp
|
|
1172
|
+
} = e.payload;
|
|
1173
|
+
let conversationId = clientId;
|
|
1174
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1175
|
+
conversationId = `video-${requestId}`;
|
|
1176
|
+
getOrCreateConversation(conversationId, "server", `Video (${requestId.substring(0, 8)})`);
|
|
1177
|
+
}
|
|
1178
|
+
addActivityEvent(conversationId, "videoEvents", {
|
|
1179
|
+
id: requestId,
|
|
1180
|
+
name: "video:request:completed",
|
|
1181
|
+
timestamp,
|
|
1182
|
+
payload: e.payload
|
|
1183
|
+
});
|
|
1184
|
+
}));
|
|
1185
|
+
cleanupFns.push(aiEventClient.on("video:usage", (e) => {
|
|
1186
|
+
const {
|
|
1187
|
+
requestId,
|
|
1188
|
+
clientId,
|
|
1189
|
+
timestamp
|
|
1190
|
+
} = e.payload;
|
|
1191
|
+
let conversationId = clientId;
|
|
1192
|
+
if (!conversationId || !state.conversations[conversationId]) {
|
|
1193
|
+
conversationId = `video-${requestId}`;
|
|
1194
|
+
getOrCreateConversation(conversationId, "server", `Video (${requestId.substring(0, 8)})`);
|
|
1195
|
+
}
|
|
1196
|
+
addActivityEvent(conversationId, "videoEvents", {
|
|
1197
|
+
id: requestId,
|
|
1198
|
+
name: "video:usage",
|
|
1199
|
+
timestamp,
|
|
1200
|
+
payload: e.payload
|
|
1201
|
+
});
|
|
1202
|
+
}));
|
|
937
1203
|
onCleanup(() => {
|
|
938
1204
|
for (const cleanup of cleanupFns) {
|
|
939
1205
|
cleanup();
|