chordia-ui 3.9.2 → 3.9.3

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.
@@ -1 +1 @@
1
- {"version":3,"file":"chat.cjs.js","sources":["../../src/components/chat/ThinkingIndicator.jsx","../../src/components/chat/ChatInterface.jsx","../../src/components/chat/ChatHistoryPanel.jsx","../../src/components/chat/MessageThread.jsx"],"sourcesContent":["\"use client\";\n\nexport default function ThinkingIndicator({ \n phase = \"thinking\", \n toolSteps = [], \n label,\n elapsedMs,\n compact = false\n}) {\n const formatElapsedTime = (ms) => {\n if (!ms || ms < 1000) return null;\n const seconds = Math.floor(ms / 1000);\n if (seconds < 60) return `${seconds}s`;\n const minutes = Math.floor(seconds / 60);\n const remainingSeconds = seconds % 60;\n return remainingSeconds > 0 ? `${minutes}m ${remainingSeconds}s` : `${minutes}m`;\n };\n\n const getPhaseLabel = () => {\n if (label) return label;\n switch (phase) {\n case \"thinking\": return \"Thinking...\";\n case \"tool\": return null;\n case \"responding\": return \"Responding...\";\n default: return \"Thinking...\";\n }\n };\n\n const renderToolStep = (step, index) => {\n const getStatusDot = () => {\n const baseDotStyle = {\n width: compact ? '4px' : '6px',\n height: compact ? '4px' : '6px',\n borderRadius: '50%',\n display: 'inline-block',\n marginRight: compact ? '6px' : '8px'\n };\n\n switch (step.status) {\n case 'active':\n return (\n <span \n style={{\n ...baseDotStyle,\n backgroundColor: 'var(--rail-purple, #9B7AA8)',\n animation: 'pulse 1.2s ease-in-out infinite'\n }}\n />\n );\n case 'done':\n return (\n <span \n style={{\n ...baseDotStyle,\n backgroundColor: 'var(--text-xfaint, rgba(30,33,37,0.28))'\n }}\n />\n );\n case 'error':\n return (\n <span \n style={{\n ...baseDotStyle,\n backgroundColor: 'var(--rail-compliance, #C98A5A)'\n }}\n />\n );\n default:\n return (\n <span \n style={{\n ...baseDotStyle,\n backgroundColor: 'var(--text-xfaint, rgba(30,33,37,0.28))'\n }}\n />\n );\n }\n };\n\n const getStatusText = () => {\n switch (step.status) {\n case 'done':\n return (\n <span style={{ \n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n fontSize: compact ? '9px' : 'var(--text-xs-plus, 10.5px)'\n }}>\n ✓\n </span>\n );\n case 'error':\n return (\n <span style={{ \n color: 'var(--rail-compliance, #C98A5A)',\n fontSize: compact ? '9px' : 'var(--text-xs-plus, 10.5px)'\n }}>\n failed\n </span>\n );\n default:\n return null;\n }\n };\n\n return (\n <div \n key={index}\n style={{\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'space-between',\n marginBottom: compact ? '2px' : '4px'\n }}\n >\n <div style={{ display: 'flex', alignItems: 'center' }}>\n {getStatusDot()}\n <span style={{\n fontFamily: 'var(--font-mono)',\n fontSize: compact ? '9px' : 'var(--text-xs-plus, 10.5px)',\n color: 'var(--text-muted)'\n }}>\n {step.name}\n </span>\n </div>\n {getStatusText()}\n </div>\n );\n };\n\n const renderShimmerBar = () => (\n <div style={{\n width: '100%',\n height: compact ? '2px' : '3px',\n backgroundColor: 'var(--border-subtle, rgba(52,58,64,0.08))',\n borderRadius: compact ? '2px' : '3px',\n overflow: 'hidden',\n position: 'relative'\n }}>\n <div style={{\n position: 'absolute',\n top: 0,\n left: 0,\n right: 0,\n bottom: 0,\n background: 'linear-gradient(90deg, transparent 0%, rgba(155,122,168,0.3) 50%, transparent 100%)',\n animation: 'shimmer 2s linear infinite'\n }} />\n </div>\n );\n\n const renderCursor = () => (\n <span style={{\n width: compact ? '4px' : '6px',\n height: compact ? '10px' : '14px',\n backgroundColor: 'var(--rail-purple, #9B7AA8)',\n borderRadius: '1px',\n display: 'inline-block',\n marginLeft: '2px',\n animation: 'cursorBlink 0.8s ease-in-out infinite'\n }} />\n );\n\n const phaseLabel = getPhaseLabel();\n const elapsedTime = formatElapsedTime(elapsedMs);\n\n return (\n <div style={{\n borderLeft: `${compact ? '3px' : '4px'} solid var(--rail-purple, #9B7AA8)`,\n backgroundColor: 'var(--card-assistant, rgba(155,122,168,0.06))',\n border: '1px solid var(--border-subtle, rgba(52,58,64,0.08))',\n borderRadius: compact ? '8px' : '10px',\n padding: compact ? '8px 10px 8px 12px' : '10px 14px 10px 18px'\n }}>\n <style>\n {`\n @keyframes shimmer {\n 0% { transform: translateX(-100%); }\n 100% { transform: translateX(200%); }\n }\n \n @keyframes pulse {\n 0%, 100% { opacity: 0.4; }\n 50% { opacity: 1.0; }\n }\n \n @keyframes cursorBlink {\n 0%, 100% { opacity: 0; }\n 50% { opacity: 1; }\n }\n `}\n </style>\n \n {/* Header */}\n {!compact && (\n <div style={{\n fontSize: 'var(--text-xs-plus, 10.5px)',\n fontWeight: 650,\n textTransform: 'uppercase',\n letterSpacing: 'var(--tracking-label, 0.16em)',\n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n marginBottom: '8px'\n }}>\n AI ASSISTANT\n </div>\n )}\n\n {/* Content based on phase */}\n {phase === \"thinking\" && (\n <div>\n <div style={{\n color: 'var(--text-muted)',\n fontWeight: 400,\n fontSize: compact ? '11px' : '13px',\n marginBottom: compact ? '4px' : '8px',\n display: 'flex',\n alignItems: 'center',\n gap: '6px'\n }}>\n {phaseLabel}\n {elapsedTime && (\n <span style={{\n fontSize: compact ? '9px' : '10px',\n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n fontFamily: 'var(--font-mono, monospace)',\n }}>\n {elapsedTime}\n </span>\n )}\n </div>\n {renderShimmerBar()}\n </div>\n )}\n\n {phase === \"tool\" && (\n <div>\n {phaseLabel && (\n <div style={{\n color: 'var(--text-muted)',\n fontWeight: 400,\n fontSize: compact ? '11px' : '13px',\n marginBottom: compact ? '4px' : '8px',\n display: 'flex',\n alignItems: 'center',\n gap: '6px'\n }}>\n {phaseLabel}\n {elapsedTime && (\n <span style={{\n fontSize: compact ? '9px' : '10px',\n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n fontFamily: 'var(--font-mono, monospace)',\n }}>\n {elapsedTime}\n </span>\n )}\n </div>\n )}\n <div style={{ marginBottom: compact ? '4px' : '8px' }}>\n {toolSteps.map((step, index) => renderToolStep(step, index))}\n </div>\n {renderShimmerBar()}\n </div>\n )}\n\n {phase === \"responding\" && (\n <div style={{\n color: 'var(--text-muted)',\n fontWeight: 400,\n fontSize: compact ? '11px' : '13px',\n display: 'flex',\n alignItems: 'center',\n gap: '6px'\n }}>\n <div style={{ display: 'flex', alignItems: 'center' }}>\n {phaseLabel}\n {renderCursor()}\n </div>\n {elapsedTime && (\n <span style={{\n fontSize: compact ? '9px' : '10px',\n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n fontFamily: 'var(--font-mono, monospace)',\n }}>\n {elapsedTime}\n </span>\n )}\n </div>\n )}\n </div>\n );\n}","\"use client\";\n\nimport React, { useState, useRef, useEffect } from \"react\";\nimport { Send } from \"lucide-react\";\nimport ChatMessage from \"./ChatMessage\";\nimport ThinkingIndicator from \"./ThinkingIndicator\";\n// TODO: replace with framework-agnostic toast\nconst toast = { error: (...args) => console.warn(\"toast.error:\", ...args) };\n\n/**\n * ChatInterface Component\n * Interactive chat interface with streaming SSE support, thinking phases, and tool visibility.\n */\nexport default function ChatInterface({\n initialMessages = [],\n onSendMessage,\n onStreamMessage, // NEW: streaming version of onSendMessage\n onMessagesChange, // NEW: callback when messages array changes\n onCodeBlockClick, // callback when \"Canvas\" button clicked on a code block: ({ code, language }) => void\n placeholder = \"Ask a question about this interaction...\",\n title = \"Chat with Chordia\",\n}) {\n const [messages, setMessages] = useState(initialMessages || []);\n const [inputValue, setInputValue] = useState(\"\");\n const [isProcessing, setIsProcessing] = useState(false);\n const [isSending, setIsSending] = useState(false);\n const [currentAssistantMessage, setCurrentAssistantMessage] = useState(null);\n const [thinkingPhase, setThinkingPhase] = useState(\"thinking\");\n const [thinkingStartTime, setThinkingStartTime] = useState(null);\n const [elapsedMs, setElapsedMs] = useState(0);\n const messagesEndRef = useRef(null);\n const inputRef = useRef(null);\n const streamAbortController = useRef(null);\n const currentAssistantRef = useRef(null);\n const lastChunkTimeRef = useRef(null);\n const [streamSilent, setStreamSilent] = useState(false);\n const [silenceSeconds, setSilenceSeconds] = useState(0);\n\n // Auto-scroll to bottom when messages change\n useEffect(() => {\n messagesEndRef.current?.scrollIntoView({ behavior: \"smooth\" });\n }, [messages, isProcessing]);\n\n // Auto-resize textarea\n useEffect(() => {\n if (inputRef.current) {\n inputRef.current.style.height = \"auto\";\n inputRef.current.style.height = `${Math.min(\n inputRef.current.scrollHeight,\n 120\n )}px`;\n }\n }, [inputValue]);\n\n // Update messages and notify parent\n useEffect(() => {\n if (onMessagesChange) {\n const allMessages = [...messages];\n if (currentAssistantMessage) {\n allMessages.push(currentAssistantMessage);\n }\n onMessagesChange(allMessages);\n }\n }, [messages, currentAssistantMessage, onMessagesChange]);\n\n // Elapsed time tracker + silence detector\n useEffect(() => {\n let interval;\n if (isProcessing && thinkingStartTime) {\n interval = setInterval(() => {\n setElapsedMs(Date.now() - thinkingStartTime);\n // Detect stream silence (no chunks for 3s+)\n if (lastChunkTimeRef.current) {\n const gap = (Date.now() - lastChunkTimeRef.current) / 1000;\n if (gap >= 3) {\n setStreamSilent(true);\n setSilenceSeconds(Math.floor(gap));\n } else {\n setStreamSilent(false);\n }\n }\n }, 500);\n }\n return () => interval && clearInterval(interval);\n }, [isProcessing, thinkingStartTime]);\n\n const resetProcessingState = () => {\n setIsProcessing(false);\n setIsSending(false);\n setCurrentAssistantMessage(null);\n currentAssistantRef.current = null;\n setThinkingPhase(\"thinking\");\n setStreamSilent(false);\n setSilenceSeconds(0);\n lastChunkTimeRef.current = null;\n setThinkingStartTime(null);\n setElapsedMs(0);\n if (streamAbortController.current) {\n streamAbortController.current.abort();\n streamAbortController.current = null;\n }\n };\n\n const parseSSELine = (line) => {\n if (line.startsWith(\"data: \")) {\n const data = line.slice(6);\n if (data === \"[DONE]\") {\n return { type: \"done\" };\n }\n try {\n const parsed = JSON.parse(data);\n return { type: \"data\", data: parsed };\n } catch (e) {\n return null;\n }\n }\n return null;\n };\n\n const handleStreamChunk = (chunk) => {\n if (!chunk.choices?.[0]?.delta) return;\n\n lastChunkTimeRef.current = Date.now();\n setStreamSilent(false);\n\n const delta = chunk.choices[0].delta;\n \n // Check for tool use/result indicators\n if (delta.tool_calls || delta.tool_results) {\n setThinkingPhase(\"tool\");\n return;\n }\n\n // If we get content, switch to responding phase\n if (delta.content !== undefined) {\n setThinkingPhase(\"responding\");\n \n // Initialize or update current assistant message\n setCurrentAssistantMessage(prev => {\n const baseMessage = prev || {\n id: Date.now().toString(),\n role: \"assistant\",\n content: \"\",\n timestamp: new Date().toLocaleTimeString(\"en-US\", {\n hour: \"2-digit\",\n minute: \"2-digit\",\n }),\n isStreaming: true,\n };\n \n const updated = {\n ...baseMessage,\n content: (baseMessage.content || \"\") + (delta.content || \"\"),\n };\n currentAssistantRef.current = updated;\n return updated;\n });\n }\n };\n\n const processStream = async (stream) => {\n const reader = stream.getReader();\n const decoder = new TextDecoder();\n let buffer = \"\";\n\n try {\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n\n buffer += decoder.decode(value, { stream: true });\n const lines = buffer.split(\"\\n\");\n buffer = lines.pop() || \"\"; // Keep incomplete line in buffer\n\n for (const line of lines) {\n if (line.trim()) {\n const parsed = parseSSELine(line);\n if (parsed) {\n if (parsed.type === \"done\") {\n return; // Stream complete\n } else if (parsed.type === \"data\") {\n handleStreamChunk(parsed.data);\n }\n }\n }\n }\n }\n } finally {\n reader.releaseLock();\n }\n };\n\n const handleSend = async () => {\n if (!inputValue.trim() || isSending) return;\n\n const userContent = inputValue.trim();\n const userMessage = {\n id: Date.now().toString(),\n role: \"user\",\n content: userContent,\n timestamp: new Date().toLocaleTimeString(\"en-US\", {\n hour: \"2-digit\",\n minute: \"2-digit\",\n }),\n };\n\n // Add user message and start processing\n const newMessages = [...messages, userMessage];\n setMessages(newMessages);\n setInputValue(\"\");\n setIsProcessing(true);\n setIsSending(true);\n setThinkingPhase(\"thinking\");\n setThinkingStartTime(Date.now());\n lastChunkTimeRef.current = Date.now();\n\n // Create abort controller for this stream\n streamAbortController.current = new AbortController();\n\n try {\n let result;\n \n // Use streaming version if provided, otherwise fall back to regular\n if (onStreamMessage) {\n result = await onStreamMessage(userContent, newMessages);\n } else if (onSendMessage) {\n result = await onSendMessage(userContent, newMessages);\n } else {\n // Fallback to dummy response\n setTimeout(() => {\n const assistantMessage = {\n id: (Date.now() + 1).toString(),\n role: \"assistant\",\n content: \"This is a demonstration response. In a real implementation, this would connect to your LLM backend.\",\n timestamp: new Date().toLocaleTimeString(\"en-US\", {\n hour: \"2-digit\",\n minute: \"2-digit\",\n }),\n };\n setMessages(prev => [...prev, assistantMessage]);\n resetProcessingState();\n }, 1000);\n return;\n }\n\n // Handle ReadableStream response\n if (result instanceof ReadableStream) {\n await processStream(result);\n } \n // Handle Response with SSE body\n else if (result instanceof Response && result.body) {\n await processStream(result.body);\n }\n // Handle Promise that resolves to a stream\n else if (result && typeof result.then === \"function\") {\n const resolved = await result;\n if (resolved instanceof ReadableStream) {\n await processStream(resolved);\n } else if (resolved instanceof Response && resolved.body) {\n await processStream(resolved.body);\n }\n }\n\n // Finalize the assistant message using ref (state is stale in this closure)\n if (currentAssistantRef.current) {\n setMessages(prev => [...prev, { \n ...currentAssistantRef.current, \n isStreaming: false \n }]);\n }\n\n } catch (error) {\n if (error.name !== \"AbortError\") {\n toast.error(\"Failed to send message\");\n console.error(\"Stream error:\", error);\n }\n } finally {\n resetProcessingState();\n }\n };\n\n const handleKeyDown = (e) => {\n if (e.key === \"Enter\" && !e.shiftKey) {\n e.preventDefault();\n handleSend();\n }\n };\n\n return (\n <div\n style={{\n display: \"flex\",\n flexDirection: \"column\",\n height: \"100%\",\n border: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n borderRadius: \"var(--radius-lg, 12px)\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n overflow: \"hidden\",\n }}\n >\n {/* Header — hidden when title is empty */}\n {title ? <div\n style={{\n padding: \"16px 20px\",\n borderBottom: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n }}\n >\n <div\n style={{\n fontSize: \"var(--text-lg, 16px)\",\n fontWeight: 720,\n letterSpacing: \"-0.01em\",\n color: \"var(--text-strong, rgba(30,33,37,0.92))\",\n }}\n >\n {title}\n </div>\n <div\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n marginTop: \"2px\",\n }}\n >\n Ask questions, get insights from analyzed interactions\n </div>\n </div> : null}\n\n {/* Messages area */}\n <div\n style={{\n flex: 1,\n minHeight: 0,\n overflowY: \"auto\",\n padding: \"20px\",\n display: \"flex\",\n flexDirection: \"column\",\n }}\n >\n {messages.length === 0 ? (\n <div\n style={{\n flex: 1,\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontSize: \"var(--text-md, 13px)\",\n textAlign: \"center\",\n padding: \"40px\",\n }}\n >\n No messages yet. Start a conversation by asking a question below.\n </div>\n ) : (\n <>\n {messages.map((message) => (\n <ChatMessage\n key={message.id}\n role={message.role}\n content={message.content}\n html={message.html}\n timestamp={message.timestamp}\n toolBadges={message.toolBadges}\n isStreaming={message.isStreaming}\n onCodeBlockClick={onCodeBlockClick}\n />\n ))}\n \n {/* Current streaming message */}\n {currentAssistantMessage && (\n <ChatMessage\n key={currentAssistantMessage.id}\n role={currentAssistantMessage.role}\n content={currentAssistantMessage.content}\n timestamp={currentAssistantMessage.timestamp}\n isStreaming={true}\n onCodeBlockClick={onCodeBlockClick}\n />\n )}\n \n {/* Thinking indicator — shows during initial thinking or stream silence */}\n {isProcessing && (!currentAssistantMessage || streamSilent) && (\n <div style={{ marginBottom: \"16px\" }}>\n <ThinkingIndicator \n phase={streamSilent ? \"tool\" : thinkingPhase}\n elapsedMs={elapsedMs}\n label={\n streamSilent && silenceSeconds >= 30\n ? \"Compacting conversation — trimming context to stay sharp...\"\n : streamSilent && silenceSeconds >= 10\n ? \"Running background tasks...\"\n : streamSilent\n ? \"Still working...\"\n : undefined\n }\n />\n </div>\n )}\n \n <div ref={messagesEndRef} />\n </>\n )}\n </div>\n\n {/* Input area */}\n <div\n style={{\n borderTop: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n padding: \"16px 20px\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n }}\n >\n <div\n style={{\n display: \"flex\",\n gap: \"12px\",\n alignItems: \"flex-end\",\n }}\n >\n <textarea\n ref={inputRef}\n value={inputValue}\n onChange={(e) => setInputValue(e.target.value)}\n onKeyDown={handleKeyDown}\n placeholder={placeholder}\n rows={1}\n disabled={isSending}\n style={{\n flex: 1,\n padding: \"10px 14px\",\n fontSize: \"var(--text-base, 14px)\",\n lineHeight: 1.5,\n color: \"var(--text-strong, rgba(30,33,37,0.92))\",\n background: \"rgba(255, 255, 255, 0.95)\",\n border: \"1px solid rgba(52, 58, 64, 0.18)\",\n borderRadius: \"var(--radius-md, 8px)\",\n resize: \"none\",\n outline: \"none\",\n transition: \"border-color 0.15s ease\",\n fontFamily: \"inherit\",\n minHeight: \"42px\",\n maxHeight: \"120px\",\n opacity: isSending ? 0.6 : 1,\n cursor: isSending ? \"not-allowed\" : \"text\",\n }}\n onFocus={(e) => {\n if (!isSending) {\n e.target.style.borderColor = \"rgba(94, 136, 176, 0.35)\";\n }\n }}\n onBlur={(e) => {\n e.target.style.borderColor = \"rgba(52, 58, 64, 0.18)\";\n }}\n />\n <button\n onClick={handleSend}\n disabled={!inputValue.trim() || isSending}\n style={{\n padding: \"10px 16px\",\n background:\n inputValue.trim() && !isSending\n ? \"var(--Base-Strong, #0B0B0B)\"\n : \"#ECEEF2\",\n color:\n inputValue.trim() && !isSending\n ? \"white\"\n : \"var(--text-base)\",\n border: \"none\",\n borderRadius: \"var(--radius-md, 8px)\",\n cursor:\n inputValue.trim() && !isSending ? \"pointer\" : \"not-allowed\",\n display: \"flex\",\n alignItems: \"center\",\n gap: \"6px\",\n fontSize: \"var(--text-md, 13px)\",\n fontWeight: 650,\n transition: \"all 0.15s ease\",\n height: \"42px\",\n }}\n // onMouseEnter={(e) => {\n // if (inputValue.trim() && !isSending) {\n // e.currentTarget.style.background = \"var(--Base-Strong, #0B0B0B)\";\n // }\n // }}\n // onMouseLeave={(e) => {\n // if (inputValue.trim() && !isSending) {\n // e.currentTarget.style.background = \"#ECEEF2\";\n // }\n // }}\n >\n {isSending ? (\n <>\n <style>\n {`\n @keyframes buttonSpin {\n from { transform: rotate(0deg); }\n to { transform: rotate(360deg); }\n }\n `}\n </style>\n <div\n style={{\n width: \"14px\",\n height: \"14px\",\n border: \"2px solid rgba(255, 255, 255, 0.3)\",\n borderTopColor: \"white\",\n borderRadius: \"50%\",\n animation: \"buttonSpin 0.6s linear infinite\",\n }}\n />\n Sending...\n </>\n ) : (\n <>\n <Send size={16} />\n Send\n </>\n )}\n </button>\n </div>\n <div\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n marginTop: \"8px\",\n }}\n >\n Press Enter to send, Shift+Enter for new line\n </div>\n </div>\n </div>\n );\n}","\"use client\";\n\nimport React, { useState, useRef, useEffect } from \"react\";\nimport { MessageSquare, Search, Clock, Pin, Pencil, Trash2, Check, X } from \"lucide-react\";\n\n/**\n * ChatHistoryPanel Component\n * Panel showing chat thread history with search functionality.\n *\n * Props:\n * threads - Array of thread objects: { id, title, created_at, updated_at, message_count, last_message_preview, pinned, archived, tags }\n * activeThreadId - Currently selected thread id\n * onSelectThread - (threadId) => void\n * onNewChat - () => void\n * onRenameThread - (threadId, newTitle) => void // optional: when provided, inline edit is enabled\n * onDeleteThread - (threadId) => void // optional: when provided, inline delete is enabled\n * loading - boolean\n */\nexport default function ChatHistoryPanel({\n threads = [],\n activeThreadId,\n onSelectThread,\n onNewChat,\n onRenameThread,\n onDeleteThread,\n loading = false,\n}) {\n const [searchQuery, setSearchQuery] = useState(\"\");\n const [hoveredId, setHoveredId] = useState(null);\n const [editingId, setEditingId] = useState(null);\n const [editValue, setEditValue] = useState(\"\");\n const [deletingId, setDeletingId] = useState(null);\n const editInputRef = useRef(null);\n\n useEffect(() => {\n if (editingId && editInputRef.current) {\n editInputRef.current.focus();\n editInputRef.current.select();\n }\n }, [editingId]);\n\n const filteredThreads = threads.filter((thread) => {\n if (!searchQuery) return true;\n const q = searchQuery.toLowerCase();\n return (\n (thread.title || \"\").toLowerCase().includes(q) ||\n (thread.last_message_preview || \"\").toLowerCase().includes(q)\n );\n });\n\n // Sort: pinned first, then by updated_at descending\n const sortedThreads = [...filteredThreads].sort((a, b) => {\n if (a.pinned && !b.pinned) return -1;\n if (!a.pinned && b.pinned) return 1;\n const aTime = new Date(a.updated_at || a.created_at || 0).getTime();\n const bTime = new Date(b.updated_at || b.created_at || 0).getTime();\n return bTime - aTime;\n });\n\n const formatTime = (dateStr) => {\n if (!dateStr) return \"\";\n const d = new Date(dateStr);\n const now = new Date();\n const diffMs = now.getTime() - d.getTime();\n const diffDays = Math.floor(diffMs / 86400000);\n if (diffDays === 0) {\n return d.toLocaleTimeString(\"en-US\", { hour: \"2-digit\", minute: \"2-digit\" });\n } else if (diffDays === 1) {\n return \"Yesterday\";\n } else if (diffDays < 7) {\n return d.toLocaleDateString(\"en-US\", { weekday: \"short\" });\n } else {\n return d.toLocaleDateString(\"en-US\", { month: \"short\", day: \"numeric\" });\n }\n };\n\n const startEdit = (e, thread) => {\n e.stopPropagation();\n setDeletingId(null);\n setEditingId(thread.id);\n setEditValue(thread.title || \"\");\n };\n\n const saveEdit = (e) => {\n if (e) e.stopPropagation();\n const trimmed = (editValue || \"\").trim();\n if (editingId && trimmed) {\n onRenameThread?.(editingId, trimmed);\n }\n setEditingId(null);\n setEditValue(\"\");\n };\n\n const cancelEdit = (e) => {\n if (e) e.stopPropagation();\n setEditingId(null);\n setEditValue(\"\");\n };\n\n const startDelete = (e, thread) => {\n e.stopPropagation();\n setEditingId(null);\n setDeletingId(thread.id);\n };\n\n const confirmDelete = (e) => {\n if (e) e.stopPropagation();\n if (deletingId) {\n onDeleteThread?.(deletingId);\n }\n setDeletingId(null);\n };\n\n const cancelDelete = (e) => {\n if (e) e.stopPropagation();\n setDeletingId(null);\n };\n\n const iconBtnStyle = {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: \"22px\",\n height: \"22px\",\n padding: 0,\n background: \"transparent\",\n border: \"none\",\n borderRadius: \"4px\",\n cursor: \"pointer\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n transition: \"all 0.12s ease\",\n flexShrink: 0,\n };\n\n return (\n <div\n style={{\n display: \"flex\",\n flexDirection: \"column\",\n height: \"100%\",\n background: \"var(--paper, rgba(255,255,255,0.95))\",\n borderRight: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n overflow: \"hidden\",\n }}\n >\n {/* Header */}\n <div\n style={{\n padding: \"12px 14px\",\n borderBottom: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n flexShrink: 0,\n }}\n >\n <div\n style={{\n display: \"flex\",\n justifyContent: \"space-between\",\n alignItems: \"center\",\n marginBottom: \"10px\",\n }}\n >\n <div\n style={{\n fontSize: \"13px\",\n fontWeight: 650,\n color: \"var(--text-ink, rgba(30,33,37,0.92))\",\n }}\n >\n Threads\n </div>\n {onNewChat && (\n <button\n onClick={onNewChat}\n style={{\n padding: \"4px 10px\",\n fontSize: \"11px\",\n fontWeight: 600,\n color: \"var(--Base-Strong, #0B0B0B)\",\n background: \"#ECEEF2\",\n border: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n borderRadius: \"6px\",\n cursor: \"pointer\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"#ECEEF2\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"rgba(94, 136, 176, 0.08)\";\n }}\n >\n + New\n </button>\n )}\n </div>\n\n {/* Search */}\n <div style={{ position: \"relative\" }}>\n <Search\n size={13}\n style={{\n position: \"absolute\",\n left: \"10px\",\n top: \"50%\",\n transform: \"translateY(-50%)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n pointerEvents: \"none\",\n }}\n />\n <input\n type=\"text\"\n value={searchQuery}\n onChange={(e) => setSearchQuery(e.target.value)}\n placeholder=\"Search threads...\"\n style={{\n width: \"100%\",\n padding: \"7px 10px 7px 32px\",\n fontSize: \"12px\",\n color: \"var(--text-ink, rgba(30,33,37,0.92))\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n border: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n borderRadius: \"6px\",\n outline: \"none\",\n transition: \"border-color 0.15s ease\",\n boxSizing: \"border-box\",\n }}\n onFocus={(e) => {\n e.target.style.borderColor = \"rgba(94, 136, 176, 0.35)\";\n }}\n onBlur={(e) => {\n e.target.style.borderColor = \"rgba(52, 58, 64, 0.12)\";\n }}\n />\n </div>\n </div>\n\n {/* Thread List */}\n <div style={{ flex: 1, overflowY: \"auto\", padding: \"4px 6px\" }}>\n {loading ? (\n <div\n style={{\n padding: \"30px 16px\",\n textAlign: \"center\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontSize: \"12px\",\n }}\n >\n Loading threads...\n </div>\n ) : sortedThreads.length === 0 ? (\n <div\n style={{\n padding: \"30px 16px\",\n textAlign: \"center\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontSize: \"12px\",\n }}\n >\n {searchQuery ? \"No threads found\" : \"No threads yet\"}\n </div>\n ) : (\n sortedThreads.map((thread) => {\n const isActive = thread.id === activeThreadId;\n const isHovered = hoveredId === thread.id;\n const isEditing = editingId === thread.id;\n const isDeleting = deletingId === thread.id;\n const canEdit = typeof onRenameThread === \"function\";\n const canDelete = typeof onDeleteThread === \"function\";\n const showActions = (canEdit || canDelete) && isHovered && !isEditing && !isDeleting;\n\n return (\n <div\n key={thread.id}\n onClick={() => {\n if (isEditing || isDeleting) return;\n onSelectThread?.(thread.id);\n }}\n onMouseEnter={(e) => {\n setHoveredId(thread.id);\n if (!isActive) e.currentTarget.style.background = \"rgba(0,0,0,0.03)\";\n }}\n onMouseLeave={(e) => {\n setHoveredId((prev) => (prev === thread.id ? null : prev));\n if (!isActive) e.currentTarget.style.background = \"transparent\";\n }}\n style={{\n padding: \"10px 10px\",\n marginBottom: \"2px\",\n borderRadius: \"6px\",\n background: isActive\n ? \"rgba(94, 136, 176, 0.10)\"\n : \"transparent\",\n border: isActive\n ? \"1px solid rgba(94, 136, 176, 0.15)\"\n : \"1px solid transparent\",\n cursor: isEditing || isDeleting ? \"default\" : \"pointer\",\n transition: \"all 0.12s ease\",\n }}\n >\n {/* Title row */}\n <div style={{ display: \"flex\", alignItems: \"center\", gap: \"6px\", marginBottom: \"4px\" }}>\n <MessageSquare\n size={12}\n style={{\n color: isActive ? \"var(--rail-discovery, #5E88B0)\" : \"var(--text-faint, rgba(30,33,37,0.36))\",\n flexShrink: 0,\n }}\n />\n\n {isEditing ? (\n <input\n ref={editInputRef}\n type=\"text\"\n value={editValue}\n onChange={(e) => setEditValue(e.target.value)}\n onClick={(e) => e.stopPropagation()}\n onKeyDown={(e) => {\n e.stopPropagation();\n if (e.key === \"Enter\") saveEdit(e);\n else if (e.key === \"Escape\") cancelEdit(e);\n }}\n style={{\n flex: 1,\n minWidth: 0,\n fontSize: \"12px\",\n fontWeight: 600,\n color: \"var(--text-ink, rgba(30,33,37,0.92))\",\n background: \"var(--paper-elevated, #fff)\",\n border: \"1px solid rgba(94, 136, 176, 0.45)\",\n borderRadius: \"4px\",\n padding: \"3px 6px\",\n outline: \"none\",\n boxSizing: \"border-box\",\n }}\n />\n ) : (\n <div\n style={{\n flex: 1,\n minWidth: 0,\n fontSize: \"12px\",\n fontWeight: isActive ? 650 : 550,\n color: isActive\n ? \"var(--text-ink, rgba(30,33,37,0.92))\"\n : \"var(--text-base, rgba(30,33,37,0.78))\",\n overflow: \"hidden\",\n textOverflow: \"ellipsis\",\n whiteSpace: \"nowrap\",\n }}\n >\n {thread.title || \"Untitled thread\"}\n </div>\n )}\n\n {!isEditing && !isDeleting && thread.pinned && (\n <Pin size={10} style={{ color: \"var(--rail-discovery, #5E88B0)\", flexShrink: 0 }} />\n )}\n\n {/* Inline edit actions: save / cancel */}\n {isEditing && (\n <div style={{ display: \"inline-flex\", alignItems: \"center\", gap: \"2px\", flexShrink: 0 }}>\n <button\n type=\"button\"\n title=\"Save\"\n onClick={saveEdit}\n style={{\n ...iconBtnStyle,\n color: \"var(--rail-discovery, #5E88B0)\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"rgba(94, 136, 176, 0.12)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n }}\n >\n <Check size={13} />\n </button>\n <button\n type=\"button\"\n title=\"Cancel\"\n onClick={cancelEdit}\n style={iconBtnStyle}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"rgba(0,0,0,0.06)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n }}\n >\n <X size={13} />\n </button>\n </div>\n )}\n\n {/* Hover actions: edit / delete */}\n {showActions && (\n <div style={{ display: \"inline-flex\", alignItems: \"center\", gap: \"2px\", flexShrink: 0 }}>\n {canEdit && (\n <button\n type=\"button\"\n title=\"Rename\"\n onClick={(e) => startEdit(e, thread)}\n style={iconBtnStyle}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"rgba(0,0,0,0.06)\";\n e.currentTarget.style.color = \"var(--text-ink, rgba(30,33,37,0.92))\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"var(--text-muted, rgba(30,33,37,0.56))\";\n }}\n >\n <Pencil size={12} />\n </button>\n )}\n {canDelete && (\n <button\n type=\"button\"\n title=\"Delete\"\n onClick={(e) => startDelete(e, thread)}\n style={iconBtnStyle}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"rgba(220, 53, 69, 0.10)\";\n e.currentTarget.style.color = \"#DC3545\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"var(--text-muted, rgba(30,33,37,0.56))\";\n }}\n >\n <Trash2 size={12} />\n </button>\n )}\n </div>\n )}\n </div>\n\n {/* Inline delete confirmation */}\n {isDeleting ? (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n flexWrap: \"wrap\",\n gap: \"8px\",\n marginLeft: \"18px\",\n marginTop: \"2px\",\n }}\n >\n <span\n style={{\n fontSize: \"11px\",\n color: \"var(--text-base, rgba(30,33,37,0.78))\",\n fontWeight: 500,\n }}\n >\n Confirm: delete this thread?\n </span>\n <button\n type=\"button\"\n onClick={confirmDelete}\n style={{\n padding: \"3px 10px\",\n fontSize: \"11px\",\n fontWeight: 600,\n color: \"var(--text-ink, rgba(30,33,37,0.92))\",\n background: \"#ECEEF2\",\n border: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n borderRadius: \"5px\",\n cursor: \"pointer\",\n transition: \"background 0.12s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"#E2E5EA\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"#ECEEF2\";\n }}\n >\n Yes\n </button>\n <button\n type=\"button\"\n onClick={cancelDelete}\n style={{\n padding: \"3px 4px\",\n fontSize: \"11px\",\n fontWeight: 500,\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n background: \"transparent\",\n border: \"none\",\n cursor: \"pointer\",\n transition: \"color 0.12s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.color = \"var(--text-ink, rgba(30,33,37,0.92))\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.color = \"var(--text-muted, rgba(30,33,37,0.56))\";\n }}\n >\n No\n </button>\n </div>\n ) : (\n <>\n {/* Preview */}\n {thread.last_message_preview && !isEditing && (\n <div\n style={{\n fontSize: \"11px\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n overflow: \"hidden\",\n textOverflow: \"ellipsis\",\n whiteSpace: \"nowrap\",\n marginLeft: \"18px\",\n marginBottom: \"4px\",\n }}\n >\n {thread.last_message_preview}\n </div>\n )}\n\n {/* Meta */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n gap: \"6px\",\n marginLeft: \"18px\",\n fontSize: \"10px\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n }}\n >\n <Clock size={9} />\n <span>{formatTime(thread.updated_at || thread.created_at)}</span>\n {thread.message_count != null && (\n <>\n <span>·</span>\n <span>{thread.message_count} msg{thread.message_count !== 1 ? \"s\" : \"\"}</span>\n </>\n )}\n </div>\n </>\n )}\n </div>\n );\n })\n )}\n </div>\n </div>\n );\n}\n","/**\n * NOTE: Deprecated component.\n *\n * This chat-scoped `MessageThread` was an early demo implementation and\n * is tightly coupled to app-specific context (`useUserContext`, `toast`, etc.).\n *\n * For new work and for consumers of the `chordia-ui` library, prefer the\n * framework-agnostic, reusable version exported from:\n *\n * `src/components/common/MessageThread.jsx`\n *\n * which is re-exported via the main package entry:\n *\n * import { MessageThread } from \"chordia-ui\";\n *\n * This file is kept only for backwards compatibility within the app.\n */\n\"use client\";\n\nimport React, { useState, useEffect, useRef } from \"react\";\nimport { Send, Paperclip, AtSign, Hash, Clock } from \"lucide-react\";\n// TODO: replace with framework-agnostic toast\nconst toast = { error: (...args) => console.warn(\"toast.error:\", ...args) };\n// TODO: replace with framework-agnostic context\nconst useUserContext = () => ({ userData: { name: \"User\", email: \"\" } });\n\n/**\n * MessageThread Component\n * Threaded messaging interface for team collaboration around sessions.\n * Supports mentions, condition references, and timestamp links.\n * Uses dummy data for demonstration purposes.\n */\nexport default function MessageThread({\n sessionTitle,\n messages: initialMessages,\n onSendMessage,\n currentUser,\n}) {\n const [messageInput, setMessageInput] = useState(\"\");\n const [isFocused, setIsFocused] = useState(false);\n const [messages, setMessages] = useState(initialMessages || []);\n const [isLoading, setIsLoading] = useState(false);\n const [isSending, setIsSending] = useState(false);\n const { userData } = useUserContext();\n const messagesEndRef = useRef(null);\n\n // Get current user from context if not provided\n const displayCurrentUser = currentUser || {\n name: userData?.name || \"You\",\n initials: userData?.name\n ?.split(\" \")\n .map((n) => n[0])\n .join(\"\")\n .toUpperCase() || \"YO\",\n color: \"#6B7C93\",\n };\n\n // Use initialMessages if provided, otherwise use empty array (no API fetching)\n useEffect(() => {\n if (initialMessages) {\n setMessages(initialMessages);\n } else {\n setMessages([]);\n }\n }, [initialMessages]);\n\n // Scroll to bottom when new messages arrive\n useEffect(() => {\n if (messagesEndRef.current) {\n messagesEndRef.current.scrollIntoView({ behavior: \"smooth\" });\n }\n }, [messages]);\n\n const handleSend = async () => {\n if (!messageInput.trim()) return;\n\n const content = messageInput.trim();\n setMessageInput(\"\");\n setIsSending(true);\n\n // Create optimistic message\n const optimisticMessage = {\n id: `temp-${Date.now()}`,\n author: {\n name: displayCurrentUser.name,\n role: userData?.role || \"\",\n initials: displayCurrentUser.initials,\n color: displayCurrentUser.color,\n },\n content: content,\n timestamp: \"Just now\",\n type: \"comment\",\n isOptimistic: true,\n };\n\n // Optimistically add message\n setMessages((prev) => [...prev, optimisticMessage]);\n\n // If onSendMessage callback is provided, use it\n if (onSendMessage) {\n try {\n await onSendMessage(content);\n // Remove optimistic flag after callback succeeds\n setMessages((prev) =>\n prev.map((msg) =>\n msg.id === optimisticMessage.id\n ? { ...msg, isOptimistic: false }\n : msg\n )\n );\n } catch (error) {\n // Remove optimistic message on error\n setMessages((prev) => prev.filter((msg) => msg.id !== optimisticMessage.id));\n toast.error(\"Failed to send message\");\n } finally {\n setIsSending(false);\n }\n return;\n }\n\n // No API - just confirm the optimistic message\n setTimeout(() => {\n setMessages((prev) =>\n prev.map((msg) =>\n msg.id === optimisticMessage.id\n ? { ...msg, isOptimistic: false }\n : msg\n )\n );\n setIsSending(false);\n }, 500);\n };\n\n const handleKeyPress = (e) => {\n if (e.key === \"Enter\" && !e.shiftKey) {\n e.preventDefault();\n handleSend();\n }\n };\n\n return (\n <div\n style={{\n display: \"flex\",\n flexDirection: \"column\",\n height: \"100%\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n border: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n borderRadius: \"var(--radius-lg, 12px)\",\n overflow: \"hidden\",\n }}\n >\n {/* Header */}\n {sessionTitle && (\n <div\n style={{\n padding: \"14px 16px\",\n borderBottom: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n }}\n >\n <div\n style={{\n fontSize: \"var(--text-md, 13px)\",\n fontWeight: 680,\n color: \"var(--text-strong, rgba(30,33,37,0.92))\",\n marginBottom: \"3px\",\n }}\n >\n Session Discussion\n </div>\n {sessionTitle && (\n <div\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n display: \"flex\",\n alignItems: \"center\",\n gap: \"8px\",\n }}\n >\n <span>{sessionTitle}</span>\n </div>\n )}\n </div>\n )}\n\n {/* Messages */}\n <div\n style={{\n flex: 1,\n overflowY: \"auto\",\n padding: \"16px\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"16px\",\n }}\n >\n {isLoading ? (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n padding: \"40px\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n }}\n >\n Loading messages...\n </div>\n ) : messages.length === 0 ? (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n padding: \"40px\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n }}\n >\n No messages yet. Start the conversation!\n </div>\n ) : (\n messages.map((message) => (\n <div\n key={message.id}\n style={{\n display: \"flex\",\n gap: \"12px\",\n opacity: message.type === \"system\" ? 0.75 : 1,\n }}\n >\n {/* Avatar */}\n {message.type !== \"system\" && (\n <div\n style={{\n width: \"32px\",\n height: \"32px\",\n borderRadius: \"8px\",\n background: message.author.color,\n color: \"white\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: \"11px\",\n fontWeight: 650,\n flexShrink: 0,\n opacity: 0.9,\n }}\n >\n {message.author.initials}\n </div>\n )}\n {message.type === \"system\" && (\n <div\n style={{\n width: \"32px\",\n height: \"32px\",\n borderRadius: \"8px\",\n background: \"rgba(30, 33, 37, 0.08)\",\n color: \"rgba(30, 33, 37, 0.52)\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: \"11px\",\n fontWeight: 650,\n flexShrink: 0,\n }}\n >\n <Clock size={14} />\n </div>\n )}\n\n {/* Message content */}\n <div style={{ flex: 1, minWidth: 0 }}>\n {/* Author and timestamp */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"baseline\",\n gap: \"8px\",\n marginBottom: \"4px\",\n }}\n >\n <span\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n fontWeight: 650,\n color: \"var(--text-base, rgba(30,33,37,0.78))\",\n }}\n >\n {message.author.name}\n </span>\n <span\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontFamily: \"var(--font-mono, monospace)\",\n }}\n >\n {message.timestamp}\n </span>\n {message.author.role && (\n <span\n style={{\n fontSize: \"var(--text-xs, 10px)\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n background: \"rgba(30, 33, 37, 0.06)\",\n padding: \"2px 6px\",\n borderRadius: \"4px\",\n textTransform: \"uppercase\",\n letterSpacing: \"0.04em\",\n fontWeight: 600,\n }}\n >\n {message.author.role}\n </span>\n )}\n {message.isEdited && (\n <span\n style={{\n fontSize: \"var(--text-xs, 10px)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontStyle: \"italic\",\n }}\n >\n (edited)\n </span>\n )}\n </div>\n\n {/* Message text */}\n <div\n style={{\n fontSize: \"var(--text-md, 13px)\",\n color: \"var(--text-base, rgba(30,33,37,0.78))\",\n lineHeight: 1.5,\n marginBottom: message.references ? \"8px\" : 0,\n }}\n >\n {message.content}\n </div>\n\n {/* References */}\n {message.references && message.references.length > 0 && (\n <div\n style={{\n display: \"flex\",\n flexWrap: \"wrap\",\n gap: \"6px\",\n marginTop: \"8px\",\n }}\n >\n {message.references.map((ref, idx) => (\n <button\n key={idx}\n type=\"button\"\n style={{\n fontSize: \"11px\",\n padding: \"4px 8px\",\n borderRadius: \"6px\",\n border: \"1px solid rgba(52, 58, 64, 0.16)\",\n background: \"rgba(255, 255, 255, 0.7)\",\n color:\n ref.type === \"condition\"\n ? \"rgba(94, 136, 176, 0.85)\"\n : ref.type === \"observation\"\n ? \"rgba(107, 123, 147, 0.85)\"\n : ref.type === \"timestamp\"\n ? \"rgba(184, 156, 106, 0.85)\"\n : \"rgba(30, 33, 37, 0.65)\",\n cursor: \"pointer\",\n display: \"inline-flex\",\n alignItems: \"center\",\n gap: \"4px\",\n transition: \"all 0.15s ease\",\n fontWeight: 550,\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background =\n \"rgba(255, 255, 255, 0.95)\";\n e.currentTarget.style.borderColor =\n \"rgba(52, 58, 64, 0.24)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background =\n \"rgba(255, 255, 255, 0.7)\";\n e.currentTarget.style.borderColor =\n \"rgba(52, 58, 64, 0.16)\";\n }}\n >\n {ref.type === \"timestamp\" && <Clock size={12} />}\n {(ref.type === \"condition\" ||\n ref.type === \"observation\") && <Hash size={12} />}\n {ref.label}\n </button>\n ))}\n </div>\n )}\n </div>\n </div>\n ))\n )}\n <div ref={messagesEndRef} />\n </div>\n\n {/* Input area */}\n <div\n style={{\n padding: \"12px\",\n borderTop: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n }}\n >\n <div\n style={{\n display: \"flex\",\n gap: \"8px\",\n alignItems: \"flex-end\",\n }}\n >\n {/* Current user avatar */}\n <div\n style={{\n width: \"32px\",\n height: \"32px\",\n borderRadius: \"var(--radius-md, 8px)\",\n background: displayCurrentUser.color,\n color: \"white\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: \"var(--text-sm, 11px)\",\n fontWeight: 650,\n flexShrink: 0,\n opacity: 0.9,\n }}\n >\n {displayCurrentUser.initials}\n </div>\n\n {/* Input field */}\n <div\n style={{\n flex: 1,\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n }}\n >\n <textarea\n value={messageInput}\n onChange={(e) => setMessageInput(e.target.value)}\n onKeyDown={handleKeyPress}\n onFocus={() => setIsFocused(true)}\n onBlur={() => setIsFocused(false)}\n placeholder=\"Add a comment...\"\n style={{\n width: \"100%\",\n minHeight: \"38px\",\n maxHeight: \"120px\",\n padding: \"8px 12px\",\n fontSize: \"var(--text-md, 13px)\",\n color: \"var(--text-base, rgba(30,33,37,0.78))\",\n background: \"white\",\n border: `1px solid ${\n isFocused\n ? \"rgba(94, 136, 176, 0.35)\"\n : \"rgba(52, 58, 64, 0.16)\"\n }`,\n borderRadius: \"var(--radius-md, 8px)\",\n resize: \"vertical\",\n outline: \"none\",\n transition: \"border-color 0.15s ease\",\n fontFamily: \"inherit\",\n lineHeight: 1.5,\n }}\n />\n\n {/* Toolbar */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"space-between\",\n }}\n >\n <div style={{ display: \"flex\", gap: \"4px\" }}>\n <button\n type=\"button\"\n style={{\n padding: \"6px\",\n background: \"transparent\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"rgba(30, 33, 37, 0.52)\",\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background =\n \"rgba(30, 33, 37, 0.06)\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.75)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.52)\";\n }}\n title=\"Mention user\"\n >\n <AtSign size={16} />\n </button>\n <button\n type=\"button\"\n style={{\n padding: \"6px\",\n background: \"transparent\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"rgba(30, 33, 37, 0.52)\",\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background =\n \"rgba(30, 33, 37, 0.06)\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.75)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.52)\";\n }}\n title=\"Reference condition\"\n >\n <Hash size={16} />\n </button>\n <button\n type=\"button\"\n style={{\n padding: \"6px\",\n background: \"transparent\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"rgba(30, 33, 37, 0.52)\",\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background =\n \"rgba(30, 33, 37, 0.06)\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.75)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.52)\";\n }}\n title=\"Attach file\"\n >\n <Paperclip size={16} />\n </button>\n </div>\n <button\n type=\"button\"\n onClick={handleSend}\n disabled={!messageInput.trim() || isSending}\n style={{\n padding: \"6px 12px\",\n background:\n messageInput.trim() && !isSending\n ? \"rgba(94, 136, 176, 0.85)\"\n : \"var(--border-subtle, rgba(52,58,64,0.08))\",\n border: \"none\",\n borderRadius: \"6px\",\n color:\n messageInput.trim() && !isSending\n ? \"white\"\n : \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontSize: \"var(--text-sm, 11px)\",\n fontWeight: 600,\n cursor:\n messageInput.trim() && !isSending\n ? \"pointer\"\n : \"not-allowed\",\n display: \"flex\",\n alignItems: \"center\",\n gap: \"6px\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n if (messageInput.trim() && !isSending) {\n e.currentTarget.style.background = \"rgba(94, 136, 176, 1)\";\n }\n }}\n onMouseLeave={(e) => {\n if (messageInput.trim() && !isSending) {\n e.currentTarget.style.background =\n \"rgba(94, 136, 176, 0.85)\";\n }\n }}\n >\n {isSending ? (\n <>\n <style>\n {`\n @keyframes messageSpin {\n from { transform: rotate(0deg); }\n to { transform: rotate(360deg); }\n }\n `}\n </style>\n <div\n style={{\n width: \"14px\",\n height: \"14px\",\n border: \"2px solid rgba(255, 255, 255, 0.3)\",\n borderTopColor: \"white\",\n borderRadius: \"50%\",\n animation: \"messageSpin 0.6s linear infinite\",\n }}\n />\n Sending...\n </>\n ) : (\n <>\n <Send size={14} />\n Send\n </>\n )}\n </button>\n </div>\n </div>\n </div>\n <div\n style={{\n marginTop: \"8px\",\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n lineHeight: 1.4,\n }}\n >\n <strong>Tip:</strong> Use{\" \"}\n <code\n style={{\n background: \"rgba(30, 33, 37, 0.06)\",\n padding: \"2px 4px\",\n borderRadius: \"3px\",\n fontFamily: \"var(--font-mono, monospace)\",\n fontSize: \"var(--text-xs, 10px)\",\n }}\n >\n @\n </code>{\" \"}\n to mention teammates,{\" \"}\n <code\n style={{\n background: \"rgba(30, 33, 37, 0.06)\",\n padding: \"2px 4px\",\n borderRadius: \"3px\",\n fontFamily: \"var(--font-mono, monospace)\",\n fontSize: \"var(--text-xs, 10px)\",\n }}\n >\n #\n </code>{\" \"}\n to reference conditions\n </div>\n </div>\n </div>\n );\n}\n\n"],"names":["ThinkingIndicator","phase","toolSteps","label","elapsedMs","compact","formatElapsedTime","ms","seconds","minutes","remainingSeconds","getPhaseLabel","renderToolStep","step","index","getStatusDot","baseDotStyle","jsx","getStatusText","jsxs","renderShimmerBar","renderCursor","phaseLabel","elapsedTime","toast","args","ChatInterface","initialMessages","onSendMessage","onStreamMessage","onMessagesChange","onCodeBlockClick","placeholder","title","messages","setMessages","useState","inputValue","setInputValue","isProcessing","setIsProcessing","isSending","setIsSending","currentAssistantMessage","setCurrentAssistantMessage","thinkingPhase","setThinkingPhase","thinkingStartTime","setThinkingStartTime","setElapsedMs","messagesEndRef","useRef","inputRef","streamAbortController","currentAssistantRef","lastChunkTimeRef","streamSilent","setStreamSilent","silenceSeconds","setSilenceSeconds","useEffect","_a","allMessages","interval","gap","resetProcessingState","parseSSELine","line","data","handleStreamChunk","chunk","_b","delta","prev","baseMessage","updated","processStream","stream","reader","decoder","buffer","done","value","lines","parsed","handleSend","userContent","userMessage","newMessages","result","assistantMessage","resolved","error","handleKeyDown","e","Fragment","message","ChatMessage","Send","ChatHistoryPanel","threads","activeThreadId","onSelectThread","onNewChat","onRenameThread","onDeleteThread","loading","searchQuery","setSearchQuery","hoveredId","setHoveredId","editingId","setEditingId","editValue","setEditValue","deletingId","setDeletingId","editInputRef","sortedThreads","thread","q","a","b","aTime","formatTime","dateStr","d","diffMs","diffDays","startEdit","saveEdit","trimmed","cancelEdit","startDelete","confirmDelete","cancelDelete","iconBtnStyle","Search","isActive","isHovered","isEditing","isDeleting","canEdit","canDelete","showActions","MessageSquare","Pin","Check","X","Pencil","Trash2","Clock","useUserContext","MessageThread","sessionTitle","currentUser","messageInput","setMessageInput","isFocused","setIsFocused","isLoading","setIsLoading","userData","displayCurrentUser","n","content","optimisticMessage","msg","handleKeyPress","ref","idx","Hash","AtSign","Paperclip"],"mappings":"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"}
1
+ {"version":3,"file":"chat.cjs.js","sources":["../../src/components/chat/ThinkingIndicator.jsx","../../src/components/chat/ChatInterface.jsx","../../src/components/chat/ChatHistoryPanel.jsx","../../src/components/chat/MessageThread.jsx"],"sourcesContent":["\"use client\";\n\nexport default function ThinkingIndicator({ \n phase = \"thinking\", \n toolSteps = [], \n label,\n elapsedMs,\n compact = false\n}) {\n const formatElapsedTime = (ms) => {\n if (!ms || ms < 1000) return null;\n const seconds = Math.floor(ms / 1000);\n if (seconds < 60) return `${seconds}s`;\n const minutes = Math.floor(seconds / 60);\n const remainingSeconds = seconds % 60;\n return remainingSeconds > 0 ? `${minutes}m ${remainingSeconds}s` : `${minutes}m`;\n };\n\n const getPhaseLabel = () => {\n if (label) return label;\n switch (phase) {\n case \"thinking\": return \"Thinking...\";\n case \"tool\": return null;\n case \"responding\": return \"Responding...\";\n default: return \"Thinking...\";\n }\n };\n\n const renderToolStep = (step, index) => {\n const getStatusDot = () => {\n const baseDotStyle = {\n width: compact ? '4px' : '6px',\n height: compact ? '4px' : '6px',\n borderRadius: '50%',\n display: 'inline-block',\n marginRight: compact ? '6px' : '8px'\n };\n\n switch (step.status) {\n case 'active':\n return (\n <span \n style={{\n ...baseDotStyle,\n backgroundColor: 'var(--rail-purple, #9B7AA8)',\n animation: 'pulse 1.2s ease-in-out infinite'\n }}\n />\n );\n case 'done':\n return (\n <span \n style={{\n ...baseDotStyle,\n backgroundColor: 'var(--text-xfaint, rgba(30,33,37,0.28))'\n }}\n />\n );\n case 'error':\n return (\n <span \n style={{\n ...baseDotStyle,\n backgroundColor: 'var(--rail-compliance, #C98A5A)'\n }}\n />\n );\n default:\n return (\n <span \n style={{\n ...baseDotStyle,\n backgroundColor: 'var(--text-xfaint, rgba(30,33,37,0.28))'\n }}\n />\n );\n }\n };\n\n const getStatusText = () => {\n switch (step.status) {\n case 'done':\n return (\n <span style={{ \n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n fontSize: compact ? '9px' : 'var(--text-xs-plus, 10.5px)'\n }}>\n ✓\n </span>\n );\n case 'error':\n return (\n <span style={{ \n color: 'var(--rail-compliance, #C98A5A)',\n fontSize: compact ? '9px' : 'var(--text-xs-plus, 10.5px)'\n }}>\n failed\n </span>\n );\n default:\n return null;\n }\n };\n\n return (\n <div \n key={index}\n style={{\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'space-between',\n marginBottom: compact ? '2px' : '4px'\n }}\n >\n <div style={{ display: 'flex', alignItems: 'center' }}>\n {getStatusDot()}\n <span style={{\n fontFamily: 'var(--font-mono)',\n fontSize: compact ? '9px' : 'var(--text-xs-plus, 10.5px)',\n color: 'var(--text-muted)'\n }}>\n {step.name}\n </span>\n </div>\n {getStatusText()}\n </div>\n );\n };\n\n const renderShimmerBar = () => (\n <div style={{\n width: '100%',\n height: compact ? '2px' : '3px',\n backgroundColor: 'var(--border-subtle, rgba(52,58,64,0.08))',\n borderRadius: compact ? '2px' : '3px',\n overflow: 'hidden',\n position: 'relative'\n }}>\n <div style={{\n position: 'absolute',\n top: 0,\n left: 0,\n right: 0,\n bottom: 0,\n background: 'linear-gradient(90deg, transparent 0%, rgba(155,122,168,0.3) 50%, transparent 100%)',\n animation: 'shimmer 2s linear infinite'\n }} />\n </div>\n );\n\n const renderCursor = () => (\n <span style={{\n width: compact ? '4px' : '6px',\n height: compact ? '10px' : '14px',\n backgroundColor: 'var(--rail-purple, #9B7AA8)',\n borderRadius: '1px',\n display: 'inline-block',\n marginLeft: '2px',\n animation: 'cursorBlink 0.8s ease-in-out infinite'\n }} />\n );\n\n const phaseLabel = getPhaseLabel();\n const elapsedTime = formatElapsedTime(elapsedMs);\n\n return (\n <div style={{\n borderLeft: `${compact ? '3px' : '4px'} solid var(--rail-purple, #9B7AA8)`,\n backgroundColor: 'var(--card-assistant, rgba(155,122,168,0.06))',\n border: '1px solid var(--border-subtle, rgba(52,58,64,0.08))',\n borderRadius: compact ? '8px' : '10px',\n padding: compact ? '8px 10px 8px 12px' : '10px 14px 10px 18px'\n }}>\n <style>\n {`\n @keyframes shimmer {\n 0% { transform: translateX(-100%); }\n 100% { transform: translateX(200%); }\n }\n \n @keyframes pulse {\n 0%, 100% { opacity: 0.4; }\n 50% { opacity: 1.0; }\n }\n \n @keyframes cursorBlink {\n 0%, 100% { opacity: 0; }\n 50% { opacity: 1; }\n }\n `}\n </style>\n \n {/* Header */}\n {!compact && (\n <div style={{\n fontSize: 'var(--text-xs-plus, 10.5px)',\n fontWeight: 650,\n textTransform: 'uppercase',\n letterSpacing: 'var(--tracking-label, 0.16em)',\n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n marginBottom: '8px'\n }}>\n AI ASSISTANT\n </div>\n )}\n\n {/* Content based on phase */}\n {phase === \"thinking\" && (\n <div>\n <div style={{\n color: 'var(--text-muted)',\n fontWeight: 400,\n fontSize: compact ? '11px' : '13px',\n marginBottom: compact ? '4px' : '8px',\n display: 'flex',\n alignItems: 'center',\n gap: '6px'\n }}>\n {phaseLabel}\n {elapsedTime && (\n <span style={{\n fontSize: compact ? '9px' : '10px',\n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n fontFamily: 'var(--font-mono, monospace)',\n }}>\n {elapsedTime}\n </span>\n )}\n </div>\n {renderShimmerBar()}\n </div>\n )}\n\n {phase === \"tool\" && (\n <div>\n {phaseLabel && (\n <div style={{\n color: 'var(--text-muted)',\n fontWeight: 400,\n fontSize: compact ? '11px' : '13px',\n marginBottom: compact ? '4px' : '8px',\n display: 'flex',\n alignItems: 'center',\n gap: '6px'\n }}>\n {phaseLabel}\n {elapsedTime && (\n <span style={{\n fontSize: compact ? '9px' : '10px',\n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n fontFamily: 'var(--font-mono, monospace)',\n }}>\n {elapsedTime}\n </span>\n )}\n </div>\n )}\n <div style={{ marginBottom: compact ? '4px' : '8px' }}>\n {toolSteps.map((step, index) => renderToolStep(step, index))}\n </div>\n {renderShimmerBar()}\n </div>\n )}\n\n {phase === \"responding\" && (\n <div style={{\n color: 'var(--text-muted)',\n fontWeight: 400,\n fontSize: compact ? '11px' : '13px',\n display: 'flex',\n alignItems: 'center',\n gap: '6px'\n }}>\n <div style={{ display: 'flex', alignItems: 'center' }}>\n {phaseLabel}\n {renderCursor()}\n </div>\n {elapsedTime && (\n <span style={{\n fontSize: compact ? '9px' : '10px',\n color: 'var(--text-faint, rgba(30,33,37,0.36))',\n fontFamily: 'var(--font-mono, monospace)',\n }}>\n {elapsedTime}\n </span>\n )}\n </div>\n )}\n </div>\n );\n}","\"use client\";\n\nimport React, { useState, useRef, useEffect } from \"react\";\nimport { Send } from \"lucide-react\";\nimport ChatMessage from \"./ChatMessage\";\nimport ThinkingIndicator from \"./ThinkingIndicator\";\n// TODO: replace with framework-agnostic toast\nconst toast = { error: (...args) => console.warn(\"toast.error:\", ...args) };\n\n/**\n * ChatInterface Component\n * Interactive chat interface with streaming SSE support, thinking phases, and tool visibility.\n */\nexport default function ChatInterface({\n initialMessages = [],\n onSendMessage,\n onStreamMessage, // NEW: streaming version of onSendMessage\n onMessagesChange, // NEW: callback when messages array changes\n onCodeBlockClick, // callback when \"Canvas\" button clicked on a code block: ({ code, language }) => void\n placeholder = \"Ask a question about this interaction...\",\n title = \"Chat with Chordia\",\n}) {\n const [messages, setMessages] = useState(initialMessages || []);\n const [inputValue, setInputValue] = useState(\"\");\n const [isProcessing, setIsProcessing] = useState(false);\n const [isSending, setIsSending] = useState(false);\n const [currentAssistantMessage, setCurrentAssistantMessage] = useState(null);\n const [thinkingPhase, setThinkingPhase] = useState(\"thinking\");\n const [thinkingStartTime, setThinkingStartTime] = useState(null);\n const [elapsedMs, setElapsedMs] = useState(0);\n const messagesEndRef = useRef(null);\n const inputRef = useRef(null);\n const streamAbortController = useRef(null);\n const currentAssistantRef = useRef(null);\n const lastChunkTimeRef = useRef(null);\n const [streamSilent, setStreamSilent] = useState(false);\n const [silenceSeconds, setSilenceSeconds] = useState(0);\n\n // Auto-scroll to bottom when messages change\n useEffect(() => {\n messagesEndRef.current?.scrollIntoView({ behavior: \"smooth\" });\n }, [messages, isProcessing]);\n\n // Auto-resize textarea\n useEffect(() => {\n if (inputRef.current) {\n inputRef.current.style.height = \"auto\";\n inputRef.current.style.height = `${Math.min(\n inputRef.current.scrollHeight,\n 120\n )}px`;\n }\n }, [inputValue]);\n\n // Update messages and notify parent\n useEffect(() => {\n if (onMessagesChange) {\n const allMessages = [...messages];\n if (currentAssistantMessage) {\n allMessages.push(currentAssistantMessage);\n }\n onMessagesChange(allMessages);\n }\n }, [messages, currentAssistantMessage, onMessagesChange]);\n\n // Elapsed time tracker + silence detector\n useEffect(() => {\n let interval;\n if (isProcessing && thinkingStartTime) {\n interval = setInterval(() => {\n setElapsedMs(Date.now() - thinkingStartTime);\n // Detect stream silence (no chunks for 3s+)\n if (lastChunkTimeRef.current) {\n const gap = (Date.now() - lastChunkTimeRef.current) / 1000;\n if (gap >= 3) {\n setStreamSilent(true);\n setSilenceSeconds(Math.floor(gap));\n } else {\n setStreamSilent(false);\n }\n }\n }, 500);\n }\n return () => interval && clearInterval(interval);\n }, [isProcessing, thinkingStartTime]);\n\n const resetProcessingState = () => {\n setIsProcessing(false);\n setIsSending(false);\n setCurrentAssistantMessage(null);\n currentAssistantRef.current = null;\n setThinkingPhase(\"thinking\");\n setStreamSilent(false);\n setSilenceSeconds(0);\n lastChunkTimeRef.current = null;\n setThinkingStartTime(null);\n setElapsedMs(0);\n if (streamAbortController.current) {\n streamAbortController.current.abort();\n streamAbortController.current = null;\n }\n };\n\n const parseSSELine = (line) => {\n if (line.startsWith(\"data: \")) {\n const data = line.slice(6);\n if (data === \"[DONE]\") {\n return { type: \"done\" };\n }\n try {\n const parsed = JSON.parse(data);\n return { type: \"data\", data: parsed };\n } catch (e) {\n return null;\n }\n }\n return null;\n };\n\n const handleStreamChunk = (chunk) => {\n if (!chunk.choices?.[0]?.delta) return;\n\n lastChunkTimeRef.current = Date.now();\n setStreamSilent(false);\n\n const delta = chunk.choices[0].delta;\n \n // Check for tool use/result indicators\n if (delta.tool_calls || delta.tool_results) {\n setThinkingPhase(\"tool\");\n return;\n }\n\n // If we get content, switch to responding phase\n if (delta.content !== undefined) {\n setThinkingPhase(\"responding\");\n \n // Initialize or update current assistant message\n setCurrentAssistantMessage(prev => {\n const baseMessage = prev || {\n id: Date.now().toString(),\n role: \"assistant\",\n content: \"\",\n timestamp: new Date().toLocaleTimeString(undefined, {\n hour: \"2-digit\",\n minute: \"2-digit\",\n }),\n isStreaming: true,\n };\n \n const updated = {\n ...baseMessage,\n content: (baseMessage.content || \"\") + (delta.content || \"\"),\n };\n currentAssistantRef.current = updated;\n return updated;\n });\n }\n };\n\n const processStream = async (stream) => {\n const reader = stream.getReader();\n const decoder = new TextDecoder();\n let buffer = \"\";\n\n try {\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n\n buffer += decoder.decode(value, { stream: true });\n const lines = buffer.split(\"\\n\");\n buffer = lines.pop() || \"\"; // Keep incomplete line in buffer\n\n for (const line of lines) {\n if (line.trim()) {\n const parsed = parseSSELine(line);\n if (parsed) {\n if (parsed.type === \"done\") {\n return; // Stream complete\n } else if (parsed.type === \"data\") {\n handleStreamChunk(parsed.data);\n }\n }\n }\n }\n }\n } finally {\n reader.releaseLock();\n }\n };\n\n const handleSend = async () => {\n if (!inputValue.trim() || isSending) return;\n\n const userContent = inputValue.trim();\n const userMessage = {\n id: Date.now().toString(),\n role: \"user\",\n content: userContent,\n timestamp: new Date().toLocaleTimeString(undefined, {\n hour: \"2-digit\",\n minute: \"2-digit\",\n }),\n };\n\n // Add user message and start processing\n const newMessages = [...messages, userMessage];\n setMessages(newMessages);\n setInputValue(\"\");\n setIsProcessing(true);\n setIsSending(true);\n setThinkingPhase(\"thinking\");\n setThinkingStartTime(Date.now());\n lastChunkTimeRef.current = Date.now();\n\n // Create abort controller for this stream\n streamAbortController.current = new AbortController();\n\n try {\n let result;\n \n // Use streaming version if provided, otherwise fall back to regular\n if (onStreamMessage) {\n result = await onStreamMessage(userContent, newMessages);\n } else if (onSendMessage) {\n result = await onSendMessage(userContent, newMessages);\n } else {\n // Fallback to dummy response\n setTimeout(() => {\n const assistantMessage = {\n id: (Date.now() + 1).toString(),\n role: \"assistant\",\n content: \"This is a demonstration response. In a real implementation, this would connect to your LLM backend.\",\n timestamp: new Date().toLocaleTimeString(undefined, {\n hour: \"2-digit\",\n minute: \"2-digit\",\n }),\n };\n setMessages(prev => [...prev, assistantMessage]);\n resetProcessingState();\n }, 1000);\n return;\n }\n\n // Handle ReadableStream response\n if (result instanceof ReadableStream) {\n await processStream(result);\n } \n // Handle Response with SSE body\n else if (result instanceof Response && result.body) {\n await processStream(result.body);\n }\n // Handle Promise that resolves to a stream\n else if (result && typeof result.then === \"function\") {\n const resolved = await result;\n if (resolved instanceof ReadableStream) {\n await processStream(resolved);\n } else if (resolved instanceof Response && resolved.body) {\n await processStream(resolved.body);\n }\n }\n\n // Finalize the assistant message using ref (state is stale in this closure)\n if (currentAssistantRef.current) {\n setMessages(prev => [...prev, { \n ...currentAssistantRef.current, \n isStreaming: false \n }]);\n }\n\n } catch (error) {\n if (error.name !== \"AbortError\") {\n toast.error(\"Failed to send message\");\n console.error(\"Stream error:\", error);\n }\n } finally {\n resetProcessingState();\n }\n };\n\n const handleKeyDown = (e) => {\n if (e.key === \"Enter\" && !e.shiftKey) {\n e.preventDefault();\n handleSend();\n }\n };\n\n return (\n <div\n style={{\n display: \"flex\",\n flexDirection: \"column\",\n height: \"100%\",\n border: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n borderRadius: \"var(--radius-lg, 12px)\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n overflow: \"hidden\",\n }}\n >\n {/* Header — hidden when title is empty */}\n {title ? <div\n style={{\n padding: \"16px 20px\",\n borderBottom: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n }}\n >\n <div\n style={{\n fontSize: \"var(--text-lg, 16px)\",\n fontWeight: 720,\n letterSpacing: \"-0.01em\",\n color: \"var(--text-strong, rgba(30,33,37,0.92))\",\n }}\n >\n {title}\n </div>\n <div\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n marginTop: \"2px\",\n }}\n >\n Ask questions, get insights from analyzed interactions\n </div>\n </div> : null}\n\n {/* Messages area */}\n <div\n style={{\n flex: 1,\n minHeight: 0,\n overflowY: \"auto\",\n padding: \"20px\",\n display: \"flex\",\n flexDirection: \"column\",\n }}\n >\n {messages.length === 0 ? (\n <div\n style={{\n flex: 1,\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontSize: \"var(--text-md, 13px)\",\n textAlign: \"center\",\n padding: \"40px\",\n }}\n >\n No messages yet. Start a conversation by asking a question below.\n </div>\n ) : (\n <>\n {messages.map((message) => (\n <ChatMessage\n key={message.id}\n role={message.role}\n content={message.content}\n html={message.html}\n timestamp={message.timestamp}\n toolBadges={message.toolBadges}\n isStreaming={message.isStreaming}\n onCodeBlockClick={onCodeBlockClick}\n />\n ))}\n \n {/* Current streaming message */}\n {currentAssistantMessage && (\n <ChatMessage\n key={currentAssistantMessage.id}\n role={currentAssistantMessage.role}\n content={currentAssistantMessage.content}\n timestamp={currentAssistantMessage.timestamp}\n isStreaming={true}\n onCodeBlockClick={onCodeBlockClick}\n />\n )}\n \n {/* Thinking indicator — shows during initial thinking or stream silence */}\n {isProcessing && (!currentAssistantMessage || streamSilent) && (\n <div style={{ marginBottom: \"16px\" }}>\n <ThinkingIndicator \n phase={streamSilent ? \"tool\" : thinkingPhase}\n elapsedMs={elapsedMs}\n label={\n streamSilent && silenceSeconds >= 30\n ? \"Compacting conversation — trimming context to stay sharp...\"\n : streamSilent && silenceSeconds >= 10\n ? \"Running background tasks...\"\n : streamSilent\n ? \"Still working...\"\n : undefined\n }\n />\n </div>\n )}\n \n <div ref={messagesEndRef} />\n </>\n )}\n </div>\n\n {/* Input area */}\n <div\n style={{\n borderTop: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n padding: \"16px 20px\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n }}\n >\n <div\n style={{\n display: \"flex\",\n gap: \"12px\",\n alignItems: \"flex-end\",\n }}\n >\n <textarea\n ref={inputRef}\n value={inputValue}\n onChange={(e) => setInputValue(e.target.value)}\n onKeyDown={handleKeyDown}\n placeholder={placeholder}\n rows={1}\n disabled={isSending}\n style={{\n flex: 1,\n padding: \"10px 14px\",\n fontSize: \"var(--text-base, 14px)\",\n lineHeight: 1.5,\n color: \"var(--text-strong, rgba(30,33,37,0.92))\",\n background: \"rgba(255, 255, 255, 0.95)\",\n border: \"1px solid rgba(52, 58, 64, 0.18)\",\n borderRadius: \"var(--radius-md, 8px)\",\n resize: \"none\",\n outline: \"none\",\n transition: \"border-color 0.15s ease\",\n fontFamily: \"inherit\",\n minHeight: \"42px\",\n maxHeight: \"120px\",\n opacity: isSending ? 0.6 : 1,\n cursor: isSending ? \"not-allowed\" : \"text\",\n }}\n onFocus={(e) => {\n if (!isSending) {\n e.target.style.borderColor = \"rgba(94, 136, 176, 0.35)\";\n }\n }}\n onBlur={(e) => {\n e.target.style.borderColor = \"rgba(52, 58, 64, 0.18)\";\n }}\n />\n <button\n onClick={handleSend}\n disabled={!inputValue.trim() || isSending}\n style={{\n padding: \"10px 16px\",\n background:\n inputValue.trim() && !isSending\n ? \"var(--Base-Strong, #0B0B0B)\"\n : \"#ECEEF2\",\n color:\n inputValue.trim() && !isSending\n ? \"white\"\n : \"var(--text-base)\",\n border: \"none\",\n borderRadius: \"var(--radius-md, 8px)\",\n cursor:\n inputValue.trim() && !isSending ? \"pointer\" : \"not-allowed\",\n display: \"flex\",\n alignItems: \"center\",\n gap: \"6px\",\n fontSize: \"var(--text-md, 13px)\",\n fontWeight: 650,\n transition: \"all 0.15s ease\",\n height: \"42px\",\n }}\n // onMouseEnter={(e) => {\n // if (inputValue.trim() && !isSending) {\n // e.currentTarget.style.background = \"var(--Base-Strong, #0B0B0B)\";\n // }\n // }}\n // onMouseLeave={(e) => {\n // if (inputValue.trim() && !isSending) {\n // e.currentTarget.style.background = \"#ECEEF2\";\n // }\n // }}\n >\n {isSending ? (\n <>\n <style>\n {`\n @keyframes buttonSpin {\n from { transform: rotate(0deg); }\n to { transform: rotate(360deg); }\n }\n `}\n </style>\n <div\n style={{\n width: \"14px\",\n height: \"14px\",\n border: \"2px solid rgba(255, 255, 255, 0.3)\",\n borderTopColor: \"white\",\n borderRadius: \"50%\",\n animation: \"buttonSpin 0.6s linear infinite\",\n }}\n />\n Sending...\n </>\n ) : (\n <>\n <Send size={16} />\n Send\n </>\n )}\n </button>\n </div>\n <div\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n marginTop: \"8px\",\n }}\n >\n Press Enter to send, Shift+Enter for new line\n </div>\n </div>\n </div>\n );\n}","\"use client\";\n\nimport React, { useState, useRef, useEffect } from \"react\";\nimport { MessageSquare, Search, Clock, Pin, Pencil, Trash2, Check, X } from \"lucide-react\";\n\n/**\n * ChatHistoryPanel Component\n * Panel showing chat thread history with search functionality.\n *\n * Props:\n * threads - Array of thread objects: { id, title, created_at, updated_at, message_count, last_message_preview, pinned, archived, tags }\n * activeThreadId - Currently selected thread id\n * onSelectThread - (threadId) => void\n * onNewChat - () => void\n * onRenameThread - (threadId, newTitle) => void // optional: when provided, inline edit is enabled\n * onDeleteThread - (threadId) => void // optional: when provided, inline delete is enabled\n * loading - boolean\n */\nexport default function ChatHistoryPanel({\n threads = [],\n activeThreadId,\n onSelectThread,\n onNewChat,\n onRenameThread,\n onDeleteThread,\n loading = false,\n}) {\n const [searchQuery, setSearchQuery] = useState(\"\");\n const [hoveredId, setHoveredId] = useState(null);\n const [editingId, setEditingId] = useState(null);\n const [editValue, setEditValue] = useState(\"\");\n const [deletingId, setDeletingId] = useState(null);\n const editInputRef = useRef(null);\n\n useEffect(() => {\n if (editingId && editInputRef.current) {\n editInputRef.current.focus();\n editInputRef.current.select();\n }\n }, [editingId]);\n\n const filteredThreads = threads.filter((thread) => {\n if (!searchQuery) return true;\n const q = searchQuery.toLowerCase();\n return (\n (thread.title || \"\").toLowerCase().includes(q) ||\n (thread.last_message_preview || \"\").toLowerCase().includes(q)\n );\n });\n\n // Sort: pinned first, then by updated_at descending\n const sortedThreads = [...filteredThreads].sort((a, b) => {\n if (a.pinned && !b.pinned) return -1;\n if (!a.pinned && b.pinned) return 1;\n const aTime = new Date(a.updated_at || a.created_at || 0).getTime();\n const bTime = new Date(b.updated_at || b.created_at || 0).getTime();\n return bTime - aTime;\n });\n\n const formatTime = (dateStr) => {\n if (!dateStr) return \"\";\n const d = new Date(dateStr);\n const now = new Date();\n const diffMs = now.getTime() - d.getTime();\n const diffDays = Math.floor(diffMs / 86400000);\n if (diffDays === 0) {\n return d.toLocaleTimeString(undefined, { hour: \"2-digit\", minute: \"2-digit\" });\n } else if (diffDays === 1) {\n return \"Yesterday\";\n } else if (diffDays < 7) {\n return d.toLocaleDateString(undefined, { weekday: \"short\" });\n } else {\n return d.toLocaleDateString(undefined, { month: \"short\", day: \"numeric\" });\n }\n };\n\n const startEdit = (e, thread) => {\n e.stopPropagation();\n setDeletingId(null);\n setEditingId(thread.id);\n setEditValue(thread.title || \"\");\n };\n\n const saveEdit = (e) => {\n if (e) e.stopPropagation();\n const trimmed = (editValue || \"\").trim();\n if (editingId && trimmed) {\n onRenameThread?.(editingId, trimmed);\n }\n setEditingId(null);\n setEditValue(\"\");\n };\n\n const cancelEdit = (e) => {\n if (e) e.stopPropagation();\n setEditingId(null);\n setEditValue(\"\");\n };\n\n const startDelete = (e, thread) => {\n e.stopPropagation();\n setEditingId(null);\n setDeletingId(thread.id);\n };\n\n const confirmDelete = (e) => {\n if (e) e.stopPropagation();\n if (deletingId) {\n onDeleteThread?.(deletingId);\n }\n setDeletingId(null);\n };\n\n const cancelDelete = (e) => {\n if (e) e.stopPropagation();\n setDeletingId(null);\n };\n\n const iconBtnStyle = {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: \"22px\",\n height: \"22px\",\n padding: 0,\n background: \"transparent\",\n border: \"none\",\n borderRadius: \"4px\",\n cursor: \"pointer\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n transition: \"all 0.12s ease\",\n flexShrink: 0,\n };\n\n return (\n <div\n style={{\n display: \"flex\",\n flexDirection: \"column\",\n height: \"100%\",\n background: \"var(--paper, rgba(255,255,255,0.95))\",\n borderRight: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n overflow: \"hidden\",\n }}\n >\n {/* Header */}\n <div\n style={{\n padding: \"12px 14px\",\n borderBottom: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n flexShrink: 0,\n }}\n >\n <div\n style={{\n display: \"flex\",\n justifyContent: \"space-between\",\n alignItems: \"center\",\n marginBottom: \"10px\",\n }}\n >\n <div\n style={{\n fontSize: \"13px\",\n fontWeight: 650,\n color: \"var(--text-ink, rgba(30,33,37,0.92))\",\n }}\n >\n Threads\n </div>\n {onNewChat && (\n <button\n onClick={onNewChat}\n style={{\n padding: \"4px 10px\",\n fontSize: \"11px\",\n fontWeight: 600,\n color: \"var(--Base-Strong, #0B0B0B)\",\n background: \"#ECEEF2\",\n border: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n borderRadius: \"6px\",\n cursor: \"pointer\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"#ECEEF2\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"rgba(94, 136, 176, 0.08)\";\n }}\n >\n + New\n </button>\n )}\n </div>\n\n {/* Search */}\n <div style={{ position: \"relative\" }}>\n <Search\n size={13}\n style={{\n position: \"absolute\",\n left: \"10px\",\n top: \"50%\",\n transform: \"translateY(-50%)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n pointerEvents: \"none\",\n }}\n />\n <input\n type=\"text\"\n value={searchQuery}\n onChange={(e) => setSearchQuery(e.target.value)}\n placeholder=\"Search threads...\"\n style={{\n width: \"100%\",\n padding: \"7px 10px 7px 32px\",\n fontSize: \"12px\",\n color: \"var(--text-ink, rgba(30,33,37,0.92))\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n border: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n borderRadius: \"6px\",\n outline: \"none\",\n transition: \"border-color 0.15s ease\",\n boxSizing: \"border-box\",\n }}\n onFocus={(e) => {\n e.target.style.borderColor = \"rgba(94, 136, 176, 0.35)\";\n }}\n onBlur={(e) => {\n e.target.style.borderColor = \"rgba(52, 58, 64, 0.12)\";\n }}\n />\n </div>\n </div>\n\n {/* Thread List */}\n <div style={{ flex: 1, overflowY: \"auto\", padding: \"4px 6px\" }}>\n {loading ? (\n <div\n style={{\n padding: \"30px 16px\",\n textAlign: \"center\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontSize: \"12px\",\n }}\n >\n Loading threads...\n </div>\n ) : sortedThreads.length === 0 ? (\n <div\n style={{\n padding: \"30px 16px\",\n textAlign: \"center\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontSize: \"12px\",\n }}\n >\n {searchQuery ? \"No threads found\" : \"No threads yet\"}\n </div>\n ) : (\n sortedThreads.map((thread) => {\n const isActive = thread.id === activeThreadId;\n const isHovered = hoveredId === thread.id;\n const isEditing = editingId === thread.id;\n const isDeleting = deletingId === thread.id;\n const canEdit = typeof onRenameThread === \"function\";\n const canDelete = typeof onDeleteThread === \"function\";\n const showActions = (canEdit || canDelete) && isHovered && !isEditing && !isDeleting;\n\n return (\n <div\n key={thread.id}\n onClick={() => {\n if (isEditing || isDeleting) return;\n onSelectThread?.(thread.id);\n }}\n onMouseEnter={(e) => {\n setHoveredId(thread.id);\n if (!isActive) e.currentTarget.style.background = \"rgba(0,0,0,0.03)\";\n }}\n onMouseLeave={(e) => {\n setHoveredId((prev) => (prev === thread.id ? null : prev));\n if (!isActive) e.currentTarget.style.background = \"transparent\";\n }}\n style={{\n padding: \"10px 10px\",\n marginBottom: \"2px\",\n borderRadius: \"6px\",\n background: isActive\n ? \"rgba(94, 136, 176, 0.10)\"\n : \"transparent\",\n border: isActive\n ? \"1px solid rgba(94, 136, 176, 0.15)\"\n : \"1px solid transparent\",\n cursor: isEditing || isDeleting ? \"default\" : \"pointer\",\n transition: \"all 0.12s ease\",\n }}\n >\n {/* Title row */}\n <div style={{ display: \"flex\", alignItems: \"center\", gap: \"6px\", marginBottom: \"4px\" }}>\n <MessageSquare\n size={12}\n style={{\n color: isActive ? \"var(--rail-discovery, #5E88B0)\" : \"var(--text-faint, rgba(30,33,37,0.36))\",\n flexShrink: 0,\n }}\n />\n\n {isEditing ? (\n <input\n ref={editInputRef}\n type=\"text\"\n value={editValue}\n onChange={(e) => setEditValue(e.target.value)}\n onClick={(e) => e.stopPropagation()}\n onKeyDown={(e) => {\n e.stopPropagation();\n if (e.key === \"Enter\") saveEdit(e);\n else if (e.key === \"Escape\") cancelEdit(e);\n }}\n style={{\n flex: 1,\n minWidth: 0,\n fontSize: \"12px\",\n fontWeight: 600,\n color: \"var(--text-ink, rgba(30,33,37,0.92))\",\n background: \"var(--paper-elevated, #fff)\",\n border: \"1px solid rgba(94, 136, 176, 0.45)\",\n borderRadius: \"4px\",\n padding: \"3px 6px\",\n outline: \"none\",\n boxSizing: \"border-box\",\n }}\n />\n ) : (\n <div\n style={{\n flex: 1,\n minWidth: 0,\n fontSize: \"12px\",\n fontWeight: isActive ? 650 : 550,\n color: isActive\n ? \"var(--text-ink, rgba(30,33,37,0.92))\"\n : \"var(--text-base, rgba(30,33,37,0.78))\",\n overflow: \"hidden\",\n textOverflow: \"ellipsis\",\n whiteSpace: \"nowrap\",\n }}\n >\n {thread.title || \"Untitled thread\"}\n </div>\n )}\n\n {!isEditing && !isDeleting && thread.pinned && (\n <Pin size={10} style={{ color: \"var(--rail-discovery, #5E88B0)\", flexShrink: 0 }} />\n )}\n\n {/* Inline edit actions: save / cancel */}\n {isEditing && (\n <div style={{ display: \"inline-flex\", alignItems: \"center\", gap: \"2px\", flexShrink: 0 }}>\n <button\n type=\"button\"\n title=\"Save\"\n onClick={saveEdit}\n style={{\n ...iconBtnStyle,\n color: \"var(--rail-discovery, #5E88B0)\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"rgba(94, 136, 176, 0.12)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n }}\n >\n <Check size={13} />\n </button>\n <button\n type=\"button\"\n title=\"Cancel\"\n onClick={cancelEdit}\n style={iconBtnStyle}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"rgba(0,0,0,0.06)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n }}\n >\n <X size={13} />\n </button>\n </div>\n )}\n\n {/* Hover actions: edit / delete */}\n {showActions && (\n <div style={{ display: \"inline-flex\", alignItems: \"center\", gap: \"2px\", flexShrink: 0 }}>\n {canEdit && (\n <button\n type=\"button\"\n title=\"Rename\"\n onClick={(e) => startEdit(e, thread)}\n style={iconBtnStyle}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"rgba(0,0,0,0.06)\";\n e.currentTarget.style.color = \"var(--text-ink, rgba(30,33,37,0.92))\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"var(--text-muted, rgba(30,33,37,0.56))\";\n }}\n >\n <Pencil size={12} />\n </button>\n )}\n {canDelete && (\n <button\n type=\"button\"\n title=\"Delete\"\n onClick={(e) => startDelete(e, thread)}\n style={iconBtnStyle}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"rgba(220, 53, 69, 0.10)\";\n e.currentTarget.style.color = \"#DC3545\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"var(--text-muted, rgba(30,33,37,0.56))\";\n }}\n >\n <Trash2 size={12} />\n </button>\n )}\n </div>\n )}\n </div>\n\n {/* Inline delete confirmation */}\n {isDeleting ? (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n flexWrap: \"wrap\",\n gap: \"8px\",\n marginLeft: \"18px\",\n marginTop: \"2px\",\n }}\n >\n <span\n style={{\n fontSize: \"11px\",\n color: \"var(--text-base, rgba(30,33,37,0.78))\",\n fontWeight: 500,\n }}\n >\n Confirm: delete this thread?\n </span>\n <button\n type=\"button\"\n onClick={confirmDelete}\n style={{\n padding: \"3px 10px\",\n fontSize: \"11px\",\n fontWeight: 600,\n color: \"var(--text-ink, rgba(30,33,37,0.92))\",\n background: \"#ECEEF2\",\n border: \"1px solid var(--border-subtle, rgba(52,58,64,0.08))\",\n borderRadius: \"5px\",\n cursor: \"pointer\",\n transition: \"background 0.12s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background = \"#E2E5EA\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"#ECEEF2\";\n }}\n >\n Yes\n </button>\n <button\n type=\"button\"\n onClick={cancelDelete}\n style={{\n padding: \"3px 4px\",\n fontSize: \"11px\",\n fontWeight: 500,\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n background: \"transparent\",\n border: \"none\",\n cursor: \"pointer\",\n transition: \"color 0.12s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.color = \"var(--text-ink, rgba(30,33,37,0.92))\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.color = \"var(--text-muted, rgba(30,33,37,0.56))\";\n }}\n >\n No\n </button>\n </div>\n ) : (\n <>\n {/* Preview */}\n {thread.last_message_preview && !isEditing && (\n <div\n style={{\n fontSize: \"11px\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n overflow: \"hidden\",\n textOverflow: \"ellipsis\",\n whiteSpace: \"nowrap\",\n marginLeft: \"18px\",\n marginBottom: \"4px\",\n }}\n >\n {thread.last_message_preview}\n </div>\n )}\n\n {/* Meta */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n gap: \"6px\",\n marginLeft: \"18px\",\n fontSize: \"10px\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n }}\n >\n <Clock size={9} />\n <span>{formatTime(thread.updated_at || thread.created_at)}</span>\n {thread.message_count != null && (\n <>\n <span>·</span>\n <span>{thread.message_count} msg{thread.message_count !== 1 ? \"s\" : \"\"}</span>\n </>\n )}\n </div>\n </>\n )}\n </div>\n );\n })\n )}\n </div>\n </div>\n );\n}\n","/**\n * NOTE: Deprecated component.\n *\n * This chat-scoped `MessageThread` was an early demo implementation and\n * is tightly coupled to app-specific context (`useUserContext`, `toast`, etc.).\n *\n * For new work and for consumers of the `chordia-ui` library, prefer the\n * framework-agnostic, reusable version exported from:\n *\n * `src/components/common/MessageThread.jsx`\n *\n * which is re-exported via the main package entry:\n *\n * import { MessageThread } from \"chordia-ui\";\n *\n * This file is kept only for backwards compatibility within the app.\n */\n\"use client\";\n\nimport React, { useState, useEffect, useRef } from \"react\";\nimport { Send, Paperclip, AtSign, Hash, Clock } from \"lucide-react\";\n// TODO: replace with framework-agnostic toast\nconst toast = { error: (...args) => console.warn(\"toast.error:\", ...args) };\n// TODO: replace with framework-agnostic context\nconst useUserContext = () => ({ userData: { name: \"User\", email: \"\" } });\n\n/**\n * MessageThread Component\n * Threaded messaging interface for team collaboration around sessions.\n * Supports mentions, condition references, and timestamp links.\n * Uses dummy data for demonstration purposes.\n */\nexport default function MessageThread({\n sessionTitle,\n messages: initialMessages,\n onSendMessage,\n currentUser,\n}) {\n const [messageInput, setMessageInput] = useState(\"\");\n const [isFocused, setIsFocused] = useState(false);\n const [messages, setMessages] = useState(initialMessages || []);\n const [isLoading, setIsLoading] = useState(false);\n const [isSending, setIsSending] = useState(false);\n const { userData } = useUserContext();\n const messagesEndRef = useRef(null);\n\n // Get current user from context if not provided\n const displayCurrentUser = currentUser || {\n name: userData?.name || \"You\",\n initials: userData?.name\n ?.split(\" \")\n .map((n) => n[0])\n .join(\"\")\n .toUpperCase() || \"YO\",\n color: \"#6B7C93\",\n };\n\n // Use initialMessages if provided, otherwise use empty array (no API fetching)\n useEffect(() => {\n if (initialMessages) {\n setMessages(initialMessages);\n } else {\n setMessages([]);\n }\n }, [initialMessages]);\n\n // Scroll to bottom when new messages arrive\n useEffect(() => {\n if (messagesEndRef.current) {\n messagesEndRef.current.scrollIntoView({ behavior: \"smooth\" });\n }\n }, [messages]);\n\n const handleSend = async () => {\n if (!messageInput.trim()) return;\n\n const content = messageInput.trim();\n setMessageInput(\"\");\n setIsSending(true);\n\n // Create optimistic message\n const optimisticMessage = {\n id: `temp-${Date.now()}`,\n author: {\n name: displayCurrentUser.name,\n role: userData?.role || \"\",\n initials: displayCurrentUser.initials,\n color: displayCurrentUser.color,\n },\n content: content,\n timestamp: \"Just now\",\n type: \"comment\",\n isOptimistic: true,\n };\n\n // Optimistically add message\n setMessages((prev) => [...prev, optimisticMessage]);\n\n // If onSendMessage callback is provided, use it\n if (onSendMessage) {\n try {\n await onSendMessage(content);\n // Remove optimistic flag after callback succeeds\n setMessages((prev) =>\n prev.map((msg) =>\n msg.id === optimisticMessage.id\n ? { ...msg, isOptimistic: false }\n : msg\n )\n );\n } catch (error) {\n // Remove optimistic message on error\n setMessages((prev) => prev.filter((msg) => msg.id !== optimisticMessage.id));\n toast.error(\"Failed to send message\");\n } finally {\n setIsSending(false);\n }\n return;\n }\n\n // No API - just confirm the optimistic message\n setTimeout(() => {\n setMessages((prev) =>\n prev.map((msg) =>\n msg.id === optimisticMessage.id\n ? { ...msg, isOptimistic: false }\n : msg\n )\n );\n setIsSending(false);\n }, 500);\n };\n\n const handleKeyPress = (e) => {\n if (e.key === \"Enter\" && !e.shiftKey) {\n e.preventDefault();\n handleSend();\n }\n };\n\n return (\n <div\n style={{\n display: \"flex\",\n flexDirection: \"column\",\n height: \"100%\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n border: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n borderRadius: \"var(--radius-lg, 12px)\",\n overflow: \"hidden\",\n }}\n >\n {/* Header */}\n {sessionTitle && (\n <div\n style={{\n padding: \"14px 16px\",\n borderBottom: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n }}\n >\n <div\n style={{\n fontSize: \"var(--text-md, 13px)\",\n fontWeight: 680,\n color: \"var(--text-strong, rgba(30,33,37,0.92))\",\n marginBottom: \"3px\",\n }}\n >\n Session Discussion\n </div>\n {sessionTitle && (\n <div\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n display: \"flex\",\n alignItems: \"center\",\n gap: \"8px\",\n }}\n >\n <span>{sessionTitle}</span>\n </div>\n )}\n </div>\n )}\n\n {/* Messages */}\n <div\n style={{\n flex: 1,\n overflowY: \"auto\",\n padding: \"16px\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"16px\",\n }}\n >\n {isLoading ? (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n padding: \"40px\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n }}\n >\n Loading messages...\n </div>\n ) : messages.length === 0 ? (\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n padding: \"40px\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n }}\n >\n No messages yet. Start the conversation!\n </div>\n ) : (\n messages.map((message) => (\n <div\n key={message.id}\n style={{\n display: \"flex\",\n gap: \"12px\",\n opacity: message.type === \"system\" ? 0.75 : 1,\n }}\n >\n {/* Avatar */}\n {message.type !== \"system\" && (\n <div\n style={{\n width: \"32px\",\n height: \"32px\",\n borderRadius: \"8px\",\n background: message.author.color,\n color: \"white\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: \"11px\",\n fontWeight: 650,\n flexShrink: 0,\n opacity: 0.9,\n }}\n >\n {message.author.initials}\n </div>\n )}\n {message.type === \"system\" && (\n <div\n style={{\n width: \"32px\",\n height: \"32px\",\n borderRadius: \"8px\",\n background: \"rgba(30, 33, 37, 0.08)\",\n color: \"rgba(30, 33, 37, 0.52)\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: \"11px\",\n fontWeight: 650,\n flexShrink: 0,\n }}\n >\n <Clock size={14} />\n </div>\n )}\n\n {/* Message content */}\n <div style={{ flex: 1, minWidth: 0 }}>\n {/* Author and timestamp */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"baseline\",\n gap: \"8px\",\n marginBottom: \"4px\",\n }}\n >\n <span\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n fontWeight: 650,\n color: \"var(--text-base, rgba(30,33,37,0.78))\",\n }}\n >\n {message.author.name}\n </span>\n <span\n style={{\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontFamily: \"var(--font-mono, monospace)\",\n }}\n >\n {message.timestamp}\n </span>\n {message.author.role && (\n <span\n style={{\n fontSize: \"var(--text-xs, 10px)\",\n color: \"var(--text-muted, rgba(30,33,37,0.56))\",\n background: \"rgba(30, 33, 37, 0.06)\",\n padding: \"2px 6px\",\n borderRadius: \"4px\",\n textTransform: \"uppercase\",\n letterSpacing: \"0.04em\",\n fontWeight: 600,\n }}\n >\n {message.author.role}\n </span>\n )}\n {message.isEdited && (\n <span\n style={{\n fontSize: \"var(--text-xs, 10px)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontStyle: \"italic\",\n }}\n >\n (edited)\n </span>\n )}\n </div>\n\n {/* Message text */}\n <div\n style={{\n fontSize: \"var(--text-md, 13px)\",\n color: \"var(--text-base, rgba(30,33,37,0.78))\",\n lineHeight: 1.5,\n marginBottom: message.references ? \"8px\" : 0,\n }}\n >\n {message.content}\n </div>\n\n {/* References */}\n {message.references && message.references.length > 0 && (\n <div\n style={{\n display: \"flex\",\n flexWrap: \"wrap\",\n gap: \"6px\",\n marginTop: \"8px\",\n }}\n >\n {message.references.map((ref, idx) => (\n <button\n key={idx}\n type=\"button\"\n style={{\n fontSize: \"11px\",\n padding: \"4px 8px\",\n borderRadius: \"6px\",\n border: \"1px solid rgba(52, 58, 64, 0.16)\",\n background: \"rgba(255, 255, 255, 0.7)\",\n color:\n ref.type === \"condition\"\n ? \"rgba(94, 136, 176, 0.85)\"\n : ref.type === \"observation\"\n ? \"rgba(107, 123, 147, 0.85)\"\n : ref.type === \"timestamp\"\n ? \"rgba(184, 156, 106, 0.85)\"\n : \"rgba(30, 33, 37, 0.65)\",\n cursor: \"pointer\",\n display: \"inline-flex\",\n alignItems: \"center\",\n gap: \"4px\",\n transition: \"all 0.15s ease\",\n fontWeight: 550,\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background =\n \"rgba(255, 255, 255, 0.95)\";\n e.currentTarget.style.borderColor =\n \"rgba(52, 58, 64, 0.24)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background =\n \"rgba(255, 255, 255, 0.7)\";\n e.currentTarget.style.borderColor =\n \"rgba(52, 58, 64, 0.16)\";\n }}\n >\n {ref.type === \"timestamp\" && <Clock size={12} />}\n {(ref.type === \"condition\" ||\n ref.type === \"observation\") && <Hash size={12} />}\n {ref.label}\n </button>\n ))}\n </div>\n )}\n </div>\n </div>\n ))\n )}\n <div ref={messagesEndRef} />\n </div>\n\n {/* Input area */}\n <div\n style={{\n padding: \"12px\",\n borderTop: \"1px solid var(--border, rgba(52,58,64,0.12))\",\n background: \"var(--paper-elevated, rgba(255,255,255,0.82))\",\n }}\n >\n <div\n style={{\n display: \"flex\",\n gap: \"8px\",\n alignItems: \"flex-end\",\n }}\n >\n {/* Current user avatar */}\n <div\n style={{\n width: \"32px\",\n height: \"32px\",\n borderRadius: \"var(--radius-md, 8px)\",\n background: displayCurrentUser.color,\n color: \"white\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: \"var(--text-sm, 11px)\",\n fontWeight: 650,\n flexShrink: 0,\n opacity: 0.9,\n }}\n >\n {displayCurrentUser.initials}\n </div>\n\n {/* Input field */}\n <div\n style={{\n flex: 1,\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n }}\n >\n <textarea\n value={messageInput}\n onChange={(e) => setMessageInput(e.target.value)}\n onKeyDown={handleKeyPress}\n onFocus={() => setIsFocused(true)}\n onBlur={() => setIsFocused(false)}\n placeholder=\"Add a comment...\"\n style={{\n width: \"100%\",\n minHeight: \"38px\",\n maxHeight: \"120px\",\n padding: \"8px 12px\",\n fontSize: \"var(--text-md, 13px)\",\n color: \"var(--text-base, rgba(30,33,37,0.78))\",\n background: \"white\",\n border: `1px solid ${\n isFocused\n ? \"rgba(94, 136, 176, 0.35)\"\n : \"rgba(52, 58, 64, 0.16)\"\n }`,\n borderRadius: \"var(--radius-md, 8px)\",\n resize: \"vertical\",\n outline: \"none\",\n transition: \"border-color 0.15s ease\",\n fontFamily: \"inherit\",\n lineHeight: 1.5,\n }}\n />\n\n {/* Toolbar */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"space-between\",\n }}\n >\n <div style={{ display: \"flex\", gap: \"4px\" }}>\n <button\n type=\"button\"\n style={{\n padding: \"6px\",\n background: \"transparent\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"rgba(30, 33, 37, 0.52)\",\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background =\n \"rgba(30, 33, 37, 0.06)\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.75)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.52)\";\n }}\n title=\"Mention user\"\n >\n <AtSign size={16} />\n </button>\n <button\n type=\"button\"\n style={{\n padding: \"6px\",\n background: \"transparent\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"rgba(30, 33, 37, 0.52)\",\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background =\n \"rgba(30, 33, 37, 0.06)\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.75)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.52)\";\n }}\n title=\"Reference condition\"\n >\n <Hash size={16} />\n </button>\n <button\n type=\"button\"\n style={{\n padding: \"6px\",\n background: \"transparent\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"rgba(30, 33, 37, 0.52)\",\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n e.currentTarget.style.background =\n \"rgba(30, 33, 37, 0.06)\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.75)\";\n }}\n onMouseLeave={(e) => {\n e.currentTarget.style.background = \"transparent\";\n e.currentTarget.style.color = \"rgba(30, 33, 37, 0.52)\";\n }}\n title=\"Attach file\"\n >\n <Paperclip size={16} />\n </button>\n </div>\n <button\n type=\"button\"\n onClick={handleSend}\n disabled={!messageInput.trim() || isSending}\n style={{\n padding: \"6px 12px\",\n background:\n messageInput.trim() && !isSending\n ? \"rgba(94, 136, 176, 0.85)\"\n : \"var(--border-subtle, rgba(52,58,64,0.08))\",\n border: \"none\",\n borderRadius: \"6px\",\n color:\n messageInput.trim() && !isSending\n ? \"white\"\n : \"var(--text-faint, rgba(30,33,37,0.36))\",\n fontSize: \"var(--text-sm, 11px)\",\n fontWeight: 600,\n cursor:\n messageInput.trim() && !isSending\n ? \"pointer\"\n : \"not-allowed\",\n display: \"flex\",\n alignItems: \"center\",\n gap: \"6px\",\n transition: \"all 0.15s ease\",\n }}\n onMouseEnter={(e) => {\n if (messageInput.trim() && !isSending) {\n e.currentTarget.style.background = \"rgba(94, 136, 176, 1)\";\n }\n }}\n onMouseLeave={(e) => {\n if (messageInput.trim() && !isSending) {\n e.currentTarget.style.background =\n \"rgba(94, 136, 176, 0.85)\";\n }\n }}\n >\n {isSending ? (\n <>\n <style>\n {`\n @keyframes messageSpin {\n from { transform: rotate(0deg); }\n to { transform: rotate(360deg); }\n }\n `}\n </style>\n <div\n style={{\n width: \"14px\",\n height: \"14px\",\n border: \"2px solid rgba(255, 255, 255, 0.3)\",\n borderTopColor: \"white\",\n borderRadius: \"50%\",\n animation: \"messageSpin 0.6s linear infinite\",\n }}\n />\n Sending...\n </>\n ) : (\n <>\n <Send size={14} />\n Send\n </>\n )}\n </button>\n </div>\n </div>\n </div>\n <div\n style={{\n marginTop: \"8px\",\n fontSize: \"var(--text-sm, 11px)\",\n color: \"var(--text-faint, rgba(30,33,37,0.36))\",\n lineHeight: 1.4,\n }}\n >\n <strong>Tip:</strong> Use{\" \"}\n <code\n style={{\n background: \"rgba(30, 33, 37, 0.06)\",\n padding: \"2px 4px\",\n borderRadius: \"3px\",\n fontFamily: \"var(--font-mono, monospace)\",\n fontSize: \"var(--text-xs, 10px)\",\n }}\n >\n @\n </code>{\" \"}\n to mention teammates,{\" \"}\n <code\n style={{\n background: \"rgba(30, 33, 37, 0.06)\",\n padding: \"2px 4px\",\n borderRadius: \"3px\",\n fontFamily: \"var(--font-mono, monospace)\",\n fontSize: \"var(--text-xs, 10px)\",\n }}\n >\n #\n </code>{\" \"}\n to reference conditions\n </div>\n </div>\n </div>\n );\n}\n\n"],"names":["ThinkingIndicator","phase","toolSteps","label","elapsedMs","compact","formatElapsedTime","ms","seconds","minutes","remainingSeconds","getPhaseLabel","renderToolStep","step","index","getStatusDot","baseDotStyle","jsx","getStatusText","jsxs","renderShimmerBar","renderCursor","phaseLabel","elapsedTime","toast","args","ChatInterface","initialMessages","onSendMessage","onStreamMessage","onMessagesChange","onCodeBlockClick","placeholder","title","messages","setMessages","useState","inputValue","setInputValue","isProcessing","setIsProcessing","isSending","setIsSending","currentAssistantMessage","setCurrentAssistantMessage","thinkingPhase","setThinkingPhase","thinkingStartTime","setThinkingStartTime","setElapsedMs","messagesEndRef","useRef","inputRef","streamAbortController","currentAssistantRef","lastChunkTimeRef","streamSilent","setStreamSilent","silenceSeconds","setSilenceSeconds","useEffect","_a","allMessages","interval","gap","resetProcessingState","parseSSELine","line","data","handleStreamChunk","chunk","_b","delta","prev","baseMessage","updated","processStream","stream","reader","decoder","buffer","done","value","lines","parsed","handleSend","userContent","userMessage","newMessages","result","assistantMessage","resolved","error","handleKeyDown","e","Fragment","message","ChatMessage","Send","ChatHistoryPanel","threads","activeThreadId","onSelectThread","onNewChat","onRenameThread","onDeleteThread","loading","searchQuery","setSearchQuery","hoveredId","setHoveredId","editingId","setEditingId","editValue","setEditValue","deletingId","setDeletingId","editInputRef","sortedThreads","thread","q","a","b","aTime","formatTime","dateStr","d","diffMs","diffDays","startEdit","saveEdit","trimmed","cancelEdit","startDelete","confirmDelete","cancelDelete","iconBtnStyle","Search","isActive","isHovered","isEditing","isDeleting","canEdit","canDelete","showActions","MessageSquare","Pin","Check","X","Pencil","Trash2","Clock","useUserContext","MessageThread","sessionTitle","currentUser","messageInput","setMessageInput","isFocused","setIsFocused","isLoading","setIsLoading","userData","displayCurrentUser","n","content","optimisticMessage","msg","handleKeyPress","ref","idx","Hash","AtSign","Paperclip"],"mappings":"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"}