@copilotz/chat-ui 0.5.0 → 0.6.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/index.cjs +99 -27
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +99 -27
- package/dist/index.js.map +1 -1
- package/dist/styles.css +0 -3
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -880,7 +880,6 @@ var arePropsEqual = (prevProps, nextProps) => {
|
|
|
880
880
|
if (prevProps.markdown !== nextProps.markdown) return false;
|
|
881
881
|
if (prevProps.isExpanded !== nextProps.isExpanded) return false;
|
|
882
882
|
if (prevProps.onToggleExpanded !== nextProps.onToggleExpanded) return false;
|
|
883
|
-
if (prevProps.isGrouped !== nextProps.isGrouped) return false;
|
|
884
883
|
if (prevProps.assistantAvatar !== nextProps.assistantAvatar) return false;
|
|
885
884
|
return true;
|
|
886
885
|
};
|
|
@@ -911,7 +910,6 @@ var Message = (0, import_react2.memo)(({
|
|
|
911
910
|
markdown,
|
|
912
911
|
isExpanded = false,
|
|
913
912
|
onToggleExpanded,
|
|
914
|
-
isGrouped = false,
|
|
915
913
|
agentOptions = []
|
|
916
914
|
}) => {
|
|
917
915
|
const [isEditing, setIsEditing] = (0, import_react2.useState)(false);
|
|
@@ -984,7 +982,7 @@ var Message = (0, import_react2.memo)(({
|
|
|
984
982
|
onMouseEnter: () => setShowActions(true),
|
|
985
983
|
onMouseLeave: () => setShowActions(false),
|
|
986
984
|
children: [
|
|
987
|
-
|
|
985
|
+
/* @__PURE__ */ (0, import_jsx_runtime8.jsxs)("div", { className: `flex gap-3 ${messageIsUser ? "flex-row-reverse" : "flex-row"} w-full mb-1`, children: [
|
|
988
986
|
showAvatar && /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("div", { className: `flex-shrink-0 ${compactMode ? "mt-1" : "mt-0"}`, children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Avatar, { className: compactMode ? "h-6 w-6" : "h-8 w-8", children: messageIsUser ? /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)(import_jsx_runtime8.Fragment, { children: [
|
|
989
987
|
/* @__PURE__ */ (0, import_jsx_runtime8.jsx)(AvatarImage, { src: userAvatar, alt: userName }),
|
|
990
988
|
/* @__PURE__ */ (0, import_jsx_runtime8.jsx)(AvatarFallback, { className: "bg-primary text-primary-foreground", children: userName.charAt(0).toUpperCase() })
|
|
@@ -4997,6 +4995,81 @@ function getMessageSpeakerKey(message) {
|
|
|
4997
4995
|
}
|
|
4998
4996
|
return message.role;
|
|
4999
4997
|
}
|
|
4998
|
+
var mergeToolCalls = (activities) => {
|
|
4999
|
+
const merged = /* @__PURE__ */ new Map();
|
|
5000
|
+
for (const activity of activities) {
|
|
5001
|
+
if (!Array.isArray(activity.toolCalls)) continue;
|
|
5002
|
+
for (const toolCall of activity.toolCalls) {
|
|
5003
|
+
const key = toolCall.id || `${toolCall.name}:${JSON.stringify(toolCall.arguments ?? {})}`;
|
|
5004
|
+
merged.set(key, toolCall);
|
|
5005
|
+
}
|
|
5006
|
+
}
|
|
5007
|
+
return merged.size > 0 ? Array.from(merged.values()) : void 0;
|
|
5008
|
+
};
|
|
5009
|
+
var mergeReasoning = (activities) => {
|
|
5010
|
+
const segments = activities.map((activity) => activity.reasoning?.trim()).filter((value) => Boolean(value));
|
|
5011
|
+
if (segments.length === 0) return void 0;
|
|
5012
|
+
return segments.filter((segment, index) => index === 0 || segment !== segments[index - 1]).join("\n\n");
|
|
5013
|
+
};
|
|
5014
|
+
var mergeGroupActivity = (messages) => {
|
|
5015
|
+
const activities = messages.map((message) => message.activity).filter((activity) => Boolean(activity));
|
|
5016
|
+
if (activities.length === 0) return void 0;
|
|
5017
|
+
const lastActivity = activities[activities.length - 1];
|
|
5018
|
+
const mergedReasoning = mergeReasoning(activities);
|
|
5019
|
+
const mergedToolCalls = mergeToolCalls(activities);
|
|
5020
|
+
return {
|
|
5021
|
+
...lastActivity,
|
|
5022
|
+
...mergedReasoning ? { reasoning: mergedReasoning } : {},
|
|
5023
|
+
...mergedToolCalls ? { toolCalls: mergedToolCalls } : {}
|
|
5024
|
+
};
|
|
5025
|
+
};
|
|
5026
|
+
var mergeMessageGroup = (messages) => {
|
|
5027
|
+
const firstMessage = messages[0];
|
|
5028
|
+
const lastMessage = messages[messages.length - 1];
|
|
5029
|
+
const content = messages.map((message) => message.content.trim()).filter((value) => value.length > 0).join("\n\n");
|
|
5030
|
+
const attachments = messages.flatMap((message) => message.attachments ?? []);
|
|
5031
|
+
return {
|
|
5032
|
+
...lastMessage,
|
|
5033
|
+
id: lastMessage.id,
|
|
5034
|
+
content,
|
|
5035
|
+
timestamp: firstMessage.timestamp,
|
|
5036
|
+
attachments: attachments.length > 0 ? attachments : void 0,
|
|
5037
|
+
isStreaming: lastMessage.isStreaming,
|
|
5038
|
+
isComplete: lastMessage.isComplete,
|
|
5039
|
+
isEdited: messages.some((message) => message.isEdited),
|
|
5040
|
+
originalContent: void 0,
|
|
5041
|
+
editedAt: lastMessage.editedAt,
|
|
5042
|
+
activity: mergeGroupActivity(messages),
|
|
5043
|
+
senderName: lastMessage.senderName ?? firstMessage.senderName,
|
|
5044
|
+
senderAgentId: lastMessage.senderAgentId ?? firstMessage.senderAgentId,
|
|
5045
|
+
metadata: lastMessage.metadata
|
|
5046
|
+
};
|
|
5047
|
+
};
|
|
5048
|
+
var groupMessagesForRender = (messages) => {
|
|
5049
|
+
if (messages.length === 0) return [];
|
|
5050
|
+
const groups = [];
|
|
5051
|
+
let currentGroup = [messages[0]];
|
|
5052
|
+
const flushGroup = () => {
|
|
5053
|
+
const mergedMessage = mergeMessageGroup(currentGroup);
|
|
5054
|
+
groups.push({
|
|
5055
|
+
id: mergedMessage.id,
|
|
5056
|
+
message: mergedMessage,
|
|
5057
|
+
suggestionMessageId: currentGroup[currentGroup.length - 1].id
|
|
5058
|
+
});
|
|
5059
|
+
};
|
|
5060
|
+
for (let index = 1; index < messages.length; index++) {
|
|
5061
|
+
const previous = currentGroup[currentGroup.length - 1];
|
|
5062
|
+
const next = messages[index];
|
|
5063
|
+
if (previous.role === next.role && getMessageSpeakerKey(previous) === getMessageSpeakerKey(next)) {
|
|
5064
|
+
currentGroup.push(next);
|
|
5065
|
+
continue;
|
|
5066
|
+
}
|
|
5067
|
+
flushGroup();
|
|
5068
|
+
currentGroup = [next];
|
|
5069
|
+
}
|
|
5070
|
+
flushGroup();
|
|
5071
|
+
return groups;
|
|
5072
|
+
};
|
|
5000
5073
|
var ChatUI = ({
|
|
5001
5074
|
messages = [],
|
|
5002
5075
|
threads = [],
|
|
@@ -5090,8 +5163,9 @@ var ChatUI = ({
|
|
|
5090
5163
|
}, [attachments]);
|
|
5091
5164
|
const [isCustomMounted, setIsCustomMounted] = (0, import_react9.useState)(false);
|
|
5092
5165
|
const [isCustomVisible, setIsCustomVisible] = (0, import_react9.useState)(false);
|
|
5166
|
+
const groupedMessages = (0, import_react9.useMemo)(() => groupMessagesForRender(messages), [messages]);
|
|
5093
5167
|
const virtualizer = (0, import_react_virtual.useVirtualizer)({
|
|
5094
|
-
count:
|
|
5168
|
+
count: groupedMessages.length,
|
|
5095
5169
|
getScrollElement: () => scrollAreaRef.current,
|
|
5096
5170
|
estimateSize: () => 100,
|
|
5097
5171
|
overscan: 5
|
|
@@ -5129,20 +5203,20 @@ var ChatUI = ({
|
|
|
5129
5203
|
}, [state.showSidebar, isMobile, config.customComponent]);
|
|
5130
5204
|
const prevMessageCountRef = (0, import_react9.useRef)(0);
|
|
5131
5205
|
(0, import_react9.useEffect)(() => {
|
|
5132
|
-
if (
|
|
5206
|
+
if (groupedMessages.length === 0) {
|
|
5133
5207
|
prevMessageCountRef.current = 0;
|
|
5134
5208
|
return;
|
|
5135
5209
|
}
|
|
5136
5210
|
if (prependSnapshotRef.current) {
|
|
5137
|
-
prevMessageCountRef.current =
|
|
5211
|
+
prevMessageCountRef.current = groupedMessages.length;
|
|
5138
5212
|
return;
|
|
5139
5213
|
}
|
|
5140
5214
|
const wasEmpty = prevMessageCountRef.current === 0;
|
|
5141
|
-
prevMessageCountRef.current =
|
|
5215
|
+
prevMessageCountRef.current = groupedMessages.length;
|
|
5142
5216
|
if (wasEmpty) {
|
|
5143
5217
|
requestAnimationFrame(() => {
|
|
5144
5218
|
requestAnimationFrame(() => {
|
|
5145
|
-
virtualizer.scrollToIndex(
|
|
5219
|
+
virtualizer.scrollToIndex(groupedMessages.length - 1, { align: "end" });
|
|
5146
5220
|
});
|
|
5147
5221
|
});
|
|
5148
5222
|
return;
|
|
@@ -5157,7 +5231,7 @@ var ChatUI = ({
|
|
|
5157
5231
|
viewport.scrollTop = viewport.scrollHeight;
|
|
5158
5232
|
}
|
|
5159
5233
|
});
|
|
5160
|
-
}, [
|
|
5234
|
+
}, [groupedMessages, state.isAtBottom, virtualizer]);
|
|
5161
5235
|
(0, import_react9.useEffect)(() => {
|
|
5162
5236
|
virtualizer.measure();
|
|
5163
5237
|
}, [expandedMessageIds, virtualizer]);
|
|
@@ -5167,13 +5241,13 @@ var ChatUI = ({
|
|
|
5167
5241
|
(0, import_react9.useEffect)(() => {
|
|
5168
5242
|
const snapshot = prependSnapshotRef.current;
|
|
5169
5243
|
if (!snapshot) return;
|
|
5170
|
-
if (
|
|
5244
|
+
if (groupedMessages.length <= snapshot.messageCount) {
|
|
5171
5245
|
if (!isLoadingOlderMessages) {
|
|
5172
5246
|
prependSnapshotRef.current = null;
|
|
5173
5247
|
}
|
|
5174
5248
|
return;
|
|
5175
5249
|
}
|
|
5176
|
-
if ((
|
|
5250
|
+
if ((groupedMessages[0]?.id ?? null) === snapshot.firstMessageId) {
|
|
5177
5251
|
if (!isLoadingOlderMessages) {
|
|
5178
5252
|
prependSnapshotRef.current = null;
|
|
5179
5253
|
}
|
|
@@ -5189,20 +5263,20 @@ var ChatUI = ({
|
|
|
5189
5263
|
prependSnapshotRef.current = null;
|
|
5190
5264
|
});
|
|
5191
5265
|
});
|
|
5192
|
-
}, [
|
|
5266
|
+
}, [groupedMessages, isLoadingOlderMessages, virtualizer]);
|
|
5193
5267
|
const requestOlderMessages = (0, import_react9.useCallback)(() => {
|
|
5194
5268
|
if (!onLoadOlderMessages || !hasMoreMessagesBefore || isLoadingOlderMessages) return;
|
|
5195
5269
|
const viewport = scrollAreaRef.current;
|
|
5196
5270
|
prependSnapshotRef.current = viewport ? {
|
|
5197
5271
|
scrollHeight: viewport.scrollHeight,
|
|
5198
5272
|
scrollTop: viewport.scrollTop,
|
|
5199
|
-
firstMessageId:
|
|
5200
|
-
messageCount:
|
|
5273
|
+
firstMessageId: groupedMessages[0]?.id ?? null,
|
|
5274
|
+
messageCount: groupedMessages.length
|
|
5201
5275
|
} : null;
|
|
5202
5276
|
onLoadOlderMessages();
|
|
5203
|
-
}, [hasMoreMessagesBefore, isLoadingOlderMessages,
|
|
5277
|
+
}, [groupedMessages, hasMoreMessagesBefore, isLoadingOlderMessages, onLoadOlderMessages]);
|
|
5204
5278
|
(0, import_react9.useEffect)(() => {
|
|
5205
|
-
const validMessageIds = new Set(
|
|
5279
|
+
const validMessageIds = new Set(groupedMessages.map((group) => group.id));
|
|
5206
5280
|
setExpandedMessageIds((prev) => {
|
|
5207
5281
|
const activeIds = Object.keys(prev);
|
|
5208
5282
|
const staleIds = activeIds.filter((messageId) => !validMessageIds.has(messageId));
|
|
@@ -5215,7 +5289,7 @@ var ChatUI = ({
|
|
|
5215
5289
|
});
|
|
5216
5290
|
return next;
|
|
5217
5291
|
});
|
|
5218
|
-
}, [
|
|
5292
|
+
}, [groupedMessages]);
|
|
5219
5293
|
const handleScroll = (0, import_react9.useCallback)((e) => {
|
|
5220
5294
|
const { scrollTop, scrollHeight, clientHeight } = e.currentTarget;
|
|
5221
5295
|
const isAtBottom = scrollHeight - scrollTop - clientHeight < 50;
|
|
@@ -5317,7 +5391,7 @@ var ChatUI = ({
|
|
|
5317
5391
|
}, [config?.customComponent?.component, closeSidebar, isMobile]);
|
|
5318
5392
|
const SuggestionIconComponents = [import_lucide_react14.MessageSquare, import_lucide_react14.Lightbulb, import_lucide_react14.Zap, import_lucide_react14.HelpCircle];
|
|
5319
5393
|
const renderSuggestions = () => {
|
|
5320
|
-
if (
|
|
5394
|
+
if (groupedMessages.length > 0 || !suggestions.length) return null;
|
|
5321
5395
|
return /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "flex flex-col items-center justify-center min-h-[60vh] py-8 px-4", children: [
|
|
5322
5396
|
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "text-center mb-8", children: [
|
|
5323
5397
|
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "inline-flex items-center justify-center w-14 h-14 rounded-2xl bg-gradient-to-br from-primary/20 to-primary/5 mb-4 shadow-sm", children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.Sparkles, { className: "w-7 h-7 text-primary" }) }),
|
|
@@ -5482,7 +5556,7 @@ var ChatUI = ({
|
|
|
5482
5556
|
onScrollCapture: handleScroll,
|
|
5483
5557
|
style: { contain: "strict" },
|
|
5484
5558
|
children: /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "max-w-4xl mx-auto pb-4", children: [
|
|
5485
|
-
|
|
5559
|
+
groupedMessages.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "flex justify-center py-2", children: isLoadingOlderMessages ? /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", { className: "text-xs text-muted-foreground", children: config.labels.loadingOlderMessages }) : hasMoreMessagesBefore ? /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
5486
5560
|
"button",
|
|
5487
5561
|
{
|
|
5488
5562
|
type: "button",
|
|
@@ -5491,7 +5565,7 @@ var ChatUI = ({
|
|
|
5491
5565
|
children: config.labels.loadOlderMessages
|
|
5492
5566
|
}
|
|
5493
5567
|
) : null }),
|
|
5494
|
-
isMessagesLoading ? renderMessageLoadingSkeleton() :
|
|
5568
|
+
isMessagesLoading ? renderMessageLoadingSkeleton() : groupedMessages.length === 0 ? renderSuggestions() : /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
5495
5569
|
"div",
|
|
5496
5570
|
{
|
|
5497
5571
|
style: {
|
|
@@ -5500,9 +5574,8 @@ var ChatUI = ({
|
|
|
5500
5574
|
position: "relative"
|
|
5501
5575
|
},
|
|
5502
5576
|
children: virtualizer.getVirtualItems().map((virtualRow) => {
|
|
5503
|
-
const
|
|
5504
|
-
const
|
|
5505
|
-
const isGrouped = prevMessage !== null && prevMessage.role === message.role && getMessageSpeakerKey(prevMessage) === getMessageSpeakerKey(message);
|
|
5577
|
+
const group = groupedMessages[virtualRow.index];
|
|
5578
|
+
const message = group.message;
|
|
5506
5579
|
return /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
5507
5580
|
"div",
|
|
5508
5581
|
{
|
|
@@ -5515,20 +5588,19 @@ var ChatUI = ({
|
|
|
5515
5588
|
width: "100%",
|
|
5516
5589
|
transform: `translateY(${virtualRow.start}px)`
|
|
5517
5590
|
},
|
|
5518
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: virtualRow.index === 0 ? "" :
|
|
5591
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: virtualRow.index === 0 ? "" : "pt-4", children: [
|
|
5519
5592
|
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
5520
5593
|
Message,
|
|
5521
5594
|
{
|
|
5522
5595
|
message,
|
|
5523
5596
|
...messageProps,
|
|
5524
|
-
isGrouped,
|
|
5525
5597
|
isExpanded: Boolean(expandedMessageIds[message.id])
|
|
5526
5598
|
}
|
|
5527
5599
|
),
|
|
5528
|
-
message.role === "assistant" && renderInlineSuggestions(
|
|
5600
|
+
message.role === "assistant" && renderInlineSuggestions(group.suggestionMessageId)
|
|
5529
5601
|
] })
|
|
5530
5602
|
},
|
|
5531
|
-
|
|
5603
|
+
group.id
|
|
5532
5604
|
);
|
|
5533
5605
|
})
|
|
5534
5606
|
}
|