@agentforge-io/chat-sdk 2.5.0 → 2.5.1
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/react.js +58 -48
- package/package.json +1 -1
package/dist/react.js
CHANGED
|
@@ -563,28 +563,34 @@ function ChatWidget(props) {
|
|
|
563
563
|
}
|
|
564
564
|
visibleIdxs.push(i);
|
|
565
565
|
}
|
|
566
|
-
//
|
|
567
|
-
//
|
|
568
|
-
//
|
|
569
|
-
//
|
|
570
|
-
const
|
|
571
|
-
for (
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
566
|
+
// Find the index of the next assistant message after each
|
|
567
|
+
// position. Used to decide whether an empty bubble has been
|
|
568
|
+
// superseded by a later speaker (in which case the visitor
|
|
569
|
+
// should not still see it typing).
|
|
570
|
+
const nextAssistantIdx = new Array(messages.length).fill(-1);
|
|
571
|
+
for (let k = messages.length - 2; k >= 0; k--) {
|
|
572
|
+
const nextI = k + 1;
|
|
573
|
+
nextAssistantIdx[k] =
|
|
574
|
+
messages[nextI].role === 'assistant'
|
|
575
|
+
? nextI
|
|
576
|
+
: nextAssistantIdx[nextI];
|
|
575
577
|
}
|
|
576
578
|
const finalIdxs = visibleIdxs.filter((i) => {
|
|
577
579
|
const m = messages[i];
|
|
578
580
|
if (m.role !== 'assistant')
|
|
579
581
|
return true;
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
//
|
|
583
|
-
//
|
|
584
|
-
//
|
|
585
|
-
//
|
|
586
|
-
//
|
|
587
|
-
|
|
582
|
+
// Any empty assistant bubble that has been overtaken by
|
|
583
|
+
// a LATER assistant bubble is an intermediate — hide it.
|
|
584
|
+
// Covers two cases at once:
|
|
585
|
+
// 1. The classic "chain head/intermediate" path: bubble
|
|
586
|
+
// i is empty and there's a final bubble after it.
|
|
587
|
+
// 2. The "live delegation" path: while a chain streams,
|
|
588
|
+
// the previous member sits at content='' isStreaming=
|
|
589
|
+
// true (the SDK only flips isStreaming when the
|
|
590
|
+
// bubble produced text). A naive filter would keep
|
|
591
|
+
// showing its typing dots; we drop it as soon as
|
|
592
|
+
// a fresher speaker exists.
|
|
593
|
+
if (!m.content && nextAssistantIdx[i] !== -1)
|
|
588
594
|
return false;
|
|
589
595
|
return true;
|
|
590
596
|
});
|
|
@@ -612,37 +618,41 @@ function ChatWidget(props) {
|
|
|
612
618
|
let chainParticipants;
|
|
613
619
|
if (isAssistant && showAvatar) {
|
|
614
620
|
const head = chainHeadFor[i];
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
644
|
-
|
|
645
|
-
|
|
621
|
+
// Collect all distinct speakers in [head…i] in
|
|
622
|
+
// chronological order. The bubble that's rendering now
|
|
623
|
+
// (i) is the most recent speaker so it becomes the
|
|
624
|
+
// "active" one at the front of the stack; everything
|
|
625
|
+
// earlier in the chain trails behind in reverse-
|
|
626
|
+
// chronological order. Works the same whether the
|
|
627
|
+
// chain has finished or is still streaming — visitor
|
|
628
|
+
// sees one bubble with a live-updating header.
|
|
629
|
+
const seen = new Set();
|
|
630
|
+
const ordered = [];
|
|
631
|
+
for (let j = head; j <= i; j++) {
|
|
632
|
+
const mj = messages[j];
|
|
633
|
+
if (mj.role !== 'assistant')
|
|
634
|
+
continue;
|
|
635
|
+
const key = mj.actingAgentId ?? null;
|
|
636
|
+
if (seen.has(key))
|
|
637
|
+
continue;
|
|
638
|
+
seen.add(key);
|
|
639
|
+
const mem = mj.actingAgentId
|
|
640
|
+
? membersById.get(mj.actingAgentId)
|
|
641
|
+
: undefined;
|
|
642
|
+
ordered.push({
|
|
643
|
+
agentId: mj.actingAgentId ?? agent?.slug,
|
|
644
|
+
name: mem?.name ?? personaName ?? agent?.name,
|
|
645
|
+
theme: mem
|
|
646
|
+
? { ...theme, avatarUrl: mem.avatarUrl }
|
|
647
|
+
: theme,
|
|
648
|
+
});
|
|
649
|
+
}
|
|
650
|
+
if (ordered.length > 1) {
|
|
651
|
+
// The visible bubble's speaker (i) sits at the END of
|
|
652
|
+
// `ordered`. Move them to the front so the active
|
|
653
|
+
// avatar leads the stack.
|
|
654
|
+
const active = ordered.pop();
|
|
655
|
+
chainParticipants = [active, ...ordered.reverse()];
|
|
646
656
|
}
|
|
647
657
|
}
|
|
648
658
|
return ((0, jsx_runtime_1.jsx)(MessageBubble, { message: m, session: session, readOnly: readOnlyApprovals, onDecision: onApprovalDecision, bare: bare, showAvatar: showAvatar, avatarTheme: bubbleAvatarTheme, avatarName: bubbleAvatarName, avatarAgentId: bubbleAgentId, speakerLabel: member?.name, chainParticipants: chainParticipants, onContinue: () => {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@agentforge-io/chat-sdk",
|
|
3
|
-
"version": "2.5.
|
|
3
|
+
"version": "2.5.1",
|
|
4
4
|
"description": "Framework-free chat session SDK for AgentForge public chat tokens. Headless — no DOM. Drop into any frontend (React, Vue, Svelte, vanilla) and listen for events.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"main": "dist/index.js",
|