@epicbagel/saas-kit 1.25.1 → 1.27.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/README.md +50 -0
- package/dist/chunk-DHXKCMKY.cjs +198 -0
- package/dist/chunk-HO6DRDGD.js +158 -0
- package/dist/chunk-NXFZULS3.js +58 -0
- package/dist/chunk-SG4ZE2EN.js +198 -0
- package/dist/chunk-U7XNNLVP.cjs +58 -0
- package/dist/chunk-ZBWL7OUW.cjs +158 -0
- package/dist/primitives/board-view.cjs +3 -3
- package/dist/primitives/board-view.js +2 -2
- package/dist/primitives/chat-turn-navigator.cjs +16 -0
- package/dist/primitives/chat-turn-navigator.d.cts +40 -0
- package/dist/primitives/chat-turn-navigator.d.ts +40 -0
- package/dist/primitives/chat-turn-navigator.js +16 -0
- package/dist/primitives/chat.cjs +175 -20
- package/dist/primitives/chat.d.cts +78 -1
- package/dist/primitives/chat.d.ts +78 -1
- package/dist/primitives/chat.js +167 -12
- package/dist/primitives/item.cjs +24 -194
- package/dist/primitives/item.js +13 -183
- package/dist/primitives/notes.cjs +3 -3
- package/dist/primitives/notes.js +3 -3
- package/dist/primitives/person-avatar.cjs +4 -50
- package/dist/primitives/person-avatar.js +5 -51
- package/dist/primitives/resource-list.cjs +3 -3
- package/dist/primitives/resource-list.js +2 -2
- package/package.json +11 -1
- package/dist/{chunk-LQPJGZIE.js → chunk-JS6BLIWL.js} +3 -3
- package/dist/{chunk-FBVZRRA4.cjs → chunk-MOJHETNO.cjs} +2 -2
package/dist/primitives/chat.cjs
CHANGED
|
@@ -17,24 +17,20 @@ var _chunkPNI354BYcjs = require('../chunk-PNI354BY.cjs');
|
|
|
17
17
|
var _chunkM4V7OJNFcjs = require('../chunk-M4V7OJNF.cjs');
|
|
18
18
|
|
|
19
19
|
|
|
20
|
-
|
|
21
|
-
var _chunkB765DSRGcjs = require('../chunk-B765DSRG.cjs');
|
|
22
|
-
|
|
20
|
+
var _chunkVMXKT67Ecjs = require('../chunk-VMXKT67E.cjs');
|
|
23
21
|
|
|
24
22
|
|
|
23
|
+
var _chunkU7XNNLVPcjs = require('../chunk-U7XNNLVP.cjs');
|
|
25
24
|
|
|
26
25
|
|
|
27
26
|
|
|
28
|
-
|
|
29
|
-
var _chunk23IETCLVcjs = require('../chunk-23IETCLV.cjs');
|
|
30
|
-
require('../chunk-DMPSKGFM.cjs');
|
|
27
|
+
var _chunkB765DSRGcjs = require('../chunk-B765DSRG.cjs');
|
|
31
28
|
|
|
32
29
|
|
|
33
30
|
|
|
34
31
|
|
|
35
32
|
|
|
36
33
|
var _chunkNWDPH2Z7cjs = require('../chunk-NWDPH2Z7.cjs');
|
|
37
|
-
require('../chunk-Z2H4LJVG.cjs');
|
|
38
34
|
|
|
39
35
|
|
|
40
36
|
|
|
@@ -44,6 +40,14 @@ require('../chunk-2HV2KKOE.cjs');
|
|
|
44
40
|
|
|
45
41
|
|
|
46
42
|
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
|
|
46
|
+
var _chunkDHXKCMKYcjs = require('../chunk-DHXKCMKY.cjs');
|
|
47
|
+
require('../chunk-NQK5ZWC7.cjs');
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
|
|
47
51
|
var _chunkZLEM2SAUcjs = require('../chunk-ZLEM2SAU.cjs');
|
|
48
52
|
|
|
49
53
|
|
|
@@ -63,6 +67,19 @@ var _chunk2BHI5ZWJcjs = require('../chunk-2BHI5ZWJ.cjs');
|
|
|
63
67
|
|
|
64
68
|
|
|
65
69
|
var _chunkZAITUDYDcjs = require('../chunk-ZAITUDYD.cjs');
|
|
70
|
+
|
|
71
|
+
|
|
72
|
+
var _chunkZBWL7OUWcjs = require('../chunk-ZBWL7OUW.cjs');
|
|
73
|
+
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
|
|
78
|
+
|
|
79
|
+
|
|
80
|
+
var _chunk23IETCLVcjs = require('../chunk-23IETCLV.cjs');
|
|
81
|
+
require('../chunk-DMPSKGFM.cjs');
|
|
82
|
+
require('../chunk-Z2H4LJVG.cjs');
|
|
66
83
|
require('../chunk-U2NES7VR.cjs');
|
|
67
84
|
|
|
68
85
|
|
|
@@ -114,6 +131,7 @@ var _chunkH2UFRLLNcjs = require('../chunk-H2UFRLLN.cjs');
|
|
|
114
131
|
|
|
115
132
|
|
|
116
133
|
|
|
134
|
+
|
|
117
135
|
var _react = require('react');
|
|
118
136
|
|
|
119
137
|
|
|
@@ -162,6 +180,24 @@ function timelineMarkers(messages, now) {
|
|
|
162
180
|
function TimelineMarker({ label }) {
|
|
163
181
|
return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkB765DSRGcjs.Marker, { variant: "separator", role: "separator", "aria-label": label, children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkB765DSRGcjs.MarkerContent, { children: label }) });
|
|
164
182
|
}
|
|
183
|
+
function authorLines(messages, markers) {
|
|
184
|
+
let previous = null;
|
|
185
|
+
return messages.map((message, index) => {
|
|
186
|
+
if (message.status === "running") return false;
|
|
187
|
+
const shown = Boolean(message.author) && (!previous || Boolean(markers[index]) || previous.role !== message.role || _optionalChain([previous, 'access', _ => _.author, 'optionalAccess', _2 => _2.id]) !== message.author.id);
|
|
188
|
+
previous = message;
|
|
189
|
+
return shown;
|
|
190
|
+
});
|
|
191
|
+
}
|
|
192
|
+
function ChatAuthorLine({ author, align }) {
|
|
193
|
+
const avatar = /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkU7XNNLVPcjs.PersonAvatar, { name: author.name, photoUrl: author.avatarUrl, size: 20, fallbackClassName: "text-[9px]" });
|
|
194
|
+
return /* @__PURE__ */ _jsxruntime.jsxs.call(void 0, "div", { "data-slot": "chat-author", className: _chunkKWLSBTB2cjs.cn.call(void 0, "flex items-center gap-2 text-xs", align === "end" ? "self-end" : "self-start"), children: [
|
|
195
|
+
align === "start" ? avatar : null,
|
|
196
|
+
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, "span", { className: "font-medium text-foreground", children: author.name }),
|
|
197
|
+
author.detail ? /* @__PURE__ */ _jsxruntime.jsx.call(void 0, "span", { className: "text-muted-foreground", children: author.detail }) : null,
|
|
198
|
+
align === "end" ? avatar : null
|
|
199
|
+
] });
|
|
200
|
+
}
|
|
165
201
|
function ChatRunningLine({
|
|
166
202
|
label,
|
|
167
203
|
align = "start",
|
|
@@ -183,9 +219,13 @@ var ChatThread = _react.forwardRef.call(void 0,
|
|
|
183
219
|
onOpenAttachment,
|
|
184
220
|
attachmentAction = "open",
|
|
185
221
|
messageActions,
|
|
222
|
+
navigator,
|
|
223
|
+
navigatorLabel,
|
|
224
|
+
navigatorSide,
|
|
186
225
|
className
|
|
187
226
|
}, ref) {
|
|
188
227
|
const markers = timelineMarkers(messages, /* @__PURE__ */ new Date());
|
|
228
|
+
const authorShown = authorLines(messages, markers);
|
|
189
229
|
const anchorId = useArrivingUserTurnId(messages);
|
|
190
230
|
const workspace = appearance === "workspace";
|
|
191
231
|
return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunk23IETCLVcjs.MessageScrollerProvider, { autoScroll: true, children: /* @__PURE__ */ _jsxruntime.jsxs.call(void 0,
|
|
@@ -226,6 +266,7 @@ var ChatThread = _react.forwardRef.call(void 0,
|
|
|
226
266
|
children: [
|
|
227
267
|
marker ? /* @__PURE__ */ _jsxruntime.jsx.call(void 0, TimelineMarker, { label: marker }) : null,
|
|
228
268
|
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkNWDPH2Z7cjs.Message, { align: isUser ? "end" : "start", children: /* @__PURE__ */ _jsxruntime.jsxs.call(void 0, _chunkNWDPH2Z7cjs.MessageContent, { children: [
|
|
269
|
+
m.author && authorShown[index] ? /* @__PURE__ */ _jsxruntime.jsx.call(void 0, ChatAuthorLine, { author: m.author, align: isUser ? "end" : "start" }) : null,
|
|
229
270
|
(m.content || m.text) && /* @__PURE__ */ _jsxruntime.jsx.call(void 0,
|
|
230
271
|
_chunkV4YWTRLDcjs.Bubble,
|
|
231
272
|
{
|
|
@@ -285,7 +326,17 @@ var ChatThread = _react.forwardRef.call(void 0,
|
|
|
285
326
|
/* @__PURE__ */ _jsxruntime.jsxs.call(void 0, _chunk23IETCLVcjs.MessageScrollerButton, { variant: "outline", className: "rounded-full shadow-sm", children: [
|
|
286
327
|
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _lucidereact.ArrowDown, { className: "h-4 w-4" }),
|
|
287
328
|
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, "span", { className: "sr-only", children: scrollButtonLabel })
|
|
288
|
-
] })
|
|
329
|
+
] }),
|
|
330
|
+
navigator && navigator.length > 0 ? /* @__PURE__ */ _jsxruntime.jsx.call(void 0,
|
|
331
|
+
_chunkZBWL7OUWcjs.ChatTurnNavigator,
|
|
332
|
+
{
|
|
333
|
+
items: navigator,
|
|
334
|
+
order: messages.map((m) => m.id),
|
|
335
|
+
label: navigatorLabel,
|
|
336
|
+
side: navigatorSide,
|
|
337
|
+
columnWidth: workspace ? 768 : void 0
|
|
338
|
+
}
|
|
339
|
+
) : null
|
|
289
340
|
]
|
|
290
341
|
}
|
|
291
342
|
) });
|
|
@@ -308,7 +359,7 @@ function ChatCopyAction({
|
|
|
308
359
|
"data-copied": copied || void 0,
|
|
309
360
|
onClick: async () => {
|
|
310
361
|
const ok = await copy(text);
|
|
311
|
-
_optionalChain([onCopy, 'optionalCall',
|
|
362
|
+
_optionalChain([onCopy, 'optionalCall', _3 => _3(ok)]);
|
|
312
363
|
},
|
|
313
364
|
children: copied ? /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _lucidereact.Check, {}) : /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _lucidereact.Copy, {})
|
|
314
365
|
}
|
|
@@ -353,7 +404,7 @@ function ChatAttachmentList({
|
|
|
353
404
|
{
|
|
354
405
|
"aria-label": `${verb} ${attachment.name}`,
|
|
355
406
|
title: `${verb} ${attachment.name}`,
|
|
356
|
-
onClick: () => _optionalChain([onOpen, 'optionalCall',
|
|
407
|
+
onClick: () => _optionalChain([onOpen, 'optionalCall', _4 => _4(attachment)]),
|
|
357
408
|
className: "rounded-xl focus-visible:ring-2 focus-visible:ring-ring/50"
|
|
358
409
|
}
|
|
359
410
|
),
|
|
@@ -533,7 +584,7 @@ function ChatInput({
|
|
|
533
584
|
"data-slot": "chat-input-actions",
|
|
534
585
|
onClick: (event) => {
|
|
535
586
|
if (!event.currentTarget.contains(event.target)) return;
|
|
536
|
-
if (!event.target.closest("button")) _optionalChain([ref, 'access',
|
|
587
|
+
if (!event.target.closest("button")) _optionalChain([ref, 'access', _5 => _5.current, 'optionalAccess', _6 => _6.focus, 'call', _7 => _7()]);
|
|
537
588
|
},
|
|
538
589
|
className: _chunkKWLSBTB2cjs.cn.call(void 0,
|
|
539
590
|
compact ? "gap-1 px-2 pb-2 pt-0" : "gap-2",
|
|
@@ -552,7 +603,7 @@ function ChatInput({
|
|
|
552
603
|
children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _lucidereact.Plus, { className: _chunkKWLSBTB2cjs.cn.call(void 0, spacious && "h-5 w-5") })
|
|
553
604
|
}
|
|
554
605
|
) }),
|
|
555
|
-
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkZAITUDYDcjs.DropdownMenuContent, { align: "start", side: "top", className: "min-w-52", children: /* @__PURE__ */ _jsxruntime.jsxs.call(void 0, _chunkZAITUDYDcjs.DropdownMenuItem, { onSelect: () => _optionalChain([fileInputRef, 'access',
|
|
606
|
+
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkZAITUDYDcjs.DropdownMenuContent, { align: "start", side: "top", className: "min-w-52", children: /* @__PURE__ */ _jsxruntime.jsxs.call(void 0, _chunkZAITUDYDcjs.DropdownMenuItem, { onSelect: () => _optionalChain([fileInputRef, 'access', _8 => _8.current, 'optionalAccess', _9 => _9.click, 'call', _10 => _10()]), children: [
|
|
556
607
|
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _lucidereact.Paperclip, { className: "h-4 w-4" }),
|
|
557
608
|
addFilesLabel
|
|
558
609
|
] }) })
|
|
@@ -719,6 +770,92 @@ function ChatSuggestions({
|
|
|
719
770
|
)
|
|
720
771
|
] });
|
|
721
772
|
}
|
|
773
|
+
var DEFAULT_EMPTY_ACTIONS_LABEL = "Pick up where you left off";
|
|
774
|
+
function ChatEmptyActionIcon({ icon }) {
|
|
775
|
+
if (!icon) return null;
|
|
776
|
+
if (_react.isValidElement.call(void 0, icon)) return icon;
|
|
777
|
+
if (typeof icon === "function" || typeof icon === "object" && icon !== null && "render" in icon) {
|
|
778
|
+
const IconComp = icon;
|
|
779
|
+
return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, IconComp, { "aria-hidden": true });
|
|
780
|
+
}
|
|
781
|
+
return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _jsxruntime.Fragment, { children: icon });
|
|
782
|
+
}
|
|
783
|
+
function ChatEmptyActions({
|
|
784
|
+
items,
|
|
785
|
+
label,
|
|
786
|
+
onError,
|
|
787
|
+
className
|
|
788
|
+
}) {
|
|
789
|
+
const labelId = _react.useId.call(void 0, );
|
|
790
|
+
const [running, setRunning] = _react.useState.call(void 0, null);
|
|
791
|
+
if (items.length === 0) return null;
|
|
792
|
+
const showLabel = label.length > 0;
|
|
793
|
+
const pick = async (item) => {
|
|
794
|
+
if (running !== null) return;
|
|
795
|
+
let result;
|
|
796
|
+
try {
|
|
797
|
+
result = item.onSelect();
|
|
798
|
+
} catch (cause) {
|
|
799
|
+
onError(cause);
|
|
800
|
+
return;
|
|
801
|
+
}
|
|
802
|
+
if (!result || typeof result.then !== "function") return;
|
|
803
|
+
setRunning(item.id);
|
|
804
|
+
try {
|
|
805
|
+
await result;
|
|
806
|
+
} catch (cause) {
|
|
807
|
+
onError(cause);
|
|
808
|
+
} finally {
|
|
809
|
+
setRunning(null);
|
|
810
|
+
}
|
|
811
|
+
};
|
|
812
|
+
return /* @__PURE__ */ _jsxruntime.jsxs.call(void 0, "div", { "data-slot": "chat-empty-actions", className: _chunkKWLSBTB2cjs.cn.call(void 0, "w-full text-left", className), children: [
|
|
813
|
+
showLabel && /* @__PURE__ */ _jsxruntime.jsx.call(void 0, "p", { id: labelId, "data-slot": "chat-empty-actions-label", className: "mb-1.5 px-3 text-xs text-muted-foreground", children: label }),
|
|
814
|
+
/* @__PURE__ */ _jsxruntime.jsx.call(void 0,
|
|
815
|
+
"div",
|
|
816
|
+
{
|
|
817
|
+
role: "group",
|
|
818
|
+
"aria-labelledby": showLabel ? labelId : void 0,
|
|
819
|
+
"aria-label": showLabel ? void 0 : DEFAULT_EMPTY_ACTIONS_LABEL,
|
|
820
|
+
className: "flex flex-col gap-0.5",
|
|
821
|
+
children: items.map((item) => {
|
|
822
|
+
const busy = running === item.id;
|
|
823
|
+
return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkDHXKCMKYcjs.Item, { asChild: true, size: "sm", children: /* @__PURE__ */ _jsxruntime.jsxs.call(void 0,
|
|
824
|
+
"button",
|
|
825
|
+
{
|
|
826
|
+
type: "button",
|
|
827
|
+
"data-slot": "chat-empty-action",
|
|
828
|
+
"data-state": busy ? "loading" : void 0,
|
|
829
|
+
"aria-busy": busy || void 0,
|
|
830
|
+
disabled: item.disabled || running !== null,
|
|
831
|
+
onClick: () => void pick(item),
|
|
832
|
+
className: _chunkKWLSBTB2cjs.cn.call(void 0,
|
|
833
|
+
"min-h-11 cursor-pointer flex-nowrap text-left",
|
|
834
|
+
"hover:bg-muted focus-visible:bg-muted",
|
|
835
|
+
"disabled:cursor-not-allowed disabled:opacity-50 disabled:hover:bg-transparent",
|
|
836
|
+
busy && "disabled:opacity-100"
|
|
837
|
+
),
|
|
838
|
+
children: [
|
|
839
|
+
/* @__PURE__ */ _jsxruntime.jsx.call(void 0,
|
|
840
|
+
_chunkDHXKCMKYcjs.ItemMedia,
|
|
841
|
+
{
|
|
842
|
+
variant: "icon",
|
|
843
|
+
className: "size-8 self-center rounded-md bg-muted text-muted-foreground group-has-data-[slot=item-description]/item:translate-y-0 group-has-data-[slot=item-description]/item:self-center",
|
|
844
|
+
children: busy ? /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkVMXKT67Ecjs.Spinner, { "aria-hidden": true }) : /* @__PURE__ */ _jsxruntime.jsx.call(void 0, ChatEmptyActionIcon, { icon: item.icon })
|
|
845
|
+
}
|
|
846
|
+
),
|
|
847
|
+
/* @__PURE__ */ _jsxruntime.jsxs.call(void 0, _chunkDHXKCMKYcjs.ItemContent, { className: "min-w-0 flex-row flex-wrap items-baseline gap-x-2 gap-y-0.5 md:flex-nowrap", children: [
|
|
848
|
+
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkDHXKCMKYcjs.ItemTitle, { className: "w-auto min-w-0 shrink-0 font-normal text-foreground md:max-w-[60%] md:truncate", children: item.label }),
|
|
849
|
+
item.detail && /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkDHXKCMKYcjs.ItemDescription, { className: "line-clamp-1 min-w-0 flex-1 truncate text-xs md:text-sm", children: item.detail })
|
|
850
|
+
] })
|
|
851
|
+
]
|
|
852
|
+
}
|
|
853
|
+
) }, item.id);
|
|
854
|
+
})
|
|
855
|
+
}
|
|
856
|
+
)
|
|
857
|
+
] });
|
|
858
|
+
}
|
|
722
859
|
function MobileReplySuggestions({
|
|
723
860
|
items,
|
|
724
861
|
onSelect,
|
|
@@ -790,11 +927,11 @@ function MobileReplySuggestions({
|
|
|
790
927
|
className: "max-h-[min(85dvh,40rem)] overflow-hidden pb-[env(safe-area-inset-bottom)]",
|
|
791
928
|
onOpenAutoFocus: (event) => {
|
|
792
929
|
event.preventDefault();
|
|
793
|
-
_optionalChain([closeRef, 'access',
|
|
930
|
+
_optionalChain([closeRef, 'access', _11 => _11.current, 'optionalAccess', _12 => _12.focus, 'call', _13 => _13({ preventScroll: true })]);
|
|
794
931
|
},
|
|
795
932
|
onCloseAutoFocus: (event) => {
|
|
796
933
|
event.preventDefault();
|
|
797
|
-
if (_optionalChain([triggerRef, 'access',
|
|
934
|
+
if (_optionalChain([triggerRef, 'access', _14 => _14.current, 'optionalAccess', _15 => _15.isConnected]) && !triggerRef.current.disabled) {
|
|
798
935
|
triggerRef.current.focus({ preventScroll: true });
|
|
799
936
|
}
|
|
800
937
|
},
|
|
@@ -874,6 +1011,8 @@ var Chat = _react.forwardRef.call(void 0, function Chat2({
|
|
|
874
1011
|
emptySubtitle,
|
|
875
1012
|
examplePrompts = [],
|
|
876
1013
|
examplePromptsLabel = "Try",
|
|
1014
|
+
emptyActions = [],
|
|
1015
|
+
emptyActionsLabel = DEFAULT_EMPTY_ACTIONS_LABEL,
|
|
877
1016
|
examplePromptsVariant = "chips",
|
|
878
1017
|
examplePromptsLoading = false,
|
|
879
1018
|
examplePromptsLoadingLabel = "Loading suggestions\u2026",
|
|
@@ -921,6 +1060,9 @@ var Chat = _react.forwardRef.call(void 0, function Chat2({
|
|
|
921
1060
|
onOpenAttachment,
|
|
922
1061
|
attachmentAction,
|
|
923
1062
|
messageActions,
|
|
1063
|
+
navigator,
|
|
1064
|
+
navigatorLabel,
|
|
1065
|
+
navigatorSide,
|
|
924
1066
|
className
|
|
925
1067
|
}, ref) {
|
|
926
1068
|
const isMobile = _chunkR35FT53Gcjs.useIsMobile.call(void 0, );
|
|
@@ -951,7 +1093,7 @@ var Chat = _react.forwardRef.call(void 0, function Chat2({
|
|
|
951
1093
|
}
|
|
952
1094
|
reportSendError(cause);
|
|
953
1095
|
}
|
|
954
|
-
window.setTimeout(() => _optionalChain([inputRef, 'access',
|
|
1096
|
+
window.setTimeout(() => _optionalChain([inputRef, 'access', _16 => _16.current, 'optionalAccess', _17 => _17.focus, 'call', _18 => _18()]), 0);
|
|
955
1097
|
},
|
|
956
1098
|
[attachments, mode, onSend, pending, reportSendError]
|
|
957
1099
|
);
|
|
@@ -964,14 +1106,14 @@ var Chat = _react.forwardRef.call(void 0, function Chat2({
|
|
|
964
1106
|
} catch (cause) {
|
|
965
1107
|
reportSendError(cause);
|
|
966
1108
|
}
|
|
967
|
-
if (focusInput) window.setTimeout(() => _optionalChain([inputRef, 'access',
|
|
1109
|
+
if (focusInput) window.setTimeout(() => _optionalChain([inputRef, 'access', _19 => _19.current, 'optionalAccess', _20 => _20.focus, 'call', _21 => _21()]), 0);
|
|
968
1110
|
},
|
|
969
1111
|
[onSend, pending, reportSendError]
|
|
970
1112
|
);
|
|
971
1113
|
_react.useImperativeHandle.call(void 0,
|
|
972
1114
|
ref,
|
|
973
1115
|
() => ({
|
|
974
|
-
focusInput: () => _optionalChain([inputRef, 'access',
|
|
1116
|
+
focusInput: () => _optionalChain([inputRef, 'access', _22 => _22.current, 'optionalAccess', _23 => _23.focus, 'call', _24 => _24()]),
|
|
975
1117
|
clearInput: () => setInput("")
|
|
976
1118
|
}),
|
|
977
1119
|
[]
|
|
@@ -979,7 +1121,7 @@ var Chat = _react.forwardRef.call(void 0, function Chat2({
|
|
|
979
1121
|
const dropFiles = _react.useCallback.call(void 0,
|
|
980
1122
|
(files) => {
|
|
981
1123
|
if (!conversationStarted && mode === "voice") setUserMode("text");
|
|
982
|
-
return _optionalChain([onFilesSelected, 'optionalCall',
|
|
1124
|
+
return _optionalChain([onFilesSelected, 'optionalCall', _25 => _25(files)]);
|
|
983
1125
|
},
|
|
984
1126
|
[conversationStarted, mode, onFilesSelected]
|
|
985
1127
|
);
|
|
@@ -1110,6 +1252,15 @@ var Chat = _react.forwardRef.call(void 0, function Chat2({
|
|
|
1110
1252
|
}
|
|
1111
1253
|
),
|
|
1112
1254
|
error && /* @__PURE__ */ _jsxruntime.jsx.call(void 0, ChatError, { children: error }),
|
|
1255
|
+
!pending && emptyActions.length > 0 && /* @__PURE__ */ _jsxruntime.jsx.call(void 0,
|
|
1256
|
+
ChatEmptyActions,
|
|
1257
|
+
{
|
|
1258
|
+
items: emptyActions,
|
|
1259
|
+
label: emptyActionsLabel,
|
|
1260
|
+
onError: reportSendError,
|
|
1261
|
+
className: "mt-3"
|
|
1262
|
+
}
|
|
1263
|
+
),
|
|
1113
1264
|
!pending && examplePromptsLoading && /* @__PURE__ */ _jsxruntime.jsx.call(void 0, ExamplePromptsLoading, { label: examplePromptsLoadingLabel }),
|
|
1114
1265
|
!pending && !examplePromptsLoading && examplePrompts.length > 0 && /* @__PURE__ */ _jsxruntime.jsx.call(void 0,
|
|
1115
1266
|
ChatSuggestions,
|
|
@@ -1144,6 +1295,9 @@ var Chat = _react.forwardRef.call(void 0, function Chat2({
|
|
|
1144
1295
|
onOpenAttachment,
|
|
1145
1296
|
attachmentAction,
|
|
1146
1297
|
messageActions,
|
|
1298
|
+
navigator,
|
|
1299
|
+
navigatorLabel,
|
|
1300
|
+
navigatorSide,
|
|
1147
1301
|
className: _chunkKWLSBTB2cjs.cn.call(void 0,
|
|
1148
1302
|
"mb-3",
|
|
1149
1303
|
application && "min-h-0 flex-1 px-4 py-4 md:px-0 md:py-0",
|
|
@@ -1187,7 +1341,7 @@ var Chat = _react.forwardRef.call(void 0, function Chat2({
|
|
|
1187
1341
|
closeLabel: replySuggestionsCloseLabel,
|
|
1188
1342
|
disabled: pending
|
|
1189
1343
|
},
|
|
1190
|
-
JSON.stringify([_optionalChain([messages, 'access',
|
|
1344
|
+
JSON.stringify([_optionalChain([messages, 'access', _26 => _26.at, 'call', _27 => _27(-1), 'optionalAccess', _28 => _28.id]), replySuggestions])
|
|
1191
1345
|
) : void 0,
|
|
1192
1346
|
value: input,
|
|
1193
1347
|
onChange: setInput,
|
|
@@ -1226,4 +1380,5 @@ var Chat = _react.forwardRef.call(void 0, function Chat2({
|
|
|
1226
1380
|
|
|
1227
1381
|
|
|
1228
1382
|
|
|
1229
|
-
|
|
1383
|
+
|
|
1384
|
+
exports.Chat = Chat; exports.ChatCopyAction = ChatCopyAction; exports.ChatInput = ChatInput; exports.ChatThread = ChatThread; exports.authorLines = authorLines;
|
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
2
2
|
import * as React$1 from 'react';
|
|
3
3
|
import { ReactNode } from 'react';
|
|
4
|
+
import { LucideIcon } from 'lucide-react';
|
|
4
5
|
import { VoiceSessionControlsProps } from './voice-session-controls.cjs';
|
|
6
|
+
import { ChatNavigatorItem } from './chat-turn-navigator.cjs';
|
|
5
7
|
import { MarkdownComponents } from './markdown.cjs';
|
|
6
8
|
import './button.cjs';
|
|
7
9
|
import 'class-variance-authority/types';
|
|
@@ -10,6 +12,17 @@ import 'react-markdown';
|
|
|
10
12
|
import './rich-text.cjs';
|
|
11
13
|
|
|
12
14
|
type ChatRole = "user" | "assistant";
|
|
15
|
+
/** A turn's author, as the thread names them above their turns. */
|
|
16
|
+
interface ChatMessageAuthor {
|
|
17
|
+
/** Stable for the person: consecutive turns with the same id are named once. */
|
|
18
|
+
id: string;
|
|
19
|
+
name: string;
|
|
20
|
+
/** Their photo; initials stand in without one. */
|
|
21
|
+
avatarUrl?: string | null;
|
|
22
|
+
/** A quiet note after the name, such as how the turn arrived ("by email"). */
|
|
23
|
+
detail?: string;
|
|
24
|
+
}
|
|
25
|
+
|
|
13
26
|
type ChatAttachment = {
|
|
14
27
|
id: string;
|
|
15
28
|
name: string;
|
|
@@ -38,6 +51,12 @@ type ChatMessage = {
|
|
|
38
51
|
content?: ReactNode;
|
|
39
52
|
/** Files that belong to this turn. */
|
|
40
53
|
attachments?: ReadonlyArray<ChatAttachment>;
|
|
54
|
+
/**
|
|
55
|
+
* Who wrote the turn. The thread names them, with their avatar, above the
|
|
56
|
+
* first of a run of turns by the same author, so a conversation with
|
|
57
|
+
* several people in it says who said what. Turns without one are unnamed.
|
|
58
|
+
*/
|
|
59
|
+
author?: ChatMessageAuthor;
|
|
41
60
|
/**
|
|
42
61
|
* `"running"`: a reply still being worked on. The thread draws the turn as
|
|
43
62
|
* its running line, the one `pending` adds at the end, labelled with `text`
|
|
@@ -105,8 +124,24 @@ interface ChatThreadProps {
|
|
|
105
124
|
* pointer reaches it; return `null` for none.
|
|
106
125
|
*/
|
|
107
126
|
messageActions?: (message: ChatMessage) => ReactNode;
|
|
127
|
+
/**
|
|
128
|
+
* Places to jump to, drawn as a rail of ticks in the thread's gutter (see
|
|
129
|
+
* `ChatTurnNavigator`): the one in view marked, a preview of each on hover
|
|
130
|
+
* or focus. It shows only where the gutter has room; omit it for none.
|
|
131
|
+
*/
|
|
132
|
+
navigator?: readonly ChatNavigatorItem[];
|
|
133
|
+
/** The rail's landmark name. */
|
|
134
|
+
navigatorLabel?: string;
|
|
135
|
+
/** The gutter the rail sits in. */
|
|
136
|
+
navigatorSide?: "start" | "end";
|
|
108
137
|
className?: string;
|
|
109
138
|
}
|
|
139
|
+
/**
|
|
140
|
+
* Which turns name their author: the first of each run of turns by the same
|
|
141
|
+
* author on the same side. A time marker, a turn by someone else or a turn
|
|
142
|
+
* with no author between them starts a new run; a running line doesn't.
|
|
143
|
+
*/
|
|
144
|
+
declare function authorLines(messages: ReadonlyArray<ChatMessage>, markers: ReadonlyArray<string | null>): boolean[];
|
|
110
145
|
/**
|
|
111
146
|
* Scrollable message thread, built on shadcn's headless `MessageScroller`
|
|
112
147
|
* (streaming-aware auto-scroll, anchored turns) + the `Message`/`Bubble`
|
|
@@ -225,6 +260,24 @@ interface ChatInputProps {
|
|
|
225
260
|
* device-aware default modes.
|
|
226
261
|
*/
|
|
227
262
|
declare function ChatInput({ value, onChange, onSend, pending, disabled, placeholder, size, uploadingLabel, voice, voiceSession, voiceTitle, voiceLang, submitLabel, autoFocus, className, inputRef, attachments, onFilesSelected, onRemoveAttachment, accept, multiple, addFilesLabel, appearance, compactOnBlur, header, helperText, privacyNote, }: ChatInputProps): react_jsx_runtime.JSX.Element;
|
|
263
|
+
/** A next step offered in the empty state, under the composer (`emptyActions`). */
|
|
264
|
+
interface ChatEmptyAction {
|
|
265
|
+
/** Stable key. */
|
|
266
|
+
id: string;
|
|
267
|
+
/** What picking it does, e.g. "Review 3 new people". */
|
|
268
|
+
label: ReactNode;
|
|
269
|
+
/** Where it applies, muted after the label, e.g. "Head of Sales · Northwind". One line, truncated. */
|
|
270
|
+
detail?: ReactNode;
|
|
271
|
+
/** Leading icon: a Lucide component or an element. */
|
|
272
|
+
icon?: LucideIcon | ReactNode;
|
|
273
|
+
/**
|
|
274
|
+
* Called when picked. While a returned promise is pending, that row shows a
|
|
275
|
+
* spinner and every row is disabled; a rejection re-enables them and is
|
|
276
|
+
* reported.
|
|
277
|
+
*/
|
|
278
|
+
onSelect: () => void | Promise<void>;
|
|
279
|
+
disabled?: boolean;
|
|
280
|
+
}
|
|
228
281
|
interface ChatProps {
|
|
229
282
|
/** Conversation messages. */
|
|
230
283
|
messages: ChatMessage[];
|
|
@@ -270,6 +323,21 @@ interface ChatProps {
|
|
|
270
323
|
examplePrompts?: ReadonlyArray<string>;
|
|
271
324
|
/** Label above the example prompts. Defaults to "Try". */
|
|
272
325
|
examplePromptsLabel?: string;
|
|
326
|
+
/**
|
|
327
|
+
* Next steps under the empty-state composer, before `examplePrompts`,
|
|
328
|
+
* ChatGPT-style: a quiet list of rows, each an icon, what picking it does
|
|
329
|
+
* and where it applies (`ChatEmptyAction`). Picking one calls its
|
|
330
|
+
* `onSelect`; nothing is sent here. While a returned promise is pending
|
|
331
|
+
* the row shows a spinner and every row is disabled. Hidden while
|
|
332
|
+
* `pending`, like the example prompts.
|
|
333
|
+
*/
|
|
334
|
+
emptyActions?: ReadonlyArray<ChatEmptyAction>;
|
|
335
|
+
/**
|
|
336
|
+
* The actions' small heading and accessible name. Defaults to "Pick up
|
|
337
|
+
* where you left off"; `""` hides the heading and keeps that default as
|
|
338
|
+
* the list's accessible name.
|
|
339
|
+
*/
|
|
340
|
+
emptyActionsLabel?: string;
|
|
273
341
|
/**
|
|
274
342
|
* `chips` (the default) wrap onto as many lines as they need; `row` is one
|
|
275
343
|
* line that scrolls sideways, for a few short prompts where height is
|
|
@@ -425,6 +493,15 @@ interface ChatProps {
|
|
|
425
493
|
* assistant turns, by default), such as `ChatCopyAction`. See `ChatThread`.
|
|
426
494
|
*/
|
|
427
495
|
messageActions?: (message: ChatMessage) => ReactNode;
|
|
496
|
+
/**
|
|
497
|
+
* Places in the conversation to jump to, as a rail of ticks in the
|
|
498
|
+
* thread's gutter, each previewed on hover or focus. See `ChatThread`.
|
|
499
|
+
*/
|
|
500
|
+
navigator?: readonly ChatNavigatorItem[];
|
|
501
|
+
/** The rail's landmark name. Defaults to "Conversation". */
|
|
502
|
+
navigatorLabel?: string;
|
|
503
|
+
/** The gutter the rail sits in. Defaults to `"start"`. */
|
|
504
|
+
navigatorSide?: "start" | "end";
|
|
428
505
|
className?: string;
|
|
429
506
|
}
|
|
430
507
|
interface ChatHandle {
|
|
@@ -457,4 +534,4 @@ interface ChatHandle {
|
|
|
457
534
|
*/
|
|
458
535
|
declare const Chat: React$1.ForwardRefExoticComponent<ChatProps & React$1.RefAttributes<ChatHandle>>;
|
|
459
536
|
|
|
460
|
-
export { Chat, type ChatAttachment, type ChatAttachmentAction, ChatCopyAction, type ChatCopyActionProps, type ChatHandle, ChatInput, type ChatInputProps, type ChatMessage, type ChatProps, type ChatRole, ChatThread, type ChatThreadProps };
|
|
537
|
+
export { Chat, type ChatAttachment, type ChatAttachmentAction, ChatCopyAction, type ChatCopyActionProps, type ChatEmptyAction, type ChatHandle, ChatInput, type ChatInputProps, type ChatMessage, type ChatMessageAuthor, ChatNavigatorItem, type ChatProps, type ChatRole, ChatThread, type ChatThreadProps, authorLines };
|
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
2
2
|
import * as React$1 from 'react';
|
|
3
3
|
import { ReactNode } from 'react';
|
|
4
|
+
import { LucideIcon } from 'lucide-react';
|
|
4
5
|
import { VoiceSessionControlsProps } from './voice-session-controls.js';
|
|
6
|
+
import { ChatNavigatorItem } from './chat-turn-navigator.js';
|
|
5
7
|
import { MarkdownComponents } from './markdown.js';
|
|
6
8
|
import './button.js';
|
|
7
9
|
import 'class-variance-authority/types';
|
|
@@ -10,6 +12,17 @@ import 'react-markdown';
|
|
|
10
12
|
import './rich-text.js';
|
|
11
13
|
|
|
12
14
|
type ChatRole = "user" | "assistant";
|
|
15
|
+
/** A turn's author, as the thread names them above their turns. */
|
|
16
|
+
interface ChatMessageAuthor {
|
|
17
|
+
/** Stable for the person: consecutive turns with the same id are named once. */
|
|
18
|
+
id: string;
|
|
19
|
+
name: string;
|
|
20
|
+
/** Their photo; initials stand in without one. */
|
|
21
|
+
avatarUrl?: string | null;
|
|
22
|
+
/** A quiet note after the name, such as how the turn arrived ("by email"). */
|
|
23
|
+
detail?: string;
|
|
24
|
+
}
|
|
25
|
+
|
|
13
26
|
type ChatAttachment = {
|
|
14
27
|
id: string;
|
|
15
28
|
name: string;
|
|
@@ -38,6 +51,12 @@ type ChatMessage = {
|
|
|
38
51
|
content?: ReactNode;
|
|
39
52
|
/** Files that belong to this turn. */
|
|
40
53
|
attachments?: ReadonlyArray<ChatAttachment>;
|
|
54
|
+
/**
|
|
55
|
+
* Who wrote the turn. The thread names them, with their avatar, above the
|
|
56
|
+
* first of a run of turns by the same author, so a conversation with
|
|
57
|
+
* several people in it says who said what. Turns without one are unnamed.
|
|
58
|
+
*/
|
|
59
|
+
author?: ChatMessageAuthor;
|
|
41
60
|
/**
|
|
42
61
|
* `"running"`: a reply still being worked on. The thread draws the turn as
|
|
43
62
|
* its running line, the one `pending` adds at the end, labelled with `text`
|
|
@@ -105,8 +124,24 @@ interface ChatThreadProps {
|
|
|
105
124
|
* pointer reaches it; return `null` for none.
|
|
106
125
|
*/
|
|
107
126
|
messageActions?: (message: ChatMessage) => ReactNode;
|
|
127
|
+
/**
|
|
128
|
+
* Places to jump to, drawn as a rail of ticks in the thread's gutter (see
|
|
129
|
+
* `ChatTurnNavigator`): the one in view marked, a preview of each on hover
|
|
130
|
+
* or focus. It shows only where the gutter has room; omit it for none.
|
|
131
|
+
*/
|
|
132
|
+
navigator?: readonly ChatNavigatorItem[];
|
|
133
|
+
/** The rail's landmark name. */
|
|
134
|
+
navigatorLabel?: string;
|
|
135
|
+
/** The gutter the rail sits in. */
|
|
136
|
+
navigatorSide?: "start" | "end";
|
|
108
137
|
className?: string;
|
|
109
138
|
}
|
|
139
|
+
/**
|
|
140
|
+
* Which turns name their author: the first of each run of turns by the same
|
|
141
|
+
* author on the same side. A time marker, a turn by someone else or a turn
|
|
142
|
+
* with no author between them starts a new run; a running line doesn't.
|
|
143
|
+
*/
|
|
144
|
+
declare function authorLines(messages: ReadonlyArray<ChatMessage>, markers: ReadonlyArray<string | null>): boolean[];
|
|
110
145
|
/**
|
|
111
146
|
* Scrollable message thread, built on shadcn's headless `MessageScroller`
|
|
112
147
|
* (streaming-aware auto-scroll, anchored turns) + the `Message`/`Bubble`
|
|
@@ -225,6 +260,24 @@ interface ChatInputProps {
|
|
|
225
260
|
* device-aware default modes.
|
|
226
261
|
*/
|
|
227
262
|
declare function ChatInput({ value, onChange, onSend, pending, disabled, placeholder, size, uploadingLabel, voice, voiceSession, voiceTitle, voiceLang, submitLabel, autoFocus, className, inputRef, attachments, onFilesSelected, onRemoveAttachment, accept, multiple, addFilesLabel, appearance, compactOnBlur, header, helperText, privacyNote, }: ChatInputProps): react_jsx_runtime.JSX.Element;
|
|
263
|
+
/** A next step offered in the empty state, under the composer (`emptyActions`). */
|
|
264
|
+
interface ChatEmptyAction {
|
|
265
|
+
/** Stable key. */
|
|
266
|
+
id: string;
|
|
267
|
+
/** What picking it does, e.g. "Review 3 new people". */
|
|
268
|
+
label: ReactNode;
|
|
269
|
+
/** Where it applies, muted after the label, e.g. "Head of Sales · Northwind". One line, truncated. */
|
|
270
|
+
detail?: ReactNode;
|
|
271
|
+
/** Leading icon: a Lucide component or an element. */
|
|
272
|
+
icon?: LucideIcon | ReactNode;
|
|
273
|
+
/**
|
|
274
|
+
* Called when picked. While a returned promise is pending, that row shows a
|
|
275
|
+
* spinner and every row is disabled; a rejection re-enables them and is
|
|
276
|
+
* reported.
|
|
277
|
+
*/
|
|
278
|
+
onSelect: () => void | Promise<void>;
|
|
279
|
+
disabled?: boolean;
|
|
280
|
+
}
|
|
228
281
|
interface ChatProps {
|
|
229
282
|
/** Conversation messages. */
|
|
230
283
|
messages: ChatMessage[];
|
|
@@ -270,6 +323,21 @@ interface ChatProps {
|
|
|
270
323
|
examplePrompts?: ReadonlyArray<string>;
|
|
271
324
|
/** Label above the example prompts. Defaults to "Try". */
|
|
272
325
|
examplePromptsLabel?: string;
|
|
326
|
+
/**
|
|
327
|
+
* Next steps under the empty-state composer, before `examplePrompts`,
|
|
328
|
+
* ChatGPT-style: a quiet list of rows, each an icon, what picking it does
|
|
329
|
+
* and where it applies (`ChatEmptyAction`). Picking one calls its
|
|
330
|
+
* `onSelect`; nothing is sent here. While a returned promise is pending
|
|
331
|
+
* the row shows a spinner and every row is disabled. Hidden while
|
|
332
|
+
* `pending`, like the example prompts.
|
|
333
|
+
*/
|
|
334
|
+
emptyActions?: ReadonlyArray<ChatEmptyAction>;
|
|
335
|
+
/**
|
|
336
|
+
* The actions' small heading and accessible name. Defaults to "Pick up
|
|
337
|
+
* where you left off"; `""` hides the heading and keeps that default as
|
|
338
|
+
* the list's accessible name.
|
|
339
|
+
*/
|
|
340
|
+
emptyActionsLabel?: string;
|
|
273
341
|
/**
|
|
274
342
|
* `chips` (the default) wrap onto as many lines as they need; `row` is one
|
|
275
343
|
* line that scrolls sideways, for a few short prompts where height is
|
|
@@ -425,6 +493,15 @@ interface ChatProps {
|
|
|
425
493
|
* assistant turns, by default), such as `ChatCopyAction`. See `ChatThread`.
|
|
426
494
|
*/
|
|
427
495
|
messageActions?: (message: ChatMessage) => ReactNode;
|
|
496
|
+
/**
|
|
497
|
+
* Places in the conversation to jump to, as a rail of ticks in the
|
|
498
|
+
* thread's gutter, each previewed on hover or focus. See `ChatThread`.
|
|
499
|
+
*/
|
|
500
|
+
navigator?: readonly ChatNavigatorItem[];
|
|
501
|
+
/** The rail's landmark name. Defaults to "Conversation". */
|
|
502
|
+
navigatorLabel?: string;
|
|
503
|
+
/** The gutter the rail sits in. Defaults to `"start"`. */
|
|
504
|
+
navigatorSide?: "start" | "end";
|
|
428
505
|
className?: string;
|
|
429
506
|
}
|
|
430
507
|
interface ChatHandle {
|
|
@@ -457,4 +534,4 @@ interface ChatHandle {
|
|
|
457
534
|
*/
|
|
458
535
|
declare const Chat: React$1.ForwardRefExoticComponent<ChatProps & React$1.RefAttributes<ChatHandle>>;
|
|
459
536
|
|
|
460
|
-
export { Chat, type ChatAttachment, type ChatAttachmentAction, ChatCopyAction, type ChatCopyActionProps, type ChatHandle, ChatInput, type ChatInputProps, type ChatMessage, type ChatProps, type ChatRole, ChatThread, type ChatThreadProps };
|
|
537
|
+
export { Chat, type ChatAttachment, type ChatAttachmentAction, ChatCopyAction, type ChatCopyActionProps, type ChatEmptyAction, type ChatHandle, ChatInput, type ChatInputProps, type ChatMessage, type ChatMessageAuthor, ChatNavigatorItem, type ChatProps, type ChatRole, ChatThread, type ChatThreadProps, authorLines };
|