@runtypelabs/persona 1.36.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.
Files changed (61) hide show
  1. package/README.md +1080 -0
  2. package/dist/index.cjs +140 -0
  3. package/dist/index.cjs.map +1 -0
  4. package/dist/index.d.cts +2626 -0
  5. package/dist/index.d.ts +2626 -0
  6. package/dist/index.global.js +1843 -0
  7. package/dist/index.global.js.map +1 -0
  8. package/dist/index.js +140 -0
  9. package/dist/index.js.map +1 -0
  10. package/dist/install.global.js +2 -0
  11. package/dist/install.global.js.map +1 -0
  12. package/dist/widget.css +1627 -0
  13. package/package.json +79 -0
  14. package/src/@types/idiomorph.d.ts +37 -0
  15. package/src/client.test.ts +387 -0
  16. package/src/client.ts +1589 -0
  17. package/src/components/composer-builder.ts +530 -0
  18. package/src/components/feedback.ts +379 -0
  19. package/src/components/forms.ts +170 -0
  20. package/src/components/header-builder.ts +455 -0
  21. package/src/components/header-layouts.ts +303 -0
  22. package/src/components/launcher.ts +193 -0
  23. package/src/components/message-bubble.ts +528 -0
  24. package/src/components/messages.ts +54 -0
  25. package/src/components/panel.ts +204 -0
  26. package/src/components/reasoning-bubble.ts +144 -0
  27. package/src/components/registry.ts +87 -0
  28. package/src/components/suggestions.ts +97 -0
  29. package/src/components/tool-bubble.ts +288 -0
  30. package/src/defaults.ts +321 -0
  31. package/src/index.ts +175 -0
  32. package/src/install.ts +284 -0
  33. package/src/plugins/registry.ts +77 -0
  34. package/src/plugins/types.ts +95 -0
  35. package/src/postprocessors.ts +194 -0
  36. package/src/runtime/init.ts +162 -0
  37. package/src/session.ts +376 -0
  38. package/src/styles/tailwind.css +20 -0
  39. package/src/styles/widget.css +1627 -0
  40. package/src/types.ts +1635 -0
  41. package/src/ui.ts +3341 -0
  42. package/src/utils/actions.ts +227 -0
  43. package/src/utils/attachment-manager.ts +384 -0
  44. package/src/utils/code-generators.test.ts +500 -0
  45. package/src/utils/code-generators.ts +1806 -0
  46. package/src/utils/component-middleware.ts +137 -0
  47. package/src/utils/component-parser.ts +119 -0
  48. package/src/utils/constants.ts +16 -0
  49. package/src/utils/content.ts +306 -0
  50. package/src/utils/dom.ts +25 -0
  51. package/src/utils/events.ts +41 -0
  52. package/src/utils/formatting.test.ts +166 -0
  53. package/src/utils/formatting.ts +470 -0
  54. package/src/utils/icons.ts +92 -0
  55. package/src/utils/message-id.ts +37 -0
  56. package/src/utils/morph.ts +36 -0
  57. package/src/utils/positioning.ts +17 -0
  58. package/src/utils/storage.ts +72 -0
  59. package/src/utils/theme.ts +105 -0
  60. package/src/widget.css +1 -0
  61. package/widget.css +1 -0
@@ -0,0 +1,2626 @@
1
+ /**
2
+ * Plugin interface for customizing widget components
3
+ */
4
+ interface AgentWidgetPlugin {
5
+ /**
6
+ * Unique identifier for the plugin
7
+ */
8
+ id: string;
9
+ /**
10
+ * Optional priority (higher = runs first). Default: 0
11
+ */
12
+ priority?: number;
13
+ /**
14
+ * Custom renderer for message bubbles
15
+ * Return null to use default renderer
16
+ */
17
+ renderMessage?: (context: {
18
+ message: AgentWidgetMessage;
19
+ defaultRenderer: () => HTMLElement;
20
+ config: AgentWidgetConfig;
21
+ }) => HTMLElement | null;
22
+ /**
23
+ * Custom renderer for launcher button
24
+ * Return null to use default renderer
25
+ */
26
+ renderLauncher?: (context: {
27
+ config: AgentWidgetConfig;
28
+ defaultRenderer: () => HTMLElement;
29
+ onToggle: () => void;
30
+ }) => HTMLElement | null;
31
+ /**
32
+ * Custom renderer for panel header
33
+ * Return null to use default renderer
34
+ */
35
+ renderHeader?: (context: {
36
+ config: AgentWidgetConfig;
37
+ defaultRenderer: () => HTMLElement;
38
+ onClose?: () => void;
39
+ }) => HTMLElement | null;
40
+ /**
41
+ * Custom renderer for composer/input area
42
+ * Return null to use default renderer
43
+ */
44
+ renderComposer?: (context: {
45
+ config: AgentWidgetConfig;
46
+ defaultRenderer: () => HTMLElement;
47
+ onSubmit: (text: string) => void;
48
+ disabled: boolean;
49
+ }) => HTMLElement | null;
50
+ /**
51
+ * Custom renderer for reasoning bubbles
52
+ * Return null to use default renderer
53
+ */
54
+ renderReasoning?: (context: {
55
+ message: AgentWidgetMessage;
56
+ defaultRenderer: () => HTMLElement;
57
+ config: AgentWidgetConfig;
58
+ }) => HTMLElement | null;
59
+ /**
60
+ * Custom renderer for tool call bubbles
61
+ * Return null to use default renderer
62
+ */
63
+ renderToolCall?: (context: {
64
+ message: AgentWidgetMessage;
65
+ defaultRenderer: () => HTMLElement;
66
+ config: AgentWidgetConfig;
67
+ }) => HTMLElement | null;
68
+ /**
69
+ * Called when plugin is registered
70
+ */
71
+ onRegister?: () => void;
72
+ /**
73
+ * Called when plugin is unregistered
74
+ */
75
+ onUnregister?: () => void;
76
+ }
77
+
78
+ /**
79
+ * Text content part for multi-modal messages
80
+ */
81
+ type TextContentPart = {
82
+ type: 'text';
83
+ text: string;
84
+ };
85
+ /**
86
+ * Image content part for multi-modal messages
87
+ * Supports base64 data URIs or URLs
88
+ */
89
+ type ImageContentPart = {
90
+ type: 'image';
91
+ image: string;
92
+ mimeType?: string;
93
+ alt?: string;
94
+ };
95
+ /**
96
+ * File content part for multi-modal messages
97
+ * Supports PDF, TXT, DOCX, and other document types
98
+ */
99
+ type FileContentPart = {
100
+ type: 'file';
101
+ data: string;
102
+ mimeType: string;
103
+ filename: string;
104
+ };
105
+ /**
106
+ * Union type for all content part types
107
+ */
108
+ type ContentPart = TextContentPart | ImageContentPart | FileContentPart;
109
+ /**
110
+ * Message content can be a simple string or an array of content parts
111
+ */
112
+ type MessageContent = string | ContentPart[];
113
+ type AgentWidgetContextProviderContext = {
114
+ messages: AgentWidgetMessage[];
115
+ config: AgentWidgetConfig;
116
+ };
117
+ type AgentWidgetContextProvider = (context: AgentWidgetContextProviderContext) => Record<string, unknown> | void | Promise<Record<string, unknown> | void>;
118
+ type AgentWidgetRequestPayloadMessage = {
119
+ role: AgentWidgetMessageRole;
120
+ content: MessageContent;
121
+ createdAt: string;
122
+ };
123
+ type AgentWidgetRequestPayload = {
124
+ messages: AgentWidgetRequestPayloadMessage[];
125
+ flowId?: string;
126
+ context?: Record<string, unknown>;
127
+ metadata?: Record<string, unknown>;
128
+ };
129
+ type AgentWidgetRequestMiddlewareContext = {
130
+ payload: AgentWidgetRequestPayload;
131
+ config: AgentWidgetConfig;
132
+ };
133
+ type AgentWidgetRequestMiddleware = (context: AgentWidgetRequestMiddlewareContext) => AgentWidgetRequestPayload | void | Promise<AgentWidgetRequestPayload | void>;
134
+ type AgentWidgetParsedAction = {
135
+ type: string;
136
+ payload: Record<string, unknown>;
137
+ raw?: unknown;
138
+ };
139
+ type AgentWidgetActionParserInput = {
140
+ text: string;
141
+ message: AgentWidgetMessage;
142
+ };
143
+ type AgentWidgetActionParser = (input: AgentWidgetActionParserInput) => AgentWidgetParsedAction | null | undefined;
144
+ type AgentWidgetActionHandlerResult = {
145
+ handled?: boolean;
146
+ displayText?: string;
147
+ persistMessage?: boolean;
148
+ };
149
+ type AgentWidgetActionContext = {
150
+ message: AgentWidgetMessage;
151
+ metadata: Record<string, unknown>;
152
+ updateMetadata: (updater: (prev: Record<string, unknown>) => Record<string, unknown>) => void;
153
+ document: Document | null;
154
+ };
155
+ type AgentWidgetActionHandler = (action: AgentWidgetParsedAction, context: AgentWidgetActionContext) => AgentWidgetActionHandlerResult | void;
156
+ type AgentWidgetStoredState = {
157
+ messages?: AgentWidgetMessage[];
158
+ metadata?: Record<string, unknown>;
159
+ };
160
+ interface AgentWidgetStorageAdapter {
161
+ load?: () => AgentWidgetStoredState | null | Promise<AgentWidgetStoredState | null>;
162
+ save?: (state: AgentWidgetStoredState) => void | Promise<void>;
163
+ clear?: () => void | Promise<void>;
164
+ }
165
+ type AgentWidgetVoiceStateEvent = {
166
+ active: boolean;
167
+ source: "user" | "auto" | "restore" | "system";
168
+ timestamp: number;
169
+ };
170
+ type AgentWidgetActionEventPayload = {
171
+ action: AgentWidgetParsedAction;
172
+ message: AgentWidgetMessage;
173
+ };
174
+ /**
175
+ * Feedback event payload for upvote/downvote actions on messages
176
+ */
177
+ type AgentWidgetMessageFeedback = {
178
+ type: "upvote" | "downvote";
179
+ messageId: string;
180
+ message: AgentWidgetMessage;
181
+ };
182
+ /**
183
+ * Configuration for message action buttons (copy, upvote, downvote)
184
+ *
185
+ * **Client Token Mode**: When using `clientToken`, feedback is automatically
186
+ * sent to your Travrse backend. Just enable the buttons and you're done!
187
+ * The `onFeedback` and `onCopy` callbacks are optional for additional local handling.
188
+ *
189
+ * @example
190
+ * ```typescript
191
+ * // With clientToken - feedback is automatic!
192
+ * config: {
193
+ * clientToken: 'ct_live_...',
194
+ * messageActions: {
195
+ * showUpvote: true,
196
+ * showDownvote: true,
197
+ * // No onFeedback needed - sent to backend automatically
198
+ * }
199
+ * }
200
+ * ```
201
+ */
202
+ type AgentWidgetMessageActionsConfig = {
203
+ /**
204
+ * Enable/disable message actions entirely
205
+ * @default true
206
+ */
207
+ enabled?: boolean;
208
+ /**
209
+ * Show copy button
210
+ * @default true
211
+ */
212
+ showCopy?: boolean;
213
+ /**
214
+ * Show upvote button.
215
+ * When using `clientToken`, feedback is sent to the backend automatically.
216
+ * @default false
217
+ */
218
+ showUpvote?: boolean;
219
+ /**
220
+ * Show downvote button.
221
+ * When using `clientToken`, feedback is sent to the backend automatically.
222
+ * @default false
223
+ */
224
+ showDownvote?: boolean;
225
+ /**
226
+ * Visibility mode: 'always' shows buttons always, 'hover' shows on hover only
227
+ * @default 'hover'
228
+ */
229
+ visibility?: "always" | "hover";
230
+ /**
231
+ * Horizontal alignment of action buttons
232
+ * @default 'right'
233
+ */
234
+ align?: "left" | "center" | "right";
235
+ /**
236
+ * Layout style for action buttons
237
+ * - 'pill-inside': Compact floating pill around just the buttons (default for hover)
238
+ * - 'row-inside': Full-width row at the bottom of the message
239
+ * @default 'pill-inside'
240
+ */
241
+ layout?: "pill-inside" | "row-inside";
242
+ /**
243
+ * Callback when user submits feedback (upvote/downvote).
244
+ *
245
+ * **Note**: When using `clientToken`, feedback is AUTOMATICALLY sent to your
246
+ * backend via `/v1/client/feedback`. This callback is called IN ADDITION to
247
+ * the automatic submission, useful for updating local UI or analytics.
248
+ */
249
+ onFeedback?: (feedback: AgentWidgetMessageFeedback) => void;
250
+ /**
251
+ * Callback when user copies a message.
252
+ *
253
+ * **Note**: When using `clientToken`, copy events are AUTOMATICALLY tracked
254
+ * via `/v1/client/feedback`. This callback is called IN ADDITION to the
255
+ * automatic tracking.
256
+ */
257
+ onCopy?: (message: AgentWidgetMessage) => void;
258
+ };
259
+ type AgentWidgetStateEvent = {
260
+ open: boolean;
261
+ source: "user" | "auto" | "api" | "system";
262
+ timestamp: number;
263
+ };
264
+ type AgentWidgetStateSnapshot = {
265
+ open: boolean;
266
+ launcherEnabled: boolean;
267
+ voiceActive: boolean;
268
+ streaming: boolean;
269
+ };
270
+ type AgentWidgetControllerEventMap = {
271
+ "assistant:message": AgentWidgetMessage;
272
+ "assistant:complete": AgentWidgetMessage;
273
+ "voice:state": AgentWidgetVoiceStateEvent;
274
+ "action:detected": AgentWidgetActionEventPayload;
275
+ "widget:opened": AgentWidgetStateEvent;
276
+ "widget:closed": AgentWidgetStateEvent;
277
+ "widget:state": AgentWidgetStateSnapshot;
278
+ "message:feedback": AgentWidgetMessageFeedback;
279
+ "message:copy": AgentWidgetMessage;
280
+ };
281
+ type AgentWidgetFeatureFlags = {
282
+ showReasoning?: boolean;
283
+ showToolCalls?: boolean;
284
+ };
285
+ type AgentWidgetTheme = {
286
+ primary?: string;
287
+ secondary?: string;
288
+ surface?: string;
289
+ muted?: string;
290
+ accent?: string;
291
+ container?: string;
292
+ border?: string;
293
+ divider?: string;
294
+ messageBorder?: string;
295
+ inputBackground?: string;
296
+ callToAction?: string;
297
+ callToActionBackground?: string;
298
+ sendButtonBackgroundColor?: string;
299
+ sendButtonTextColor?: string;
300
+ sendButtonBorderColor?: string;
301
+ closeButtonColor?: string;
302
+ closeButtonBackgroundColor?: string;
303
+ closeButtonBorderColor?: string;
304
+ clearChatIconColor?: string;
305
+ clearChatBackgroundColor?: string;
306
+ clearChatBorderColor?: string;
307
+ tooltipBackground?: string;
308
+ tooltipForeground?: string;
309
+ micIconColor?: string;
310
+ micBackgroundColor?: string;
311
+ micBorderColor?: string;
312
+ recordingIconColor?: string;
313
+ recordingBackgroundColor?: string;
314
+ recordingBorderColor?: string;
315
+ inputFontFamily?: "sans-serif" | "serif" | "mono";
316
+ inputFontWeight?: string;
317
+ radiusSm?: string;
318
+ radiusMd?: string;
319
+ radiusLg?: string;
320
+ launcherRadius?: string;
321
+ buttonRadius?: string;
322
+ /**
323
+ * Border style for the chat panel container.
324
+ * @example "1px solid #e5e7eb" | "none"
325
+ * @default "1px solid var(--tvw-cw-border)"
326
+ */
327
+ panelBorder?: string;
328
+ /**
329
+ * Box shadow for the chat panel container.
330
+ * @example "0 25px 50px -12px rgba(0,0,0,0.25)" | "none"
331
+ * @default "0 25px 50px -12px rgba(0,0,0,0.25)"
332
+ */
333
+ panelShadow?: string;
334
+ /**
335
+ * Border radius for the chat panel container.
336
+ * @example "16px" | "0"
337
+ * @default "16px"
338
+ */
339
+ panelBorderRadius?: string;
340
+ };
341
+ type AgentWidgetLauncherConfig = {
342
+ enabled?: boolean;
343
+ title?: string;
344
+ subtitle?: string;
345
+ textHidden?: boolean;
346
+ iconUrl?: string;
347
+ agentIconText?: string;
348
+ agentIconName?: string;
349
+ agentIconHidden?: boolean;
350
+ position?: "bottom-right" | "bottom-left" | "top-right" | "top-left";
351
+ autoExpand?: boolean;
352
+ width?: string;
353
+ /**
354
+ * When true, the widget panel will fill the full height of its container.
355
+ * Useful for sidebar layouts where the chat should take up the entire viewport height.
356
+ * The widget will use flex layout to ensure header stays at top, messages scroll in middle,
357
+ * and composer stays fixed at bottom.
358
+ *
359
+ * @default false
360
+ */
361
+ fullHeight?: boolean;
362
+ /**
363
+ * When true, the widget panel will be positioned as a sidebar flush with the viewport edges.
364
+ * The panel will have:
365
+ * - No border-radius (square corners)
366
+ * - No margins (flush with top, left/right, and bottom edges)
367
+ * - Full viewport height
368
+ * - Subtle shadow on the edge facing the content
369
+ * - No border between footer and messages
370
+ *
371
+ * Use with `position` to control which side ('bottom-left' for left sidebar, 'bottom-right' for right sidebar).
372
+ * Automatically enables fullHeight when true.
373
+ *
374
+ * @default false
375
+ */
376
+ sidebarMode?: boolean;
377
+ /**
378
+ * Width of the sidebar panel when sidebarMode is true.
379
+ * @default "420px"
380
+ */
381
+ sidebarWidth?: string;
382
+ /**
383
+ * Offset (in pixels) to subtract from the calculated panel height.
384
+ * Useful for adjusting the panel height when there are other fixed elements on the page.
385
+ * Only applies when not in fullHeight or sidebarMode.
386
+ *
387
+ * @default 0
388
+ */
389
+ heightOffset?: number;
390
+ callToActionIconText?: string;
391
+ callToActionIconName?: string;
392
+ callToActionIconColor?: string;
393
+ callToActionIconBackgroundColor?: string;
394
+ callToActionIconHidden?: boolean;
395
+ callToActionIconPadding?: string;
396
+ agentIconSize?: string;
397
+ callToActionIconSize?: string;
398
+ headerIconSize?: string;
399
+ headerIconName?: string;
400
+ headerIconHidden?: boolean;
401
+ closeButtonSize?: string;
402
+ closeButtonColor?: string;
403
+ closeButtonBackgroundColor?: string;
404
+ closeButtonBorderWidth?: string;
405
+ closeButtonBorderColor?: string;
406
+ closeButtonBorderRadius?: string;
407
+ closeButtonPaddingX?: string;
408
+ closeButtonPaddingY?: string;
409
+ closeButtonPlacement?: "inline" | "top-right";
410
+ closeButtonIconName?: string;
411
+ closeButtonIconText?: string;
412
+ closeButtonTooltipText?: string;
413
+ closeButtonShowTooltip?: boolean;
414
+ clearChat?: AgentWidgetClearChatConfig;
415
+ /**
416
+ * Border style for the launcher button.
417
+ * @example "1px solid #e5e7eb" | "2px solid #3b82f6" | "none"
418
+ * @default "1px solid #e5e7eb"
419
+ */
420
+ border?: string;
421
+ /**
422
+ * Box shadow for the launcher button.
423
+ * @example "0 10px 15px -3px rgba(0,0,0,0.1)" | "none"
424
+ * @default "0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -4px rgba(0, 0, 0, 0.1)"
425
+ */
426
+ shadow?: string;
427
+ };
428
+ type AgentWidgetSendButtonConfig = {
429
+ borderWidth?: string;
430
+ borderColor?: string;
431
+ paddingX?: string;
432
+ paddingY?: string;
433
+ iconText?: string;
434
+ iconName?: string;
435
+ useIcon?: boolean;
436
+ tooltipText?: string;
437
+ showTooltip?: boolean;
438
+ backgroundColor?: string;
439
+ textColor?: string;
440
+ size?: string;
441
+ };
442
+ type AgentWidgetClearChatConfig = {
443
+ enabled?: boolean;
444
+ placement?: "inline" | "top-right";
445
+ iconName?: string;
446
+ iconColor?: string;
447
+ backgroundColor?: string;
448
+ borderWidth?: string;
449
+ borderColor?: string;
450
+ borderRadius?: string;
451
+ size?: string;
452
+ paddingX?: string;
453
+ paddingY?: string;
454
+ tooltipText?: string;
455
+ showTooltip?: boolean;
456
+ };
457
+ type AgentWidgetStatusIndicatorConfig = {
458
+ visible?: boolean;
459
+ idleText?: string;
460
+ connectingText?: string;
461
+ connectedText?: string;
462
+ errorText?: string;
463
+ };
464
+ type AgentWidgetVoiceRecognitionConfig = {
465
+ enabled?: boolean;
466
+ pauseDuration?: number;
467
+ iconName?: string;
468
+ iconSize?: string;
469
+ iconColor?: string;
470
+ backgroundColor?: string;
471
+ borderColor?: string;
472
+ borderWidth?: string;
473
+ paddingX?: string;
474
+ paddingY?: string;
475
+ tooltipText?: string;
476
+ showTooltip?: boolean;
477
+ recordingIconColor?: string;
478
+ recordingBackgroundColor?: string;
479
+ recordingBorderColor?: string;
480
+ showRecordingIndicator?: boolean;
481
+ autoResume?: boolean | "assistant";
482
+ };
483
+ type AgentWidgetToolCallConfig = {
484
+ backgroundColor?: string;
485
+ borderColor?: string;
486
+ borderWidth?: string;
487
+ borderRadius?: string;
488
+ headerBackgroundColor?: string;
489
+ headerTextColor?: string;
490
+ headerPaddingX?: string;
491
+ headerPaddingY?: string;
492
+ contentBackgroundColor?: string;
493
+ contentTextColor?: string;
494
+ contentPaddingX?: string;
495
+ contentPaddingY?: string;
496
+ codeBlockBackgroundColor?: string;
497
+ codeBlockBorderColor?: string;
498
+ codeBlockTextColor?: string;
499
+ toggleTextColor?: string;
500
+ labelTextColor?: string;
501
+ };
502
+ type AgentWidgetSuggestionChipsConfig = {
503
+ fontFamily?: "sans-serif" | "serif" | "mono";
504
+ fontWeight?: string;
505
+ paddingX?: string;
506
+ paddingY?: string;
507
+ };
508
+ /**
509
+ * Interface for pluggable stream parsers that extract text from streaming responses.
510
+ * Parsers handle incremental parsing to extract text values from structured formats (JSON, XML, etc.).
511
+ *
512
+ * @example
513
+ * ```typescript
514
+ * const jsonParser: AgentWidgetStreamParser = {
515
+ * processChunk: async (content) => {
516
+ * // Extract text from JSON - return null if not JSON or text not available yet
517
+ * if (!content.trim().startsWith('{')) return null;
518
+ * const match = content.match(/"text"\s*:\s*"([^"]*)"/);
519
+ * return match ? match[1] : null;
520
+ * },
521
+ * getExtractedText: () => extractedText
522
+ * };
523
+ * ```
524
+ */
525
+ interface AgentWidgetStreamParserResult {
526
+ /**
527
+ * The extracted text to display (may be partial during streaming)
528
+ */
529
+ text: string | null;
530
+ /**
531
+ * The raw accumulated content. Built-in parsers always populate this so
532
+ * downstream middleware (action handlers, logging, etc.) can
533
+ * inspect/parse the original structured payload.
534
+ */
535
+ raw?: string;
536
+ }
537
+ interface AgentWidgetStreamParser {
538
+ /**
539
+ * Process a chunk of content and return the extracted text (if available).
540
+ * This method is called for each chunk as it arrives during streaming.
541
+ * Return null if the content doesn't match this parser's format or if text is not yet available.
542
+ *
543
+ * @param accumulatedContent - The full accumulated content so far (including new chunk)
544
+ * @returns The extracted text value and optionally raw content, or null if not yet available or format doesn't match
545
+ */
546
+ processChunk(accumulatedContent: string): Promise<AgentWidgetStreamParserResult | string | null> | AgentWidgetStreamParserResult | string | null;
547
+ /**
548
+ * Get the currently extracted text value (may be partial).
549
+ * This is called synchronously to get the latest extracted text without processing.
550
+ *
551
+ * @returns The currently extracted text value, or null if not yet available
552
+ */
553
+ getExtractedText(): string | null;
554
+ /**
555
+ * Clean up any resources when parsing is complete.
556
+ */
557
+ close?(): Promise<void> | void;
558
+ }
559
+ /**
560
+ * Component renderer function signature for custom components
561
+ */
562
+ type AgentWidgetComponentRenderer = (props: Record<string, unknown>, context: {
563
+ message: AgentWidgetMessage;
564
+ config: AgentWidgetConfig;
565
+ updateProps: (newProps: Record<string, unknown>) => void;
566
+ }) => HTMLElement;
567
+ /**
568
+ * Result from custom SSE event parser
569
+ */
570
+ type AgentWidgetSSEEventResult = {
571
+ /** Text content to display */
572
+ text?: string;
573
+ /** Whether the stream is complete */
574
+ done?: boolean;
575
+ /** Error message if an error occurred */
576
+ error?: string;
577
+ } | null;
578
+ /**
579
+ * Custom SSE event parser function
580
+ * Allows transforming non-standard SSE event formats to persona's expected format
581
+ */
582
+ type AgentWidgetSSEEventParser = (eventData: unknown) => AgentWidgetSSEEventResult | Promise<AgentWidgetSSEEventResult>;
583
+ /**
584
+ * Custom fetch function for full control over API requests
585
+ * Use this for custom authentication, request transformation, etc.
586
+ */
587
+ type AgentWidgetCustomFetch = (url: string, init: RequestInit, payload: AgentWidgetRequestPayload) => Promise<Response>;
588
+ /**
589
+ * Dynamic headers function - called before each request
590
+ */
591
+ type AgentWidgetHeadersFunction = () => Record<string, string> | Promise<Record<string, string>>;
592
+ /**
593
+ * Session information returned after client token initialization.
594
+ * Contains session ID, expiry time, flow info, and config from the server.
595
+ */
596
+ type ClientSession = {
597
+ /** Unique session identifier */
598
+ sessionId: string;
599
+ /** When the session expires */
600
+ expiresAt: Date;
601
+ /** Flow information */
602
+ flow: {
603
+ id: string;
604
+ name: string;
605
+ description: string | null;
606
+ };
607
+ /** Configuration from the server */
608
+ config: {
609
+ welcomeMessage: string | null;
610
+ placeholder: string;
611
+ theme: Record<string, unknown> | null;
612
+ };
613
+ };
614
+ /**
615
+ * Raw API response from /v1/client/init endpoint
616
+ */
617
+ type ClientInitResponse = {
618
+ session_id: string;
619
+ expires_at: string;
620
+ flow: {
621
+ id: string;
622
+ name: string;
623
+ description: string | null;
624
+ };
625
+ config: {
626
+ welcome_message: string | null;
627
+ placeholder: string;
628
+ theme: Record<string, unknown> | null;
629
+ };
630
+ };
631
+ /**
632
+ * Request payload for /v1/client/chat endpoint
633
+ */
634
+ type ClientChatRequest = {
635
+ session_id: string;
636
+ messages: Array<{
637
+ id?: string;
638
+ role: 'user' | 'assistant' | 'system';
639
+ content: MessageContent;
640
+ }>;
641
+ /** ID for the expected assistant response message */
642
+ assistant_message_id?: string;
643
+ metadata?: Record<string, unknown>;
644
+ context?: Record<string, unknown>;
645
+ };
646
+ /**
647
+ * Feedback types supported by the API
648
+ */
649
+ type ClientFeedbackType = 'upvote' | 'downvote' | 'copy' | 'csat' | 'nps';
650
+ /**
651
+ * Request payload for /v1/client/feedback endpoint
652
+ */
653
+ type ClientFeedbackRequest = {
654
+ session_id: string;
655
+ /** Required for upvote, downvote, copy feedback types */
656
+ message_id?: string;
657
+ type: ClientFeedbackType;
658
+ /** Required for csat (1-5) and nps (0-10) feedback types */
659
+ rating?: number;
660
+ /** Optional comment for any feedback type */
661
+ comment?: string;
662
+ };
663
+ /**
664
+ * Context provided to header render functions
665
+ */
666
+ type HeaderRenderContext = {
667
+ config: AgentWidgetConfig;
668
+ onClose?: () => void;
669
+ onClearChat?: () => void;
670
+ };
671
+ /**
672
+ * Context provided to message render functions
673
+ */
674
+ type MessageRenderContext = {
675
+ message: AgentWidgetMessage;
676
+ config: AgentWidgetConfig;
677
+ streaming: boolean;
678
+ };
679
+ /**
680
+ * Context provided to slot render functions
681
+ */
682
+ type SlotRenderContext = {
683
+ config: AgentWidgetConfig;
684
+ defaultContent: () => HTMLElement | null;
685
+ };
686
+ /**
687
+ * Header layout configuration
688
+ * Allows customization of the header section appearance and behavior
689
+ */
690
+ type AgentWidgetHeaderLayoutConfig = {
691
+ /**
692
+ * Layout preset: "default" | "minimal" | "expanded"
693
+ * - default: Standard layout with icon, title, subtitle, and buttons
694
+ * - minimal: Simplified layout with just title and close button
695
+ * - expanded: Full branding area with additional content space
696
+ */
697
+ layout?: "default" | "minimal" | "expanded";
698
+ /** Show/hide the header icon */
699
+ showIcon?: boolean;
700
+ /** Show/hide the title */
701
+ showTitle?: boolean;
702
+ /** Show/hide the subtitle */
703
+ showSubtitle?: boolean;
704
+ /** Show/hide the close button */
705
+ showCloseButton?: boolean;
706
+ /** Show/hide the clear chat button */
707
+ showClearChat?: boolean;
708
+ /**
709
+ * Custom renderer for complete header override
710
+ * When provided, replaces the entire header with custom content
711
+ */
712
+ render?: (context: HeaderRenderContext) => HTMLElement;
713
+ };
714
+ /**
715
+ * Avatar configuration for message bubbles
716
+ */
717
+ type AgentWidgetAvatarConfig = {
718
+ /** Whether to show avatars */
719
+ show?: boolean;
720
+ /** Position of avatar relative to message bubble */
721
+ position?: "left" | "right";
722
+ /** URL or emoji for user avatar */
723
+ userAvatar?: string;
724
+ /** URL or emoji for assistant avatar */
725
+ assistantAvatar?: string;
726
+ };
727
+ /**
728
+ * Timestamp configuration for message bubbles
729
+ */
730
+ type AgentWidgetTimestampConfig = {
731
+ /** Whether to show timestamps */
732
+ show?: boolean;
733
+ /** Position of timestamp relative to message */
734
+ position?: "inline" | "below";
735
+ /** Custom formatter for timestamp display */
736
+ format?: (date: Date) => string;
737
+ };
738
+ /**
739
+ * Message layout configuration
740
+ * Allows customization of how chat messages are displayed
741
+ */
742
+ type AgentWidgetMessageLayoutConfig = {
743
+ /**
744
+ * Layout preset: "bubble" | "flat" | "minimal"
745
+ * - bubble: Standard chat bubble appearance (default)
746
+ * - flat: Flat messages without bubble styling
747
+ * - minimal: Minimal styling with reduced padding/borders
748
+ */
749
+ layout?: "bubble" | "flat" | "minimal";
750
+ /** Avatar configuration */
751
+ avatar?: AgentWidgetAvatarConfig;
752
+ /** Timestamp configuration */
753
+ timestamp?: AgentWidgetTimestampConfig;
754
+ /** Group consecutive messages from the same role */
755
+ groupConsecutive?: boolean;
756
+ /**
757
+ * Custom renderer for user messages
758
+ * When provided, replaces the default user message rendering
759
+ */
760
+ renderUserMessage?: (context: MessageRenderContext) => HTMLElement;
761
+ /**
762
+ * Custom renderer for assistant messages
763
+ * When provided, replaces the default assistant message rendering
764
+ */
765
+ renderAssistantMessage?: (context: MessageRenderContext) => HTMLElement;
766
+ };
767
+ /**
768
+ * Available layout slots for content injection
769
+ */
770
+ type WidgetLayoutSlot = "header-left" | "header-center" | "header-right" | "body-top" | "messages" | "body-bottom" | "footer-top" | "composer" | "footer-bottom";
771
+ /**
772
+ * Slot renderer function signature
773
+ * Returns HTMLElement to render in the slot, or null to use default content
774
+ */
775
+ type SlotRenderer = (context: SlotRenderContext) => HTMLElement | null;
776
+ /**
777
+ * Main layout configuration
778
+ * Provides comprehensive control over widget layout and appearance
779
+ *
780
+ * @example
781
+ * ```typescript
782
+ * config: {
783
+ * layout: {
784
+ * header: { layout: "minimal" },
785
+ * messages: {
786
+ * avatar: { show: true, assistantAvatar: "/bot.png" },
787
+ * timestamp: { show: true, position: "below" }
788
+ * },
789
+ * slots: {
790
+ * "footer-top": () => {
791
+ * const el = document.createElement("div");
792
+ * el.textContent = "Powered by AI";
793
+ * return el;
794
+ * }
795
+ * }
796
+ * }
797
+ * }
798
+ * ```
799
+ */
800
+ type AgentWidgetLayoutConfig = {
801
+ /** Header layout configuration */
802
+ header?: AgentWidgetHeaderLayoutConfig;
803
+ /** Message layout configuration */
804
+ messages?: AgentWidgetMessageLayoutConfig;
805
+ /** Slot renderers for custom content injection */
806
+ slots?: Partial<Record<WidgetLayoutSlot, SlotRenderer>>;
807
+ /**
808
+ * Show/hide the header section entirely.
809
+ * When false, the header (including icon, title, buttons) is completely hidden.
810
+ * @default true
811
+ */
812
+ showHeader?: boolean;
813
+ /**
814
+ * Show/hide the footer/composer section entirely.
815
+ * When false, the footer (including input field, send button, suggestions) is completely hidden.
816
+ * Useful for read-only conversation previews.
817
+ * @default true
818
+ */
819
+ showFooter?: boolean;
820
+ };
821
+ /**
822
+ * Token types for marked renderer methods
823
+ */
824
+ type AgentWidgetMarkdownHeadingToken = {
825
+ type: "heading";
826
+ raw: string;
827
+ depth: 1 | 2 | 3 | 4 | 5 | 6;
828
+ text: string;
829
+ tokens: unknown[];
830
+ };
831
+ type AgentWidgetMarkdownCodeToken = {
832
+ type: "code";
833
+ raw: string;
834
+ text: string;
835
+ lang?: string;
836
+ escaped?: boolean;
837
+ };
838
+ type AgentWidgetMarkdownBlockquoteToken = {
839
+ type: "blockquote";
840
+ raw: string;
841
+ text: string;
842
+ tokens: unknown[];
843
+ };
844
+ type AgentWidgetMarkdownTableToken = {
845
+ type: "table";
846
+ raw: string;
847
+ header: Array<{
848
+ text: string;
849
+ tokens: unknown[];
850
+ }>;
851
+ rows: Array<Array<{
852
+ text: string;
853
+ tokens: unknown[];
854
+ }>>;
855
+ align: Array<"left" | "center" | "right" | null>;
856
+ };
857
+ type AgentWidgetMarkdownLinkToken = {
858
+ type: "link";
859
+ raw: string;
860
+ href: string;
861
+ title: string | null;
862
+ text: string;
863
+ tokens: unknown[];
864
+ };
865
+ type AgentWidgetMarkdownImageToken = {
866
+ type: "image";
867
+ raw: string;
868
+ href: string;
869
+ title: string | null;
870
+ text: string;
871
+ };
872
+ type AgentWidgetMarkdownListToken = {
873
+ type: "list";
874
+ raw: string;
875
+ ordered: boolean;
876
+ start: number | "";
877
+ loose: boolean;
878
+ items: unknown[];
879
+ };
880
+ type AgentWidgetMarkdownListItemToken = {
881
+ type: "list_item";
882
+ raw: string;
883
+ task: boolean;
884
+ checked?: boolean;
885
+ loose: boolean;
886
+ text: string;
887
+ tokens: unknown[];
888
+ };
889
+ type AgentWidgetMarkdownParagraphToken = {
890
+ type: "paragraph";
891
+ raw: string;
892
+ text: string;
893
+ tokens: unknown[];
894
+ };
895
+ type AgentWidgetMarkdownCodespanToken = {
896
+ type: "codespan";
897
+ raw: string;
898
+ text: string;
899
+ };
900
+ type AgentWidgetMarkdownStrongToken = {
901
+ type: "strong";
902
+ raw: string;
903
+ text: string;
904
+ tokens: unknown[];
905
+ };
906
+ type AgentWidgetMarkdownEmToken = {
907
+ type: "em";
908
+ raw: string;
909
+ text: string;
910
+ tokens: unknown[];
911
+ };
912
+ /**
913
+ * Custom renderer overrides for markdown elements.
914
+ * Each method receives the token and should return an HTML string.
915
+ * Return `false` to use the default renderer.
916
+ *
917
+ * @example
918
+ * ```typescript
919
+ * renderer: {
920
+ * heading(token) {
921
+ * return `<h${token.depth} class="custom-heading">${token.text}</h${token.depth}>`;
922
+ * },
923
+ * link(token) {
924
+ * return `<a href="${token.href}" target="_blank" rel="noopener">${token.text}</a>`;
925
+ * }
926
+ * }
927
+ * ```
928
+ */
929
+ type AgentWidgetMarkdownRendererOverrides = {
930
+ /** Override heading rendering (h1-h6) */
931
+ heading?: (token: AgentWidgetMarkdownHeadingToken) => string | false;
932
+ /** Override code block rendering */
933
+ code?: (token: AgentWidgetMarkdownCodeToken) => string | false;
934
+ /** Override blockquote rendering */
935
+ blockquote?: (token: AgentWidgetMarkdownBlockquoteToken) => string | false;
936
+ /** Override table rendering */
937
+ table?: (token: AgentWidgetMarkdownTableToken) => string | false;
938
+ /** Override link rendering */
939
+ link?: (token: AgentWidgetMarkdownLinkToken) => string | false;
940
+ /** Override image rendering */
941
+ image?: (token: AgentWidgetMarkdownImageToken) => string | false;
942
+ /** Override list rendering (ul/ol) */
943
+ list?: (token: AgentWidgetMarkdownListToken) => string | false;
944
+ /** Override list item rendering */
945
+ listitem?: (token: AgentWidgetMarkdownListItemToken) => string | false;
946
+ /** Override paragraph rendering */
947
+ paragraph?: (token: AgentWidgetMarkdownParagraphToken) => string | false;
948
+ /** Override inline code rendering */
949
+ codespan?: (token: AgentWidgetMarkdownCodespanToken) => string | false;
950
+ /** Override strong/bold rendering */
951
+ strong?: (token: AgentWidgetMarkdownStrongToken) => string | false;
952
+ /** Override emphasis/italic rendering */
953
+ em?: (token: AgentWidgetMarkdownEmToken) => string | false;
954
+ /** Override horizontal rule rendering */
955
+ hr?: () => string | false;
956
+ /** Override line break rendering */
957
+ br?: () => string | false;
958
+ /** Override deleted/strikethrough rendering */
959
+ del?: (token: {
960
+ type: "del";
961
+ raw: string;
962
+ text: string;
963
+ tokens: unknown[];
964
+ }) => string | false;
965
+ /** Override checkbox rendering (in task lists) */
966
+ checkbox?: (token: {
967
+ checked: boolean;
968
+ }) => string | false;
969
+ /** Override HTML passthrough */
970
+ html?: (token: {
971
+ type: "html";
972
+ raw: string;
973
+ text: string;
974
+ }) => string | false;
975
+ /** Override text rendering */
976
+ text?: (token: {
977
+ type: "text";
978
+ raw: string;
979
+ text: string;
980
+ }) => string | false;
981
+ };
982
+ /**
983
+ * Markdown parsing options (subset of marked options)
984
+ */
985
+ type AgentWidgetMarkdownOptions = {
986
+ /**
987
+ * Enable GitHub Flavored Markdown (tables, strikethrough, autolinks).
988
+ * @default true
989
+ */
990
+ gfm?: boolean;
991
+ /**
992
+ * Convert \n in paragraphs into <br>.
993
+ * @default true
994
+ */
995
+ breaks?: boolean;
996
+ /**
997
+ * Conform to original markdown.pl as much as possible.
998
+ * @default false
999
+ */
1000
+ pedantic?: boolean;
1001
+ /**
1002
+ * Add id attributes to headings.
1003
+ * @default false
1004
+ */
1005
+ headerIds?: boolean;
1006
+ /**
1007
+ * Prefix for heading id attributes.
1008
+ * @default ""
1009
+ */
1010
+ headerPrefix?: string;
1011
+ /**
1012
+ * Mangle email addresses for spam protection.
1013
+ * @default true
1014
+ */
1015
+ mangle?: boolean;
1016
+ /**
1017
+ * Silent mode - don't throw on parse errors.
1018
+ * @default false
1019
+ */
1020
+ silent?: boolean;
1021
+ };
1022
+ /**
1023
+ * Markdown configuration for customizing how markdown is rendered in chat messages.
1024
+ * Provides three levels of control:
1025
+ *
1026
+ * 1. **CSS Variables** - Override styles via `--cw-md-*` CSS custom properties
1027
+ * 2. **Parsing Options** - Configure marked behavior via `options`
1028
+ * 3. **Custom Renderers** - Full control via `renderer` overrides
1029
+ *
1030
+ * @example
1031
+ * ```typescript
1032
+ * // Level 2: Configure parsing options
1033
+ * config: {
1034
+ * markdown: {
1035
+ * options: {
1036
+ * gfm: true,
1037
+ * breaks: true,
1038
+ * headerIds: true
1039
+ * }
1040
+ * }
1041
+ * }
1042
+ * ```
1043
+ *
1044
+ * @example
1045
+ * ```typescript
1046
+ * // Level 3: Custom renderers
1047
+ * config: {
1048
+ * markdown: {
1049
+ * renderer: {
1050
+ * heading(token) {
1051
+ * return `<h${token.depth} class="custom-h${token.depth}">${token.text}</h${token.depth}>`;
1052
+ * },
1053
+ * link(token) {
1054
+ * return `<a href="${token.href}" target="_blank">${token.text}</a>`;
1055
+ * },
1056
+ * table(token) {
1057
+ * // Wrap tables in a scrollable container
1058
+ * return `<div class="table-scroll">${this.parser.parse(token.tokens)}</div>`;
1059
+ * }
1060
+ * }
1061
+ * }
1062
+ * }
1063
+ * ```
1064
+ */
1065
+ type AgentWidgetMarkdownConfig = {
1066
+ /**
1067
+ * Markdown parsing options.
1068
+ * These are passed directly to the marked parser.
1069
+ */
1070
+ options?: AgentWidgetMarkdownOptions;
1071
+ /**
1072
+ * Custom renderer overrides for specific markdown elements.
1073
+ * Each method receives a token object and should return an HTML string.
1074
+ * Return `false` to fall back to the default renderer.
1075
+ */
1076
+ renderer?: AgentWidgetMarkdownRendererOverrides;
1077
+ /**
1078
+ * Disable default markdown CSS styles.
1079
+ * When true, the widget won't apply any default styles to markdown elements,
1080
+ * allowing you to provide your own CSS.
1081
+ *
1082
+ * @default false
1083
+ */
1084
+ disableDefaultStyles?: boolean;
1085
+ };
1086
+ /**
1087
+ * Configuration for file attachments in the composer.
1088
+ * Enables users to attach images to their messages.
1089
+ *
1090
+ * @example
1091
+ * ```typescript
1092
+ * config: {
1093
+ * attachments: {
1094
+ * enabled: true,
1095
+ * allowedTypes: ['image/png', 'image/jpeg', 'image/gif', 'image/webp'],
1096
+ * maxFileSize: 5 * 1024 * 1024, // 5MB
1097
+ * maxFiles: 4
1098
+ * }
1099
+ * }
1100
+ * ```
1101
+ */
1102
+ type AgentWidgetAttachmentsConfig = {
1103
+ /**
1104
+ * Enable/disable file attachments.
1105
+ * @default false
1106
+ */
1107
+ enabled?: boolean;
1108
+ /**
1109
+ * Allowed MIME types for attachments.
1110
+ * @default ['image/png', 'image/jpeg', 'image/gif', 'image/webp']
1111
+ */
1112
+ allowedTypes?: string[];
1113
+ /**
1114
+ * Maximum file size in bytes.
1115
+ * @default 10485760 (10MB)
1116
+ */
1117
+ maxFileSize?: number;
1118
+ /**
1119
+ * Maximum number of files per message.
1120
+ * @default 4
1121
+ */
1122
+ maxFiles?: number;
1123
+ /**
1124
+ * Button icon name (from Lucide icons).
1125
+ * @default 'image-plus'
1126
+ */
1127
+ buttonIconName?: string;
1128
+ /**
1129
+ * Tooltip text for the attachment button.
1130
+ * @default 'Attach image'
1131
+ */
1132
+ buttonTooltipText?: string;
1133
+ /**
1134
+ * Callback when a file is rejected (wrong type or too large).
1135
+ */
1136
+ onFileRejected?: (file: File, reason: 'type' | 'size' | 'count') => void;
1137
+ };
1138
+ type AgentWidgetConfig = {
1139
+ apiUrl?: string;
1140
+ flowId?: string;
1141
+ /**
1142
+ * Client token for direct browser-to-API communication.
1143
+ * When set, the widget uses /v1/client/* endpoints instead of /v1/dispatch.
1144
+ * Mutually exclusive with apiKey/headers authentication.
1145
+ *
1146
+ * @example
1147
+ * ```typescript
1148
+ * config: {
1149
+ * clientToken: 'ct_live_flow01k7_a8b9c0d1e2f3g4h5i6j7k8l9'
1150
+ * }
1151
+ * ```
1152
+ */
1153
+ clientToken?: string;
1154
+ /**
1155
+ * Callback when session is initialized (client token mode only).
1156
+ * Receives session info including expiry time.
1157
+ *
1158
+ * @example
1159
+ * ```typescript
1160
+ * config: {
1161
+ * onSessionInit: (session) => {
1162
+ * console.log('Session started:', session.sessionId);
1163
+ * }
1164
+ * }
1165
+ * ```
1166
+ */
1167
+ onSessionInit?: (session: ClientSession) => void;
1168
+ /**
1169
+ * Callback when session expires or errors (client token mode only).
1170
+ * Widget should prompt user to refresh.
1171
+ *
1172
+ * @example
1173
+ * ```typescript
1174
+ * config: {
1175
+ * onSessionExpired: () => {
1176
+ * alert('Your session has expired. Please refresh the page.');
1177
+ * }
1178
+ * }
1179
+ * ```
1180
+ */
1181
+ onSessionExpired?: () => void;
1182
+ /**
1183
+ * Get stored session ID for session resumption (client token mode only).
1184
+ * Called when initializing a new session to check if there's a previous session_id
1185
+ * that should be passed to /client/init to resume the same conversation record.
1186
+ *
1187
+ * @example
1188
+ * ```typescript
1189
+ * config: {
1190
+ * getStoredSessionId: () => {
1191
+ * const stored = localStorage.getItem('session_id');
1192
+ * return stored || null;
1193
+ * }
1194
+ * }
1195
+ * ```
1196
+ */
1197
+ getStoredSessionId?: () => string | null;
1198
+ /**
1199
+ * Store session ID for session resumption (client token mode only).
1200
+ * Called when a new session is initialized to persist the session_id
1201
+ * so it can be used to resume the conversation later.
1202
+ *
1203
+ * @example
1204
+ * ```typescript
1205
+ * config: {
1206
+ * setStoredSessionId: (sessionId) => {
1207
+ * localStorage.setItem('session_id', sessionId);
1208
+ * }
1209
+ * }
1210
+ * ```
1211
+ */
1212
+ setStoredSessionId?: (sessionId: string) => void;
1213
+ /**
1214
+ * Static headers to include with each request.
1215
+ * For dynamic headers (e.g., auth tokens), use `getHeaders` instead.
1216
+ */
1217
+ headers?: Record<string, string>;
1218
+ /**
1219
+ * Dynamic headers function - called before each request.
1220
+ * Useful for adding auth tokens that may change.
1221
+ * @example
1222
+ * ```typescript
1223
+ * getHeaders: async () => ({
1224
+ * 'Authorization': `Bearer ${await getAuthToken()}`
1225
+ * })
1226
+ * ```
1227
+ */
1228
+ getHeaders?: AgentWidgetHeadersFunction;
1229
+ copy?: {
1230
+ welcomeTitle?: string;
1231
+ welcomeSubtitle?: string;
1232
+ inputPlaceholder?: string;
1233
+ sendButtonLabel?: string;
1234
+ };
1235
+ theme?: AgentWidgetTheme;
1236
+ /**
1237
+ * Theme colors for dark mode. Applied when dark mode is detected
1238
+ * (when colorScheme is 'dark' or 'auto' with dark mode active).
1239
+ * If not provided, falls back to `theme` colors.
1240
+ *
1241
+ * @example
1242
+ * ```typescript
1243
+ * config: {
1244
+ * theme: { primary: '#111827', surface: '#ffffff' },
1245
+ * darkTheme: { primary: '#f9fafb', surface: '#1f2937' },
1246
+ * colorScheme: 'auto'
1247
+ * }
1248
+ * ```
1249
+ */
1250
+ darkTheme?: AgentWidgetTheme;
1251
+ /**
1252
+ * Color scheme mode for the widget.
1253
+ * - 'light': Always use light theme (default)
1254
+ * - 'dark': Always use dark theme
1255
+ * - 'auto': Automatically detect from page (HTML class or prefers-color-scheme)
1256
+ *
1257
+ * When 'auto', detection order:
1258
+ * 1. Check if `<html>` has 'dark' class
1259
+ * 2. Fall back to `prefers-color-scheme: dark` media query
1260
+ *
1261
+ * @default 'light'
1262
+ */
1263
+ colorScheme?: 'auto' | 'light' | 'dark';
1264
+ features?: AgentWidgetFeatureFlags;
1265
+ launcher?: AgentWidgetLauncherConfig;
1266
+ initialMessages?: AgentWidgetMessage[];
1267
+ suggestionChips?: string[];
1268
+ suggestionChipsConfig?: AgentWidgetSuggestionChipsConfig;
1269
+ debug?: boolean;
1270
+ formEndpoint?: string;
1271
+ launcherWidth?: string;
1272
+ sendButton?: AgentWidgetSendButtonConfig;
1273
+ statusIndicator?: AgentWidgetStatusIndicatorConfig;
1274
+ voiceRecognition?: AgentWidgetVoiceRecognitionConfig;
1275
+ toolCall?: AgentWidgetToolCallConfig;
1276
+ postprocessMessage?: (context: {
1277
+ text: string;
1278
+ message: AgentWidgetMessage;
1279
+ streaming: boolean;
1280
+ raw?: string;
1281
+ }) => string;
1282
+ plugins?: AgentWidgetPlugin[];
1283
+ contextProviders?: AgentWidgetContextProvider[];
1284
+ requestMiddleware?: AgentWidgetRequestMiddleware;
1285
+ actionParsers?: AgentWidgetActionParser[];
1286
+ actionHandlers?: AgentWidgetActionHandler[];
1287
+ storageAdapter?: AgentWidgetStorageAdapter;
1288
+ /**
1289
+ * Registry of custom components that can be rendered from JSON directives.
1290
+ * Components are registered by name and can be invoked via JSON responses
1291
+ * with the format: `{"component": "ComponentName", "props": {...}}`
1292
+ *
1293
+ * @example
1294
+ * ```typescript
1295
+ * config: {
1296
+ * components: {
1297
+ * ProductCard: (props, context) => {
1298
+ * const card = document.createElement("div");
1299
+ * card.innerHTML = `<h3>${props.title}</h3><p>$${props.price}</p>`;
1300
+ * return card;
1301
+ * }
1302
+ * }
1303
+ * }
1304
+ * ```
1305
+ */
1306
+ components?: Record<string, AgentWidgetComponentRenderer>;
1307
+ /**
1308
+ * Enable component streaming. When true, component props will be updated
1309
+ * incrementally as they stream in from the JSON response.
1310
+ *
1311
+ * @default true
1312
+ */
1313
+ enableComponentStreaming?: boolean;
1314
+ /**
1315
+ * Custom stream parser for extracting text from streaming structured responses.
1316
+ * Handles incremental parsing of JSON, XML, or other formats.
1317
+ * If not provided, uses the default JSON parser.
1318
+ *
1319
+ * @example
1320
+ * ```typescript
1321
+ * streamParser: () => ({
1322
+ * processChunk: async (content) => {
1323
+ * // Return null if not your format, or extracted text if available
1324
+ * if (!content.trim().startsWith('{')) return null;
1325
+ * return extractText(content);
1326
+ * },
1327
+ * getExtractedText: () => extractedText
1328
+ * })
1329
+ * ```
1330
+ */
1331
+ streamParser?: () => AgentWidgetStreamParser;
1332
+ /**
1333
+ * Additional localStorage key to clear when the clear chat button is clicked.
1334
+ * The widget automatically clears `"persona-chat-history"` by default.
1335
+ * Use this option to clear additional keys (e.g., if you're using a custom storage key).
1336
+ *
1337
+ * @example
1338
+ * ```typescript
1339
+ * config: {
1340
+ * clearChatHistoryStorageKey: "my-custom-chat-history"
1341
+ * }
1342
+ * ```
1343
+ */
1344
+ clearChatHistoryStorageKey?: string;
1345
+ /**
1346
+ * Built-in parser type selector. Provides an easy way to choose a parser without importing functions.
1347
+ * If both `parserType` and `streamParser` are provided, `streamParser` takes precedence.
1348
+ *
1349
+ * - `"plain"` - Plain text parser (default). Passes through text as-is.
1350
+ * - `"json"` - JSON parser using partial-json. Extracts `text` field from JSON objects incrementally.
1351
+ * - `"regex-json"` - Regex-based JSON parser. Less robust but faster fallback for simple JSON.
1352
+ * - `"xml"` - XML parser. Extracts text content from XML tags.
1353
+ *
1354
+ * @example
1355
+ * ```typescript
1356
+ * config: {
1357
+ * parserType: "json" // Use built-in JSON parser
1358
+ * }
1359
+ * ```
1360
+ *
1361
+ * @example
1362
+ * ```typescript
1363
+ * config: {
1364
+ * parserType: "json",
1365
+ * streamParser: () => customParser() // Custom parser overrides parserType
1366
+ * }
1367
+ * ```
1368
+ */
1369
+ parserType?: "plain" | "json" | "regex-json" | "xml";
1370
+ /**
1371
+ * Custom fetch function for full control over API requests.
1372
+ * Use this for custom authentication, request/response transformation, etc.
1373
+ *
1374
+ * When provided, this function is called instead of the default fetch.
1375
+ * You receive the URL, RequestInit, and the payload that would be sent.
1376
+ *
1377
+ * @example
1378
+ * ```typescript
1379
+ * config: {
1380
+ * customFetch: async (url, init, payload) => {
1381
+ * // Transform request for your API format
1382
+ * const myPayload = {
1383
+ * flow: { id: 'my-flow-id' },
1384
+ * messages: payload.messages,
1385
+ * options: { stream_response: true }
1386
+ * };
1387
+ *
1388
+ * // Add auth header
1389
+ * const token = await getAuthToken();
1390
+ *
1391
+ * return fetch('/my-api/dispatch', {
1392
+ * method: 'POST',
1393
+ * headers: {
1394
+ * 'Content-Type': 'application/json',
1395
+ * 'Authorization': `Bearer ${token}`
1396
+ * },
1397
+ * body: JSON.stringify(myPayload),
1398
+ * signal: init.signal
1399
+ * });
1400
+ * }
1401
+ * }
1402
+ * ```
1403
+ */
1404
+ customFetch?: AgentWidgetCustomFetch;
1405
+ /**
1406
+ * Custom SSE event parser for non-standard streaming response formats.
1407
+ *
1408
+ * Use this when your API returns SSE events in a different format than expected.
1409
+ * Return `{ text }` for text chunks, `{ done: true }` for completion,
1410
+ * `{ error }` for errors, or `null` to ignore the event.
1411
+ *
1412
+ * @example
1413
+ * ```typescript
1414
+ * // For Travrse API format
1415
+ * config: {
1416
+ * parseSSEEvent: (data) => {
1417
+ * if (data.type === 'step_chunk' && data.chunk) {
1418
+ * return { text: data.chunk };
1419
+ * }
1420
+ * if (data.type === 'flow_complete') {
1421
+ * return { done: true };
1422
+ * }
1423
+ * if (data.type === 'step_error') {
1424
+ * return { error: data.error };
1425
+ * }
1426
+ * return null; // Ignore other events
1427
+ * }
1428
+ * }
1429
+ * ```
1430
+ */
1431
+ parseSSEEvent?: AgentWidgetSSEEventParser;
1432
+ /**
1433
+ * Layout configuration for customizing widget appearance and structure.
1434
+ * Provides control over header, messages, and content slots.
1435
+ *
1436
+ * @example
1437
+ * ```typescript
1438
+ * config: {
1439
+ * layout: {
1440
+ * header: { layout: "minimal" },
1441
+ * messages: { avatar: { show: true } }
1442
+ * }
1443
+ * }
1444
+ * ```
1445
+ */
1446
+ layout?: AgentWidgetLayoutConfig;
1447
+ /**
1448
+ * Markdown rendering configuration.
1449
+ * Customize how markdown is parsed and rendered in chat messages.
1450
+ *
1451
+ * Override methods:
1452
+ * 1. **CSS Variables** - Override `--cw-md-*` variables in your stylesheet
1453
+ * 2. **Options** - Configure marked parser behavior
1454
+ * 3. **Renderers** - Custom rendering functions for specific elements
1455
+ * 4. **postprocessMessage** - Complete control over message transformation
1456
+ *
1457
+ * @example
1458
+ * ```typescript
1459
+ * config: {
1460
+ * markdown: {
1461
+ * options: { breaks: true, gfm: true },
1462
+ * renderer: {
1463
+ * link(token) {
1464
+ * return `<a href="${token.href}" target="_blank">${token.text}</a>`;
1465
+ * }
1466
+ * }
1467
+ * }
1468
+ * }
1469
+ * ```
1470
+ */
1471
+ markdown?: AgentWidgetMarkdownConfig;
1472
+ /**
1473
+ * Configuration for message action buttons (copy, upvote, downvote).
1474
+ * Shows action buttons on assistant messages for user feedback.
1475
+ *
1476
+ * @example
1477
+ * ```typescript
1478
+ * config: {
1479
+ * messageActions: {
1480
+ * enabled: true,
1481
+ * showCopy: true,
1482
+ * showUpvote: true,
1483
+ * showDownvote: true,
1484
+ * visibility: 'hover',
1485
+ * onFeedback: (feedback) => {
1486
+ * console.log('Feedback:', feedback.type, feedback.messageId);
1487
+ * },
1488
+ * onCopy: (message) => {
1489
+ * console.log('Copied message:', message.id);
1490
+ * }
1491
+ * }
1492
+ * }
1493
+ * ```
1494
+ */
1495
+ messageActions?: AgentWidgetMessageActionsConfig;
1496
+ /**
1497
+ * Configuration for file attachments in the composer.
1498
+ * When enabled, users can attach images to their messages.
1499
+ *
1500
+ * @example
1501
+ * ```typescript
1502
+ * config: {
1503
+ * attachments: {
1504
+ * enabled: true,
1505
+ * maxFileSize: 5 * 1024 * 1024, // 5MB
1506
+ * maxFiles: 4
1507
+ * }
1508
+ * }
1509
+ * ```
1510
+ */
1511
+ attachments?: AgentWidgetAttachmentsConfig;
1512
+ };
1513
+ type AgentWidgetMessageRole = "user" | "assistant" | "system";
1514
+ type AgentWidgetReasoning = {
1515
+ id: string;
1516
+ status: "pending" | "streaming" | "complete";
1517
+ chunks: string[];
1518
+ startedAt?: number;
1519
+ completedAt?: number;
1520
+ durationMs?: number;
1521
+ };
1522
+ type AgentWidgetToolCall = {
1523
+ id: string;
1524
+ name?: string;
1525
+ status: "pending" | "running" | "complete";
1526
+ args?: unknown;
1527
+ chunks?: string[];
1528
+ result?: unknown;
1529
+ duration?: number;
1530
+ startedAt?: number;
1531
+ completedAt?: number;
1532
+ durationMs?: number;
1533
+ };
1534
+ type AgentWidgetMessageVariant = "assistant" | "reasoning" | "tool";
1535
+ /**
1536
+ * Represents a message in the chat conversation.
1537
+ *
1538
+ * @property id - Unique message identifier
1539
+ * @property role - Message role: "user", "assistant", or "system"
1540
+ * @property content - Message text content (for display)
1541
+ * @property contentParts - Original multi-modal content parts (for API requests)
1542
+ * @property createdAt - ISO timestamp when message was created
1543
+ * @property streaming - Whether message is still streaming (for assistant messages)
1544
+ * @property variant - Message variant for assistant messages: "assistant", "reasoning", or "tool"
1545
+ * @property sequence - Message ordering number
1546
+ * @property reasoning - Reasoning data for assistant reasoning messages
1547
+ * @property toolCall - Tool call data for assistant tool messages
1548
+ * @property tools - Array of tool calls
1549
+ * @property viaVoice - Set to `true` when a user message is sent via voice recognition.
1550
+ * Useful for implementing voice-specific behaviors like auto-reactivation.
1551
+ */
1552
+ type AgentWidgetMessage = {
1553
+ id: string;
1554
+ role: AgentWidgetMessageRole;
1555
+ content: string;
1556
+ createdAt: string;
1557
+ /**
1558
+ * Original multi-modal content parts for this message.
1559
+ * When present, this is sent to the API instead of `content`.
1560
+ * The `content` field contains the text-only representation for display.
1561
+ */
1562
+ contentParts?: ContentPart[];
1563
+ streaming?: boolean;
1564
+ variant?: AgentWidgetMessageVariant;
1565
+ sequence?: number;
1566
+ reasoning?: AgentWidgetReasoning;
1567
+ toolCall?: AgentWidgetToolCall;
1568
+ tools?: AgentWidgetToolCall[];
1569
+ viaVoice?: boolean;
1570
+ /**
1571
+ * Raw structured payload for this message (e.g., JSON action response).
1572
+ * Populated automatically when structured parsers run.
1573
+ */
1574
+ rawContent?: string;
1575
+ };
1576
+ type AgentWidgetEvent = {
1577
+ type: "message";
1578
+ message: AgentWidgetMessage;
1579
+ } | {
1580
+ type: "status";
1581
+ status: "connecting" | "connected" | "error" | "idle";
1582
+ } | {
1583
+ type: "error";
1584
+ error: Error;
1585
+ };
1586
+ type AgentWidgetInitOptions = {
1587
+ target: string | HTMLElement;
1588
+ config?: AgentWidgetConfig;
1589
+ useShadowDom?: boolean;
1590
+ onReady?: () => void;
1591
+ windowKey?: string;
1592
+ debugTools?: boolean;
1593
+ };
1594
+
1595
+ type DispatchOptions = {
1596
+ messages: AgentWidgetMessage[];
1597
+ signal?: AbortSignal;
1598
+ /** Pre-generated ID for the expected assistant response (for feedback tracking) */
1599
+ assistantMessageId?: string;
1600
+ };
1601
+ type SSEHandler = (event: AgentWidgetEvent) => void;
1602
+ declare class AgentWidgetClient {
1603
+ private config;
1604
+ private readonly apiUrl;
1605
+ private readonly headers;
1606
+ private readonly debug;
1607
+ private readonly createStreamParser;
1608
+ private readonly contextProviders;
1609
+ private readonly requestMiddleware?;
1610
+ private readonly customFetch?;
1611
+ private readonly parseSSEEvent?;
1612
+ private readonly getHeaders?;
1613
+ private clientSession;
1614
+ private sessionInitPromise;
1615
+ constructor(config?: AgentWidgetConfig);
1616
+ /**
1617
+ * Check if running in client token mode
1618
+ */
1619
+ isClientTokenMode(): boolean;
1620
+ /**
1621
+ * Get the appropriate API URL based on mode
1622
+ */
1623
+ private getClientApiUrl;
1624
+ /**
1625
+ * Get the current client session (if any)
1626
+ */
1627
+ getClientSession(): ClientSession | null;
1628
+ /**
1629
+ * Initialize session for client token mode.
1630
+ * Called automatically on first message if not already initialized.
1631
+ */
1632
+ initSession(): Promise<ClientSession>;
1633
+ private _doInitSession;
1634
+ /**
1635
+ * Clear the current client session
1636
+ */
1637
+ clearClientSession(): void;
1638
+ /**
1639
+ * Get the feedback API URL
1640
+ */
1641
+ private getFeedbackApiUrl;
1642
+ /**
1643
+ * Send feedback for a message (client token mode only).
1644
+ * Supports upvote, downvote, copy, csat, and nps feedback types.
1645
+ *
1646
+ * @param feedback - The feedback request payload
1647
+ * @returns Promise that resolves when feedback is sent successfully
1648
+ * @throws Error if not in client token mode or if session is invalid
1649
+ *
1650
+ * @example
1651
+ * ```typescript
1652
+ * // Message feedback (upvote/downvote/copy)
1653
+ * await client.sendFeedback({
1654
+ * session_id: sessionId,
1655
+ * message_id: messageId,
1656
+ * type: 'upvote'
1657
+ * });
1658
+ *
1659
+ * // CSAT feedback (1-5 rating)
1660
+ * await client.sendFeedback({
1661
+ * session_id: sessionId,
1662
+ * type: 'csat',
1663
+ * rating: 5,
1664
+ * comment: 'Great experience!'
1665
+ * });
1666
+ *
1667
+ * // NPS feedback (0-10 rating)
1668
+ * await client.sendFeedback({
1669
+ * session_id: sessionId,
1670
+ * type: 'nps',
1671
+ * rating: 9
1672
+ * });
1673
+ * ```
1674
+ */
1675
+ sendFeedback(feedback: ClientFeedbackRequest): Promise<void>;
1676
+ /**
1677
+ * Submit message feedback (upvote, downvote, or copy).
1678
+ * Convenience method for sendFeedback with message-level feedback.
1679
+ *
1680
+ * @param messageId - The ID of the message to provide feedback for
1681
+ * @param type - The feedback type: 'upvote', 'downvote', or 'copy'
1682
+ */
1683
+ submitMessageFeedback(messageId: string, type: 'upvote' | 'downvote' | 'copy'): Promise<void>;
1684
+ /**
1685
+ * Submit CSAT (Customer Satisfaction) feedback.
1686
+ * Convenience method for sendFeedback with CSAT feedback.
1687
+ *
1688
+ * @param rating - Rating from 1 to 5
1689
+ * @param comment - Optional comment
1690
+ */
1691
+ submitCSATFeedback(rating: number, comment?: string): Promise<void>;
1692
+ /**
1693
+ * Submit NPS (Net Promoter Score) feedback.
1694
+ * Convenience method for sendFeedback with NPS feedback.
1695
+ *
1696
+ * @param rating - Rating from 0 to 10
1697
+ * @param comment - Optional comment
1698
+ */
1699
+ submitNPSFeedback(rating: number, comment?: string): Promise<void>;
1700
+ /**
1701
+ * Send a message - handles both proxy and client token modes
1702
+ */
1703
+ dispatch(options: DispatchOptions, onEvent: SSEHandler): Promise<void>;
1704
+ /**
1705
+ * Client token mode dispatch
1706
+ */
1707
+ private dispatchClientToken;
1708
+ /**
1709
+ * Proxy mode dispatch (original implementation)
1710
+ */
1711
+ private dispatchProxy;
1712
+ private buildPayload;
1713
+ /**
1714
+ * Handle custom SSE event parsing via parseSSEEvent callback
1715
+ * Returns true if event was handled, false otherwise
1716
+ */
1717
+ private handleCustomSSEEvent;
1718
+ private streamResponse;
1719
+ }
1720
+
1721
+ type AgentWidgetSessionStatus = "idle" | "connecting" | "connected" | "error";
1722
+ type SessionCallbacks = {
1723
+ onMessagesChanged: (messages: AgentWidgetMessage[]) => void;
1724
+ onStatusChanged: (status: AgentWidgetSessionStatus) => void;
1725
+ onStreamingChanged: (streaming: boolean) => void;
1726
+ onError?: (error: Error) => void;
1727
+ };
1728
+ declare class AgentWidgetSession {
1729
+ private config;
1730
+ private callbacks;
1731
+ private client;
1732
+ private messages;
1733
+ private status;
1734
+ private streaming;
1735
+ private abortController;
1736
+ private sequenceCounter;
1737
+ private clientSession;
1738
+ constructor(config: AgentWidgetConfig | undefined, callbacks: SessionCallbacks);
1739
+ /**
1740
+ * Check if running in client token mode
1741
+ */
1742
+ isClientTokenMode(): boolean;
1743
+ /**
1744
+ * Initialize the client session (for client token mode).
1745
+ * This is called automatically on first message, but can be called
1746
+ * explicitly to pre-initialize the session and get config from server.
1747
+ */
1748
+ initClientSession(): Promise<ClientSession | null>;
1749
+ /**
1750
+ * Set the client session after initialization
1751
+ */
1752
+ setClientSession(session: ClientSession): void;
1753
+ /**
1754
+ * Get current client session
1755
+ */
1756
+ getClientSession(): ClientSession | null;
1757
+ /**
1758
+ * Check if session is valid and not expired
1759
+ */
1760
+ isSessionValid(): boolean;
1761
+ /**
1762
+ * Clear session (on expiry or error)
1763
+ */
1764
+ clearClientSession(): void;
1765
+ /**
1766
+ * Get the underlying client instance (for advanced use cases like feedback)
1767
+ */
1768
+ getClient(): AgentWidgetClient;
1769
+ /**
1770
+ * Submit message feedback (upvote, downvote, or copy) to the API.
1771
+ * Only available in client token mode.
1772
+ *
1773
+ * @param messageId - The ID of the message to provide feedback for
1774
+ * @param type - The feedback type: 'upvote', 'downvote', or 'copy'
1775
+ */
1776
+ submitMessageFeedback(messageId: string, type: 'upvote' | 'downvote' | 'copy'): Promise<void>;
1777
+ /**
1778
+ * Submit CSAT (Customer Satisfaction) feedback to the API.
1779
+ * Only available in client token mode.
1780
+ *
1781
+ * @param rating - Rating from 1 to 5
1782
+ * @param comment - Optional comment
1783
+ */
1784
+ submitCSATFeedback(rating: number, comment?: string): Promise<void>;
1785
+ /**
1786
+ * Submit NPS (Net Promoter Score) feedback to the API.
1787
+ * Only available in client token mode.
1788
+ *
1789
+ * @param rating - Rating from 0 to 10
1790
+ * @param comment - Optional comment
1791
+ */
1792
+ submitNPSFeedback(rating: number, comment?: string): Promise<void>;
1793
+ updateConfig(next: AgentWidgetConfig): void;
1794
+ getMessages(): AgentWidgetMessage[];
1795
+ getStatus(): AgentWidgetSessionStatus;
1796
+ isStreaming(): boolean;
1797
+ injectTestEvent(event: AgentWidgetEvent): void;
1798
+ sendMessage(rawInput: string, options?: {
1799
+ viaVoice?: boolean;
1800
+ /** Multi-modal content parts (e.g., images) to include with the message */
1801
+ contentParts?: ContentPart[];
1802
+ }): Promise<void>;
1803
+ cancel(): void;
1804
+ clearMessages(): void;
1805
+ hydrateMessages(messages: AgentWidgetMessage[]): void;
1806
+ private handleEvent;
1807
+ private setStatus;
1808
+ private setStreaming;
1809
+ private appendMessage;
1810
+ private upsertMessage;
1811
+ private ensureSequence;
1812
+ private nextSequence;
1813
+ private sortMessages;
1814
+ }
1815
+
1816
+ /**
1817
+ * Feedback UI components for CSAT and NPS collection
1818
+ */
1819
+ type CSATFeedbackOptions = {
1820
+ /** Callback when user submits CSAT feedback */
1821
+ onSubmit: (rating: number, comment?: string) => void | Promise<void>;
1822
+ /** Callback when user dismisses the feedback form */
1823
+ onDismiss?: () => void;
1824
+ /** Title text */
1825
+ title?: string;
1826
+ /** Subtitle/question text */
1827
+ subtitle?: string;
1828
+ /** Placeholder for optional comment field */
1829
+ commentPlaceholder?: string;
1830
+ /** Submit button text */
1831
+ submitText?: string;
1832
+ /** Skip button text */
1833
+ skipText?: string;
1834
+ /** Show comment field */
1835
+ showComment?: boolean;
1836
+ /** Rating labels (5 items for ratings 1-5) */
1837
+ ratingLabels?: [string, string, string, string, string];
1838
+ };
1839
+ type NPSFeedbackOptions = {
1840
+ /** Callback when user submits NPS feedback */
1841
+ onSubmit: (rating: number, comment?: string) => void | Promise<void>;
1842
+ /** Callback when user dismisses the feedback form */
1843
+ onDismiss?: () => void;
1844
+ /** Title text */
1845
+ title?: string;
1846
+ /** Subtitle/question text */
1847
+ subtitle?: string;
1848
+ /** Placeholder for optional comment field */
1849
+ commentPlaceholder?: string;
1850
+ /** Submit button text */
1851
+ submitText?: string;
1852
+ /** Skip button text */
1853
+ skipText?: string;
1854
+ /** Show comment field */
1855
+ showComment?: boolean;
1856
+ /** Low label (left side) */
1857
+ lowLabel?: string;
1858
+ /** High label (right side) */
1859
+ highLabel?: string;
1860
+ };
1861
+ /**
1862
+ * Create a CSAT (Customer Satisfaction) feedback form
1863
+ * Rating scale: 1-5
1864
+ */
1865
+ declare function createCSATFeedback(options: CSATFeedbackOptions): HTMLElement;
1866
+ /**
1867
+ * Create an NPS (Net Promoter Score) feedback form
1868
+ * Rating scale: 0-10
1869
+ */
1870
+ declare function createNPSFeedback(options: NPSFeedbackOptions): HTMLElement;
1871
+
1872
+ type Controller = {
1873
+ update: (config: AgentWidgetConfig) => void;
1874
+ destroy: () => void;
1875
+ open: () => void;
1876
+ close: () => void;
1877
+ toggle: () => void;
1878
+ clearChat: () => void;
1879
+ setMessage: (message: string) => boolean;
1880
+ submitMessage: (message?: string) => boolean;
1881
+ startVoiceRecognition: () => boolean;
1882
+ stopVoiceRecognition: () => boolean;
1883
+ injectTestMessage: (event: AgentWidgetEvent) => void;
1884
+ getMessages: () => AgentWidgetMessage[];
1885
+ getStatus: () => AgentWidgetSessionStatus;
1886
+ getPersistentMetadata: () => Record<string, unknown>;
1887
+ updatePersistentMetadata: (updater: (prev: Record<string, unknown>) => Record<string, unknown>) => void;
1888
+ on: <K extends keyof AgentWidgetControllerEventMap>(event: K, handler: (payload: AgentWidgetControllerEventMap[K]) => void) => () => void;
1889
+ off: <K extends keyof AgentWidgetControllerEventMap>(event: K, handler: (payload: AgentWidgetControllerEventMap[K]) => void) => void;
1890
+ isOpen: () => boolean;
1891
+ isVoiceActive: () => boolean;
1892
+ getState: () => AgentWidgetStateSnapshot;
1893
+ showCSATFeedback: (options?: Partial<CSATFeedbackOptions>) => void;
1894
+ showNPSFeedback: (options?: Partial<NPSFeedbackOptions>) => void;
1895
+ submitCSATFeedback: (rating: number, comment?: string) => Promise<void>;
1896
+ submitNPSFeedback: (rating: number, comment?: string) => Promise<void>;
1897
+ };
1898
+ declare const createAgentExperience: (mount: HTMLElement, initialConfig?: AgentWidgetConfig, runtimeOptions?: {
1899
+ debugTools?: boolean;
1900
+ }) => Controller;
1901
+ type AgentWidgetController = Controller;
1902
+
1903
+ type AgentWidgetInitHandle = AgentWidgetController & {
1904
+ host: HTMLElement;
1905
+ };
1906
+ declare const initAgentWidget: (options: AgentWidgetInitOptions) => AgentWidgetInitHandle;
1907
+
1908
+ declare const createLocalStorageAdapter: (key?: string) => AgentWidgetStorageAdapter;
1909
+
1910
+ type ActionManagerProcessContext = {
1911
+ text: string;
1912
+ message: AgentWidgetMessage;
1913
+ streaming: boolean;
1914
+ raw?: string;
1915
+ };
1916
+ type ActionManagerOptions = {
1917
+ parsers: AgentWidgetActionParser[];
1918
+ handlers: AgentWidgetActionHandler[];
1919
+ getSessionMetadata: () => Record<string, unknown>;
1920
+ updateSessionMetadata: (updater: (prev: Record<string, unknown>) => Record<string, unknown>) => void;
1921
+ emit: <K extends keyof AgentWidgetControllerEventMap>(event: K, payload: AgentWidgetControllerEventMap[K]) => void;
1922
+ documentRef: Document | null;
1923
+ };
1924
+ declare const defaultJsonActionParser: AgentWidgetActionParser;
1925
+ declare const defaultActionHandlers: Record<string, AgentWidgetActionHandler>;
1926
+ declare const createActionManager: (options: ActionManagerOptions) => {
1927
+ process: (context: ActionManagerProcessContext) => {
1928
+ text: string;
1929
+ persist: boolean;
1930
+ } | null;
1931
+ syncFromMetadata: () => void;
1932
+ };
1933
+
1934
+ /**
1935
+ * Options for creating a markdown processor
1936
+ */
1937
+ type MarkdownProcessorOptions = {
1938
+ /** Marked parsing options */
1939
+ markedOptions?: AgentWidgetMarkdownOptions;
1940
+ /** Custom renderer overrides */
1941
+ renderer?: AgentWidgetMarkdownRendererOverrides;
1942
+ };
1943
+ /**
1944
+ * Creates a configured markdown processor with custom options and renderers.
1945
+ *
1946
+ * @param options - Configuration options for the markdown processor
1947
+ * @returns A function that converts markdown text to HTML
1948
+ *
1949
+ * @example
1950
+ * ```typescript
1951
+ * // Basic usage with defaults
1952
+ * const processor = createMarkdownProcessor();
1953
+ * const html = processor("# Hello World");
1954
+ *
1955
+ * // With custom options
1956
+ * const processor = createMarkdownProcessor({
1957
+ * markedOptions: { gfm: true, breaks: true },
1958
+ * renderer: {
1959
+ * link(token) {
1960
+ * return `<a href="${token.href}" target="_blank">${token.text}</a>`;
1961
+ * }
1962
+ * }
1963
+ * });
1964
+ * ```
1965
+ */
1966
+ declare const createMarkdownProcessor: (options?: MarkdownProcessorOptions) => (text: string) => string;
1967
+ /**
1968
+ * Creates a markdown processor from AgentWidgetMarkdownConfig.
1969
+ * This is a convenience function that maps the widget config to processor options.
1970
+ *
1971
+ * @param config - The markdown configuration from widget config
1972
+ * @returns A function that converts markdown text to HTML
1973
+ */
1974
+ declare const createMarkdownProcessorFromConfig: (config?: AgentWidgetMarkdownConfig) => (text: string) => string;
1975
+ /**
1976
+ * Basic markdown renderer using default settings.
1977
+ * Remember to sanitize the returned HTML if you render untrusted content in your host page.
1978
+ *
1979
+ * For custom configuration, use `createMarkdownProcessor()` or `createMarkdownProcessorFromConfig()`.
1980
+ */
1981
+ declare const markdownPostprocessor: (text: string) => string;
1982
+ /**
1983
+ * Escapes HTML entities. Used as the default safe renderer.
1984
+ */
1985
+ declare const escapeHtml: (text: string) => string;
1986
+ /**
1987
+ * Creates a directive postprocessor with custom markdown configuration.
1988
+ * Converts special directives (either `<Form type="init" />` or
1989
+ * `<Directive>{"component":"form","type":"init"}</Directive>`) into placeholder
1990
+ * elements that the widget upgrades after render. Remaining text is rendered as
1991
+ * Markdown with the provided configuration.
1992
+ *
1993
+ * @param markdownConfig - Optional markdown configuration
1994
+ * @returns A function that processes text with directives and markdown
1995
+ */
1996
+ declare const createDirectivePostprocessor: (markdownConfig?: AgentWidgetMarkdownConfig) => (text: string) => string;
1997
+ /**
1998
+ * Converts special directives (either `<Form type="init" />` or
1999
+ * `<Directive>{"component":"form","type":"init"}</Directive>`) into placeholder
2000
+ * elements that the widget upgrades after render. Remaining text is rendered as
2001
+ * Markdown using default settings.
2002
+ *
2003
+ * For custom markdown configuration, use `createDirectivePostprocessor()`.
2004
+ */
2005
+ declare const directivePostprocessor: (text: string) => string;
2006
+
2007
+ /**
2008
+ * Plain text parser - passes through text as-is without any parsing.
2009
+ * This is the default parser.
2010
+ */
2011
+ declare const createPlainTextParser: () => AgentWidgetStreamParser;
2012
+ /**
2013
+ * JSON parser using regex-based extraction.
2014
+ * Extracts the 'text' field from JSON responses using regex patterns.
2015
+ * This is a simpler regex-based alternative to createJsonStreamParser.
2016
+ * Less robust for complex/malformed JSON but has no external dependencies.
2017
+ */
2018
+ declare const createRegexJsonParser: () => AgentWidgetStreamParser;
2019
+ /**
2020
+ * JSON stream parser using partial-json library.
2021
+ * Extracts the 'text' field from JSON responses using the partial-json library,
2022
+ * which is specifically designed for parsing incomplete JSON from LLMs.
2023
+ * This is the recommended parser as it's more robust than regex.
2024
+ *
2025
+ * Library: https://github.com/promplate/partial-json-parser-js
2026
+ */
2027
+ declare const createJsonStreamParser: () => AgentWidgetStreamParser;
2028
+ /**
2029
+ * Flexible JSON stream parser that can extract text from various field names.
2030
+ * This parser looks for display text in multiple possible fields, making it
2031
+ * compatible with different JSON response formats.
2032
+ *
2033
+ * @param textExtractor Optional function to extract display text from parsed JSON.
2034
+ * If not provided, looks for common text fields.
2035
+ */
2036
+ declare const createFlexibleJsonStreamParser: (textExtractor?: (parsed: any) => string | null) => AgentWidgetStreamParser;
2037
+ /**
2038
+ * XML stream parser.
2039
+ * Extracts text from <text>...</text> tags in XML responses.
2040
+ */
2041
+ declare const createXmlParser: () => AgentWidgetStreamParser;
2042
+
2043
+ /**
2044
+ * Content Utilities
2045
+ *
2046
+ * Helper functions for working with multi-modal message content.
2047
+ */
2048
+
2049
+ /**
2050
+ * Normalize content to ContentPart[] format.
2051
+ * Converts string content to a single text content part.
2052
+ */
2053
+ declare function normalizeContent(content: MessageContent): ContentPart[];
2054
+ /**
2055
+ * Extract display text from content parts.
2056
+ * Concatenates all text parts into a single string.
2057
+ */
2058
+ declare function getDisplayText(content: MessageContent): string;
2059
+ /**
2060
+ * Check if content contains any images.
2061
+ */
2062
+ declare function hasImages(content: MessageContent): boolean;
2063
+ /**
2064
+ * Get all image parts from content.
2065
+ */
2066
+ declare function getImageParts(content: MessageContent): ImageContentPart[];
2067
+ /**
2068
+ * Create a text-only content part.
2069
+ */
2070
+ declare function createTextPart(text: string): TextContentPart;
2071
+ /**
2072
+ * Create an image content part from a base64 data URI or URL.
2073
+ *
2074
+ * @param image - Base64 data URI (data:image/...) or URL
2075
+ * @param options - Optional mimeType and alt text
2076
+ */
2077
+ declare function createImagePart(image: string, options?: {
2078
+ mimeType?: string;
2079
+ alt?: string;
2080
+ }): ImageContentPart;
2081
+ /**
2082
+ * Convert a File object to an image content part.
2083
+ * Reads the file and converts it to a base64 data URI.
2084
+ */
2085
+ declare function fileToImagePart(file: File): Promise<ImageContentPart>;
2086
+ /**
2087
+ * Validate that a file is an acceptable image type.
2088
+ *
2089
+ * @param file - The file to validate
2090
+ * @param acceptedTypes - Array of accepted MIME types (default: common image types)
2091
+ * @param maxSizeBytes - Maximum file size in bytes (default: 10MB)
2092
+ */
2093
+ declare function validateImageFile(file: File, acceptedTypes?: string[], maxSizeBytes?: number): {
2094
+ valid: boolean;
2095
+ error?: string;
2096
+ };
2097
+
2098
+ /**
2099
+ * Attachment Manager
2100
+ *
2101
+ * Handles file selection, validation, preview generation, and content part creation
2102
+ * for the composer attachment feature. Supports both images and documents.
2103
+ */
2104
+
2105
+ /**
2106
+ * Pending attachment with preview
2107
+ */
2108
+ interface PendingAttachment {
2109
+ id: string;
2110
+ file: File;
2111
+ previewUrl: string | null;
2112
+ contentPart: ImageContentPart | FileContentPart;
2113
+ }
2114
+ /**
2115
+ * Attachment manager configuration
2116
+ */
2117
+ interface AttachmentManagerConfig {
2118
+ allowedTypes?: string[];
2119
+ maxFileSize?: number;
2120
+ maxFiles?: number;
2121
+ onFileRejected?: (file: File, reason: "type" | "size" | "count") => void;
2122
+ onAttachmentsChange?: (attachments: PendingAttachment[]) => void;
2123
+ }
2124
+ /**
2125
+ * Creates and manages attachments for the composer
2126
+ */
2127
+ declare class AttachmentManager {
2128
+ private attachments;
2129
+ private config;
2130
+ private previewsContainer;
2131
+ constructor(config?: AttachmentManagerConfig);
2132
+ /**
2133
+ * Set the previews container element
2134
+ */
2135
+ setPreviewsContainer(container: HTMLElement | null): void;
2136
+ /**
2137
+ * Update the configuration (e.g., when allowed types change)
2138
+ */
2139
+ updateConfig(config: Partial<AttachmentManagerConfig>): void;
2140
+ /**
2141
+ * Get current attachments
2142
+ */
2143
+ getAttachments(): PendingAttachment[];
2144
+ /**
2145
+ * Get content parts for all attachments
2146
+ */
2147
+ getContentParts(): ContentPart[];
2148
+ /**
2149
+ * Check if there are any attachments
2150
+ */
2151
+ hasAttachments(): boolean;
2152
+ /**
2153
+ * Get the number of attachments
2154
+ */
2155
+ count(): number;
2156
+ /**
2157
+ * Handle file input change event
2158
+ */
2159
+ handleFileSelect(files: FileList | null): Promise<void>;
2160
+ /**
2161
+ * Remove an attachment by ID
2162
+ */
2163
+ removeAttachment(id: string): void;
2164
+ /**
2165
+ * Clear all attachments
2166
+ */
2167
+ clearAttachments(): void;
2168
+ /**
2169
+ * Render a preview for an attachment (image thumbnail or file icon)
2170
+ */
2171
+ private renderPreview;
2172
+ /**
2173
+ * Update the visibility of the previews container
2174
+ */
2175
+ private updatePreviewsVisibility;
2176
+ /**
2177
+ * Create an AttachmentManager from widget config
2178
+ */
2179
+ static fromConfig(config?: AgentWidgetAttachmentsConfig, onAttachmentsChange?: (attachments: PendingAttachment[]) => void): AttachmentManager;
2180
+ }
2181
+
2182
+ /**
2183
+ * Message ID utilities for client-side message tracking
2184
+ * Used for feedback integration with the Travrse API
2185
+ */
2186
+ /**
2187
+ * Generate a unique message ID for tracking
2188
+ * Format: msg_{timestamp_base36}_{random_8chars}
2189
+ */
2190
+ declare function generateMessageId(): string;
2191
+ /**
2192
+ * Generate a unique user message ID
2193
+ * Format: usr_{timestamp_base36}_{random_8chars}
2194
+ */
2195
+ declare function generateUserMessageId(): string;
2196
+ /**
2197
+ * Generate a unique assistant message ID
2198
+ * Format: ast_{timestamp_base36}_{random_8chars}
2199
+ */
2200
+ declare function generateAssistantMessageId(): string;
2201
+
2202
+ type CodeFormat = "esm" | "script-installer" | "script-manual" | "script-advanced" | "react-component" | "react-advanced";
2203
+ /**
2204
+ * Hook code templates for code generation.
2205
+ * Each hook can be provided as a string (code template) OR as an actual function.
2206
+ * Functions are automatically serialized via `.toString()`.
2207
+ *
2208
+ * IMPORTANT: When providing functions:
2209
+ * - Functions must be self-contained (no external variables/closures)
2210
+ * - External variables will be undefined when the generated code runs
2211
+ * - Use arrow functions or regular function expressions
2212
+ *
2213
+ * @example
2214
+ * ```typescript
2215
+ * // Both of these work:
2216
+ *
2217
+ * // As string:
2218
+ * { getHeaders: "async () => ({ 'Authorization': 'Bearer token' })" }
2219
+ *
2220
+ * // As function (recommended - better IDE support):
2221
+ * { getHeaders: async () => ({ 'Authorization': 'Bearer token' }) }
2222
+ * ```
2223
+ */
2224
+ type CodeGeneratorHooks = {
2225
+ /**
2226
+ * Custom getHeaders function.
2227
+ * Should return an object with header key-value pairs.
2228
+ *
2229
+ * @example
2230
+ * ```typescript
2231
+ * async () => ({ 'Authorization': `Bearer ${await getAuthToken()}` })
2232
+ * ```
2233
+ */
2234
+ getHeaders?: string | (() => Record<string, string> | Promise<Record<string, string>>);
2235
+ /**
2236
+ * Custom onFeedback callback for message actions.
2237
+ * Receives a feedback object with type, messageId, and message.
2238
+ *
2239
+ * @example
2240
+ * ```typescript
2241
+ * (feedback) => { console.log('Feedback:', feedback.type); }
2242
+ * ```
2243
+ */
2244
+ onFeedback?: string | ((feedback: {
2245
+ type: string;
2246
+ messageId: string;
2247
+ message: unknown;
2248
+ }) => void);
2249
+ /**
2250
+ * Custom onCopy callback for message actions.
2251
+ * Receives the message that was copied.
2252
+ *
2253
+ * @example
2254
+ * ```typescript
2255
+ * (message) => { analytics.track('message_copied', { id: message.id }); }
2256
+ * ```
2257
+ */
2258
+ onCopy?: string | ((message: unknown) => void);
2259
+ /**
2260
+ * Custom requestMiddleware function.
2261
+ * Receives { payload, config } context.
2262
+ *
2263
+ * @example
2264
+ * ```typescript
2265
+ * ({ payload }) => ({ ...payload, metadata: { pageUrl: window.location.href } })
2266
+ * ```
2267
+ */
2268
+ requestMiddleware?: string | ((context: {
2269
+ payload: unknown;
2270
+ config: unknown;
2271
+ }) => unknown);
2272
+ /**
2273
+ * Custom action handlers array.
2274
+ * Array of handler functions.
2275
+ *
2276
+ * @example
2277
+ * ```typescript
2278
+ * [
2279
+ * (action, context) => {
2280
+ * if (action.type === 'custom') {
2281
+ * return { handled: true };
2282
+ * }
2283
+ * }
2284
+ * ]
2285
+ * ```
2286
+ */
2287
+ actionHandlers?: string | Array<(action: unknown, context: unknown) => unknown>;
2288
+ /**
2289
+ * Custom action parsers array.
2290
+ * Array of parser functions.
2291
+ */
2292
+ actionParsers?: string | Array<(context: unknown) => unknown>;
2293
+ /**
2294
+ * Custom postprocessMessage function.
2295
+ * Receives { text, message, streaming, raw } context.
2296
+ * Will override the default markdownPostprocessor.
2297
+ *
2298
+ * @example
2299
+ * ```typescript
2300
+ * ({ text }) => customMarkdownProcessor(text)
2301
+ * ```
2302
+ */
2303
+ postprocessMessage?: string | ((context: {
2304
+ text: string;
2305
+ message?: unknown;
2306
+ streaming?: boolean;
2307
+ raw?: string;
2308
+ }) => string);
2309
+ /**
2310
+ * Custom context providers array.
2311
+ * Array of provider functions.
2312
+ */
2313
+ contextProviders?: string | Array<() => unknown>;
2314
+ /**
2315
+ * Custom stream parser factory.
2316
+ * Should be a function that returns a StreamParser.
2317
+ */
2318
+ streamParser?: string | (() => unknown);
2319
+ };
2320
+ /**
2321
+ * Options for code generation beyond format selection.
2322
+ */
2323
+ type CodeGeneratorOptions = {
2324
+ /**
2325
+ * Custom hook code to inject into the generated snippet.
2326
+ * Hooks are JavaScript/TypeScript code strings that will be
2327
+ * inserted at appropriate locations in the output.
2328
+ */
2329
+ hooks?: CodeGeneratorHooks;
2330
+ /**
2331
+ * Whether to include comments explaining each hook.
2332
+ * @default true
2333
+ */
2334
+ includeHookComments?: boolean;
2335
+ };
2336
+ declare function generateCodeSnippet(config: any, format?: CodeFormat, options?: CodeGeneratorOptions): string;
2337
+
2338
+ declare class PluginRegistry {
2339
+ private plugins;
2340
+ /**
2341
+ * Register a plugin
2342
+ */
2343
+ register(plugin: AgentWidgetPlugin): void;
2344
+ /**
2345
+ * Unregister a plugin
2346
+ */
2347
+ unregister(pluginId: string): void;
2348
+ /**
2349
+ * Get all plugins sorted by priority
2350
+ */
2351
+ getAll(): AgentWidgetPlugin[];
2352
+ /**
2353
+ * Get plugins for a specific instance (from config)
2354
+ * Merges instance plugins with globally registered plugins
2355
+ */
2356
+ getForInstance(instancePlugins?: AgentWidgetPlugin[]): AgentWidgetPlugin[];
2357
+ /**
2358
+ * Clear all plugins
2359
+ */
2360
+ clear(): void;
2361
+ }
2362
+ declare const pluginRegistry: PluginRegistry;
2363
+
2364
+ /**
2365
+ * Context provided to component renderers
2366
+ */
2367
+ interface ComponentContext {
2368
+ message: AgentWidgetMessage;
2369
+ config: AgentWidgetConfig;
2370
+ /**
2371
+ * Update component props during streaming
2372
+ */
2373
+ updateProps: (newProps: Record<string, unknown>) => void;
2374
+ }
2375
+ /**
2376
+ * Component renderer function signature
2377
+ */
2378
+ type ComponentRenderer = (props: Record<string, unknown>, context: ComponentContext) => HTMLElement;
2379
+ /**
2380
+ * Component registry for managing custom components
2381
+ */
2382
+ declare class ComponentRegistry {
2383
+ private components;
2384
+ /**
2385
+ * Register a custom component
2386
+ */
2387
+ register(name: string, renderer: ComponentRenderer): void;
2388
+ /**
2389
+ * Unregister a component
2390
+ */
2391
+ unregister(name: string): void;
2392
+ /**
2393
+ * Get a component renderer by name
2394
+ */
2395
+ get(name: string): ComponentRenderer | undefined;
2396
+ /**
2397
+ * Check if a component is registered
2398
+ */
2399
+ has(name: string): boolean;
2400
+ /**
2401
+ * Get all registered component names
2402
+ */
2403
+ getAllNames(): string[];
2404
+ /**
2405
+ * Clear all registered components
2406
+ */
2407
+ clear(): void;
2408
+ /**
2409
+ * Register multiple components at once
2410
+ */
2411
+ registerAll(components: Record<string, ComponentRenderer>): void;
2412
+ }
2413
+ /**
2414
+ * Global component registry instance
2415
+ */
2416
+ declare const componentRegistry: ComponentRegistry;
2417
+
2418
+ /**
2419
+ * Represents a component directive extracted from JSON
2420
+ */
2421
+ interface ComponentDirective {
2422
+ component: string;
2423
+ props: Record<string, unknown>;
2424
+ raw: string;
2425
+ }
2426
+ /**
2427
+ * Creates a parser that extracts component directives from JSON streams
2428
+ * This parser looks for objects with a "component" field and extracts
2429
+ * the component name and props incrementally as they stream in.
2430
+ */
2431
+ declare function createComponentStreamParser(): {
2432
+ /**
2433
+ * Get the currently extracted component directive
2434
+ */
2435
+ getExtractedDirective: () => ComponentDirective | null;
2436
+ /**
2437
+ * Process a chunk of JSON and extract component directive if present
2438
+ */
2439
+ processChunk: (accumulatedContent: string) => ComponentDirective | null;
2440
+ /**
2441
+ * Reset the parser state
2442
+ */
2443
+ reset: () => void;
2444
+ };
2445
+ /**
2446
+ * Type guard to check if an object is a component directive
2447
+ */
2448
+ declare function isComponentDirectiveType(obj: unknown): obj is ComponentDirective;
2449
+
2450
+ type MessageTransform = (context: {
2451
+ text: string;
2452
+ message: AgentWidgetMessage;
2453
+ streaming: boolean;
2454
+ raw?: string;
2455
+ }) => string;
2456
+ type MessageActionCallbacks = {
2457
+ onCopy?: (message: AgentWidgetMessage) => void;
2458
+ onFeedback?: (feedback: AgentWidgetMessageFeedback) => void;
2459
+ };
2460
+ declare const createTypingIndicator: () => HTMLElement;
2461
+ /**
2462
+ * Create message action buttons (copy, upvote, downvote)
2463
+ */
2464
+ declare const createMessageActions: (message: AgentWidgetMessage, actionsConfig: AgentWidgetMessageActionsConfig, callbacks?: MessageActionCallbacks) => HTMLElement;
2465
+ /**
2466
+ * Create standard message bubble
2467
+ * Supports layout configuration for avatars, timestamps, and visual presets
2468
+ */
2469
+ declare const createStandardBubble: (message: AgentWidgetMessage, transform: MessageTransform, layoutConfig?: AgentWidgetMessageLayoutConfig, actionsConfig?: AgentWidgetMessageActionsConfig, actionCallbacks?: MessageActionCallbacks) => HTMLElement;
2470
+ /**
2471
+ * Create bubble with custom renderer support
2472
+ * Uses custom renderer if provided in layout config, otherwise falls back to standard bubble
2473
+ */
2474
+ declare const createBubbleWithLayout: (message: AgentWidgetMessage, transform: MessageTransform, layoutConfig?: AgentWidgetMessageLayoutConfig, actionsConfig?: AgentWidgetMessageActionsConfig, actionCallbacks?: MessageActionCallbacks) => HTMLElement;
2475
+
2476
+ /**
2477
+ * Options for component middleware
2478
+ */
2479
+ interface ComponentMiddlewareOptions {
2480
+ config: AgentWidgetConfig;
2481
+ message: AgentWidgetMessage;
2482
+ transform: MessageTransform;
2483
+ onPropsUpdate?: (props: Record<string, unknown>) => void;
2484
+ }
2485
+ /**
2486
+ * Renders a component directive into an HTMLElement
2487
+ */
2488
+ declare function renderComponentDirective(directive: ComponentDirective, options: ComponentMiddlewareOptions): HTMLElement | null;
2489
+ /**
2490
+ * Creates middleware that processes component directives from streamed JSON
2491
+ */
2492
+ declare function createComponentMiddleware(): {
2493
+ /**
2494
+ * Process accumulated content and extract component directive
2495
+ */
2496
+ processChunk: (accumulatedContent: string) => ComponentDirective | null;
2497
+ /**
2498
+ * Get the currently extracted directive
2499
+ */
2500
+ getDirective: () => ComponentDirective | null;
2501
+ /**
2502
+ * Reset the parser state
2503
+ */
2504
+ reset: () => void;
2505
+ };
2506
+ /**
2507
+ * Checks if a message contains a component directive in its raw content
2508
+ */
2509
+ declare function hasComponentDirective(message: AgentWidgetMessage): boolean;
2510
+ /**
2511
+ * Extracts component directive from a complete message
2512
+ */
2513
+ declare function extractComponentDirectiveFromMessage(message: AgentWidgetMessage): ComponentDirective | null;
2514
+
2515
+ /**
2516
+ * Default light theme colors
2517
+ */
2518
+ declare const DEFAULT_LIGHT_THEME: AgentWidgetTheme;
2519
+ /**
2520
+ * Default dark theme colors
2521
+ */
2522
+ declare const DEFAULT_DARK_THEME: AgentWidgetTheme;
2523
+ /**
2524
+ * Default widget configuration
2525
+ * Single source of truth for all default values
2526
+ */
2527
+ declare const DEFAULT_WIDGET_CONFIG: Partial<AgentWidgetConfig>;
2528
+ /**
2529
+ * Helper to deep merge user config with defaults
2530
+ * This ensures all default values are present while allowing selective overrides
2531
+ */
2532
+ declare function mergeWithDefaults(config?: Partial<AgentWidgetConfig>): Partial<AgentWidgetConfig>;
2533
+
2534
+ interface HeaderElements {
2535
+ header: HTMLElement;
2536
+ iconHolder: HTMLElement;
2537
+ headerTitle: HTMLElement;
2538
+ headerSubtitle: HTMLElement;
2539
+ closeButton: HTMLButtonElement;
2540
+ closeButtonWrapper: HTMLElement;
2541
+ clearChatButton: HTMLButtonElement | null;
2542
+ clearChatButtonWrapper: HTMLElement | null;
2543
+ }
2544
+ interface HeaderBuildContext {
2545
+ config?: AgentWidgetConfig;
2546
+ showClose?: boolean;
2547
+ onClose?: () => void;
2548
+ onClearChat?: () => void;
2549
+ }
2550
+ /**
2551
+ * Build the header section of the panel.
2552
+ * Extracted for reuse and plugin override support.
2553
+ */
2554
+ declare const buildHeader: (context: HeaderBuildContext) => HeaderElements;
2555
+ /**
2556
+ * Attach header elements to the container, handling placement modes.
2557
+ */
2558
+ declare const attachHeaderToContainer: (container: HTMLElement, headerElements: HeaderElements, config?: AgentWidgetConfig) => void;
2559
+
2560
+ interface ComposerElements {
2561
+ footer: HTMLElement;
2562
+ suggestions: HTMLElement;
2563
+ composerForm: HTMLFormElement;
2564
+ textarea: HTMLTextAreaElement;
2565
+ sendButton: HTMLButtonElement;
2566
+ sendButtonWrapper: HTMLElement;
2567
+ micButton: HTMLButtonElement | null;
2568
+ micButtonWrapper: HTMLElement | null;
2569
+ statusText: HTMLElement;
2570
+ attachmentButton: HTMLButtonElement | null;
2571
+ attachmentButtonWrapper: HTMLElement | null;
2572
+ attachmentInput: HTMLInputElement | null;
2573
+ attachmentPreviewsContainer: HTMLElement | null;
2574
+ actionsRow: HTMLElement;
2575
+ leftActions: HTMLElement;
2576
+ rightActions: HTMLElement;
2577
+ }
2578
+ interface ComposerBuildContext {
2579
+ config?: AgentWidgetConfig;
2580
+ onSubmit?: (text: string) => void;
2581
+ disabled?: boolean;
2582
+ }
2583
+ /**
2584
+ * Build the composer/footer section of the panel.
2585
+ * Extracted for reuse and plugin override support.
2586
+ */
2587
+ declare const buildComposer: (context: ComposerBuildContext) => ComposerElements;
2588
+
2589
+ interface HeaderLayoutContext {
2590
+ config: AgentWidgetConfig;
2591
+ showClose?: boolean;
2592
+ onClose?: () => void;
2593
+ onClearChat?: () => void;
2594
+ }
2595
+ type HeaderLayoutRenderer = (context: HeaderLayoutContext) => HeaderElements;
2596
+ /**
2597
+ * Build default header layout
2598
+ * Full header with icon, title, subtitle, clear chat, and close button
2599
+ */
2600
+ declare const buildDefaultHeader: HeaderLayoutRenderer;
2601
+ /**
2602
+ * Build minimal header layout
2603
+ * Simplified layout with just title and close button
2604
+ */
2605
+ declare const buildMinimalHeader: HeaderLayoutRenderer;
2606
+ /**
2607
+ * Build expanded header layout
2608
+ * Full branding area with additional space for custom content
2609
+ */
2610
+ declare const buildExpandedHeader: HeaderLayoutRenderer;
2611
+ /**
2612
+ * Header layout registry
2613
+ * Maps layout names to their renderer functions
2614
+ */
2615
+ declare const headerLayouts: Record<string, HeaderLayoutRenderer>;
2616
+ /**
2617
+ * Get header layout renderer by name
2618
+ */
2619
+ declare const getHeaderLayout: (layoutName: string) => HeaderLayoutRenderer;
2620
+ /**
2621
+ * Build header based on layout configuration
2622
+ * Applies layout config settings to determine which layout to use
2623
+ */
2624
+ declare const buildHeaderWithLayout: (config: AgentWidgetConfig, layoutConfig?: AgentWidgetHeaderLayoutConfig, context?: Partial<HeaderLayoutContext>) => HeaderElements;
2625
+
2626
+ export { type AgentWidgetAttachmentsConfig, type AgentWidgetAvatarConfig, AgentWidgetClient, type AgentWidgetConfig, type AgentWidgetController, type AgentWidgetCustomFetch, type AgentWidgetEvent, type AgentWidgetFeatureFlags, type AgentWidgetHeaderLayoutConfig, type AgentWidgetHeadersFunction, type AgentWidgetInitHandle, type AgentWidgetInitOptions, type AgentWidgetLauncherConfig, type AgentWidgetLayoutConfig, type AgentWidgetMarkdownConfig, type AgentWidgetMarkdownOptions, type AgentWidgetMarkdownRendererOverrides, type AgentWidgetMessage, type AgentWidgetMessageActionsConfig, type AgentWidgetMessageFeedback, type AgentWidgetMessageLayoutConfig, type AgentWidgetPlugin, type AgentWidgetRequestPayload, type AgentWidgetSSEEventParser, type AgentWidgetSSEEventResult, AgentWidgetSession, type AgentWidgetSessionStatus, type AgentWidgetStreamParser, type AgentWidgetStreamParserResult, type AgentWidgetTheme, type AgentWidgetTimestampConfig, AttachmentManager, type AttachmentManagerConfig, type CSATFeedbackOptions, type ClientChatRequest, type ClientFeedbackRequest, type ClientFeedbackType, type ClientInitResponse, type ClientSession, type CodeFormat, type CodeGeneratorHooks, type CodeGeneratorOptions, type ComponentContext, type ComponentDirective, type ComponentRenderer, type ComposerBuildContext, type ComposerElements, type ContentPart, DEFAULT_DARK_THEME, DEFAULT_LIGHT_THEME, DEFAULT_WIDGET_CONFIG, type HeaderBuildContext, type HeaderElements, type HeaderLayoutContext, type HeaderLayoutRenderer, type HeaderRenderContext, type ImageContentPart, type MarkdownProcessorOptions, type MessageActionCallbacks, type MessageContent, type MessageRenderContext, type MessageTransform, type NPSFeedbackOptions, type PendingAttachment, type SlotRenderContext, type SlotRenderer, type TextContentPart, type WidgetLayoutSlot, attachHeaderToContainer, buildComposer, buildDefaultHeader, buildExpandedHeader, buildHeader, buildHeaderWithLayout, buildMinimalHeader, componentRegistry, createActionManager, createAgentExperience, createBubbleWithLayout, createCSATFeedback, createComponentMiddleware, createComponentStreamParser, createDirectivePostprocessor, createFlexibleJsonStreamParser, createImagePart, createJsonStreamParser, createLocalStorageAdapter, createMarkdownProcessor, createMarkdownProcessorFromConfig, createMessageActions, createNPSFeedback, createPlainTextParser, createRegexJsonParser, createStandardBubble, createTextPart, createTypingIndicator, createXmlParser, initAgentWidget as default, defaultActionHandlers, defaultJsonActionParser, directivePostprocessor, escapeHtml, extractComponentDirectiveFromMessage, fileToImagePart, generateAssistantMessageId, generateCodeSnippet, generateMessageId, generateUserMessageId, getDisplayText, getHeaderLayout, getImageParts, hasComponentDirective, hasImages, headerLayouts, initAgentWidget, isComponentDirectiveType, markdownPostprocessor, mergeWithDefaults, normalizeContent, pluginRegistry, renderComponentDirective, validateImageFile };