@admin-layout/demo-perplexity-browser 12.2.4-alpha.1 → 12.2.4-alpha.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/api/index.d.ts +2 -0
- package/lib/api/index.d.ts.map +1 -0
- package/lib/api/llm.d.ts +34 -0
- package/lib/api/llm.d.ts.map +1 -0
- package/lib/api/llm.js +200 -0
- package/lib/api/llm.js.map +1 -0
- package/lib/api/stt.d.ts +21 -0
- package/lib/api/stt.d.ts.map +1 -0
- package/lib/api/stt.js +111 -0
- package/lib/api/stt.js.map +1 -0
- package/lib/components/AttachmentPreview.d.ts +10 -0
- package/lib/components/AttachmentPreview.d.ts.map +1 -0
- package/lib/components/AttachmentPreview.js +50 -0
- package/lib/components/AttachmentPreview.js.map +1 -0
- package/lib/components/AudioRecorder.d.ts +8 -0
- package/lib/components/AudioRecorder.d.ts.map +1 -0
- package/lib/components/AudioRecorder.js +221 -0
- package/lib/components/AudioRecorder.js.map +1 -0
- package/lib/components/AudioVisualizer.d.ts +7 -0
- package/lib/components/AudioVisualizer.d.ts.map +1 -0
- package/lib/components/AudioVisualizer.js +116 -0
- package/lib/components/AudioVisualizer.js.map +1 -0
- package/lib/components/ChatFiles.d.ts +8 -0
- package/lib/components/ChatFiles.d.ts.map +1 -0
- package/lib/components/ChatFiles.js +76 -0
- package/lib/components/ChatFiles.js.map +1 -0
- package/lib/components/ChatScreenshot.d.ts +7 -0
- package/lib/components/ChatScreenshot.d.ts.map +1 -0
- package/lib/components/ChatScreenshot.js +113 -0
- package/lib/components/ChatScreenshot.js.map +1 -0
- package/lib/components/SearchBar.d.ts +9 -1
- package/lib/components/SearchBar.d.ts.map +1 -1
- package/lib/components/SearchBar.js +176 -240
- package/lib/components/SearchBar.js.map +1 -1
- package/lib/config/constants.d.ts +108 -0
- package/lib/config/constants.d.ts.map +1 -0
- package/lib/config/constants.js +115 -0
- package/lib/config/constants.js.map +1 -0
- package/lib/config/env.d.ts +20 -0
- package/lib/config/env.d.ts.map +1 -0
- package/lib/config/env.js +22 -0
- package/lib/config/env.js.map +1 -0
- package/lib/config/index.d.ts +4 -0
- package/lib/config/index.d.ts.map +1 -0
- package/lib/config/providers.d.ts +54 -0
- package/lib/config/providers.d.ts.map +1 -0
- package/lib/config/providers.js +65 -0
- package/lib/config/providers.js.map +1 -0
- package/lib/pages/home/HomePage.d.ts +1 -3
- package/lib/pages/home/HomePage.d.ts.map +1 -1
- package/lib/pages/home/HomePage.js +232 -4
- package/lib/pages/home/HomePage.js.map +1 -1
- package/lib/platform/browser.d.ts +18 -0
- package/lib/platform/browser.d.ts.map +1 -0
- package/lib/platform/context.d.ts +76 -0
- package/lib/platform/context.d.ts.map +1 -0
- package/lib/platform/index.d.ts +25 -0
- package/lib/platform/index.d.ts.map +1 -0
- package/lib/platform/tauri.d.ts +35 -0
- package/lib/platform/tauri.d.ts.map +1 -0
- package/lib/platform/types.d.ts +164 -0
- package/lib/platform/types.d.ts.map +1 -0
- package/lib/state/chatMachine.d.ts +554 -0
- package/lib/state/chatMachine.d.ts.map +1 -0
- package/lib/state/chatMachine.js +458 -0
- package/lib/state/chatMachine.js.map +1 -0
- package/lib/state/index.d.ts +3 -0
- package/lib/state/index.d.ts.map +1 -0
- package/lib/state/useChatWithPlatform.d.ts +43 -0
- package/lib/state/useChatWithPlatform.d.ts.map +1 -0
- package/lib/types/chat.d.ts +56 -0
- package/lib/types/chat.d.ts.map +1 -0
- package/lib/types/index.d.ts +2 -0
- package/lib/types/index.d.ts.map +1 -0
- package/lib/utils/chatStorage.d.ts +25 -0
- package/lib/utils/chatStorage.d.ts.map +1 -0
- package/lib/utils/chatStorage.js +17 -0
- package/lib/utils/chatStorage.js.map +1 -0
- package/package.json +9 -5
|
@@ -0,0 +1,458 @@
|
|
|
1
|
+
import {setup,fromCallback,assign}from'xstate';import {fetchLLMResponse}from'../api/llm.js';/**
|
|
2
|
+
* Chat State Machine
|
|
3
|
+
*
|
|
4
|
+
* This XState machine manages the chat state and is platform-agnostic.
|
|
5
|
+
* It uses injected platform services for storage, screenshot, and microphone
|
|
6
|
+
* functionality, allowing the same machine to work on both browser and Tauri desktop.
|
|
7
|
+
*
|
|
8
|
+
* Architecture:
|
|
9
|
+
* - The machine itself is pure and doesn't import any platform-specific code
|
|
10
|
+
* - Platform services are passed via the machine's input or context factory
|
|
11
|
+
* - Actions use the services from context for persistence
|
|
12
|
+
*/
|
|
13
|
+
// ============================================================================
|
|
14
|
+
// Helper Functions
|
|
15
|
+
// ============================================================================
|
|
16
|
+
/**
|
|
17
|
+
* Convert messages to storage format (strips heavy data)
|
|
18
|
+
*/
|
|
19
|
+
function messagesToStoredFormat(messages) {
|
|
20
|
+
return messages.map(msg => ({
|
|
21
|
+
role: msg.role,
|
|
22
|
+
content: msg.content,
|
|
23
|
+
attachments: msg.attachments?.map(att => ({
|
|
24
|
+
id: att.id,
|
|
25
|
+
name: att.name,
|
|
26
|
+
type: att.type
|
|
27
|
+
}))
|
|
28
|
+
}));
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Persist messages using the storage service (fire-and-forget)
|
|
32
|
+
*/
|
|
33
|
+
function persistMessages(storageService, messages) {
|
|
34
|
+
if (!storageService) {
|
|
35
|
+
console.warn('💾 [MACHINE] No storage service available, skipping persistence');
|
|
36
|
+
return;
|
|
37
|
+
}
|
|
38
|
+
const storedMessages = messagesToStoredFormat(messages);
|
|
39
|
+
storageService.saveChat(storedMessages).catch(error => {
|
|
40
|
+
console.error('💾 [MACHINE] Error persisting messages:', error);
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Clear chat using the storage service
|
|
45
|
+
*/
|
|
46
|
+
function clearStoredChat(storageService) {
|
|
47
|
+
if (!storageService) {
|
|
48
|
+
console.warn('💾 [MACHINE] No storage service available, skipping clear');
|
|
49
|
+
return;
|
|
50
|
+
}
|
|
51
|
+
storageService.clearChat().catch(error => {
|
|
52
|
+
console.error('💾 [MACHINE] Error clearing chat:', error);
|
|
53
|
+
});
|
|
54
|
+
}
|
|
55
|
+
// ============================================================================
|
|
56
|
+
// Machine Definition
|
|
57
|
+
// ============================================================================
|
|
58
|
+
/**
|
|
59
|
+
* Create the chat machine with optional platform services
|
|
60
|
+
* @param platformServices - Optional platform services for storage, etc.
|
|
61
|
+
*/
|
|
62
|
+
function createChatMachine(platformServices) {
|
|
63
|
+
return setup({
|
|
64
|
+
types: {
|
|
65
|
+
context: {},
|
|
66
|
+
events: {},
|
|
67
|
+
input: {}
|
|
68
|
+
},
|
|
69
|
+
actors: {
|
|
70
|
+
sendToAI: fromCallback(({
|
|
71
|
+
input,
|
|
72
|
+
sendBack
|
|
73
|
+
}) => {
|
|
74
|
+
const {
|
|
75
|
+
messages,
|
|
76
|
+
systemPrompt,
|
|
77
|
+
screenshot,
|
|
78
|
+
attachedFiles
|
|
79
|
+
} = input;
|
|
80
|
+
// Extract images from screenshot and attached files
|
|
81
|
+
const imagesBase64 = [];
|
|
82
|
+
let documentContent = '';
|
|
83
|
+
// Add screenshot if present
|
|
84
|
+
if (screenshot) {
|
|
85
|
+
// Remove data URL prefix if present
|
|
86
|
+
const base64 = screenshot.includes('base64,') ? screenshot.split('base64,')[1] : screenshot;
|
|
87
|
+
imagesBase64.push(base64);
|
|
88
|
+
}
|
|
89
|
+
// Process attached files
|
|
90
|
+
if (attachedFiles && attachedFiles.length > 0) {
|
|
91
|
+
console.log('📎 [MACHINE] Processing attached files:', attachedFiles.length);
|
|
92
|
+
for (const file of attachedFiles) {
|
|
93
|
+
// Check if it's an image by looking at the dataUrl mime type
|
|
94
|
+
const isImage = file.dataUrl?.startsWith('data:image/') || file.type?.startsWith('image/');
|
|
95
|
+
const isTextFile = file.dataUrl?.startsWith('data:text/') || file.name?.endsWith('.txt') || file.name?.endsWith('.md') || file.name?.endsWith('.json') || file.name?.endsWith('.csv');
|
|
96
|
+
if (isImage) {
|
|
97
|
+
// Add to images array for vision API
|
|
98
|
+
const base64 = file.base64 || (file.dataUrl?.includes('base64,') ? file.dataUrl.split('base64,')[1] : undefined);
|
|
99
|
+
if (base64) {
|
|
100
|
+
imagesBase64.push(base64);
|
|
101
|
+
console.log('📎 [MACHINE] Added image to vision API');
|
|
102
|
+
}
|
|
103
|
+
} else if (isTextFile || file.dataUrl) {
|
|
104
|
+
// Decode text files and add to message content
|
|
105
|
+
try {
|
|
106
|
+
const base64Content = file.base64 || (file.dataUrl?.includes('base64,') ? file.dataUrl.split('base64,')[1] : undefined);
|
|
107
|
+
if (base64Content) {
|
|
108
|
+
const textContent = atob(base64Content);
|
|
109
|
+
documentContent += `\n\n--- Content of ${file.name} ---\n${textContent}\n--- End of ${file.name} ---\n`;
|
|
110
|
+
console.log('📎 [MACHINE] Added text content from:', file.name, 'length:', textContent.length);
|
|
111
|
+
}
|
|
112
|
+
} catch (error) {
|
|
113
|
+
console.error('Error decoding file:', file.name, error);
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
// Convert messages to the format expected by fetchLLMResponse
|
|
119
|
+
// If we have document content, append it to the last user message
|
|
120
|
+
const chatMessages = messages.map((msg, index) => {
|
|
121
|
+
if (msg.role === 'user' && index === messages.length - 1 && documentContent) {
|
|
122
|
+
return {
|
|
123
|
+
role: msg.role,
|
|
124
|
+
content: msg.content + documentContent
|
|
125
|
+
};
|
|
126
|
+
}
|
|
127
|
+
return {
|
|
128
|
+
role: msg.role,
|
|
129
|
+
content: msg.content
|
|
130
|
+
};
|
|
131
|
+
});
|
|
132
|
+
console.log('🤖 [MACHINE] Sending to AI:', {
|
|
133
|
+
messageCount: chatMessages.length,
|
|
134
|
+
hasSystemPrompt: !!systemPrompt,
|
|
135
|
+
imageCount: imagesBase64.length,
|
|
136
|
+
hasDocuments: !!documentContent
|
|
137
|
+
});
|
|
138
|
+
// Stream response with batched UI updates for performance
|
|
139
|
+
// Using requestAnimationFrame to batch chunks and prevent main thread blocking
|
|
140
|
+
(async () => {
|
|
141
|
+
let fullResponse = '';
|
|
142
|
+
let pendingChunks = '';
|
|
143
|
+
let rafScheduled = false;
|
|
144
|
+
const flushChunks = () => {
|
|
145
|
+
if (pendingChunks) {
|
|
146
|
+
sendBack({
|
|
147
|
+
type: 'STREAM_CHUNK',
|
|
148
|
+
chunk: pendingChunks
|
|
149
|
+
});
|
|
150
|
+
pendingChunks = '';
|
|
151
|
+
}
|
|
152
|
+
rafScheduled = false;
|
|
153
|
+
};
|
|
154
|
+
try {
|
|
155
|
+
for await (const chunk of fetchLLMResponse({
|
|
156
|
+
messages: chatMessages,
|
|
157
|
+
systemPrompt: systemPrompt || undefined,
|
|
158
|
+
imagesBase64: imagesBase64.length > 0 ? imagesBase64 : undefined,
|
|
159
|
+
stream: true
|
|
160
|
+
})) {
|
|
161
|
+
fullResponse += chunk;
|
|
162
|
+
pendingChunks += chunk;
|
|
163
|
+
// Batch updates using requestAnimationFrame (~60fps)
|
|
164
|
+
// This prevents blocking the main thread with rapid state updates
|
|
165
|
+
if (!rafScheduled) {
|
|
166
|
+
rafScheduled = true;
|
|
167
|
+
requestAnimationFrame(flushChunks);
|
|
168
|
+
}
|
|
169
|
+
}
|
|
170
|
+
// Flush any remaining chunks before completion
|
|
171
|
+
if (pendingChunks) {
|
|
172
|
+
sendBack({
|
|
173
|
+
type: 'STREAM_CHUNK',
|
|
174
|
+
chunk: pendingChunks
|
|
175
|
+
});
|
|
176
|
+
}
|
|
177
|
+
// Send completion event with full response
|
|
178
|
+
sendBack({
|
|
179
|
+
type: 'STREAM_COMPLETE',
|
|
180
|
+
response: fullResponse
|
|
181
|
+
});
|
|
182
|
+
} catch (error) {
|
|
183
|
+
sendBack({
|
|
184
|
+
type: 'STREAM_ERROR',
|
|
185
|
+
error: error instanceof Error ? error.message : String(error)
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
})();
|
|
189
|
+
// Cleanup function
|
|
190
|
+
return () => {
|
|
191
|
+
// Any cleanup if needed
|
|
192
|
+
};
|
|
193
|
+
})
|
|
194
|
+
},
|
|
195
|
+
actions: {
|
|
196
|
+
persistMessages: ({
|
|
197
|
+
context
|
|
198
|
+
}) => {
|
|
199
|
+
persistMessages(context.storageService, context.messages);
|
|
200
|
+
},
|
|
201
|
+
clearStoredChat: ({
|
|
202
|
+
context
|
|
203
|
+
}) => {
|
|
204
|
+
clearStoredChat(context.storageService);
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
}).createMachine({
|
|
208
|
+
id: 'chat',
|
|
209
|
+
initial: 'idle',
|
|
210
|
+
context: ({
|
|
211
|
+
input
|
|
212
|
+
}) => ({
|
|
213
|
+
storageService: input?.storageService ?? platformServices?.storage ?? null,
|
|
214
|
+
systemPrompt: '',
|
|
215
|
+
screenshot: null,
|
|
216
|
+
attachedFiles: [],
|
|
217
|
+
messages: [],
|
|
218
|
+
response: '',
|
|
219
|
+
isStreaming: false,
|
|
220
|
+
error: null
|
|
221
|
+
}),
|
|
222
|
+
states: {
|
|
223
|
+
idle: {
|
|
224
|
+
on: {
|
|
225
|
+
LOAD_MESSAGES: {
|
|
226
|
+
actions: assign({
|
|
227
|
+
messages: ({
|
|
228
|
+
event
|
|
229
|
+
}) => event.messages
|
|
230
|
+
})
|
|
231
|
+
},
|
|
232
|
+
INPUT_SYSTEMPROMPT: {
|
|
233
|
+
actions: assign({
|
|
234
|
+
systemPrompt: ({
|
|
235
|
+
event
|
|
236
|
+
}) => event.value
|
|
237
|
+
})
|
|
238
|
+
},
|
|
239
|
+
INPUT_SCREENSHOT: {
|
|
240
|
+
actions: assign({
|
|
241
|
+
screenshot: ({
|
|
242
|
+
event
|
|
243
|
+
}) => event.value
|
|
244
|
+
})
|
|
245
|
+
},
|
|
246
|
+
SCREENSHOT_CAPTURED: {
|
|
247
|
+
actions: assign({
|
|
248
|
+
screenshot: ({
|
|
249
|
+
event
|
|
250
|
+
}) => event.dataUrl
|
|
251
|
+
})
|
|
252
|
+
},
|
|
253
|
+
INPUT_FILES: {
|
|
254
|
+
actions: assign({
|
|
255
|
+
attachedFiles: ({
|
|
256
|
+
event
|
|
257
|
+
}) => event.value
|
|
258
|
+
})
|
|
259
|
+
},
|
|
260
|
+
SEND_MESSAGE: {
|
|
261
|
+
target: 'sending',
|
|
262
|
+
actions: assign({
|
|
263
|
+
messages: ({
|
|
264
|
+
context,
|
|
265
|
+
event
|
|
266
|
+
}) => {
|
|
267
|
+
// Create user message with attachments if present
|
|
268
|
+
const userMessage = {
|
|
269
|
+
role: 'user',
|
|
270
|
+
content: event.content
|
|
271
|
+
};
|
|
272
|
+
// Add display attachments from event
|
|
273
|
+
if (event.attachments && event.attachments.length > 0) {
|
|
274
|
+
userMessage.attachments = event.attachments;
|
|
275
|
+
}
|
|
276
|
+
// Add attachments to message if present
|
|
277
|
+
const allAttachments = [...context.attachedFiles];
|
|
278
|
+
// Add screenshot as attachment if present
|
|
279
|
+
if (context.screenshot) {
|
|
280
|
+
const screenshotFile = {
|
|
281
|
+
id: `screenshot_${Date.now()}`,
|
|
282
|
+
name: 'screenshot.png',
|
|
283
|
+
type: 'image/png',
|
|
284
|
+
base64: context.screenshot.includes('base64,') ? context.screenshot.split('base64,')[1] : context.screenshot,
|
|
285
|
+
dataUrl: context.screenshot,
|
|
286
|
+
size: 0 // Size not available for screenshot
|
|
287
|
+
};
|
|
288
|
+
allAttachments.push(screenshotFile);
|
|
289
|
+
}
|
|
290
|
+
// Convert event attachments to AttachedFile format for API
|
|
291
|
+
if (event.attachments) {
|
|
292
|
+
for (const attachment of event.attachments) {
|
|
293
|
+
if (attachment.dataUrl) {
|
|
294
|
+
// Extract MIME type from data URL (e.g., "data:image/png;base64,..." -> "image/png")
|
|
295
|
+
const mimeMatch = attachment.dataUrl.match(/^data:([^;,]+)/);
|
|
296
|
+
const mimeType = mimeMatch ? mimeMatch[1] : 'application/octet-stream';
|
|
297
|
+
const attachedFile = {
|
|
298
|
+
id: attachment.id,
|
|
299
|
+
name: attachment.name,
|
|
300
|
+
type: mimeType,
|
|
301
|
+
dataUrl: attachment.dataUrl,
|
|
302
|
+
base64: attachment.dataUrl.includes('base64,') ? attachment.dataUrl.split('base64,')[1] : undefined
|
|
303
|
+
};
|
|
304
|
+
allAttachments.push(attachedFile);
|
|
305
|
+
}
|
|
306
|
+
}
|
|
307
|
+
}
|
|
308
|
+
if (allAttachments.length > 0) {
|
|
309
|
+
userMessage.attachedFiles = allAttachments;
|
|
310
|
+
}
|
|
311
|
+
return [...context.messages, userMessage];
|
|
312
|
+
},
|
|
313
|
+
// Store attached files for the API call
|
|
314
|
+
attachedFiles: ({
|
|
315
|
+
context,
|
|
316
|
+
event
|
|
317
|
+
}) => {
|
|
318
|
+
const allAttachments = [];
|
|
319
|
+
// Add screenshot if present
|
|
320
|
+
if (context.screenshot) {
|
|
321
|
+
allAttachments.push({
|
|
322
|
+
id: `screenshot_${Date.now()}`,
|
|
323
|
+
name: 'screenshot.png',
|
|
324
|
+
type: 'image/png',
|
|
325
|
+
base64: context.screenshot.includes('base64,') ? context.screenshot.split('base64,')[1] : context.screenshot,
|
|
326
|
+
dataUrl: context.screenshot
|
|
327
|
+
});
|
|
328
|
+
}
|
|
329
|
+
// Convert event attachments
|
|
330
|
+
if (event.attachments) {
|
|
331
|
+
for (const attachment of event.attachments) {
|
|
332
|
+
if (attachment.dataUrl) {
|
|
333
|
+
// Extract MIME type from data URL
|
|
334
|
+
const mimeMatch = attachment.dataUrl.match(/^data:([^;,]+)/);
|
|
335
|
+
const mimeType = mimeMatch ? mimeMatch[1] : 'application/octet-stream';
|
|
336
|
+
allAttachments.push({
|
|
337
|
+
id: attachment.id,
|
|
338
|
+
name: attachment.name,
|
|
339
|
+
type: mimeType,
|
|
340
|
+
dataUrl: attachment.dataUrl,
|
|
341
|
+
base64: attachment.dataUrl.includes('base64,') ? attachment.dataUrl.split('base64,')[1] : undefined
|
|
342
|
+
});
|
|
343
|
+
}
|
|
344
|
+
}
|
|
345
|
+
}
|
|
346
|
+
return allAttachments;
|
|
347
|
+
}
|
|
348
|
+
})
|
|
349
|
+
},
|
|
350
|
+
CLEAR_MESSAGES: {
|
|
351
|
+
actions: [assign({
|
|
352
|
+
messages: [],
|
|
353
|
+
response: '',
|
|
354
|
+
error: null,
|
|
355
|
+
screenshot: null,
|
|
356
|
+
attachedFiles: []
|
|
357
|
+
}), 'clearStoredChat']
|
|
358
|
+
},
|
|
359
|
+
CLEAR_ATTACHMENTS: {
|
|
360
|
+
actions: assign({
|
|
361
|
+
screenshot: null,
|
|
362
|
+
attachedFiles: []
|
|
363
|
+
})
|
|
364
|
+
}
|
|
365
|
+
}
|
|
366
|
+
},
|
|
367
|
+
sending: {
|
|
368
|
+
entry: assign({
|
|
369
|
+
isStreaming: true,
|
|
370
|
+
error: null,
|
|
371
|
+
response: '' // Clear response before streaming starts
|
|
372
|
+
}),
|
|
373
|
+
invoke: {
|
|
374
|
+
src: 'sendToAI',
|
|
375
|
+
input: ({
|
|
376
|
+
context
|
|
377
|
+
}) => context
|
|
378
|
+
},
|
|
379
|
+
on: {
|
|
380
|
+
STREAM_CHUNK: {
|
|
381
|
+
actions: assign({
|
|
382
|
+
response: ({
|
|
383
|
+
context,
|
|
384
|
+
event
|
|
385
|
+
}) => context.response + event.chunk
|
|
386
|
+
})
|
|
387
|
+
},
|
|
388
|
+
STREAM_COMPLETE: {
|
|
389
|
+
target: 'idle',
|
|
390
|
+
actions: [assign({
|
|
391
|
+
response: ({
|
|
392
|
+
event
|
|
393
|
+
}) => event.response,
|
|
394
|
+
messages: ({
|
|
395
|
+
context,
|
|
396
|
+
event
|
|
397
|
+
}) => {
|
|
398
|
+
const updatedMessages = [...context.messages, {
|
|
399
|
+
role: 'assistant',
|
|
400
|
+
content: event.response
|
|
401
|
+
}];
|
|
402
|
+
// Persist immediately after updating messages
|
|
403
|
+
persistMessages(context.storageService, updatedMessages);
|
|
404
|
+
return updatedMessages;
|
|
405
|
+
},
|
|
406
|
+
isStreaming: false,
|
|
407
|
+
screenshot: null,
|
|
408
|
+
attachedFiles: []
|
|
409
|
+
})]
|
|
410
|
+
},
|
|
411
|
+
STREAM_ERROR: {
|
|
412
|
+
target: 'error',
|
|
413
|
+
actions: assign({
|
|
414
|
+
error: ({
|
|
415
|
+
event
|
|
416
|
+
}) => event.error,
|
|
417
|
+
isStreaming: false
|
|
418
|
+
})
|
|
419
|
+
}
|
|
420
|
+
}
|
|
421
|
+
},
|
|
422
|
+
error: {
|
|
423
|
+
on: {
|
|
424
|
+
RETRY: 'sending',
|
|
425
|
+
CLEAR_MESSAGES: {
|
|
426
|
+
target: 'idle',
|
|
427
|
+
actions: [assign({
|
|
428
|
+
messages: [],
|
|
429
|
+
response: '',
|
|
430
|
+
error: null
|
|
431
|
+
}), 'clearStoredChat']
|
|
432
|
+
},
|
|
433
|
+
SEND_MESSAGE: {
|
|
434
|
+
target: 'sending',
|
|
435
|
+
actions: assign({
|
|
436
|
+
messages: ({
|
|
437
|
+
context,
|
|
438
|
+
event
|
|
439
|
+
}) => {
|
|
440
|
+
const userMessage = {
|
|
441
|
+
role: 'user',
|
|
442
|
+
content: event.content
|
|
443
|
+
};
|
|
444
|
+
return [...context.messages, userMessage];
|
|
445
|
+
},
|
|
446
|
+
error: null
|
|
447
|
+
})
|
|
448
|
+
}
|
|
449
|
+
}
|
|
450
|
+
}
|
|
451
|
+
}
|
|
452
|
+
});
|
|
453
|
+
}
|
|
454
|
+
/**
|
|
455
|
+
* Default chat machine (backward compatible - no platform services injected)
|
|
456
|
+
* For new code, use createChatMachine(platformServices) instead
|
|
457
|
+
*/
|
|
458
|
+
const chatMachine = createChatMachine();export{chatMachine,createChatMachine};//# sourceMappingURL=chatMachine.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chatMachine.js","sources":["../../src/state/chatMachine.ts"],"sourcesContent":[null],"names":[],"mappings":"4FAAA;;;;;;;;;;;AAWG;AA2EH;AACA;AACA;AAEA;;AAEG;AACH,SAAS,sBAAsB,CAAC,QAAmB,EAAA;SAC/C,QAAO,CAAA,GAAS,CAAA,GAAK,KAAK;QACtB,EAAA,GAAI,CAAE,IAAI;WACV,EAAA,GAAO,CAAE,OAAI;AACb,IAAA,WAAA,EAAA,GAAW,CAAE,WAAI,EAAA,GAAW,CAAE,GAAG,KAAK;aAClC,CAAE,EAAE;YACJ,GAAA,CAAI,IAAE;YACN,GAAA,CAAI;AACP,KAAA,CAAA;AACJ,GAAA,CAAA,CAAA;AACL;AAEA;;AAEG;AACH,SAAS,eAAe,CAAC,cAAsC,EAAE,QAAmB,EAAA;MAChF,CAAA,cAAK,EAAc;AACf,IAAA,OAAA,CAAA,IAAQ,CAAA,iEAAK,CAAA;;;AAIjB,EAAA,MAAA,iBAAoB,sBAAG,CAAA,QAAuB,CAAA;gBAC9C,CAAA,QAAe,CAAA,cAAS,CAAA,CAAc,KAAE,CAAA,KAAO,IAAK;AAChD,IAAA,OAAA,CAAA,KAAQ,CAAA,gDAAiD,CAAA;AAC7D,EAAA,CAAA,CAAA;AACJ;AAEA;;AAEG;AACH,SAAS,eAAe,CAAC,cAAsC,EAAA;MAC3D,CAAA,cAAK,EAAc;AACf,IAAA,OAAA,CAAA,IAAQ,CAAA,2DAAK,CAAA;;;gBAIjB,CAAA,WAAwB,CAAA,WAAU,IAAK;AACnC,IAAA,OAAA,CAAA,KAAQ,CAAA,0CAA2C,CAAA;AACvD,EAAA,CAAA,CAAA;AACJ;AAEA;AACA;AACA;AAEA;;;AAGG;AACG,SAAU,iBAAiB,CAAC,gBAAoC,EAAA;AAClE,EAAA,OAAA;AACI,IAAA,KAAA,EAAA;AACI,MAAA,OAAA,EAAA,EAAA;AACA,MAAA,MAAA,EAAA,EAAA;AACA,MAAA,KAAA,EAAA;AACH,KAAA;AACD,IAAA,MAAA,EAAA;cACI,EAAA,YAAU,CAAA,CAAA;;;;;kBAQF;sBACI;oBACA;;AAEA,SAAA,GAAA,KAAA;;0BAGJ,GAAA,EAAA;2BACI,GAAA,EAAA;;AAEA,QAAA,IAAA,UAAA,EAAA;;AAEI,UAAA,MAAA,MAAA,GAAA,mBAAoB,CAAC,SAAS,cAAW,CAAA,KAAA,CAAA,SAAkB,CAAA,CAAA,CAAI,CAAC,GAAA;2BAChE,CAAA,MAAM,CAAA;AAEF,QAAA;AACA;AACA,QAAA,IAAA,aAAA,IAAA,aAAW,CAAA,YAAgB;AAC3B,UAAA,OAAA,CAAA,GAAA,CAAA,yCAA4B,EAAA,aAAA,CAAA,MAAA,CAAA;yBAEhC,IAAI,aAAU,EAAA;;AAEV,YAAA,MAAA,OAAA,GAAA,IAAA,CAAA,OAAY,EAAA,UACH,CAAA,aAAM,CAAA,IAAA,IAAA,CAAA,IAAA,EAAA,UAAA,CAAA,QAAA,CAAA;mCACV,CAAA,OAAK,EAAO,UAAU,CAAC,YAAY,CAAC,IAAI,IAAC,CAAA,IAAQ,EAAA,QAAM,CAAA,MAAW,CAAC,IAAI,IAAA,CAAA,IAAS,EAAE,QAAA,CAAA,KAAA,CAAA,IAAA,IAAA,CAAA,IAAA,EAAA,QAAA,CAAA,OAAA,CAAA,IAAA,IAAA,CAAA,IAAA,EAAA,QAAA,CAAA,MAAA,CAAA;;AAEnF;AACA,cAAA,MAAA,MAAA,GAAA,IAAA,CAAA,MAAQ,KAAI,IAAA,CAAA,OAAA,EAAA,QAAA,CAAA,SAAA,CAAA,GAAA,IAAyC,CAAC,OAAA,CAAA,KAAA,CAAA,SAAA,CAAA,CAAA,CAAA,CAAA,GAAA,SAAA,CAAA;;4BAE7D,CAAA,IAAA,CAAA,MAAA,CAAA;AAAM,gBAAA,OAAA,CAAA,GAAA,CAAA,wCAAiC,CAAA;;AAEpC,YAAA,CAAA,MAAA,IAAA,UAAK,IAAA,IAAA,CAAA,OAAA,EAAA;AACD;AAEI,cAAA,IAAA;0CACM,CAAA,MAAK,KAAO,IAAC,CAAA,OAAM,EAAA,QAAa,CAAA,SAAA,CAAA,GAAA,IAAA,CAAA,OAAA,CAAA,KAAA,CAAA,SAAA,CAAA,CAAA,CAAA,CAAA,GAAA,SAAA,CAAA;;mCAE1C,GAAI,IAAA,CAAA,aAAgB,CAAA;AAChB,kBAAA,eAAA,IAAA,CAAA,mBAAoB,EAAA,IAAK,CAAA,IAAA,CAAA,MAAc,EAAC,WAAA,CAAA,aAAA,EAAA,IAAA,CAAA,IAAA,CAAA,MAAA,CAAA;AACxC,kBAAA,OAAA,CAAA,GAAA,CAAA,uCAAmB,EAAA,IAAA,CAAA,IAAsB,EAAK,SAAI,EAAA,WAAS,CAAA,MAAW,CAAA;AACtE,gBAAA;;6BAOP,CAAA,sBAAA,EAAA,IAAA,CAAA,IAAA,EAAA,KAAA,CAAA;;;;;;;0BAOb,GAAA,QAAA,CAAA,GAAA,CAAA,CAAA,GAAA,EAAA,KAAA,KAAA;iBACA,CAAA,IAAA,KAAA,MAAA,IAAA,KAAA,KAAA,QAAA,CAAA,MAAA,GAAA,CAAA,IAAA,eAAkE,EAAA;mBAClE;AACI,cAAA,IAAA,EAAA,GAAA,CAAI,IAAI;0BACJ,CAAA,OAAO,GAAA;;AAEH,UAAA;;qBAEP,CAAA,IAAA;qBACD,GAAA,CAAA;;;iDAGE,EAAA;AACN,UAAA,YAAG,EAAA,YAAA,CAAA,MAAA;AAEH,UAAA,eAAQ,EAAG,CAAC,CAAA,YAAA;oBACR,EAAA,YAAc,CAAA,MAAA;sBACd,EAAA,CAAA,CAAA;;;AAGH;qBAED;0BACA,GAAA,EAAA;2BACU,GAAE,EAAA;0BACJ,GAAA,KAAA;2BACA,GAAA,MAAA;6BACA,EAAA;sBAEJ,CAAA;oCACQ;;;2BAGH,GAAA,EAAA;;AAEL,YAAA,YAAE,GAAA,KAAA;AAEF,UAAA,CAAA;AACI,UAAA,IAAA;AACI,YAAA,WAAA,MAAA,KAAA,IAAU,gBAAY,CAAA;oCACtB;AACA,cAAA,YAAA,EAAA,YAAY,IAAE,SAAA;AACd,cAAA,YAAA,EAAA,YAAY,CAAA,MAAA,GAAA,CAAA,GAAA,YAAA,GAAA,SAAA;AACf,cAAA,MAAA,EAAA;;8BAEG,KAAA;+BAEA,KAAA;;;iCAGI;mCACA;qCACH,CAAA,WAAA,CAAA;;;;6BAKD,EAAA;;oCAGJ;;;;AAGA;AACI,YAAA,QAAA,CAAA;AACA,cAAA,IAAA,EAAA,iBAAO;AACV,cAAA,QAAA,EAAA;;wBAEJ,EAAA;oBAEL,CAAA;AACA,cAAA,IAAA,EAAA,cAAY;qBACR,KAAA,YAAA,KAAA,GAAwB,KAAA,CAAA,OAAA,GAAA,MAAA,CAAA,KAAA;AAC5B,aAAA,CAAA;AACJ,UAAA;AAEP,QAAA,CAAA,GAAA;AACD;AACI,QAAA,OAAA,MAAA;;;AAGA,MAAA,CAAA;AACI,KAAA;aACH;AACJ,MAAA,eAAA,EAAA,CAAA;;AAED,OAAA,KAAI;AACJ,QAAA,eAAe,CAAA,OAAA,CAAA,cAAA,EAAA,OAAA,CAAA,QAAA,CAAA;;qBAEX,EAAA,CAAA;AACA,QAAA;AACA,OAAA,KAAA;AACA,QAAA,eAAA,CAAA,OAAiB,CAAA,cAAA,CAAA;AACjB,MAAA;AACA;AACA,GAAA,CAAA,CAAA,aAAA,CAAA;AACA,IAAA,EAAA,EAAA,MAAA;WACF,EAAA,MAAA;AACF,IAAA,OAAA,EAAA,CAAM;AACF,MAAA;AACI,KAAA,MAAA;AACI,MAAA,cAAA,EAAA,KAAA,EAAA,cAAe,IAAA,gBAAA,EAAA,OAAA,IAAA,IAAA;;;;AAId,MAAA,QAAA,EAAA,EAAA;AACD,MAAA,QAAA,EAAA,EAAA;wBACI;;;AAGH,IAAA,MAAA,EAAA;AACD,MAAA,IAAA,EAAA;;;2BAGM,CAAA;AACL,cAAA,QAAA,EAAA,CAAA;AACD,gBAAA;yBACI,CAAA;;;AAGH,UAAA,kBAAA,EAAA;AACD,YAAA,OAAA,EAAA,MAAA,CAAA;0BACI,EAAA,CAAA;;yBAEC,CAAC;AACL,aAAA;AACD,WAAA;AACI,UAAA,gBAAA,EAAA;2BACA,CAAA;;;AAGQ,eAAA,KAAA,KAAA,CAAA;AACI,aAAA;;;;AAKJ,cAAA,UAAA,EAAA,CAAA;AACI,gBAAA;;;;;AAOJ,YAAA,OAAA,EAAA,MAAA,CAAA;AACI,cAAA,aAAA,EAAA,CAAA;AACI,gBAAA;AACA,eAAA,KAAA,KAAA,CAAA;AACA,aAAA;;;;;;;AAOJ,gBAAA;;;AAIJ,gBAAA,MAAA,WAAA,GAAI;AACA,kBAAA,IAAA,EAAA,MAAA;AACI,kBAAA,OAAA,EAAA,KAAA,CAAA;;;AAGI,gBAAA,IAAA,KAAA,CAAA,WAAA,IAAA,KAAA,CAAA,WAAc,CAAA,MAAG,GAAA,CAAA,EAAU;AAE3B,kBAAA,WAAA,CAAA,WAAA,GAAA,KAAA,CAAM;;;AAGF,gBAAA,MAAA,cAAA,GAAA,CAAA,GAAA,OAAA,CAAA,aAAc,CAAA;;;;AAIV,oBAAA,EAAA,EAAA,CAAA,WAAA,EAAA,IAAA,CAAA,GAAA,EAAA,CAAA,CAAA;;AAER,oBAAA,IAAA,EAAA,WAAA;8CACH,CAAA,QAAA,CAAA,SAAA,CAAA,GAAA,OAAA,CAAA,UAAA,CAAA,KAAA,CAAA,SAAA,CAAA,CAAA,CAAA,CAAA,GAAA,OAAA,CAAA,UAAA;oCACL,CAAC,UAAA;;AAGL,mBAAA;AACI,kBAAA,cAAA,CAAA,IAAA,CAAA,cAAY,CAAA;;;qCAInB,EAAA;6BACD,UAAA,IAAA,KAAA,CAAA,WAAA,EAAA;kCACA,CAAA,OAAa,EAAG;;qCAGZ,GAAA,UAAA,CAAA,OAAA,CAAA,KAA4B,CAAA,gBAAA,CAAA;AAC5B,sBAAA,MAAA,QAAI,GAAA,SAAQ,GAAA,SAAa,CAAA,CAAA,CAAA,GAAA,0BAAA;wCACrB,GAAA;AACI,wBAAA,EAAA,EAAA,UAAA,CAAA,EAAA;AACA,wBAAA,IAAA,EAAA,UAAA,CAAA;AACA,wBAAA,IAAA,EAAA,QAAA;2CACA,CAAA;kDACM,CAAA,QAAQ,CAAA,SAAW,CAAK,GAAC,UAAY,CAAC,OAAA,CAAA,KAAA,CAAA,SAAA,CAAA,CAAA,CAAA,CAAA,GAAA;;yCAE5C,CAAA,YAAS,CAAA;AACZ,oBAAA;;;AAIL,gBAAA,IAAA,cAAA,CAAA,MAAS,GAAC,CAAA,EAAA;AACN,kBAAA,WAAA,CAAA,8BAAqB;AACjB,gBAAA;6CACI,WAAA,CAAA;;AAEA;;;;AAKI,eAAA,KAAA;;;;AAII,kBAAA,cAAA,CAAA,IAAA,CAAA;AACP,oBAAA,EAAA,EAAA,CAAA,WAAA,EAAA,IAAA,CAAA,GAAC,EAAC,CAAA,CAAA;0CACN;qCACJ;mCACJ,CAAA,UAAA,CAAA,QAAA,CAAA,SAAA,CAAA,GAAA,OAAA,CAAA,UAAA,CAAA,KAAA,CAAA,SAAA,CAAA,CAAA,CAAA,CAAA,GAAA,OAAA,CAAA,UAAA;AAED,oBAAA,OAAA,EAAA,OAAA,CAAA;;;AAGX;AACD,gBAAA,IAAA,KAAA,CAAA,WAAgB,EAAA;AACZ,kBAAA,KAAA,MAAA,UAAS,IAAA,KAAA,CAAA,WAAA,EAAA;AACL,oBAAA,IAAA,UAAM,CAAC,OAAA,EAAA;AACH;AACA,sBAAA,MAAA,SAAA,GAAQ,UAAI,CAAA,OAAA,CAAA,KAAA,CAAA,gBAAA,CAAA;AACZ,sBAAA,MAAA,QAAA,GAAO,SAAI,GAAA,SAAA,CAAA,CAAA,CAAA,GAAA,0BAAA;AACX,sBAAA,cAAA,CAAA,IAAA,CAAU;AACV,wBAAA,EAAA,EAAA,UAAA,CAAA,EAAA;8BACF,UAAA,CAAA,IAAA;4BACF,EAAA,QAAA;AACH,wBAAA,OAAA,EAAA,UAAA,CAAA,OAAA;AACJ,wBAAA,MAAA,EAAA,UAAA,CAAA,OAAA,CAAA,QAAA,CAAA,SAAA,CAAA,GAAA,UAAA,CAAA,OAAA,CAAA,KAAA,CAAA,SAAA,CAAA,CAAA,CAAA,CAAA,GAAA;AACD,uBAAA,CAAA;;AAEQ,kBAAA;AACA,gBAAA;qCACF;AACL,cAAA;AACJ,aAAA;AACJ,WAAA;AACD,UAAA,cAAS,EAAA;mBACL,EAAK,CAAA,OAAQ;AACT,cAAA,QAAA,EAAA,EAAA;AACA,cAAA,QAAA,EAAA;qBACA,IAAA;wBACF,EAAA,IAAA;AACF,cAAA,aAAQ,EAAA;AACJ,aAAA,CAAA,EAAA,iBAAK;;AAER,UAAA,iBAAA,EAAA;AACD,YAAA,OAAE,EAAE,MAAA,CAAA;AACA,cAAA,UAAA,EAAA,IAAA;2BACI,EAAA;AACI,aAAA;;AAEP;AACD,OAAA;AACI,MAAA,OAAA,EAAA;AACA,QAAA,KAAA,EAAA,MAAA,CAAA;AACI,UAAA,WAAA,EAAA,IAAA;;;AAGQ,SAAA,CAAA;;;;;AAKA,WAAA,KAAA;AACA,SAAA;;AAEJ,UAAA,YAAA,EAAA;AACA,YAAA,OAAA,EAAA,MAAA,CAAA;AACA,cAAA,QAAA,EAAA,CAAA;;AAEP,gBAAA;AACJ,eAAA,KAAA,OAAA,CAAA,QAAA,GAAA,KAAA,CAAA;AACD,aAAA;AACI,WAAA;yBACA,EAAA;;AAEI,YAAA,OAAA,EAAA,CAAA,MAAA,CAAA;yBACH;AACJ,gBAAA;AACJ,eAAA,KAAA,KAAA,CAAA,QAAA;AACJ,cAAA,QAAA,EAAA,CAAA;AACD,gBAAA,OAAO;AACH,gBAAA;AACI,eAAA,KAAA;AACA,gBAAA,MAAA,eAAgB,GAAA,CAAA,GAAA,OAAA,CAAA,QAAA,EAAA;AACZ,kBAAA,IAAA,EAAA,WAAQ;AACR,kBAAA,OAAA,EAAA,KAAO,CAAE;AACL,iBAAA,CAAA;AACI;AACA,gBAAA,eAAA,CAAA,OAAA,CAAQ,cAAI,EAAA,eAAA,CAAA;AACZ,gBAAA,OAAA;;gCAEJ;AACH,cAAA,UAAA,EAAA,IAAA;AACJ,cAAA,aAAA,EAAA;AACD,aAAA,CAAA;AACI,WAAA;wBACA;;AAEQ,YAAA,OAAA,EAAA,MAAA,CAAA;AACI,cAAA,KAAA,EAAA,CAAA;;;;;AAKR;;AAEP,OAAA;AACJ,MAAA,KAAA,EAAA;AACJ,QAAA,EAAA,EAAA;AACJ,UAAA,KAAA,EAAA,SAAA;AACJ,UAAE,cAAA,EAAA;AACP,YAAC,MAAA,EAAA,MAAA;AAED,YAAA,OAAA,EAAA,CAAA,MAAA,CAAA;;;AAGG,cAAA,KAAA,EAAA;AACH,aAAa,CAAA,EAAA,iBAAc;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/state/index.ts"],"names":[],"mappings":"AACA,cAAc,eAAe,CAAC;AAG9B,OAAO,EACH,mBAAmB,EACnB,KAAK,0BAA0B,EAC/B,KAAK,yBAAyB,GACjC,MAAM,uBAAuB,CAAC"}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* useChatWithPlatform Hook
|
|
3
|
+
*
|
|
4
|
+
* A React hook that creates and manages a chat machine instance with platform services.
|
|
5
|
+
* This hook automatically integrates storage, screenshot, and microphone functionality
|
|
6
|
+
* based on the current platform (browser or Tauri desktop).
|
|
7
|
+
*/
|
|
8
|
+
import { type Message, type AttachedFile, type MessageAttachment } from './chatMachine';
|
|
9
|
+
export interface UseChatWithPlatformOptions {
|
|
10
|
+
/** System prompt to use for the chat */
|
|
11
|
+
systemPrompt?: string;
|
|
12
|
+
/** Whether to auto-load chat history on mount */
|
|
13
|
+
autoLoadHistory?: boolean;
|
|
14
|
+
}
|
|
15
|
+
export interface UseChatWithPlatformReturn {
|
|
16
|
+
messages: Message[];
|
|
17
|
+
response: string;
|
|
18
|
+
isStreaming: boolean;
|
|
19
|
+
error: string | null;
|
|
20
|
+
screenshot: string | null;
|
|
21
|
+
attachedFiles: AttachedFile[];
|
|
22
|
+
sendMessage: (content: string, attachments?: MessageAttachment[]) => void;
|
|
23
|
+
setSystemPrompt: (prompt: string) => void;
|
|
24
|
+
setScreenshot: (screenshot: string | null) => void;
|
|
25
|
+
setAttachedFiles: (files: AttachedFile[]) => void;
|
|
26
|
+
clearMessages: () => void;
|
|
27
|
+
clearAttachments: () => void;
|
|
28
|
+
retry: () => void;
|
|
29
|
+
loadMessages: (messages: Message[]) => void;
|
|
30
|
+
captureScreenshot: () => Promise<void>;
|
|
31
|
+
captureSelectedArea: () => Promise<void>;
|
|
32
|
+
startRecording: () => Promise<void>;
|
|
33
|
+
stopRecording: () => Promise<void>;
|
|
34
|
+
cancelRecording: () => Promise<void>;
|
|
35
|
+
isDesktop: boolean;
|
|
36
|
+
isBrowser: boolean;
|
|
37
|
+
hasScreenshotSupport: boolean;
|
|
38
|
+
hasMicrophoneSupport: boolean;
|
|
39
|
+
microphoneStatus: 'idle' | 'recording' | 'processing' | 'error';
|
|
40
|
+
}
|
|
41
|
+
export declare function useChatWithPlatform(options?: UseChatWithPlatformOptions): UseChatWithPlatformReturn;
|
|
42
|
+
export default useChatWithPlatform;
|
|
43
|
+
//# sourceMappingURL=useChatWithPlatform.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useChatWithPlatform.d.ts","sourceRoot":"","sources":["../../src/state/useChatWithPlatform.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAIH,OAAO,EAAqB,KAAK,OAAO,EAAE,KAAK,YAAY,EAAE,KAAK,iBAAiB,EAAE,MAAM,eAAe,CAAC;AAO3G,MAAM,WAAW,0BAA0B;IACvC,wCAAwC;IACxC,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,iDAAiD;IACjD,eAAe,CAAC,EAAE,OAAO,CAAC;CAC7B;AAED,MAAM,WAAW,yBAAyB;IAEtC,QAAQ,EAAE,OAAO,EAAE,CAAC;IACpB,QAAQ,EAAE,MAAM,CAAC;IACjB,WAAW,EAAE,OAAO,CAAC;IACrB,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;IACrB,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,aAAa,EAAE,YAAY,EAAE,CAAC;IAG9B,WAAW,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,iBAAiB,EAAE,KAAK,IAAI,CAAC;IAC1E,eAAe,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1C,aAAa,EAAE,CAAC,UAAU,EAAE,MAAM,GAAG,IAAI,KAAK,IAAI,CAAC;IACnD,gBAAgB,EAAE,CAAC,KAAK,EAAE,YAAY,EAAE,KAAK,IAAI,CAAC;IAClD,aAAa,EAAE,MAAM,IAAI,CAAC;IAC1B,gBAAgB,EAAE,MAAM,IAAI,CAAC;IAC7B,KAAK,EAAE,MAAM,IAAI,CAAC;IAClB,YAAY,EAAE,CAAC,QAAQ,EAAE,OAAO,EAAE,KAAK,IAAI,CAAC;IAG5C,iBAAiB,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IACvC,mBAAmB,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IACzC,cAAc,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IACpC,aAAa,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IACnC,eAAe,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAGrC,SAAS,EAAE,OAAO,CAAC;IACnB,SAAS,EAAE,OAAO,CAAC;IACnB,oBAAoB,EAAE,OAAO,CAAC;IAC9B,oBAAoB,EAAE,OAAO,CAAC;IAC9B,gBAAgB,EAAE,MAAM,GAAG,WAAW,GAAG,YAAY,GAAG,OAAO,CAAC;CACnE;AAMD,wBAAgB,mBAAmB,CAAC,OAAO,GAAE,0BAA+B,GAAG,yBAAyB,CA4LvG;AAED,eAAe,mBAAmB,CAAC"}
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Chat message types
|
|
3
|
+
*/
|
|
4
|
+
export interface ChatMessage {
|
|
5
|
+
role: 'user' | 'assistant' | 'system';
|
|
6
|
+
content: string;
|
|
7
|
+
}
|
|
8
|
+
export interface ChatMessageWithMeta {
|
|
9
|
+
id: string;
|
|
10
|
+
role: 'user' | 'assistant' | 'system';
|
|
11
|
+
content: string;
|
|
12
|
+
timestamp: number;
|
|
13
|
+
attachedFiles?: AttachedFile[];
|
|
14
|
+
}
|
|
15
|
+
export interface AttachedFile {
|
|
16
|
+
id: string;
|
|
17
|
+
name: string;
|
|
18
|
+
type: string;
|
|
19
|
+
base64?: string;
|
|
20
|
+
dataUrl?: string;
|
|
21
|
+
file?: File | null;
|
|
22
|
+
size?: number;
|
|
23
|
+
}
|
|
24
|
+
export interface ChatConversation {
|
|
25
|
+
id: string;
|
|
26
|
+
title: string;
|
|
27
|
+
messages: ChatMessageWithMeta[];
|
|
28
|
+
createdAt: number;
|
|
29
|
+
updatedAt: number;
|
|
30
|
+
}
|
|
31
|
+
export interface CompletionState {
|
|
32
|
+
input: string;
|
|
33
|
+
response: string;
|
|
34
|
+
isLoading: boolean;
|
|
35
|
+
error: string | null;
|
|
36
|
+
attachedFiles: AttachedFile[];
|
|
37
|
+
currentConversationId: string | null;
|
|
38
|
+
conversationHistory: ChatMessageWithMeta[];
|
|
39
|
+
}
|
|
40
|
+
/**
|
|
41
|
+
* Provider-related types for multimodal messages
|
|
42
|
+
*/
|
|
43
|
+
export interface MultimodalContent {
|
|
44
|
+
type: string;
|
|
45
|
+
text?: string;
|
|
46
|
+
image_url?: {
|
|
47
|
+
url: string;
|
|
48
|
+
};
|
|
49
|
+
source?: any;
|
|
50
|
+
inline_data?: any;
|
|
51
|
+
}
|
|
52
|
+
export interface MultimodalMessage {
|
|
53
|
+
role: 'system' | 'user' | 'assistant';
|
|
54
|
+
content: string | MultimodalContent[];
|
|
55
|
+
}
|
|
56
|
+
//# sourceMappingURL=chat.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chat.d.ts","sourceRoot":"","sources":["../../src/types/chat.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,MAAM,WAAW,WAAW;IACxB,IAAI,EAAE,MAAM,GAAG,WAAW,GAAG,QAAQ,CAAC;IACtC,OAAO,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,mBAAmB;IAChC,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,GAAG,WAAW,GAAG,QAAQ,CAAC;IACtC,OAAO,EAAE,MAAM,CAAC;IAChB,SAAS,EAAE,MAAM,CAAC;IAClB,aAAa,CAAC,EAAE,YAAY,EAAE,CAAC;CAClC;AAED,MAAM,WAAW,YAAY;IACzB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IAEb,IAAI,EAAE,MAAM,CAAC;IAEb,MAAM,CAAC,EAAE,MAAM,CAAC;IAEhB,OAAO,CAAC,EAAE,MAAM,CAAC;IAEjB,IAAI,CAAC,EAAE,IAAI,GAAG,IAAI,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,gBAAgB;IAC7B,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,mBAAmB,EAAE,CAAC;IAChC,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,WAAW,eAAe;IAC5B,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,OAAO,CAAC;IACnB,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;IACrB,aAAa,EAAE,YAAY,EAAE,CAAC;IAC9B,qBAAqB,EAAE,MAAM,GAAG,IAAI,CAAC;IACrC,mBAAmB,EAAE,mBAAmB,EAAE,CAAC;CAC9C;AAED;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,SAAS,CAAC,EAAE;QAAE,GAAG,EAAE,MAAM,CAAA;KAAE,CAAC;IAC5B,MAAM,CAAC,EAAE,GAAG,CAAC;IACb,WAAW,CAAC,EAAE,GAAG,CAAC;CACrB;AAED,MAAM,WAAW,iBAAiB;IAC9B,IAAI,EAAE,QAAQ,GAAG,MAAM,GAAG,WAAW,CAAC;IACtC,OAAO,EAAE,MAAM,GAAG,iBAAiB,EAAE,CAAC;CACzC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/types/index.ts"],"names":[],"mappings":"AAAA,cAAc,QAAQ,CAAC"}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
type StoredAttachment = {
|
|
2
|
+
id: string;
|
|
3
|
+
name: string;
|
|
4
|
+
type: 'file' | 'screenshot';
|
|
5
|
+
};
|
|
6
|
+
type StoredMessage = {
|
|
7
|
+
role: 'user' | 'assistant' | 'system';
|
|
8
|
+
content: string;
|
|
9
|
+
attachments?: StoredAttachment[];
|
|
10
|
+
};
|
|
11
|
+
/**
|
|
12
|
+
* Load chat history from IndexedDB
|
|
13
|
+
*/
|
|
14
|
+
export declare function loadChat(): Promise<StoredMessage[] | null>;
|
|
15
|
+
/**
|
|
16
|
+
* Save chat messages to IndexedDB
|
|
17
|
+
* Strips dataUrl/base64 from attachments, keeping only name and type
|
|
18
|
+
*/
|
|
19
|
+
export declare function saveChat(messages: StoredMessage[]): Promise<void>;
|
|
20
|
+
/**
|
|
21
|
+
* Clear chat history from IndexedDB
|
|
22
|
+
*/
|
|
23
|
+
export declare function clearChat(): Promise<void>;
|
|
24
|
+
export {};
|
|
25
|
+
//# sourceMappingURL=chatStorage.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chatStorage.d.ts","sourceRoot":"","sources":["../../src/utils/chatStorage.ts"],"names":[],"mappings":"AAKA,KAAK,gBAAgB,GAAG;IACpB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,GAAG,YAAY,CAAC;CAC/B,CAAC;AAEF,KAAK,aAAa,GAAG;IACjB,IAAI,EAAE,MAAM,GAAG,WAAW,GAAG,QAAQ,CAAC;IACtC,OAAO,EAAE,MAAM,CAAC;IAChB,WAAW,CAAC,EAAE,gBAAgB,EAAE,CAAC;CACpC,CAAC;AAQF;;GAEG;AACH,wBAAsB,QAAQ,IAAI,OAAO,CAAC,aAAa,EAAE,GAAG,IAAI,CAAC,CAYhE;AAED;;;GAGG;AACH,wBAAsB,QAAQ,CAAC,QAAQ,EAAE,aAAa,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC,CAwBvE;AAED;;GAEG;AACH,wBAAsB,SAAS,IAAI,OAAO,CAAC,IAAI,CAAC,CAO/C"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import {get}from'idb-keyval';const CHAT_KEY = 'LLM-chat-history';
|
|
2
|
+
/**
|
|
3
|
+
* Load chat history from IndexedDB
|
|
4
|
+
*/
|
|
5
|
+
async function loadChat() {
|
|
6
|
+
try {
|
|
7
|
+
const chat = await get(CHAT_KEY);
|
|
8
|
+
if (chat?.messages && chat.messages.length > 0) {
|
|
9
|
+
console.log('💾 [STORAGE] Loaded chat with', chat.messages.length, 'messages');
|
|
10
|
+
return chat.messages;
|
|
11
|
+
}
|
|
12
|
+
return null;
|
|
13
|
+
} catch (error) {
|
|
14
|
+
console.error('💾 [STORAGE] Error loading chat:', error);
|
|
15
|
+
return null;
|
|
16
|
+
}
|
|
17
|
+
}export{loadChat};//# sourceMappingURL=chatStorage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chatStorage.js","sources":["../../src/utils/chatStorage.ts"],"sourcesContent":[null],"names":[],"mappings":"6BAEA,MAAM,QAAQ,GAAG,kBAAkB;AAqBnC;;AAEG;AACI,eAAe,QAAQ,GAAA;AAC1B,EAAA,IAAA;AACI,IAAA,MAAA,IAAM,SAAO,GAAA,CAAM,QAAgB,CAAA;AACnC,IAAA,IAAA,IAAI,EAAA,QAAM,IAAQ,IAAI,CAAA,QAAK,CAAA,MAAS,GAAA,CAAM,EAAA;AACtC,MAAA,OAAA,CAAA,GAAA,CAAA,+BAAY,EAAA,IAA+B,CAAA,QAAO,CAAA,MAAS,EAAA,UAAQ,CAAA;aACnE,IAAA,CAAA,QAAY;;AAEhB,IAAA,OAAA,IAAO;IACX,OAAC,KAAA,EAAA;IAAC,OAAO,CAAA,MAAO,kCAAC,EAAA,KAAA,CAAA;AACb,IAAA,OAAA,IAAO;AACP,EAAA;"}
|