@surf-kit/agent 0.2.2 → 0.4.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/dist/chat/index.cjs +733 -222
- package/dist/chat/index.cjs.map +1 -1
- package/dist/chat/index.d.cts +13 -7
- package/dist/chat/index.d.ts +13 -7
- package/dist/chat/index.js +715 -204
- package/dist/chat/index.js.map +1 -1
- package/dist/{chat-ChYl2XjV.d.cts → chat-BRY3xGg_.d.cts} +11 -2
- package/dist/{chat--OifhIRe.d.ts → chat-CcKc6OAR.d.ts} +11 -2
- package/dist/{hooks-BGs8-4GK.d.ts → hooks-BLeiVk-x.d.ts} +22 -5
- package/dist/{hooks-DLfF18IU.d.cts → hooks-CSGGLd7j.d.cts} +22 -5
- package/dist/hooks.cjs +160 -85
- package/dist/hooks.cjs.map +1 -1
- package/dist/hooks.d.cts +3 -3
- package/dist/hooks.d.ts +3 -3
- package/dist/hooks.js +160 -85
- package/dist/hooks.js.map +1 -1
- package/dist/index.cjs +794 -283
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +3 -3
- package/dist/index.d.ts +3 -3
- package/dist/index.js +758 -247
- package/dist/index.js.map +1 -1
- package/dist/layouts/index.cjs +754 -243
- package/dist/layouts/index.cjs.map +1 -1
- package/dist/layouts/index.d.cts +1 -1
- package/dist/layouts/index.d.ts +1 -1
- package/dist/layouts/index.js +733 -222
- package/dist/layouts/index.js.map +1 -1
- package/dist/mcp/index.cjs +1 -1
- package/dist/mcp/index.cjs.map +1 -1
- package/dist/mcp/index.js +2 -2
- package/dist/mcp/index.js.map +1 -1
- package/dist/response/index.cjs +100 -15
- package/dist/response/index.cjs.map +1 -1
- package/dist/response/index.d.cts +2 -2
- package/dist/response/index.d.ts +2 -2
- package/dist/response/index.js +99 -14
- package/dist/response/index.js.map +1 -1
- package/dist/sources/index.cjs +30 -1
- package/dist/sources/index.cjs.map +1 -1
- package/dist/sources/index.js +30 -1
- package/dist/sources/index.js.map +1 -1
- package/dist/streaming/index.cjs +213 -93
- package/dist/streaming/index.cjs.map +1 -1
- package/dist/streaming/index.d.cts +4 -3
- package/dist/streaming/index.d.ts +4 -3
- package/dist/streaming/index.js +183 -73
- package/dist/streaming/index.js.map +1 -1
- package/dist/{streaming-DfT22A0z.d.cts → streaming-BHPXnwwo.d.cts} +3 -1
- package/dist/{streaming-DbQxScpi.d.ts → streaming-C6mbU7My.d.ts} +3 -1
- package/package.json +17 -5
package/dist/streaming/index.js
CHANGED
|
@@ -2,7 +2,8 @@
|
|
|
2
2
|
|
|
3
3
|
// src/streaming/StreamingMessage/StreamingMessage.tsx
|
|
4
4
|
import { useEffect as useEffect2, useRef as useRef2 } from "react";
|
|
5
|
-
import {
|
|
5
|
+
import { twMerge as twMerge2 } from "tailwind-merge";
|
|
6
|
+
import { WaveLoader } from "@surf-kit/core";
|
|
6
7
|
|
|
7
8
|
// src/hooks/useCharacterDrain.ts
|
|
8
9
|
import { useState, useRef, useEffect } from "react";
|
|
@@ -31,7 +32,10 @@ function useCharacterDrain(target, msPerChar = 15) {
|
|
|
31
32
|
const elapsed = now - lastTimeRef.current;
|
|
32
33
|
const charsToAdvance = Math.floor(elapsed / msPerCharRef.current);
|
|
33
34
|
if (charsToAdvance > 0 && indexRef.current < currentTarget.length) {
|
|
34
|
-
|
|
35
|
+
let nextIndex = Math.min(indexRef.current + charsToAdvance, currentTarget.length);
|
|
36
|
+
while (nextIndex < currentTarget.length && currentTarget[nextIndex - 1].trim() === "") {
|
|
37
|
+
nextIndex++;
|
|
38
|
+
}
|
|
35
39
|
indexRef.current = nextIndex;
|
|
36
40
|
lastTimeRef.current = now;
|
|
37
41
|
setDisplayed(currentTarget.slice(0, nextIndex));
|
|
@@ -66,8 +70,87 @@ function useCharacterDrain(target, msPerChar = 15) {
|
|
|
66
70
|
return { displayed, isDraining };
|
|
67
71
|
}
|
|
68
72
|
|
|
73
|
+
// src/response/ResponseMessage/ResponseMessage.tsx
|
|
74
|
+
import React from "react";
|
|
75
|
+
import ReactMarkdown from "react-markdown";
|
|
76
|
+
import rehypeSanitize from "rehype-sanitize";
|
|
77
|
+
import remarkGfm from "remark-gfm";
|
|
78
|
+
import { twMerge } from "tailwind-merge";
|
|
79
|
+
import { jsx } from "react/jsx-runtime";
|
|
80
|
+
function normalizeMarkdownLists(content) {
|
|
81
|
+
return content.replace(/:\s+-\s+/g, ":\n\n- ");
|
|
82
|
+
}
|
|
83
|
+
function ResponseMessage({ content, className }) {
|
|
84
|
+
return /* @__PURE__ */ jsx(
|
|
85
|
+
"div",
|
|
86
|
+
{
|
|
87
|
+
className: twMerge(
|
|
88
|
+
"text-sm leading-relaxed text-text-primary",
|
|
89
|
+
"[&_p]:my-2",
|
|
90
|
+
"[&_ul]:my-2 [&_ul]:list-disc [&_ul]:pl-6",
|
|
91
|
+
"[&_ol]:my-2 [&_ol]:list-decimal [&_ol]:pl-6",
|
|
92
|
+
"[&_li]:my-1",
|
|
93
|
+
"[&_strong]:text-text-primary [&_strong]:font-semibold",
|
|
94
|
+
"[&_em]:text-text-secondary",
|
|
95
|
+
"[&_h1]:text-lg [&_h1]:font-semibold [&_h1]:text-text-primary [&_h1]:mt-4 [&_h1]:mb-2",
|
|
96
|
+
"[&_h2]:text-base [&_h2]:font-semibold [&_h2]:text-text-primary [&_h2]:mt-3 [&_h2]:mb-1.5",
|
|
97
|
+
"[&_h3]:text-sm [&_h3]:font-semibold [&_h3]:text-accent [&_h3]:mt-2 [&_h3]:mb-1",
|
|
98
|
+
"[&_code]:bg-surface-raised [&_code]:text-accent [&_code]:px-1.5 [&_code]:py-0.5 [&_code]:rounded [&_code]:text-xs [&_code]:font-mono",
|
|
99
|
+
"[&_pre]:bg-surface-raised [&_pre]:border [&_pre]:border-border [&_pre]:rounded-xl [&_pre]:p-4 [&_pre]:overflow-x-auto",
|
|
100
|
+
"[&_hr]:my-3 [&_hr]:border-border",
|
|
101
|
+
"[&_blockquote]:border-l-2 [&_blockquote]:border-border-strong [&_blockquote]:pl-4 [&_blockquote]:text-text-secondary",
|
|
102
|
+
"[&_table]:w-full [&_table]:text-sm [&_table]:border-collapse [&_table]:my-2",
|
|
103
|
+
"[&_thead]:border-b [&_thead]:border-border",
|
|
104
|
+
"[&_th]:text-left [&_th]:px-2 [&_th]:py-1.5 [&_th]:font-semibold",
|
|
105
|
+
"[&_td]:px-2 [&_td]:py-1.5 [&_td]:border-t [&_td]:border-border/50",
|
|
106
|
+
"[&_a]:text-accent [&_a]:underline-offset-2 [&_a]:hover:text-accent/80",
|
|
107
|
+
className
|
|
108
|
+
),
|
|
109
|
+
"data-testid": "response-message",
|
|
110
|
+
children: /* @__PURE__ */ jsx(
|
|
111
|
+
ReactMarkdown,
|
|
112
|
+
{
|
|
113
|
+
remarkPlugins: [remarkGfm],
|
|
114
|
+
rehypePlugins: [rehypeSanitize],
|
|
115
|
+
components: {
|
|
116
|
+
script: () => null,
|
|
117
|
+
iframe: () => null,
|
|
118
|
+
p: ({ children }) => /* @__PURE__ */ jsx("p", { className: "my-2", children }),
|
|
119
|
+
ul: ({ children }) => /* @__PURE__ */ jsx("ul", { className: "my-2 list-disc pl-6", children }),
|
|
120
|
+
ol: ({ children }) => /* @__PURE__ */ jsx("ol", { className: "my-2 list-decimal pl-6", children }),
|
|
121
|
+
li: ({ children, ...props }) => {
|
|
122
|
+
let content2 = children;
|
|
123
|
+
if (props.ordered) {
|
|
124
|
+
content2 = React.Children.map(children, (child, i) => {
|
|
125
|
+
if (i === 0 && typeof child === "string") {
|
|
126
|
+
return child.replace(/^\d+[.)]\s*/, "");
|
|
127
|
+
}
|
|
128
|
+
return child;
|
|
129
|
+
});
|
|
130
|
+
}
|
|
131
|
+
return /* @__PURE__ */ jsx("li", { className: "my-1", children: content2 });
|
|
132
|
+
},
|
|
133
|
+
strong: ({ children }) => /* @__PURE__ */ jsx("strong", { className: "font-semibold", children }),
|
|
134
|
+
em: ({ children }) => /* @__PURE__ */ jsx("em", { className: "italic text-text-secondary", children }),
|
|
135
|
+
h1: ({ children }) => /* @__PURE__ */ jsx("h1", { className: "text-base font-bold mt-4 mb-2", children }),
|
|
136
|
+
h2: ({ children }) => /* @__PURE__ */ jsx("h2", { className: "text-sm font-bold mt-3 mb-1", children }),
|
|
137
|
+
h3: ({ children }) => /* @__PURE__ */ jsx("h3", { className: "text-sm font-semibold mt-2 mb-1", children }),
|
|
138
|
+
hr: () => /* @__PURE__ */ jsx("hr", { className: "my-3 border-border" }),
|
|
139
|
+
code: ({ children }) => /* @__PURE__ */ jsx("code", { className: "bg-surface-sunken rounded px-1 py-0.5 text-xs font-mono", children }),
|
|
140
|
+
table: ({ children }) => /* @__PURE__ */ jsx("div", { className: "overflow-x-auto my-2", children: /* @__PURE__ */ jsx("table", { className: "w-full text-sm border-collapse", children }) }),
|
|
141
|
+
thead: ({ children }) => /* @__PURE__ */ jsx("thead", { className: "border-b border-border", children }),
|
|
142
|
+
th: ({ children }) => /* @__PURE__ */ jsx("th", { className: "text-left px-2 py-1.5 font-semibold", children }),
|
|
143
|
+
td: ({ children }) => /* @__PURE__ */ jsx("td", { className: "px-2 py-1.5 border-t border-border/50", children })
|
|
144
|
+
},
|
|
145
|
+
children: normalizeMarkdownLists(content)
|
|
146
|
+
}
|
|
147
|
+
)
|
|
148
|
+
}
|
|
149
|
+
);
|
|
150
|
+
}
|
|
151
|
+
|
|
69
152
|
// src/streaming/StreamingMessage/StreamingMessage.tsx
|
|
70
|
-
import { jsx, jsxs } from "react/jsx-runtime";
|
|
153
|
+
import { jsx as jsx2, jsxs } from "react/jsx-runtime";
|
|
71
154
|
var phaseLabels = {
|
|
72
155
|
idle: "",
|
|
73
156
|
waiting: "Waiting...",
|
|
@@ -76,14 +159,36 @@ var phaseLabels = {
|
|
|
76
159
|
generating: "Writing...",
|
|
77
160
|
verifying: "Verifying..."
|
|
78
161
|
};
|
|
162
|
+
var CURSOR_STYLES = `
|
|
163
|
+
.sk-streaming-cursor > :not(ul,ol,blockquote,div:has(table)):last-child::after,
|
|
164
|
+
.sk-streaming-cursor > :is(ul,ol):last-child > li:last-child::after,
|
|
165
|
+
.sk-streaming-cursor > blockquote:last-child > p:last-child::after,
|
|
166
|
+
.sk-streaming-cursor > div:has(table):last-child table tbody tr:last-child td:last-child::after {
|
|
167
|
+
content: "";
|
|
168
|
+
display: inline-block;
|
|
169
|
+
width: 2px;
|
|
170
|
+
height: 1em;
|
|
171
|
+
background: var(--color-accent, #38bdf8);
|
|
172
|
+
animation: sk-cursor-blink 0.8s steps(1) infinite;
|
|
173
|
+
margin-left: 2px;
|
|
174
|
+
vertical-align: text-bottom;
|
|
175
|
+
}
|
|
176
|
+
@keyframes sk-cursor-blink {
|
|
177
|
+
0%, 60% { opacity: 1; }
|
|
178
|
+
61%, 100% { opacity: 0; }
|
|
179
|
+
}
|
|
180
|
+
`;
|
|
79
181
|
function StreamingMessage({
|
|
80
182
|
stream,
|
|
81
183
|
onComplete,
|
|
184
|
+
onDraining,
|
|
82
185
|
showPhases = true,
|
|
83
186
|
className
|
|
84
187
|
}) {
|
|
85
188
|
const onCompleteRef = useRef2(onComplete);
|
|
86
189
|
onCompleteRef.current = onComplete;
|
|
190
|
+
const onDrainingRef = useRef2(onDraining);
|
|
191
|
+
onDrainingRef.current = onDraining;
|
|
87
192
|
const wasActiveRef = useRef2(stream.active);
|
|
88
193
|
useEffect2(() => {
|
|
89
194
|
if (wasActiveRef.current && !stream.active) {
|
|
@@ -92,42 +197,47 @@ function StreamingMessage({
|
|
|
92
197
|
wasActiveRef.current = stream.active;
|
|
93
198
|
}, [stream.active]);
|
|
94
199
|
const phaseLabel = phaseLabels[stream.phase];
|
|
95
|
-
const { displayed:
|
|
96
|
-
|
|
200
|
+
const { displayed: rawDisplayed, isDraining } = useCharacterDrain(stream.content);
|
|
201
|
+
const displayedContent = stream.active || isDraining ? rawDisplayed.trimEnd() : rawDisplayed;
|
|
202
|
+
useEffect2(() => {
|
|
203
|
+
onDrainingRef.current?.(isDraining);
|
|
204
|
+
}, [isDraining]);
|
|
205
|
+
const agentLabel = stream.agent ? stream.agent.replace("_agent", "").replace("_", " ") : null;
|
|
206
|
+
const showPhaseIndicator = showPhases && stream.active && stream.phase !== "idle" && !displayedContent;
|
|
207
|
+
const showCursor = (stream.active || isDraining) && !!displayedContent;
|
|
208
|
+
return /* @__PURE__ */ jsxs("div", { className: twMerge2("flex w-full flex-col items-start", className), "data-testid": "streaming-message", children: [
|
|
97
209
|
/* @__PURE__ */ jsxs("div", { "aria-live": "assertive", className: "sr-only", children: [
|
|
98
210
|
stream.active && stream.phase !== "idle" && "Response started",
|
|
99
211
|
!stream.active && stream.content && "Response complete"
|
|
100
212
|
] }),
|
|
213
|
+
showCursor && /* @__PURE__ */ jsx2("style", { children: CURSOR_STYLES }),
|
|
214
|
+
agentLabel && /* @__PURE__ */ jsx2("div", { className: "text-[11px] font-display font-semibold uppercase tracking-[0.08em] text-text-muted px-1 mb-1.5", children: agentLabel }),
|
|
101
215
|
/* @__PURE__ */ jsxs("div", { className: "max-w-[88%] px-4 py-3 rounded-[18px] rounded-tl-[4px] bg-surface border border-border motion-safe:animate-springFromLeft", children: [
|
|
102
|
-
|
|
216
|
+
showPhaseIndicator && /* @__PURE__ */ jsxs(
|
|
103
217
|
"div",
|
|
104
218
|
{
|
|
105
|
-
className: "flex items-center gap-2
|
|
219
|
+
className: "flex items-center gap-2 text-sm text-text-secondary",
|
|
106
220
|
"data-testid": "phase-indicator",
|
|
107
221
|
children: [
|
|
108
|
-
/* @__PURE__ */
|
|
109
|
-
/* @__PURE__ */
|
|
222
|
+
/* @__PURE__ */ jsx2("span", { "aria-hidden": "true", children: /* @__PURE__ */ jsx2(WaveLoader, { size: "sm", color: "#38bdf8" }) }),
|
|
223
|
+
/* @__PURE__ */ jsx2("span", { children: phaseLabel })
|
|
110
224
|
]
|
|
111
225
|
}
|
|
112
226
|
),
|
|
113
|
-
/* @__PURE__ */
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
"data-testid": "streaming-cursor"
|
|
121
|
-
}
|
|
122
|
-
)
|
|
123
|
-
] })
|
|
227
|
+
displayedContent && /* @__PURE__ */ jsx2(
|
|
228
|
+
ResponseMessage,
|
|
229
|
+
{
|
|
230
|
+
content: displayedContent,
|
|
231
|
+
className: showCursor ? "sk-streaming-cursor" : void 0
|
|
232
|
+
}
|
|
233
|
+
)
|
|
124
234
|
] })
|
|
125
235
|
] });
|
|
126
236
|
}
|
|
127
237
|
|
|
128
238
|
// src/streaming/ThinkingIndicator/ThinkingIndicator.tsx
|
|
129
239
|
import { useReducedMotion } from "@surf-kit/hooks";
|
|
130
|
-
import { jsx as
|
|
240
|
+
import { jsx as jsx3, jsxs as jsxs2 } from "react/jsx-runtime";
|
|
131
241
|
function ThinkingIndicator({ label = "Thinking...", className }) {
|
|
132
242
|
const reducedMotion = useReducedMotion();
|
|
133
243
|
return /* @__PURE__ */ jsxs2(
|
|
@@ -137,11 +247,11 @@ function ThinkingIndicator({ label = "Thinking...", className }) {
|
|
|
137
247
|
className: `inline-flex items-center gap-2 text-sm motion-safe:animate-fadeSlideUpSm ${className ?? ""}`,
|
|
138
248
|
"data-testid": "thinking-indicator",
|
|
139
249
|
children: [
|
|
140
|
-
/* @__PURE__ */
|
|
250
|
+
/* @__PURE__ */ jsx3("span", { className: "text-text-secondary", children: label }),
|
|
141
251
|
!reducedMotion && /* @__PURE__ */ jsxs2("span", { className: "flex gap-1", "aria-hidden": "true", "data-testid": "animated-dots", children: [
|
|
142
|
-
/* @__PURE__ */
|
|
143
|
-
/* @__PURE__ */
|
|
144
|
-
/* @__PURE__ */
|
|
252
|
+
/* @__PURE__ */ jsx3("span", { className: "w-1.5 h-1.5 rounded-full bg-current animate-bounce [animation-delay:0ms]" }),
|
|
253
|
+
/* @__PURE__ */ jsx3("span", { className: "w-1.5 h-1.5 rounded-full bg-current animate-bounce [animation-delay:150ms]" }),
|
|
254
|
+
/* @__PURE__ */ jsx3("span", { className: "w-1.5 h-1.5 rounded-full bg-current animate-bounce [animation-delay:300ms]" })
|
|
145
255
|
] })
|
|
146
256
|
]
|
|
147
257
|
}
|
|
@@ -149,8 +259,8 @@ function ThinkingIndicator({ label = "Thinking...", className }) {
|
|
|
149
259
|
}
|
|
150
260
|
|
|
151
261
|
// src/streaming/ToolExecution/ToolExecution.tsx
|
|
152
|
-
import {
|
|
153
|
-
import { jsx as
|
|
262
|
+
import { WaveLoader as WaveLoader2 } from "@surf-kit/core";
|
|
263
|
+
import { jsx as jsx4, jsxs as jsxs3 } from "react/jsx-runtime";
|
|
154
264
|
var defaultLabels = {
|
|
155
265
|
search: "Searching knowledge base...",
|
|
156
266
|
retrieve: "Retrieving documents...",
|
|
@@ -165,16 +275,16 @@ function ToolExecution({ tool, label, className }) {
|
|
|
165
275
|
role: "status",
|
|
166
276
|
"data-testid": "tool-execution",
|
|
167
277
|
children: [
|
|
168
|
-
/* @__PURE__ */
|
|
169
|
-
/* @__PURE__ */
|
|
278
|
+
/* @__PURE__ */ jsx4("span", { "aria-hidden": "true", children: /* @__PURE__ */ jsx4(WaveLoader2, { size: "sm", color: "#38bdf8" }) }),
|
|
279
|
+
/* @__PURE__ */ jsx4("span", { children: displayLabel })
|
|
170
280
|
]
|
|
171
281
|
}
|
|
172
282
|
);
|
|
173
283
|
}
|
|
174
284
|
|
|
175
285
|
// src/streaming/RetrievalProgress/RetrievalProgress.tsx
|
|
176
|
-
import {
|
|
177
|
-
import { jsx as
|
|
286
|
+
import { WaveLoader as WaveLoader3 } from "@surf-kit/core";
|
|
287
|
+
import { jsx as jsx5, jsxs as jsxs4 } from "react/jsx-runtime";
|
|
178
288
|
function RetrievalProgress({ sources, isActive, className }) {
|
|
179
289
|
return /* @__PURE__ */ jsxs4(
|
|
180
290
|
"div",
|
|
@@ -185,18 +295,18 @@ function RetrievalProgress({ sources, isActive, className }) {
|
|
|
185
295
|
"data-testid": "retrieval-progress",
|
|
186
296
|
children: [
|
|
187
297
|
isActive && /* @__PURE__ */ jsxs4("div", { className: "flex items-center gap-2 text-sm text-text-secondary", children: [
|
|
188
|
-
/* @__PURE__ */
|
|
189
|
-
/* @__PURE__ */
|
|
298
|
+
/* @__PURE__ */ jsx5("span", { "aria-hidden": "true", children: /* @__PURE__ */ jsx5(WaveLoader3, { size: "sm", color: "#38bdf8" }) }),
|
|
299
|
+
/* @__PURE__ */ jsx5("span", { children: "Retrieving sources..." })
|
|
190
300
|
] }),
|
|
191
|
-
sources.length > 0 && /* @__PURE__ */
|
|
301
|
+
sources.length > 0 && /* @__PURE__ */ jsx5("ul", { className: "space-y-1", "data-testid": "source-list", children: sources.map((source, index) => /* @__PURE__ */ jsxs4(
|
|
192
302
|
"li",
|
|
193
303
|
{
|
|
194
304
|
className: "text-sm text-text-secondary flex items-center gap-2 animate-in fade-in slide-in-from-left-2",
|
|
195
305
|
style: { animationDelay: `${index * 100}ms`, animationFillMode: "both" },
|
|
196
306
|
"data-testid": "retrieval-source-item",
|
|
197
307
|
children: [
|
|
198
|
-
/* @__PURE__ */
|
|
199
|
-
/* @__PURE__ */
|
|
308
|
+
/* @__PURE__ */ jsx5("span", { className: "w-1.5 h-1.5 rounded-full bg-accent flex-shrink-0", "aria-hidden": "true" }),
|
|
309
|
+
/* @__PURE__ */ jsx5("span", { className: "truncate", children: source.title })
|
|
200
310
|
]
|
|
201
311
|
},
|
|
202
312
|
source.document_id
|
|
@@ -207,7 +317,7 @@ function RetrievalProgress({ sources, isActive, className }) {
|
|
|
207
317
|
}
|
|
208
318
|
|
|
209
319
|
// src/streaming/VerificationProgress/VerificationProgress.tsx
|
|
210
|
-
import { jsx as
|
|
320
|
+
import { jsx as jsx6, jsxs as jsxs5 } from "react/jsx-runtime";
|
|
211
321
|
function VerificationProgress({
|
|
212
322
|
isActive,
|
|
213
323
|
label = "Checking accuracy...",
|
|
@@ -230,12 +340,12 @@ function VerificationProgress({
|
|
|
230
340
|
viewBox: "0 0 24 24",
|
|
231
341
|
"aria-hidden": "true",
|
|
232
342
|
children: [
|
|
233
|
-
/* @__PURE__ */
|
|
234
|
-
/* @__PURE__ */
|
|
343
|
+
/* @__PURE__ */ jsx6("circle", { className: "opacity-25", cx: "12", cy: "12", r: "10", stroke: "currentColor", strokeWidth: "4" }),
|
|
344
|
+
/* @__PURE__ */ jsx6("path", { className: "opacity-75", fill: "currentColor", d: "M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4z" })
|
|
235
345
|
]
|
|
236
346
|
}
|
|
237
347
|
),
|
|
238
|
-
/* @__PURE__ */
|
|
348
|
+
/* @__PURE__ */ jsx6("span", { className: "text-accent animate-pulse", children: label })
|
|
239
349
|
]
|
|
240
350
|
}
|
|
241
351
|
);
|
|
@@ -243,7 +353,7 @@ function VerificationProgress({
|
|
|
243
353
|
|
|
244
354
|
// src/streaming/TypewriterText/TypewriterText.tsx
|
|
245
355
|
import { useEffect as useEffect3, useState as useState2 } from "react";
|
|
246
|
-
import { jsx as
|
|
356
|
+
import { jsx as jsx7, jsxs as jsxs6 } from "react/jsx-runtime";
|
|
247
357
|
function TypewriterText({
|
|
248
358
|
text,
|
|
249
359
|
speed = 30,
|
|
@@ -278,14 +388,14 @@ function TypewriterText({
|
|
|
278
388
|
}, [text, speed, delay, onComplete]);
|
|
279
389
|
return /* @__PURE__ */ jsxs6("span", { className, children: [
|
|
280
390
|
displayedText,
|
|
281
|
-
showCursor && !isComplete && /* @__PURE__ */
|
|
391
|
+
showCursor && !isComplete && /* @__PURE__ */ jsx7("span", { className: "typewriter-cursor", "aria-hidden": "true" })
|
|
282
392
|
] });
|
|
283
393
|
}
|
|
284
394
|
|
|
285
395
|
// src/streaming/TypingIndicator/TypingIndicator.tsx
|
|
286
|
-
import { twMerge } from "tailwind-merge";
|
|
396
|
+
import { twMerge as twMerge3 } from "tailwind-merge";
|
|
287
397
|
import { useReducedMotion as useReducedMotion2 } from "@surf-kit/hooks";
|
|
288
|
-
import { jsx as
|
|
398
|
+
import { jsx as jsx8, jsxs as jsxs7 } from "react/jsx-runtime";
|
|
289
399
|
var bounceKeyframes = `
|
|
290
400
|
@keyframes typing-bounce {
|
|
291
401
|
0%, 80%, 100% { transform: translateY(0); }
|
|
@@ -303,12 +413,12 @@ function TypingIndicator({
|
|
|
303
413
|
{
|
|
304
414
|
role: "status",
|
|
305
415
|
"aria-label": label ?? "typing",
|
|
306
|
-
className:
|
|
416
|
+
className: twMerge3("inline-flex items-center gap-2", className),
|
|
307
417
|
"data-testid": "typing-indicator",
|
|
308
418
|
children: [
|
|
309
|
-
!reducedMotion && /* @__PURE__ */
|
|
310
|
-
label && /* @__PURE__ */
|
|
311
|
-
/* @__PURE__ */
|
|
419
|
+
!reducedMotion && /* @__PURE__ */ jsx8("style", { children: bounceKeyframes }),
|
|
420
|
+
label && /* @__PURE__ */ jsx8("span", { className: "text-sm text-text-secondary", children: label }),
|
|
421
|
+
/* @__PURE__ */ jsx8("span", { className: "flex gap-1", "data-testid": "typing-dots", children: Array.from({ length: dotCount }, (_, i) => /* @__PURE__ */ jsx8(
|
|
312
422
|
"span",
|
|
313
423
|
{
|
|
314
424
|
className: "w-2 h-2 rounded-full bg-text-secondary",
|
|
@@ -325,9 +435,9 @@ function TypingIndicator({
|
|
|
325
435
|
}
|
|
326
436
|
|
|
327
437
|
// src/streaming/TextGlimmer/TextGlimmer.tsx
|
|
328
|
-
import { twMerge as
|
|
438
|
+
import { twMerge as twMerge4 } from "tailwind-merge";
|
|
329
439
|
import { useReducedMotion as useReducedMotion3 } from "@surf-kit/hooks";
|
|
330
|
-
import { jsx as
|
|
440
|
+
import { jsx as jsx9, jsxs as jsxs8 } from "react/jsx-runtime";
|
|
331
441
|
var shimmerKeyframes = `
|
|
332
442
|
@keyframes text-shimmer {
|
|
333
443
|
0% { background-position: 200% 0; }
|
|
@@ -342,11 +452,11 @@ function TextGlimmer({ lines = 3, className }) {
|
|
|
342
452
|
{
|
|
343
453
|
role: "status",
|
|
344
454
|
"aria-label": "Loading",
|
|
345
|
-
className:
|
|
455
|
+
className: twMerge4("flex flex-col gap-2", className),
|
|
346
456
|
"data-testid": "text-glimmer",
|
|
347
457
|
children: [
|
|
348
|
-
!reducedMotion && /* @__PURE__ */
|
|
349
|
-
Array.from({ length: lines }, (_, i) => /* @__PURE__ */
|
|
458
|
+
!reducedMotion && /* @__PURE__ */ jsx9("style", { children: shimmerKeyframes }),
|
|
459
|
+
Array.from({ length: lines }, (_, i) => /* @__PURE__ */ jsx9(
|
|
350
460
|
"div",
|
|
351
461
|
{
|
|
352
462
|
className: "h-3 rounded bg-surface-raised",
|
|
@@ -368,9 +478,9 @@ function TextGlimmer({ lines = 3, className }) {
|
|
|
368
478
|
}
|
|
369
479
|
|
|
370
480
|
// src/streaming/StreamingList/StreamingList.tsx
|
|
371
|
-
import { twMerge as
|
|
481
|
+
import { twMerge as twMerge5 } from "tailwind-merge";
|
|
372
482
|
import { useReducedMotion as useReducedMotion4 } from "@surf-kit/hooks";
|
|
373
|
-
import { jsx as
|
|
483
|
+
import { jsx as jsx10, jsxs as jsxs9 } from "react/jsx-runtime";
|
|
374
484
|
var fadeSlideInKeyframes = `
|
|
375
485
|
@keyframes fadeSlideIn {
|
|
376
486
|
from { opacity: 0; transform: translateY(8px); }
|
|
@@ -386,17 +496,17 @@ function StreamingList({
|
|
|
386
496
|
}) {
|
|
387
497
|
const reducedMotion = useReducedMotion4();
|
|
388
498
|
if (items.length === 0 && !isStreaming) {
|
|
389
|
-
return emptyMessage ? /* @__PURE__ */
|
|
499
|
+
return emptyMessage ? /* @__PURE__ */ jsx10("p", { className: twMerge5("text-sm text-text-secondary", className), "data-testid": "streaming-list-empty", children: emptyMessage }) : null;
|
|
390
500
|
}
|
|
391
501
|
return /* @__PURE__ */ jsxs9(
|
|
392
502
|
"ul",
|
|
393
503
|
{
|
|
394
504
|
"aria-live": "polite",
|
|
395
|
-
className:
|
|
505
|
+
className: twMerge5("list-none p-0 m-0", className),
|
|
396
506
|
"data-testid": "streaming-list",
|
|
397
507
|
children: [
|
|
398
|
-
!reducedMotion && /* @__PURE__ */
|
|
399
|
-
items.map((item, index) => /* @__PURE__ */
|
|
508
|
+
!reducedMotion && /* @__PURE__ */ jsx10("style", { children: fadeSlideInKeyframes }),
|
|
509
|
+
items.map((item, index) => /* @__PURE__ */ jsx10(
|
|
400
510
|
"li",
|
|
401
511
|
{
|
|
402
512
|
style: reducedMotion ? void 0 : { animation: "fadeSlideIn 0.3s ease-out" },
|
|
@@ -405,16 +515,16 @@ function StreamingList({
|
|
|
405
515
|
},
|
|
406
516
|
index
|
|
407
517
|
)),
|
|
408
|
-
isStreaming && /* @__PURE__ */
|
|
518
|
+
isStreaming && /* @__PURE__ */ jsx10("li", { "data-testid": "streaming-list-loading", children: /* @__PURE__ */ jsx10(TypingIndicator, {}) })
|
|
409
519
|
]
|
|
410
520
|
}
|
|
411
521
|
);
|
|
412
522
|
}
|
|
413
523
|
|
|
414
524
|
// src/streaming/StreamingStructure/StreamingStructure.tsx
|
|
415
|
-
import { twMerge as
|
|
525
|
+
import { twMerge as twMerge6 } from "tailwind-merge";
|
|
416
526
|
import { useReducedMotion as useReducedMotion5 } from "@surf-kit/hooks";
|
|
417
|
-
import { jsx as
|
|
527
|
+
import { jsx as jsx11, jsxs as jsxs10 } from "react/jsx-runtime";
|
|
418
528
|
var fadeSlideInKeyframes2 = `
|
|
419
529
|
@keyframes fadeSlideIn {
|
|
420
530
|
from { opacity: 0; transform: translateY(8px); }
|
|
@@ -423,13 +533,13 @@ var fadeSlideInKeyframes2 = `
|
|
|
423
533
|
`;
|
|
424
534
|
function renderValue(value, reducedMotion) {
|
|
425
535
|
if (value === null) {
|
|
426
|
-
return /* @__PURE__ */
|
|
536
|
+
return /* @__PURE__ */ jsx11("span", { className: "italic text-text-secondary", children: "null" });
|
|
427
537
|
}
|
|
428
538
|
if (value === void 0) {
|
|
429
|
-
return /* @__PURE__ */
|
|
539
|
+
return /* @__PURE__ */ jsx11("span", { className: "italic text-text-secondary", children: "undefined" });
|
|
430
540
|
}
|
|
431
541
|
if (Array.isArray(value)) {
|
|
432
|
-
return /* @__PURE__ */
|
|
542
|
+
return /* @__PURE__ */ jsx11("ol", { className: "list-decimal pl-4 m-0", children: value.map((item, i) => /* @__PURE__ */ jsx11("li", { className: "text-text-secondary text-sm", children: renderValue(item, reducedMotion) }, i)) });
|
|
433
543
|
}
|
|
434
544
|
if (typeof value === "object") {
|
|
435
545
|
return renderNestedDl(value, reducedMotion);
|
|
@@ -438,13 +548,13 @@ function renderValue(value, reducedMotion) {
|
|
|
438
548
|
}
|
|
439
549
|
function renderNestedDl(data, reducedMotion) {
|
|
440
550
|
const entries = Object.entries(data);
|
|
441
|
-
return /* @__PURE__ */
|
|
551
|
+
return /* @__PURE__ */ jsx11("dl", { className: "pl-4 m-0", "data-testid": "streaming-structure-nested", children: entries.map(([key, value]) => /* @__PURE__ */ jsxs10(
|
|
442
552
|
"div",
|
|
443
553
|
{
|
|
444
554
|
style: reducedMotion ? void 0 : { animation: "fadeSlideIn 0.3s ease-out" },
|
|
445
555
|
children: [
|
|
446
|
-
/* @__PURE__ */
|
|
447
|
-
/* @__PURE__ */
|
|
556
|
+
/* @__PURE__ */ jsx11("dt", { className: "font-medium text-text-primary text-sm", children: key }),
|
|
557
|
+
/* @__PURE__ */ jsx11("dd", { className: "text-text-secondary text-sm ml-0 mb-3", children: renderValue(value, reducedMotion) })
|
|
448
558
|
]
|
|
449
559
|
},
|
|
450
560
|
key
|
|
@@ -461,23 +571,23 @@ function StreamingStructure({
|
|
|
461
571
|
"dl",
|
|
462
572
|
{
|
|
463
573
|
"aria-live": "polite",
|
|
464
|
-
className:
|
|
574
|
+
className: twMerge6("m-0", className),
|
|
465
575
|
"data-testid": "streaming-structure",
|
|
466
576
|
children: [
|
|
467
|
-
!reducedMotion && /* @__PURE__ */
|
|
577
|
+
!reducedMotion && /* @__PURE__ */ jsx11("style", { children: fadeSlideInKeyframes2 }),
|
|
468
578
|
entries.map(([key, value]) => /* @__PURE__ */ jsxs10(
|
|
469
579
|
"div",
|
|
470
580
|
{
|
|
471
581
|
style: reducedMotion ? void 0 : { animation: "fadeSlideIn 0.3s ease-out" },
|
|
472
582
|
"data-testid": "streaming-structure-entry",
|
|
473
583
|
children: [
|
|
474
|
-
/* @__PURE__ */
|
|
475
|
-
/* @__PURE__ */
|
|
584
|
+
/* @__PURE__ */ jsx11("dt", { className: "font-medium text-text-primary text-sm", children: key }),
|
|
585
|
+
/* @__PURE__ */ jsx11("dd", { className: "text-text-secondary text-sm ml-0 mb-3", children: renderValue(value, reducedMotion) })
|
|
476
586
|
]
|
|
477
587
|
},
|
|
478
588
|
key
|
|
479
589
|
)),
|
|
480
|
-
isStreaming && /* @__PURE__ */
|
|
590
|
+
isStreaming && /* @__PURE__ */ jsx11("div", { "data-testid": "streaming-structure-loading", children: /* @__PURE__ */ jsx11(TextGlimmer, { lines: 1 }) })
|
|
481
591
|
]
|
|
482
592
|
}
|
|
483
593
|
);
|