@ash-ai/ui 0.0.3 → 0.0.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +2 -2
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +2 -2
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.ts","../src/utils.ts","../src/context/PlaygroundContext.tsx","../src/hooks/usePlaygroundChat.ts","../src/hooks/useAgents.ts","../src/hooks/useSessions.ts","../src/hooks/useHealthCheck.ts","../src/hooks/useFileUpload.ts","../src/icons.tsx","../src/components/StatusIndicator.tsx","../src/components/PlaygroundHeader.tsx","../src/components/ChatMessages.tsx","../src/components/ToolCallBlock.tsx","../src/components/ChatMessage.tsx","../src/components/ChatInput.tsx","../src/components/Chat.tsx","../src/components/SessionHistory.tsx","../src/components/Terminal.tsx","../src/components/FileBrowser.tsx","../src/components/FileTree.tsx","../src/components/BottomPanels.tsx","../src/hooks/useTerminal.ts","../src/hooks/useFileBrowser.ts","../src/components/Playground.tsx"],"sourcesContent":["// Components\nexport { Playground } from './components/Playground.js';\nexport type { PlaygroundProps } from './components/Playground.js';\n\nexport { Chat } from './components/Chat.js';\nexport type { ChatProps } from './components/Chat.js';\n\nexport { ChatMessages } from './components/ChatMessages.js';\nexport type { ChatMessagesProps } from './components/ChatMessages.js';\n\nexport { ChatInput } from './components/ChatInput.js';\nexport type { ChatInputProps } from './components/ChatInput.js';\n\nexport { ChatMessage } from './components/ChatMessage.js';\nexport type { ChatMessageProps } from './components/ChatMessage.js';\n\nexport { ToolCallBlock, ThinkingBlock } from './components/ToolCallBlock.js';\n\nexport { Terminal } from './components/Terminal.js';\nexport type { TerminalProps } from './components/Terminal.js';\n\nexport { FileBrowser } from './components/FileBrowser.js';\nexport type { FileBrowserProps } from './components/FileBrowser.js';\n\nexport { FileTree } from './components/FileTree.js';\nexport type { FileTreeProps } from './components/FileTree.js';\n\nexport { SessionHistory } from './components/SessionHistory.js';\nexport type { SessionHistoryProps } from './components/SessionHistory.js';\n\nexport { StatusIndicator } from './components/StatusIndicator.js';\nexport type { StatusIndicatorProps } from './components/StatusIndicator.js';\n\nexport { PlaygroundHeader } from './components/PlaygroundHeader.js';\nexport type { PlaygroundHeaderProps } from './components/PlaygroundHeader.js';\n\nexport { BottomPanels } from './components/BottomPanels.js';\nexport type { BottomPanelsProps } from './components/BottomPanels.js';\n\n// Context\nexport { PlaygroundProvider, usePlaygroundContext } from './context/PlaygroundContext.js';\nexport type { PlaygroundContextValue, PlaygroundProviderProps } from './context/PlaygroundContext.js';\n\n// Hooks\nexport {\n usePlaygroundChat,\n useTerminal,\n useFileBrowser,\n useFileUpload,\n useAgents,\n useSessions,\n useHealthCheck,\n} from './hooks/index.js';\n\nexport type {\n UsePlaygroundChatOptions,\n UsePlaygroundChatReturn,\n UseTerminalOptions,\n UseTerminalReturn,\n UseFileBrowserOptions,\n UseFileBrowserReturn,\n UseFileUploadOptions,\n UseFileUploadReturn,\n UseAgentsOptions,\n UseAgentsReturn,\n UseSessionsOptions,\n UseSessionsReturn,\n UseHealthCheckOptions,\n UseHealthCheckReturn,\n} from './hooks/index.js';\n\n// Types\nexport type { ChatMessage as ChatMessageType, ToolCall, AttachedFile, TreeNode, LogEntry } from './types.js';\n\n// Utils\nexport { cn, formatBytes, formatTime, buildFileTree, parseContentBlocks, isImageFile, getFileLanguage } from './utils.js';\n","import { clsx, type ClassValue } from 'clsx';\nimport { twMerge } from 'tailwind-merge';\nimport type { TreeNode, ToolCall } from './types.js';\n\nexport function cn(...inputs: ClassValue[]): string {\n return twMerge(clsx(inputs));\n}\n\nexport function formatBytes(bytes: number): string {\n if (bytes === 0) return '0 B';\n const k = 1024;\n const sizes = ['B', 'KB', 'MB', 'GB'];\n const i = Math.floor(Math.log(bytes) / Math.log(k));\n return parseFloat((bytes / Math.pow(k, i)).toFixed(1)) + ' ' + sizes[i];\n}\n\nexport function formatTime(ts: string): string {\n return new Date(ts).toLocaleTimeString('en-US', { hour12: false, hour: '2-digit', minute: '2-digit' });\n}\n\nexport function formatTimestamp(ts: string): string {\n return new Date(ts).toLocaleTimeString('en-US', {\n hour12: false,\n hour: '2-digit',\n minute: '2-digit',\n second: '2-digit',\n });\n}\n\nexport function buildFileTree(files: Array<{ path: string; size: number; modifiedAt: string }>): TreeNode[] {\n const root: TreeNode[] = [];\n\n for (const file of files) {\n const parts = file.path.split('/');\n let current = root;\n\n for (let i = 0; i < parts.length; i++) {\n const name = parts[i];\n const isLast = i === parts.length - 1;\n const partialPath = parts.slice(0, i + 1).join('/');\n\n let existing = current.find((n) => n.name === name && n.isDir === !isLast);\n if (!existing) {\n existing = {\n name,\n path: partialPath,\n isDir: !isLast,\n size: isLast ? file.size : undefined,\n modifiedAt: isLast ? file.modifiedAt : undefined,\n children: [],\n };\n current.push(existing);\n }\n current = existing.children;\n }\n }\n\n function sortNodes(nodes: TreeNode[]) {\n nodes.sort((a, b) => {\n if (a.isDir !== b.isDir) return a.isDir ? -1 : 1;\n return a.name.localeCompare(b.name);\n });\n for (const n of nodes) {\n if (n.children.length > 0) sortNodes(n.children);\n }\n }\n\n sortNodes(root);\n return root;\n}\n\n/**\n * Unwrap a message envelope object into content blocks or plain text.\n * Handles Claude Code conversation formats like:\n * { type: \"user\", content: \"hello\" }\n * { type: \"assistant\", message: { content: [...blocks] } }\n * { type: \"result\", result: \"text\" }\n */\nfunction unwrapMessageObject(obj: Record<string, unknown>): unknown {\n if (obj.message && typeof obj.message === 'object') {\n const msg = obj.message as Record<string, unknown>;\n if (Array.isArray(msg.content)) return msg.content;\n }\n if (Array.isArray(obj.content)) return obj.content;\n if (typeof obj.content === 'string') return obj.content;\n if (typeof obj.result === 'string') return obj.result;\n return '';\n}\n\n/**\n * Parse content blocks (from Anthropic SDK format) into text + tool calls + thinking.\n * Handles both JSON string content and pre-parsed arrays, as well as\n * wrapped message envelopes from Claude Code conversations.\n */\nexport function parseContentBlocks(content: unknown): { text: string; toolCalls: ToolCall[]; thinking: string[] } {\n let blocks: unknown[] | null = null;\n\n if (typeof content === 'string') {\n try {\n const parsed = JSON.parse(content);\n if (Array.isArray(parsed)) {\n blocks = parsed;\n } else if (parsed && typeof parsed === 'object') {\n return parseContentBlocks(unwrapMessageObject(parsed));\n }\n } catch {\n return { text: content, toolCalls: [], thinking: [] };\n }\n } else if (Array.isArray(content)) {\n blocks = content;\n } else if (content && typeof content === 'object') {\n return parseContentBlocks(unwrapMessageObject(content as Record<string, unknown>));\n }\n\n if (!blocks) {\n return { text: typeof content === 'string' ? content : '', toolCalls: [], thinking: [] };\n }\n\n let text = '';\n const toolCalls: ToolCall[] = [];\n const thinking: string[] = [];\n\n for (const block of blocks) {\n const b = block as Record<string, unknown>;\n if (b.type === 'text' && typeof b.text === 'string') {\n text += (text ? '\\n' : '') + b.text;\n } else if (b.type === 'tool_use') {\n toolCalls.push({\n id: (b.id as string) || `tool-${toolCalls.length}`,\n name: (b.name as string) || 'unknown',\n input: b.input,\n state: 'completed',\n });\n } else if (b.type === 'tool_result') {\n const match = toolCalls.find((tc) => tc.id === (b.tool_use_id as string));\n if (match) {\n match.output = b.content;\n match.isError = (b.is_error as boolean) ?? false;\n match.state = b.is_error ? 'error' : 'completed';\n }\n } else if (b.type === 'thinking') {\n const t = (b.thinking as string) || (b.text as string) || '';\n if (t) thinking.push(t);\n }\n }\n\n return { text, toolCalls, thinking };\n}\n\nconst IMAGE_EXTS = new Set(['png', 'jpg', 'jpeg', 'gif', 'svg', 'webp', 'ico']);\n\nexport function isImageFile(name: string): boolean {\n const ext = name.split('.').pop()?.toLowerCase();\n return IMAGE_EXTS.has(ext || '');\n}\n\nexport function getFileLanguage(name: string): string {\n const ext = name.split('.').pop()?.toLowerCase();\n const map: Record<string, string> = {\n ts: 'typescript', tsx: 'typescript', js: 'javascript', jsx: 'javascript',\n py: 'python', rs: 'rust', go: 'go', rb: 'ruby',\n json: 'json', yaml: 'yaml', yml: 'yaml', toml: 'toml',\n md: 'markdown', sh: 'bash', bash: 'bash', css: 'css',\n html: 'html', sql: 'sql', xml: 'xml',\n };\n return map[ext || ''] || 'text';\n}\n","import { createContext, useContext, useState, useCallback } from 'react';\nimport type { AshClient, Agent, Session } from '@ash-ai/sdk';\nimport { usePlaygroundChat, type UsePlaygroundChatReturn } from '../hooks/usePlaygroundChat.js';\nimport { useAgents, type UseAgentsReturn } from '../hooks/useAgents.js';\nimport { useSessions, type UseSessionsReturn } from '../hooks/useSessions.js';\nimport { useHealthCheck, type UseHealthCheckReturn } from '../hooks/useHealthCheck.js';\nimport { useFileUpload, type UseFileUploadReturn } from '../hooks/useFileUpload.js';\n\nexport interface PlaygroundContextValue {\n client: AshClient;\n chat: UsePlaygroundChatReturn;\n agents: UseAgentsReturn;\n sessions: UseSessionsReturn;\n health: UseHealthCheckReturn;\n fileUpload: UseFileUploadReturn;\n selectedAgent: string;\n setSelectedAgent: (slug: string) => void;\n showHistory: boolean;\n setShowHistory: (show: boolean) => void;\n terminalOpen: boolean;\n setTerminalOpen: (open: boolean) => void;\n filesOpen: boolean;\n setFilesOpen: (open: boolean) => void;\n}\n\nconst PlaygroundCtx = createContext<PlaygroundContextValue | null>(null);\n\nexport function usePlaygroundContext(): PlaygroundContextValue {\n const ctx = useContext(PlaygroundCtx);\n if (!ctx) throw new Error('usePlaygroundContext must be used within <PlaygroundProvider>');\n return ctx;\n}\n\nexport interface PlaygroundProviderProps {\n client: AshClient;\n defaultAgent?: string;\n children: React.ReactNode;\n}\n\nexport function PlaygroundProvider({ client, defaultAgent, children }: PlaygroundProviderProps) {\n const [selectedAgent, setSelectedAgentRaw] = useState(defaultAgent || '');\n const [showHistory, setShowHistory] = useState(false);\n const [terminalOpen, setTerminalOpen] = useState(false);\n const [filesOpen, setFilesOpen] = useState(false);\n\n const agentsHook = useAgents({ client });\n const health = useHealthCheck({ client });\n\n // Auto-select first agent if none provided\n const resolvedAgent = selectedAgent || agentsHook.agents[0]?.slug || agentsHook.agents[0]?.name || '';\n\n const chat = usePlaygroundChat({\n client,\n agentSlug: resolvedAgent,\n });\n\n const sessions = useSessions({\n client,\n agent: resolvedAgent,\n enabled: showHistory,\n });\n\n const fileUpload = useFileUpload({\n client,\n onFilesChange: chat.setAttachedFiles,\n onError: (err) => {\n // Surface upload errors as chat errors\n chat.setMessages((prev) => [\n ...prev,\n { id: `err-${Date.now()}`, role: 'system', content: err },\n ]);\n },\n });\n\n const setSelectedAgent = useCallback((slug: string) => {\n setSelectedAgentRaw(slug);\n chat.startNewChat();\n }, [chat]);\n\n const value: PlaygroundContextValue = {\n client,\n chat,\n agents: agentsHook,\n sessions,\n health,\n fileUpload,\n selectedAgent: resolvedAgent,\n setSelectedAgent,\n showHistory,\n setShowHistory,\n terminalOpen,\n setTerminalOpen,\n filesOpen,\n setFilesOpen,\n };\n\n return <PlaygroundCtx.Provider value={value}>{children}</PlaygroundCtx.Provider>;\n}\n","import { useState, useCallback, useRef } from 'react';\nimport type { AshClient } from '@ash-ai/sdk';\nimport type { ChatMessage, ToolCall, AttachedFile } from '../types.js';\n\nexport interface UsePlaygroundChatOptions {\n client: AshClient;\n agentSlug: string;\n initialSessionId?: string;\n onSessionStart?: (sessionId: string) => void;\n onError?: (error: string) => void;\n}\n\nexport interface UsePlaygroundChatReturn {\n messages: ChatMessage[];\n input: string;\n setInput: (input: string) => void;\n sending: boolean;\n loading: boolean;\n error: string | null;\n sessionId: string | null;\n attachedFiles: AttachedFile[];\n setAttachedFiles: React.Dispatch<React.SetStateAction<AttachedFile[]>>;\n send: () => Promise<void>;\n loadSession: (sessionId: string) => Promise<void>;\n startNewChat: () => void;\n setMessages: React.Dispatch<React.SetStateAction<ChatMessage[]>>;\n}\n\nexport function usePlaygroundChat({\n client,\n agentSlug,\n initialSessionId,\n onSessionStart,\n onError,\n}: UsePlaygroundChatOptions): UsePlaygroundChatReturn {\n const [messages, setMessages] = useState<ChatMessage[]>([]);\n const [input, setInput] = useState('');\n const [sending, setSending] = useState(false);\n const [loading, setLoading] = useState(false);\n const [error, setError] = useState<string | null>(null);\n const [sessionId, setSessionId] = useState<string | null>(initialSessionId ?? null);\n const [attachedFiles, setAttachedFiles] = useState<AttachedFile[]>([]);\n const sendingRef = useRef(false);\n\n const startNewChat = useCallback(() => {\n setSessionId(null);\n setMessages([]);\n setAttachedFiles([]);\n setError(null);\n }, []);\n\n const loadSession = useCallback(async (sid: string) => {\n setSessionId(sid);\n setLoading(true);\n setError(null);\n\n try {\n const sdkMessages = await client.listMessages(sid);\n const msgs: ChatMessage[] = [];\n\n for (let i = 0; i < sdkMessages.length; i++) {\n const m = sdkMessages[i];\n let text = '';\n const tools: ToolCall[] = [];\n\n let parsed: unknown;\n try {\n parsed = JSON.parse(m.content);\n } catch {\n parsed = m.content;\n }\n\n const data = parsed as Record<string, any>;\n\n // Assistant message with content blocks\n if (data.type === 'assistant' && Array.isArray(data.message?.content)) {\n for (const b of data.message.content) {\n if (b.type === 'text' && b.text) {\n text += (text ? '\\n' : '') + b.text;\n } else if (b.type === 'tool_use') {\n tools.push({\n id: b.id || `tool-${tools.length}`,\n name: b.name || 'unknown',\n input: b.input,\n state: 'completed',\n });\n }\n }\n }\n\n // Tool result message\n if (data.type === 'user' && data.tool_use_result) {\n const r = data.tool_use_result;\n const match = tools.find((tc) => tc.id === r.tool_use_id) ||\n (msgs.length > 0 ? msgs[msgs.length - 1].toolCalls?.find((tc) => tc.id === r.tool_use_id) : undefined);\n if (match) {\n match.output = r.stdout ?? r.content;\n match.isError = r.is_error ?? false;\n match.state = r.is_error ? 'error' : 'completed';\n }\n continue; // Tool results get merged into the previous assistant message\n }\n\n // User message\n if (data.type === 'user' && !data.tool_use_result) {\n const content = Array.isArray(data.content)\n ? data.content.filter((b: any) => b.type === 'text').map((b: any) => b.text).join('\\n')\n : typeof data.content === 'string' ? data.content : '';\n if (content) {\n msgs.push({\n id: m.id || `msg-${i}`,\n role: 'user',\n content,\n timestamp: m.createdAt,\n });\n }\n continue;\n }\n\n // Result message (turn complete)\n if (data.type === 'result' && typeof data.result === 'string') {\n text = data.result;\n }\n\n if (text || tools.length > 0) {\n msgs.push({\n id: m.id || `msg-${i}`,\n role: m.role === 'user' ? 'user' : 'assistant',\n content: text,\n toolCalls: tools.length > 0 ? tools : undefined,\n timestamp: m.createdAt,\n });\n }\n }\n setMessages(msgs);\n } catch {\n setMessages([{ id: 'err', role: 'system', content: 'Failed to load session messages.' }]);\n } finally {\n setLoading(false);\n }\n }, [client]);\n\n const send = useCallback(async () => {\n const textContent = input.trim();\n const readyFiles = attachedFiles.filter((f) => !f.uploading);\n if ((!textContent && readyFiles.length === 0) || !agentSlug || sendingRef.current) return;\n\n let content = textContent;\n if (readyFiles.length > 0) {\n const fileRefs = readyFiles.map((f) => `[Attached file: ${f.filename}](${f.url})`).join('\\n');\n content = content ? `${content}\\n\\n${fileRefs}` : fileRefs;\n }\n\n // Create session on-the-fly if none exists\n let activeSessionId = sessionId;\n if (!activeSessionId) {\n setSending(true);\n sendingRef.current = true;\n setError(null);\n try {\n const session = await client.createSession(agentSlug);\n activeSessionId = session.id;\n setSessionId(activeSessionId);\n onSessionStart?.(activeSessionId);\n } catch (err) {\n const msg = err instanceof Error ? err.message : 'Failed to create session';\n setError(msg);\n onError?.(msg);\n setSending(false);\n sendingRef.current = false;\n return;\n }\n }\n\n setInput('');\n setAttachedFiles([]);\n\n const userMsg: ChatMessage = {\n id: `user-${Date.now()}`,\n role: 'user',\n content,\n timestamp: new Date().toISOString(),\n };\n setMessages((prev) => [...prev, userMsg]);\n setSending(true);\n sendingRef.current = true;\n\n const assistantId = `assistant-${Date.now()}`;\n setMessages((prev) => [...prev, { id: assistantId, role: 'assistant', content: '', isStreaming: true }]);\n\n try {\n let fullContent = '';\n const toolCalls: ToolCall[] = [];\n\n for await (const event of client.sendMessageStream(activeSessionId, content, { includePartialMessages: true })) {\n if (event.type === 'text_delta') {\n const delta = (event.data as { delta: string }).delta || '';\n fullContent += delta;\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, content: fullContent, toolCalls: [...toolCalls], isStreaming: true } : m\n ));\n } else if (event.type === 'tool_use') {\n const data = event.data as { id: string; name: string; input: unknown };\n const tc: ToolCall = {\n id: data.id || `tool-${Date.now()}-${toolCalls.length}`,\n name: data.name || 'unknown',\n input: data.input,\n state: 'running',\n };\n toolCalls.push(tc);\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, content: fullContent, toolCalls: [...toolCalls], isStreaming: true } : m\n ));\n } else if (event.type === 'tool_result') {\n const data = event.data as { tool_use_id: string; content: unknown; is_error?: boolean };\n const matchIdx = toolCalls.findIndex((tc) => tc.id === data.tool_use_id);\n if (matchIdx !== -1) {\n toolCalls[matchIdx] = {\n ...toolCalls[matchIdx],\n output: data.content,\n isError: data.is_error ?? false,\n state: data.is_error ? 'error' : 'completed',\n };\n } else {\n toolCalls.push({\n id: data.tool_use_id || `result-${Date.now()}`,\n name: 'tool_result',\n input: undefined,\n output: data.content,\n isError: data.is_error ?? false,\n state: data.is_error ? 'error' : 'completed',\n });\n }\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, content: fullContent, toolCalls: [...toolCalls], isStreaming: true } : m\n ));\n } else if (event.type === 'turn_complete' || event.type === 'done') {\n const data = event.data as { result?: string };\n if (!fullContent && data.result) {\n fullContent = data.result;\n }\n for (const tc of toolCalls) {\n if (tc.state === 'running' || tc.state === 'pending') tc.state = 'completed';\n }\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, content: fullContent || '(no response)', toolCalls: [...toolCalls], isStreaming: false, timestamp: new Date().toISOString() } : m\n ));\n } else if (event.type === 'error') {\n const data = event.data as { error: string };\n const errText = data.error || 'Unknown error';\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, role: 'system' as const, content: `Error: ${errText}`, isStreaming: false } : m\n ));\n }\n }\n\n // Finalize\n for (const tc of toolCalls) {\n if (tc.state === 'running' || tc.state === 'pending') tc.state = 'completed';\n }\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId && m.isStreaming\n ? { ...m, content: fullContent || '(no response)', toolCalls: toolCalls.length > 0 ? [...toolCalls] : undefined, isStreaming: false, timestamp: new Date().toISOString() }\n : m\n ));\n } catch (err) {\n const errMsg = err instanceof Error ? err.message : 'Failed to send';\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, role: 'system' as const, content: `Error: ${errMsg}`, isStreaming: false } : m\n ));\n } finally {\n setSending(false);\n sendingRef.current = false;\n }\n }, [input, attachedFiles, sessionId, agentSlug, client, onSessionStart, onError]);\n\n return {\n messages,\n input,\n setInput,\n sending,\n loading,\n error,\n sessionId,\n attachedFiles,\n setAttachedFiles,\n send,\n loadSession,\n startNewChat,\n setMessages,\n };\n}\n","import { useEffect, useState } from 'react';\nimport type { AshClient, Agent } from '@ash-ai/sdk';\n\nexport interface UseAgentsOptions {\n client: AshClient;\n}\n\nexport interface UseAgentsReturn {\n agents: Agent[];\n loading: boolean;\n error: string | null;\n refresh: () => void;\n}\n\nexport function useAgents({ client }: UseAgentsOptions): UseAgentsReturn {\n const [agents, setAgents] = useState<Agent[]>([]);\n const [loading, setLoading] = useState(true);\n const [error, setError] = useState<string | null>(null);\n\n const fetch_ = async () => {\n setLoading(true);\n setError(null);\n try {\n const result = await client.listAgents();\n setAgents(result);\n } catch (err) {\n setError(err instanceof Error ? err.message : 'Failed to fetch agents');\n } finally {\n setLoading(false);\n }\n };\n\n useEffect(() => {\n fetch_();\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n\n return { agents, loading, error, refresh: fetch_ };\n}\n","import { useEffect, useState, useCallback } from 'react';\nimport type { AshClient, Session } from '@ash-ai/sdk';\n\nexport interface UseSessionsOptions {\n client: AshClient;\n agent?: string;\n limit?: number;\n /** If false, don't auto-fetch on mount. */\n enabled?: boolean;\n}\n\nexport interface UseSessionsReturn {\n sessions: Session[];\n loading: boolean;\n error: string | null;\n refresh: () => void;\n}\n\nexport function useSessions({\n client,\n agent,\n limit = 20,\n enabled = true,\n}: UseSessionsOptions): UseSessionsReturn {\n const [sessions, setSessions] = useState<Session[]>([]);\n const [loading, setLoading] = useState(false);\n const [error, setError] = useState<string | null>(null);\n\n const fetch_ = useCallback(async () => {\n setLoading(true);\n setError(null);\n try {\n const result = await client.listSessions({ agent, limit });\n setSessions(result);\n } catch (err) {\n setError(err instanceof Error ? err.message : 'Failed to fetch sessions');\n } finally {\n setLoading(false);\n }\n }, [client, agent, limit]);\n\n useEffect(() => {\n if (enabled) fetch_();\n }, [enabled, fetch_]);\n\n return { sessions, loading, error, refresh: fetch_ };\n}\n","import { useEffect, useState } from 'react';\nimport type { AshClient } from '@ash-ai/sdk';\n\nexport interface UseHealthCheckOptions {\n client: AshClient;\n}\n\nexport interface UseHealthCheckReturn {\n connected: boolean | null;\n refresh: () => void;\n}\n\nexport function useHealthCheck({ client }: UseHealthCheckOptions): UseHealthCheckReturn {\n const [connected, setConnected] = useState<boolean | null>(null);\n\n const check = async () => {\n try {\n await client.health();\n setConnected(true);\n } catch {\n setConnected(false);\n }\n };\n\n useEffect(() => {\n check();\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n\n return { connected, refresh: check };\n}\n","import { useCallback } from 'react';\nimport type { AshClient } from '@ash-ai/sdk';\nimport type { AttachedFile } from '../types.js';\n\nexport interface UseFileUploadOptions {\n client: AshClient;\n onFilesChange: React.Dispatch<React.SetStateAction<AttachedFile[]>>;\n onError?: (error: string) => void;\n}\n\nexport interface UseFileUploadReturn {\n handleFileSelect: (e: React.ChangeEvent<HTMLInputElement>) => Promise<void>;\n removeFile: (fileId: string) => void;\n}\n\nexport function useFileUpload({\n client,\n onFilesChange,\n onError,\n}: UseFileUploadOptions): UseFileUploadReturn {\n const handleFileSelect = useCallback(async (e: React.ChangeEvent<HTMLInputElement>) => {\n const files = e.target.files;\n if (!files || files.length === 0) return;\n\n for (const file of Array.from(files)) {\n const tempId = `uploading-${Date.now()}-${Math.random().toString(36).slice(2)}`;\n onFilesChange((prev) => [...prev, { id: tempId, filename: file.name, url: '', uploading: true }]);\n\n try {\n // Read file as base64\n const base64 = await new Promise<string>((resolve, reject) => {\n const reader = new FileReader();\n reader.onload = () => {\n const result = reader.result as string;\n resolve(result.split(',')[1]);\n };\n reader.onerror = () => reject(new Error('Failed to read file'));\n reader.readAsDataURL(file);\n });\n\n // Upload via SDK\n const uploaded = await client.uploadFile({\n filename: file.name,\n content: base64,\n mimeType: file.type || undefined,\n ttl: '24h',\n });\n\n // Get download URL\n const url = await client.getFileUrl(uploaded.id);\n\n onFilesChange((prev) =>\n prev.map((f) => f.id === tempId ? { id: uploaded.id, filename: file.name, url, uploading: false } : f)\n );\n } catch {\n onFilesChange((prev) => prev.filter((f) => f.id !== tempId));\n onError?.(`Failed to upload ${file.name}`);\n }\n }\n\n // Reset input so the same file can be re-selected\n e.target.value = '';\n }, [client, onFilesChange, onError]);\n\n const removeFile = useCallback((fileId: string) => {\n onFilesChange((prev) => prev.filter((f) => f.id !== fileId));\n }, [onFilesChange]);\n\n return { handleFileSelect, removeFile };\n}\n","import type { SVGProps } from 'react';\n\ntype IconProps = SVGProps<SVGSVGElement>;\n\nfunction icon(d: string, opts?: { fill?: boolean; viewBox?: string }) {\n const Component = (props: IconProps) => (\n <svg\n xmlns=\"http://www.w3.org/2000/svg\"\n width=\"24\"\n height=\"24\"\n viewBox={opts?.viewBox ?? '0 0 24 24'}\n fill={opts?.fill ? 'currentColor' : 'none'}\n stroke=\"currentColor\"\n strokeWidth=\"2\"\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n {...props}\n >\n <path d={d} />\n </svg>\n );\n return Component;\n}\n\n// Multi-path icons need custom components\nexport const Brain = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M12 5a3 3 0 1 0-5.997.125 4 4 0 0 0-2.526 5.77 4 4 0 0 0 .556 6.588A4 4 0 1 0 12 18Z\" />\n <path d=\"M12 5a3 3 0 1 1 5.997.125 4 4 0 0 1 2.526 5.77 4 4 0 0 1-.556 6.588A4 4 0 1 1 12 18Z\" />\n <path d=\"M15 13a4.5 4.5 0 0 1-3-4 4.5 4.5 0 0 1-3 4\" />\n <path d=\"M17.599 6.5a3 3 0 0 0 .399-1.375\" />\n <path d=\"M6.003 5.125A3 3 0 0 0 6.401 6.5\" />\n <path d=\"M3.477 10.896a4 4 0 0 1 .585-.396\" />\n <path d=\"M19.938 10.5a4 4 0 0 1 .585.396\" />\n <path d=\"M6 18a4 4 0 0 1-1.967-.516\" />\n <path d=\"M19.967 17.484A4 4 0 0 1 18 18\" />\n </svg>\n);\n\nexport const Bot = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M12 8V4H8\" />\n <rect width=\"16\" height=\"12\" x=\"4\" y=\"8\" rx=\"2\" />\n <path d=\"M2 14h2\" />\n <path d=\"M20 14h2\" />\n <path d=\"M15 13v2\" />\n <path d=\"M9 13v2\" />\n </svg>\n);\n\nexport const User = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M19 21v-2a4 4 0 0 0-4-4H9a4 4 0 0 0-4 4v2\" />\n <circle cx=\"12\" cy=\"7\" r=\"4\" />\n </svg>\n);\n\nexport const Send = icon('m22 2-7 20-4-9-9-4Z M22 2 11 13');\n\nexport const MessageSquare = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M21 15a2 2 0 0 1-2 2H7l-4 4V5a2 2 0 0 1 2-2h14a2 2 0 0 1 2 2z\" />\n </svg>\n);\n\nexport const Terminal = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <polyline points=\"4 17 10 11 4 5\" />\n <line x1=\"12\" x2=\"20\" y1=\"19\" y2=\"19\" />\n </svg>\n);\n\nexport const FolderOpen = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"m6 14 1.5-2.9A2 2 0 0 1 9.24 10H20a2 2 0 0 1 1.94 2.5l-1.54 6a2 2 0 0 1-1.95 1.5H4a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h3.9a2 2 0 0 1 1.69.9l.81 1.2a2 2 0 0 0 1.67.9H18a2 2 0 0 1 2 2v2\" />\n </svg>\n);\n\nexport const Folder = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M20 20a2 2 0 0 0 2-2V8a2 2 0 0 0-2-2h-7.9a2 2 0 0 1-1.69-.9L9.6 3.9A2 2 0 0 0 7.93 3H4a2 2 0 0 0-2 2v13a2 2 0 0 0 2 2Z\" />\n </svg>\n);\n\nexport const FileText = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M15 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7Z\" />\n <path d=\"M14 2v4a2 2 0 0 0 2 2h4\" />\n <path d=\"M10 9H8\" />\n <path d=\"M16 13H8\" />\n <path d=\"M16 17H8\" />\n </svg>\n);\n\nexport const FileCode = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M15 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7Z\" />\n <path d=\"M14 2v4a2 2 0 0 0 2 2h4\" />\n <path d=\"m10 13-2 2 2 2\" />\n <path d=\"m14 17 2-2-2-2\" />\n </svg>\n);\n\nexport const FileJson = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M15 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7Z\" />\n <path d=\"M14 2v4a2 2 0 0 0 2 2h4\" />\n <path d=\"M10 12a1 1 0 0 0-1 1v1a1 1 0 0 1-1 1 1 1 0 0 1 1 1v1a1 1 0 0 0 1 1\" />\n <path d=\"M14 18a1 1 0 0 0 1-1v-1a1 1 0 0 1 1-1 1 1 0 0 1-1-1v-1a1 1 0 0 0-1-1\" />\n </svg>\n);\n\nexport const ImageIcon = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <rect width=\"18\" height=\"18\" x=\"3\" y=\"3\" rx=\"2\" ry=\"2\" />\n <circle cx=\"9\" cy=\"9\" r=\"2\" />\n <path d=\"m21 15-3.086-3.086a2 2 0 0 0-2.828 0L6 21\" />\n </svg>\n);\n\nexport const Loader2 = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M21 12a9 9 0 1 1-6.219-8.56\" />\n </svg>\n);\n\nexport const ChevronDown = icon('m6 9 6 6 6-6');\nexport const ChevronUp = icon('m18 15-6-6-6 6');\nexport const ChevronRight = icon('m9 18 6-6-6-6');\n\nexport const Plus = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M5 12h14\" />\n <path d=\"M12 5v14\" />\n </svg>\n);\n\nexport const X = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M18 6 6 18\" />\n <path d=\"m6 6 12 12\" />\n </svg>\n);\n\nexport const Paperclip = icon('m21.44 11.05-9.19 9.19a6 6 0 0 1-8.49-8.49l8.57-8.57A4 4 0 1 1 18 8.84l-8.59 8.57a2 2 0 0 1-2.83-2.83l8.49-8.48');\n\nexport const Clock = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <circle cx=\"12\" cy=\"12\" r=\"10\" />\n <polyline points=\"12 6 12 12 16 14\" />\n </svg>\n);\n\nexport const Wifi = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M12 20h.01\" />\n <path d=\"M2 8.82a15 15 0 0 1 20 0\" />\n <path d=\"M5 12.859a10 10 0 0 1 14 0\" />\n <path d=\"M8.5 16.429a5 5 0 0 1 7 0\" />\n </svg>\n);\n\nexport const WifiOff = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M12 20h.01\" />\n <path d=\"M8.5 16.429a5 5 0 0 1 7 0\" />\n <path d=\"M5 12.859a10 10 0 0 1 5.17-2.69\" />\n <path d=\"M19 12.859a10 10 0 0 0-2.007-1.523\" />\n <path d=\"M2 8.82a15 15 0 0 1 4.177-2.643\" />\n <path d=\"M22 8.82a15 15 0 0 0-11.288-3.764\" />\n <path d=\"m2 2 20 20\" />\n </svg>\n);\n\nexport const Wrench = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z\" />\n </svg>\n);\n\nexport const CheckCircle2 = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <circle cx=\"12\" cy=\"12\" r=\"10\" />\n <path d=\"m9 12 2 2 4-4\" />\n </svg>\n);\n\nexport const XCircle = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <circle cx=\"12\" cy=\"12\" r=\"10\" />\n <path d=\"m15 9-6 6\" />\n <path d=\"m9 9 6 6\" />\n </svg>\n);\n\nexport const Search = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <circle cx=\"11\" cy=\"11\" r=\"8\" />\n <path d=\"m21 21-4.3-4.3\" />\n </svg>\n);\n\nexport const Trash2 = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M3 6h18\" />\n <path d=\"M19 6v14c0 1-1 2-2 2H7c-1 0-2-1-2-2V6\" />\n <path d=\"M8 6V4c0-1 1-2 2-2h4c1 0 2 1 2 2v2\" />\n <line x1=\"10\" x2=\"10\" y1=\"11\" y2=\"17\" />\n <line x1=\"14\" x2=\"14\" y1=\"11\" y2=\"17\" />\n </svg>\n);\n\nexport const ArrowDown = icon('M12 5v14 m7-7-7 7-7-7');\n\nexport const Download = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4\" />\n <polyline points=\"7 10 12 15 17 10\" />\n <line x1=\"12\" x2=\"12\" y1=\"15\" y2=\"3\" />\n </svg>\n);\n\nexport const RefreshCw = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M3 12a9 9 0 0 1 9-9 9.75 9.75 0 0 1 6.74 2.74L21 8\" />\n <path d=\"M21 3v5h-5\" />\n <path d=\"M21 12a9 9 0 0 1-9 9 9.75 9.75 0 0 1-6.74-2.74L3 16\" />\n <path d=\"M8 16H3v5\" />\n </svg>\n);\n\n/** Returns the appropriate file icon component for a given filename */\nexport function getFileIcon(name: string): typeof FileText {\n const ext = name.split('.').pop()?.toLowerCase();\n if (['ts', 'tsx', 'js', 'jsx', 'py', 'rs', 'go', 'rb', 'sh', 'bash'].includes(ext || ''))\n return FileCode;\n if (['json', 'yaml', 'yml', 'toml'].includes(ext || ''))\n return FileJson;\n if (['png', 'jpg', 'jpeg', 'gif', 'svg', 'webp', 'ico'].includes(ext || ''))\n return ImageIcon;\n return FileText;\n}\n","import { cn } from '../utils.js';\nimport { Wifi, WifiOff } from '../icons.js';\n\nexport interface StatusIndicatorProps {\n connected: boolean | null;\n className?: string;\n}\n\nexport function StatusIndicator({ connected, className }: StatusIndicatorProps) {\n if (connected === null) return null;\n\n return (\n <div className={cn(\n 'flex items-center gap-1.5 rounded-full px-2.5 py-1 text-[10px] font-medium border',\n connected\n ? 'bg-green-500/10 text-green-400 border-green-500/20'\n : 'bg-red-500/10 text-red-400 border-red-500/20',\n className,\n )}>\n {connected\n ? <><Wifi className=\"h-3 w-3\" /> Runtime connected</>\n : <><WifiOff className=\"h-3 w-3\" /> Runtime disconnected</>\n }\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport type { Agent } from '@ash-ai/sdk';\nimport { StatusIndicator } from './StatusIndicator.js';\nimport { Clock, Plus } from '../icons.js';\n\nexport interface PlaygroundHeaderProps {\n agents: Agent[];\n selectedAgent: string;\n onAgentChange: (slug: string) => void;\n runtimeConnected: boolean | null;\n showHistory: boolean;\n onToggleHistory: () => void;\n sessionId: string | null;\n onNewChat: () => void;\n className?: string;\n}\n\nexport function PlaygroundHeader({\n agents,\n selectedAgent,\n onAgentChange,\n runtimeConnected,\n showHistory,\n onToggleHistory,\n sessionId,\n onNewChat,\n className,\n}: PlaygroundHeaderProps) {\n return (\n <div className={cn('shrink-0 flex items-center justify-between border-b border-white/10 pb-3 mb-4', className)}>\n <div className=\"flex items-center gap-3\">\n <div className=\"flex items-center gap-2 text-xs font-medium text-white/40 uppercase tracking-wider\">\n <span className=\"w-1.5 h-1.5 rounded-full bg-accent animate-pulse\" />\n PLAYGROUND\n </div>\n\n <select\n value={selectedAgent}\n onChange={(e) => onAgentChange(e.target.value)}\n className=\"rounded-lg border border-white/10 bg-white/5 px-3 py-1.5 text-sm text-white focus:border-accent/50 focus:outline-none\"\n >\n <option value=\"\" disabled>Select agent...</option>\n {agents.map((a) => (\n <option key={a.id} value={a.slug || a.name}>{a.name}</option>\n ))}\n </select>\n\n <StatusIndicator connected={runtimeConnected} />\n </div>\n\n <div className=\"flex items-center gap-2\">\n <button\n onClick={onToggleHistory}\n className={cn(\n 'flex items-center gap-1.5 px-3 py-1.5 rounded-lg text-xs font-medium border transition-all',\n showHistory\n ? 'bg-accent/10 text-accent border-accent/30'\n : 'bg-white/5 text-white/50 border-white/10 hover:bg-white/10'\n )}\n >\n <Clock className=\"h-3 w-3\" />\n History\n </button>\n {selectedAgent && (\n <button\n onClick={onNewChat}\n className={cn(\n 'flex items-center gap-1.5 px-3 py-1.5 rounded-lg text-xs font-medium border transition-all',\n !sessionId\n ? 'bg-accent/10 text-accent border-accent/30'\n : 'bg-white/5 text-white/50 border-white/10 hover:bg-white/10'\n )}\n >\n <Plus className=\"h-3 w-3\" />\n New Chat\n </button>\n )}\n </div>\n </div>\n );\n}\n","import { useEffect, useRef } from 'react';\nimport type { ChatMessage as ChatMessageType } from '../types.js';\nimport { ChatMessage } from './ChatMessage.js';\nimport { MessageSquare } from '../icons.js';\n\nexport interface ChatMessagesProps {\n messages: ChatMessageType[];\n className?: string;\n}\n\nexport function ChatMessages({ messages, className }: ChatMessagesProps) {\n const chatRef = useRef<HTMLDivElement>(null);\n\n useEffect(() => {\n if (chatRef.current) {\n chatRef.current.scrollTo({ top: chatRef.current.scrollHeight, behavior: 'smooth' });\n }\n }, [messages]);\n\n return (\n <div ref={chatRef} className={className ?? 'flex-1 overflow-auto p-4 space-y-3 scrollbar-thin'}>\n {messages.length === 0 ? (\n <div className=\"flex h-full flex-col items-center justify-center text-center\">\n <MessageSquare className=\"mb-3 h-8 w-8 text-white/20\" />\n <p className=\"text-sm text-white/40\">No messages yet</p>\n <p className=\"mt-1 text-xs text-white/30\">Send a message to start the conversation</p>\n </div>\n ) : (\n messages.map((msg) => <ChatMessage key={msg.id} message={msg} />)\n )}\n </div>\n );\n}\n","import { useState } from 'react';\nimport { cn } from '../utils.js';\nimport type { ToolCall } from '../types.js';\nimport { Brain, Wrench, CheckCircle2, XCircle, Loader2, ChevronDown, ChevronRight } from '../icons.js';\n\nexport function ThinkingBlock({ thinking }: { thinking: string[] }) {\n const [open, setOpen] = useState(false);\n const combined = thinking.join('\\n\\n');\n\n return (\n <div className=\"my-2 rounded-lg border border-amber-500/20 bg-amber-500/[0.03] overflow-hidden\">\n <button\n onClick={() => setOpen(!open)}\n className=\"flex w-full items-center gap-2 px-3 py-2 text-left hover:bg-amber-500/5 transition-colors\"\n >\n <Brain className=\"h-3.5 w-3.5 shrink-0 text-amber-500/60\" />\n <span className=\"text-xs font-medium text-amber-400/70\">Thinking</span>\n <span className=\"ml-auto flex items-center gap-1.5\">\n {open ? (\n <ChevronDown className=\"h-3 w-3 text-white/30\" />\n ) : (\n <ChevronRight className=\"h-3 w-3 text-white/30\" />\n )}\n </span>\n </button>\n {open && (\n <div className=\"border-t border-amber-500/10 px-3 py-2\">\n <pre className=\"whitespace-pre-wrap text-xs text-white/50 leading-relaxed max-h-96 overflow-y-auto\">\n {combined}\n </pre>\n </div>\n )}\n </div>\n );\n}\n\nexport function ToolCallBlock({ tool }: { tool: ToolCall }) {\n const [open, setOpen] = useState(false);\n\n const isRunning = tool.state === 'running' || tool.state === 'pending';\n const isError = tool.state === 'error';\n const isDone = tool.state === 'completed';\n\n return (\n <div className=\"my-2 rounded-lg border border-white/10 bg-white/[0.03] overflow-hidden\">\n <button\n onClick={() => setOpen(!open)}\n className=\"flex w-full items-center gap-2 px-3 py-2 text-left hover:bg-white/5 transition-colors\"\n >\n <Wrench className=\"h-3.5 w-3.5 shrink-0 text-white/40\" />\n <span className=\"text-xs font-medium text-white/70 truncate\">{tool.name}</span>\n <span className=\"ml-auto flex items-center gap-1.5\">\n {isRunning && (\n <span className=\"flex items-center gap-1 rounded-full bg-blue-500/10 border border-blue-500/20 px-2 py-0.5 text-[10px] font-medium text-blue-400\">\n <Loader2 className=\"h-3 w-3 animate-spin\" />\n Running\n </span>\n )}\n {isDone && (\n <span className=\"flex items-center gap-1 rounded-full bg-green-500/10 border border-green-500/20 px-2 py-0.5 text-[10px] font-medium text-green-400\">\n <CheckCircle2 className=\"h-3 w-3\" />\n Done\n </span>\n )}\n {isError && (\n <span className=\"flex items-center gap-1 rounded-full bg-red-500/10 border border-red-500/20 px-2 py-0.5 text-[10px] font-medium text-red-400\">\n <XCircle className=\"h-3 w-3\" />\n Error\n </span>\n )}\n {open ? (\n <ChevronDown className=\"h-3 w-3 text-white/30\" />\n ) : (\n <ChevronRight className=\"h-3 w-3 text-white/30\" />\n )}\n </span>\n </button>\n {open && (\n <div className=\"border-t border-white/10 px-3 py-2 space-y-2\">\n {tool.input != null && (\n <div>\n <div className=\"text-[10px] font-medium text-white/30 uppercase tracking-wider mb-1\">\n Input\n </div>\n <pre className=\"rounded-md bg-black/30 px-3 py-2 text-[11px] text-white/60 overflow-x-auto max-h-48 scrollbar-thin\">\n {typeof tool.input === 'string' ? tool.input : JSON.stringify(tool.input, null, 2)}\n </pre>\n </div>\n )}\n {tool.output != null && (\n <div>\n <div className=\"text-[10px] font-medium text-white/30 uppercase tracking-wider mb-1\">\n {isError ? 'Error' : 'Output'}\n </div>\n <pre\n className={cn(\n 'rounded-md px-3 py-2 text-[11px] overflow-x-auto max-h-64 scrollbar-thin',\n isError ? 'bg-red-500/10 text-red-400' : 'bg-black/30 text-white/60'\n )}\n >\n {typeof tool.output === 'string'\n ? tool.output\n : JSON.stringify(tool.output, null, 2)}\n </pre>\n </div>\n )}\n </div>\n )}\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport { formatTime } from '../utils.js';\nimport type { ChatMessage as ChatMessageType } from '../types.js';\nimport { Bot, User } from '../icons.js';\nimport { ToolCallBlock, ThinkingBlock } from './ToolCallBlock.js';\n\nexport interface ChatMessageProps {\n message: ChatMessageType;\n}\n\nexport function ChatMessage({ message: msg }: ChatMessageProps) {\n const isUser = msg.role === 'user';\n const isSystem = msg.role === 'system';\n\n if (isSystem) {\n return (\n <div className=\"flex justify-center\">\n <span className=\"max-w-lg rounded-xl bg-red-500/10 border border-red-500/20 px-4 py-2 text-xs text-red-400\">{msg.content}</span>\n </div>\n );\n }\n\n return (\n <div className={cn('flex gap-3', isUser ? 'flex-row-reverse' : 'flex-row')}>\n <div className={cn(\n 'flex h-8 w-8 shrink-0 items-center justify-center rounded-full',\n isUser ? 'bg-accent/20' : 'bg-white/10'\n )}>\n {isUser ? <User className=\"h-4 w-4 text-accent\" /> : <Bot className=\"h-4 w-4 text-white/60\" />}\n </div>\n <div className={cn(\n 'max-w-[75%] rounded-2xl px-4 py-2.5',\n isUser ? 'bg-accent/10 border border-accent/20 text-white' : 'bg-white/5 border border-white/10 text-white/80'\n )}>\n {/* Thinking */}\n {msg.thinking && msg.thinking.length > 0 && (\n <ThinkingBlock thinking={msg.thinking} />\n )}\n {/* Text content */}\n {msg.content && (\n <div className=\"whitespace-pre-wrap text-sm leading-relaxed\">\n {msg.content}\n {msg.isStreaming && !msg.toolCalls?.some((tc) => tc.state === 'running') && (\n <span className=\"ml-1 inline-block h-4 w-0.5 animate-pulse bg-accent align-text-bottom\" />\n )}\n </div>\n )}\n {/* Tool calls */}\n {msg.toolCalls && msg.toolCalls.length > 0 && (\n <div className={cn(msg.content && 'mt-2')}>\n {msg.toolCalls.map((tc) => (\n <ToolCallBlock key={tc.id} tool={tc} />\n ))}\n {msg.isStreaming && msg.toolCalls.some((tc) => tc.state === 'running') && (\n <span className=\"ml-1 inline-block h-4 w-0.5 animate-pulse bg-accent align-text-bottom\" />\n )}\n </div>\n )}\n {/* Streaming cursor when no content yet */}\n {msg.isStreaming && !msg.content && (!msg.toolCalls || msg.toolCalls.length === 0) && (\n <span className=\"inline-block h-4 w-0.5 animate-pulse bg-accent align-text-bottom\" />\n )}\n {msg.timestamp && (\n <div className=\"mt-1 text-right text-xs text-white/30\">{formatTime(msg.timestamp)}</div>\n )}\n </div>\n </div>\n );\n}\n","import { useRef } from 'react';\nimport { cn } from '../utils.js';\nimport type { AttachedFile } from '../types.js';\nimport { Send, Paperclip, Loader2, X } from '../icons.js';\n\nexport interface ChatInputProps {\n input: string;\n onInputChange: (value: string) => void;\n onSend: () => void;\n sending: boolean;\n disabled?: boolean;\n placeholder?: string;\n attachedFiles?: AttachedFile[];\n onFileSelect?: (e: React.ChangeEvent<HTMLInputElement>) => void;\n onRemoveFile?: (fileId: string) => void;\n className?: string;\n}\n\nexport function ChatInput({\n input,\n onInputChange,\n onSend,\n sending,\n disabled,\n placeholder = 'Send a message...',\n attachedFiles = [],\n onFileSelect,\n onRemoveFile,\n className,\n}: ChatInputProps) {\n const textareaRef = useRef<HTMLTextAreaElement>(null);\n const fileInputRef = useRef<HTMLInputElement>(null);\n\n const handleKeyDown = (e: React.KeyboardEvent) => {\n if (e.key === 'Enter' && !e.shiftKey) {\n e.preventDefault();\n onSend();\n }\n };\n\n const readyFiles = attachedFiles.filter((f) => !f.uploading);\n const canSend = (input.trim() || readyFiles.length > 0) && !sending && !disabled;\n\n return (\n <div className={cn('shrink-0 border-t border-white/10 p-4', className)}>\n {/* Attached files chips */}\n {attachedFiles.length > 0 && (\n <div className=\"mb-2 flex flex-wrap gap-2\">\n {attachedFiles.map((file) => (\n <div\n key={file.id}\n className={cn(\n 'flex items-center gap-1.5 rounded-lg border px-2.5 py-1 text-xs',\n file.uploading\n ? 'border-white/10 bg-white/5 text-white/40'\n : 'border-accent/20 bg-accent/5 text-accent'\n )}\n >\n {file.uploading ? (\n <Loader2 className=\"h-3 w-3 animate-spin\" />\n ) : (\n <Paperclip className=\"h-3 w-3\" />\n )}\n <span className=\"max-w-[180px] truncate\">{file.filename}</span>\n {!file.uploading && onRemoveFile && (\n <button\n onClick={() => onRemoveFile(file.id)}\n className=\"ml-0.5 rounded-full p-0.5 hover:bg-white/10 transition-colors\"\n >\n <X className=\"h-3 w-3\" />\n </button>\n )}\n </div>\n ))}\n </div>\n )}\n\n <div className=\"flex items-end gap-3\">\n {/* Hidden file input */}\n {onFileSelect && (\n <>\n <input\n ref={fileInputRef}\n type=\"file\"\n multiple\n onChange={onFileSelect}\n className=\"hidden\"\n />\n <button\n onClick={() => fileInputRef.current?.click()}\n disabled={sending || disabled}\n className={cn(\n 'flex h-11 w-11 shrink-0 items-center justify-center rounded-xl border transition-colors',\n 'border-white/10 bg-white/5 text-white/40 hover:bg-white/10 hover:text-white/60',\n (sending || disabled) && 'opacity-50 cursor-not-allowed'\n )}\n title=\"Attach files\"\n >\n <Paperclip className=\"h-4 w-4\" />\n </button>\n </>\n )}\n <textarea\n ref={textareaRef}\n value={input}\n onChange={(e) => {\n onInputChange(e.target.value);\n const el = e.target;\n el.style.height = 'auto';\n el.style.height = Math.min(el.scrollHeight, 160) + 'px';\n }}\n onKeyDown={handleKeyDown}\n placeholder={placeholder}\n rows={1}\n className={cn(\n 'w-full resize-none rounded-xl border bg-white/5 px-4 py-3 text-sm text-white',\n 'border-white/10 placeholder:text-white/40',\n 'focus:border-accent/50 focus:outline-none focus:ring-0',\n )}\n />\n <button\n onClick={onSend}\n disabled={!canSend}\n className={cn(\n 'flex h-11 w-11 shrink-0 items-center justify-center rounded-xl transition-colors',\n canSend\n ? 'bg-accent text-white hover:bg-accent/90'\n : 'bg-white/5 text-white/20 cursor-not-allowed'\n )}\n >\n {sending ? <Loader2 className=\"h-4 w-4 animate-spin\" /> : <Send className=\"h-4 w-4\" />}\n </button>\n </div>\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport type { ChatMessage, AttachedFile } from '../types.js';\nimport { ChatMessages } from './ChatMessages.js';\nimport { ChatInput } from './ChatInput.js';\nimport { MessageSquare, Bot, Loader2 } from '../icons.js';\n\nexport interface ChatProps {\n messages: ChatMessage[];\n input: string;\n onInputChange: (value: string) => void;\n onSend: () => void;\n sending: boolean;\n loading?: boolean;\n error?: string | null;\n /** Whether an active session exists */\n isActive: boolean;\n agentName?: string;\n attachedFiles?: AttachedFile[];\n onFileSelect?: (e: React.ChangeEvent<HTMLInputElement>) => void;\n onRemoveFile?: (fileId: string) => void;\n className?: string;\n}\n\nexport function Chat({\n messages,\n input,\n onInputChange,\n onSend,\n sending,\n loading,\n error,\n isActive,\n agentName,\n attachedFiles,\n onFileSelect,\n onRemoveFile,\n className,\n}: ChatProps) {\n return (\n <div className={cn('flex flex-col overflow-hidden', className)}>\n {loading ? (\n <div className=\"flex flex-1 items-center justify-center\">\n <Loader2 className=\"mr-2 h-5 w-5 animate-spin text-white/40\" />\n <span className=\"text-sm text-white/50\">Loading session...</span>\n </div>\n ) : !isActive ? (\n <div className=\"flex flex-1 flex-col items-center justify-center text-center px-8\">\n <div className=\"mb-4 flex h-16 w-16 items-center justify-center rounded-2xl bg-accent/10 border border-accent/20\">\n <MessageSquare className=\"h-8 w-8 text-accent\" />\n </div>\n <h2 className=\"text-xl font-semibold text-white\">Agent Playground</h2>\n <p className=\"mt-2 max-w-md text-sm text-white/50\">\n {agentName\n ? `Start a new conversation with ${agentName}, or resume a past session from History.`\n : 'Select an agent above to get started.'}\n </p>\n {agentName && (\n <div className=\"mt-4 inline-flex items-center gap-2 rounded-full bg-white/10 px-4 py-2 text-sm text-white/70\">\n <Bot className=\"h-4 w-4 text-accent\" />\n {agentName}\n </div>\n )}\n </div>\n ) : (\n <ChatMessages messages={messages} />\n )}\n\n {/* Error banner */}\n {error && (\n <div className=\"shrink-0 mx-4 mb-2 rounded-xl border border-red-500/20 bg-red-500/10 px-4 py-2.5 text-sm text-red-400\">\n {error}\n </div>\n )}\n\n {/* Input */}\n {agentName && (\n <ChatInput\n input={input}\n onInputChange={onInputChange}\n onSend={onSend}\n sending={sending}\n placeholder={isActive ? 'Send a message...' : 'Send a message to start a new session...'}\n attachedFiles={attachedFiles}\n onFileSelect={onFileSelect}\n onRemoveFile={onRemoveFile}\n />\n )}\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport type { Session } from '@ash-ai/sdk';\n\nexport interface SessionHistoryProps {\n sessions: Session[];\n activeSessionId: string | null;\n onSelectSession: (session: Session) => void;\n className?: string;\n}\n\nexport function SessionHistory({ sessions, activeSessionId, onSelectSession, className }: SessionHistoryProps) {\n return (\n <div className={cn('w-64 shrink-0 rounded-lg border border-white/10 bg-white/[0.02] flex flex-col overflow-hidden', className)}>\n <div className=\"px-3 py-2 border-b border-white/10 text-xs font-medium text-white/40 uppercase tracking-wider\">\n Recent Sessions\n </div>\n <div className=\"flex-1 overflow-auto scrollbar-thin\">\n {sessions.length === 0 ? (\n <p className=\"px-3 py-6 text-center text-xs text-white/30\">No sessions yet</p>\n ) : (\n sessions.map((s) => (\n <button\n key={s.id}\n onClick={() => onSelectSession(s)}\n className={cn(\n 'w-full text-left px-3 py-2.5 border-b border-white/5 hover:bg-white/5 transition-colors',\n activeSessionId === s.id && 'border-l-2 border-l-accent bg-accent/5'\n )}\n >\n <div className=\"text-xs font-medium text-white truncate\">{s.agentName}</div>\n <div className=\"text-[10px] text-white/30 mt-0.5\">\n {s.createdAt ? new Date(s.createdAt).toLocaleDateString() : 'No events'}\n <span className=\"mx-1 text-white/15\">|</span>\n <span className={cn(\n s.status === 'active' ? 'text-green-400' : 'text-white/30'\n )}>{s.status}</span>\n </div>\n </button>\n ))\n )}\n </div>\n </div>\n );\n}\n","import { useEffect, useState, useRef, useCallback } from 'react';\nimport { cn } from '../utils.js';\nimport { formatTimestamp } from '../utils.js';\nimport type { LogEntry } from '../types.js';\nimport {\n Terminal as TerminalIcon,\n Search,\n Trash2,\n ArrowDown,\n Wifi,\n WifiOff,\n Clock,\n} from '../icons.js';\n\nconst levelColors: Record<string, string> = {\n stdout: 'text-green-300',\n stderr: 'text-red-400',\n system: 'text-white/40',\n};\n\nexport interface TerminalProps {\n logs: LogEntry[];\n connected: boolean | null;\n onClear?: () => void;\n className?: string;\n}\n\nexport function Terminal({ logs, connected, onClear, className }: TerminalProps) {\n const [filter, setFilter] = useState('');\n const [showTimestamps, setShowTimestamps] = useState(false);\n const [autoScroll, setAutoScroll] = useState(true);\n const containerRef = useRef<HTMLDivElement>(null);\n\n useEffect(() => {\n if (autoScroll && containerRef.current) {\n containerRef.current.scrollTop = containerRef.current.scrollHeight;\n }\n }, [logs, autoScroll]);\n\n const handleScroll = useCallback(() => {\n if (!containerRef.current) return;\n const { scrollTop, scrollHeight, clientHeight } = containerRef.current;\n const atBottom = scrollHeight - scrollTop - clientHeight < 40;\n setAutoScroll(atBottom);\n }, []);\n\n const scrollToBottom = () => {\n if (containerRef.current) {\n containerRef.current.scrollTop = containerRef.current.scrollHeight;\n setAutoScroll(true);\n }\n };\n\n const filteredLogs = filter\n ? logs.filter((l) => l.text.toLowerCase().includes(filter.toLowerCase()))\n : logs;\n\n return (\n <div className={cn('flex flex-col bg-[#0d1117] rounded-lg border border-white/10 overflow-hidden', className)}>\n {/* Toolbar */}\n <div className=\"flex items-center gap-2 border-b border-white/10 px-3 py-2 bg-[#161b22]\">\n <TerminalIcon className=\"h-3.5 w-3.5 text-white/50\" />\n <span className=\"text-xs font-medium text-white/60\">Terminal</span>\n\n <div className={cn(\n 'ml-1 flex items-center gap-1 rounded-full px-2 py-0.5 text-[10px] font-medium',\n connected === true ? 'text-green-400' : connected === false ? 'text-red-400' : 'text-white/30'\n )}>\n {connected === true ? (\n <><Wifi className=\"h-2.5 w-2.5\" /> Live</>\n ) : connected === false ? (\n <><WifiOff className=\"h-2.5 w-2.5\" /> Disconnected</>\n ) : (\n 'Connecting...'\n )}\n </div>\n\n <div className=\"flex-1\" />\n\n <span className=\"text-[10px] text-white/30\">\n {filteredLogs.length.toLocaleString()} line{filteredLogs.length !== 1 ? 's' : ''}\n </span>\n\n <button\n onClick={() => setShowTimestamps(!showTimestamps)}\n className={cn(\n 'rounded p-1 text-white/40 hover:bg-white/10 hover:text-white/70 transition-colors',\n showTimestamps && 'bg-white/10 text-white/70'\n )}\n title=\"Toggle timestamps\"\n >\n <Clock className=\"h-3 w-3\" />\n </button>\n\n <div className=\"relative\">\n <Search className=\"absolute left-2 top-1/2 h-3 w-3 -translate-y-1/2 text-white/30\" />\n <input\n type=\"text\"\n value={filter}\n onChange={(e) => setFilter(e.target.value)}\n placeholder=\"Filter...\"\n className=\"h-6 w-32 rounded border border-white/10 bg-white/5 pl-7 pr-2 text-[11px] text-white placeholder:text-white/30 focus:border-white/20 focus:outline-none\"\n />\n </div>\n\n {!autoScroll && (\n <button\n onClick={scrollToBottom}\n className=\"rounded p-1 text-white/40 hover:bg-white/10 hover:text-white/70 transition-colors\"\n title=\"Scroll to bottom\"\n >\n <ArrowDown className=\"h-3 w-3\" />\n </button>\n )}\n\n {onClear && (\n <button\n onClick={onClear}\n className=\"rounded p-1 text-white/40 hover:bg-white/10 hover:text-white/70 transition-colors\"\n title=\"Clear\"\n >\n <Trash2 className=\"h-3 w-3\" />\n </button>\n )}\n </div>\n\n {/* Log content */}\n <div\n ref={containerRef}\n onScroll={handleScroll}\n className=\"flex-1 overflow-auto p-3 font-mono text-xs leading-5 scrollbar-thin min-h-[120px]\"\n >\n {filteredLogs.length === 0 ? (\n <div className=\"flex h-full items-center justify-center text-white/20 text-xs\">\n {logs.length === 0 ? 'Waiting for sandbox output...' : 'No matching lines'}\n </div>\n ) : (\n filteredLogs.map((entry) => (\n <div key={entry.index} className=\"flex hover:bg-white/5 rounded px-1 -mx-1\">\n {showTimestamps && (\n <span className=\"mr-3 shrink-0 select-none text-white/20\">\n {formatTimestamp(entry.ts)}\n </span>\n )}\n <span className={cn(\n 'whitespace-pre-wrap break-all',\n levelColors[entry.level] || 'text-white/60'\n )}>\n {entry.text}\n </span>\n </div>\n ))\n )}\n </div>\n </div>\n );\n}\n","import { useRef } from 'react';\nimport { cn } from '../utils.js';\nimport { formatBytes, isImageFile, buildFileTree } from '../utils.js';\nimport type { TreeNode } from '../types.js';\nimport { FileTree } from './FileTree.js';\nimport { FolderOpen, FileText, Search, RefreshCw, Download, Loader2, X } from '../icons.js';\n\nexport interface FileBrowserProps {\n files: Array<{ path: string; size: number; modifiedAt: string }>;\n source?: string | null;\n loading: boolean;\n selectedPath: string | null;\n fileContent: string | null;\n fileLoading: boolean;\n fileError: string | null;\n expandedDirs: Set<string>;\n filter: string;\n onFilterChange: (filter: string) => void;\n onSelectFile: (path: string) => void;\n onToggleDir: (path: string) => void;\n onRefresh: () => void;\n /** Base URL for file downloads/images. Will append `/${path}` */\n fileBaseUrl?: string;\n className?: string;\n}\n\nexport function FileBrowser({\n files,\n source,\n loading,\n selectedPath,\n fileContent,\n fileLoading,\n fileError,\n expandedDirs,\n filter,\n onFilterChange,\n onSelectFile,\n onToggleDir,\n onRefresh,\n fileBaseUrl,\n className,\n}: FileBrowserProps) {\n const contentRef = useRef<HTMLPreElement>(null);\n\n if (loading) {\n return (\n <div className={cn('flex items-center justify-center py-12', className)}>\n <Loader2 className=\"mr-2 h-4 w-4 animate-spin text-white/40\" />\n <span className=\"text-sm text-white/50\">Loading files...</span>\n </div>\n );\n }\n\n if (files.length === 0) {\n return (\n <div className={cn('flex flex-col items-center justify-center py-12 text-center', className)}>\n <FolderOpen className=\"mb-3 h-10 w-10 text-white/20\" />\n <p className=\"text-sm font-medium text-white/50\">No files in workspace</p>\n <p className=\"mt-1 text-xs text-white/40\">\n Files created by the agent will appear here\n </p>\n </div>\n );\n }\n\n const filteredFiles = filter\n ? files.filter((f) => f.path.toLowerCase().includes(filter.toLowerCase()))\n : files;\n\n const tree = buildFileTree(filteredFiles);\n const selectedFile = files.find((f) => f.path === selectedPath);\n const downloadUrl = fileBaseUrl && selectedPath ? `${fileBaseUrl}/${selectedPath}` : undefined;\n\n return (\n <div className={cn('flex flex-col h-full', className)}>\n {/* Toolbar */}\n <div className=\"flex items-center gap-2 border-b border-white/10 px-3 py-2 shrink-0\">\n {source && (\n <span className={cn(\n 'rounded-full px-2 py-0.5 text-[10px] font-medium border',\n source === 'sandbox'\n ? 'bg-green-500/10 text-green-400 border-green-500/20'\n : 'bg-white/5 text-white/40 border-white/10'\n )}>\n {source}\n </span>\n )}\n <span className=\"text-xs text-white/40\">{files.length} files</span>\n <div className=\"flex-1\" />\n <div className=\"relative\">\n <Search className=\"absolute left-2 top-1/2 h-3 w-3 -translate-y-1/2 text-white/30\" />\n <input\n type=\"text\"\n value={filter}\n onChange={(e) => onFilterChange(e.target.value)}\n placeholder=\"Filter...\"\n className=\"w-40 rounded-md border border-white/10 bg-white/5 pl-7 pr-2 py-1 text-xs text-white placeholder:text-white/30 focus:border-accent/50 focus:outline-none\"\n />\n {filter && (\n <button\n onClick={() => onFilterChange('')}\n className=\"absolute right-1.5 top-1/2 -translate-y-1/2 text-white/30 hover:text-white\"\n >\n <X className=\"h-3 w-3\" />\n </button>\n )}\n </div>\n <button\n onClick={onRefresh}\n className=\"rounded-md p-1 text-white/40 hover:bg-white/5 hover:text-white transition-colors\"\n title=\"Refresh\"\n >\n <RefreshCw className=\"h-3.5 w-3.5\" />\n </button>\n </div>\n\n {/* Two-panel layout */}\n <div className=\"flex flex-1 min-h-0\">\n {/* File tree */}\n <div className=\"w-64 shrink-0 border-r border-white/10 overflow-y-auto scrollbar-thin\">\n <FileTree\n nodes={tree}\n selectedPath={selectedPath}\n expandedDirs={expandedDirs}\n onSelectFile={onSelectFile}\n onToggleDir={onToggleDir}\n />\n </div>\n\n {/* File content viewer */}\n <div className=\"flex-1 min-w-0 flex flex-col overflow-hidden\">\n {!selectedPath ? (\n <div className=\"flex flex-1 items-center justify-center text-center\">\n <div>\n <FileText className=\"mx-auto mb-2 h-8 w-8 text-white/15\" />\n <p className=\"text-xs text-white/30\">Select a file to view its contents</p>\n </div>\n </div>\n ) : (\n <>\n {/* File header */}\n <div className=\"flex items-center justify-between border-b border-white/10 px-4 py-2 shrink-0\">\n <div className=\"flex items-center gap-2 min-w-0\">\n <span className=\"font-mono text-xs text-white/60 truncate\">{selectedPath}</span>\n {selectedFile && (\n <span className=\"text-[10px] text-white/30 shrink-0\">\n {formatBytes(selectedFile.size)}\n </span>\n )}\n </div>\n {downloadUrl && (\n <a\n href={downloadUrl}\n download\n className=\"rounded-md p-1.5 text-white/40 hover:bg-white/5 hover:text-white transition-colors shrink-0\"\n title=\"Download\"\n >\n <Download className=\"h-3.5 w-3.5\" />\n </a>\n )}\n </div>\n\n {/* Content */}\n <div className=\"flex-1 overflow-auto bg-[#0d1117]\">\n {fileLoading ? (\n <div className=\"flex items-center justify-center py-12\">\n <Loader2 className=\"mr-2 h-4 w-4 animate-spin text-white/40\" />\n <span className=\"text-xs text-white/50\">Loading...</span>\n </div>\n ) : fileError ? (\n <div className=\"flex flex-col items-center justify-center py-12 text-center px-4\">\n <p className=\"text-xs text-white/40\">{fileError}</p>\n {downloadUrl && (\n <a\n href={downloadUrl}\n download\n className=\"mt-2 text-xs text-accent hover:underline\"\n >\n Download file\n </a>\n )}\n </div>\n ) : isImageFile(selectedPath) ? (\n <div className=\"flex items-center justify-center p-4\">\n {downloadUrl && (\n <img\n src={downloadUrl}\n alt={selectedPath}\n className=\"max-w-full max-h-[60vh] object-contain rounded\"\n />\n )}\n </div>\n ) : (\n <pre\n ref={contentRef}\n className=\"p-4 text-xs font-mono text-white/70 leading-relaxed whitespace-pre-wrap break-words\"\n >\n {fileContent}\n </pre>\n )}\n </div>\n </>\n )}\n </div>\n </div>\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport type { TreeNode } from '../types.js';\nimport { FolderOpen, Folder, ChevronDown, ChevronRight, getFileIcon } from '../icons.js';\n\nexport interface FileTreeProps {\n nodes: TreeNode[];\n selectedPath: string | null;\n expandedDirs: Set<string>;\n onSelectFile: (path: string) => void;\n onToggleDir: (path: string) => void;\n}\n\nfunction TreeItem({\n node,\n depth,\n selectedPath,\n expandedDirs,\n onSelectFile,\n onToggleDir,\n}: {\n node: TreeNode;\n depth: number;\n selectedPath: string | null;\n expandedDirs: Set<string>;\n onSelectFile: (path: string) => void;\n onToggleDir: (path: string) => void;\n}) {\n const isExpanded = expandedDirs.has(node.path);\n const isSelected = selectedPath === node.path;\n const Icon = node.isDir ? (isExpanded ? FolderOpen : Folder) : getFileIcon(node.name);\n\n return (\n <>\n <button\n onClick={() => node.isDir ? onToggleDir(node.path) : onSelectFile(node.path)}\n className={cn(\n 'flex items-center gap-1.5 w-full text-left py-1 pr-2 text-xs transition-colors hover:bg-white/5',\n isSelected && !node.isDir && 'bg-accent/10 text-accent',\n !isSelected && 'text-white/60'\n )}\n style={{ paddingLeft: `${depth * 16 + 8}px` }}\n >\n {node.isDir ? (\n isExpanded ? (\n <ChevronDown className=\"h-3 w-3 shrink-0 text-white/30\" />\n ) : (\n <ChevronRight className=\"h-3 w-3 shrink-0 text-white/30\" />\n )\n ) : (\n <span className=\"w-3\" />\n )}\n <Icon className={cn(\n 'h-3.5 w-3.5 shrink-0',\n node.isDir ? 'text-accent' : 'text-white/40'\n )} />\n <span className=\"truncate\">{node.name}</span>\n {node.isDir && node.children.length > 0 && (\n <span className=\"ml-auto text-[10px] text-white/20 shrink-0\">{node.children.length}</span>\n )}\n </button>\n {node.isDir && isExpanded && node.children.map((child) => (\n <TreeItem\n key={child.path}\n node={child}\n depth={depth + 1}\n selectedPath={selectedPath}\n expandedDirs={expandedDirs}\n onSelectFile={onSelectFile}\n onToggleDir={onToggleDir}\n />\n ))}\n </>\n );\n}\n\nexport function FileTree({ nodes, selectedPath, expandedDirs, onSelectFile, onToggleDir }: FileTreeProps) {\n return (\n <div className=\"overflow-y-auto scrollbar-thin\">\n {nodes.map((node) => (\n <TreeItem\n key={node.path}\n node={node}\n depth={0}\n selectedPath={selectedPath}\n expandedDirs={expandedDirs}\n onSelectFile={onSelectFile}\n onToggleDir={onToggleDir}\n />\n ))}\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport { Terminal as TerminalIcon, FolderOpen, ChevronDown, ChevronUp } from '../icons.js';\n\nexport interface BottomPanelsProps {\n terminalOpen: boolean;\n onToggleTerminal: () => void;\n filesOpen: boolean;\n onToggleFiles: () => void;\n className?: string;\n}\n\nexport function BottomPanels({\n terminalOpen,\n onToggleTerminal,\n filesOpen,\n onToggleFiles,\n className,\n}: BottomPanelsProps) {\n return (\n <div className={cn('flex border-t border-white/10 bg-[#161b22] rounded-b-lg', className)}>\n <button\n onClick={onToggleTerminal}\n className={cn(\n 'flex flex-1 items-center justify-center gap-1.5 py-1 text-[10px] font-medium transition-colors',\n terminalOpen\n ? 'text-accent hover:text-accent/80'\n : 'text-white/40 hover:text-white/60 hover:bg-[#1c2128]'\n )}\n >\n <TerminalIcon className=\"h-3 w-3\" />\n Terminal\n {terminalOpen ? <ChevronDown className=\"h-3 w-3\" /> : <ChevronUp className=\"h-3 w-3\" />}\n </button>\n <div className=\"w-px bg-white/10\" />\n <button\n onClick={onToggleFiles}\n className={cn(\n 'flex flex-1 items-center justify-center gap-1.5 py-1 text-[10px] font-medium transition-colors',\n filesOpen\n ? 'text-accent hover:text-accent/80'\n : 'text-white/40 hover:text-white/60 hover:bg-[#1c2128]'\n )}\n >\n <FolderOpen className=\"h-3 w-3\" />\n Files\n {filesOpen ? <ChevronDown className=\"h-3 w-3\" /> : <ChevronUp className=\"h-3 w-3\" />}\n </button>\n </div>\n );\n}\n","import { useEffect, useState, useRef, useCallback } from 'react';\nimport type { AshClient } from '@ash-ai/sdk';\nimport type { LogEntry } from '../types.js';\n\nexport interface UseTerminalOptions {\n client: AshClient;\n sessionId: string;\n /** If true, fetch all logs once (no polling). Used for ended sessions. */\n historical?: boolean;\n /** Polling interval in ms. Defaults to 500. */\n pollInterval?: number;\n}\n\nexport interface UseTerminalReturn {\n logs: LogEntry[];\n connected: boolean | null;\n clearLogs: () => void;\n}\n\nexport function useTerminal({\n client,\n sessionId,\n historical,\n pollInterval = 500,\n}: UseTerminalOptions): UseTerminalReturn {\n const [logs, setLogs] = useState<LogEntry[]>([]);\n const [connected, setConnected] = useState<boolean | null>(null);\n const lastIndexRef = useRef(-1);\n const pollingRef = useRef<ReturnType<typeof setInterval> | null>(null);\n\n const fetchLogs = useCallback(async () => {\n try {\n const afterOpt = lastIndexRef.current >= 0 ? { after: lastIndexRef.current } : undefined;\n const data = await client.getSessionLogs(sessionId, afterOpt);\n setConnected(true);\n\n if (data.logs && data.logs.length > 0) {\n setLogs((prev) => [...prev, ...data.logs]);\n lastIndexRef.current = data.logs[data.logs.length - 1].index;\n }\n } catch {\n setConnected(false);\n }\n }, [client, sessionId]);\n\n useEffect(() => {\n setLogs([]);\n lastIndexRef.current = -1;\n setConnected(null);\n\n fetchLogs();\n\n if (!historical) {\n pollingRef.current = setInterval(fetchLogs, pollInterval);\n return () => {\n if (pollingRef.current) clearInterval(pollingRef.current);\n };\n }\n }, [sessionId, historical, pollInterval, fetchLogs]);\n\n const clearLogs = useCallback(() => {\n setLogs([]);\n }, []);\n\n return { logs, connected, clearLogs };\n}\n","import { useEffect, useState, useCallback } from 'react';\nimport type { AshClient, FileEntry } from '@ash-ai/sdk';\n\nexport interface UseFileBrowserOptions {\n client: AshClient;\n sessionId: string;\n}\n\nexport interface UseFileBrowserReturn {\n files: FileEntry[];\n source: string | null;\n loading: boolean;\n selectedPath: string | null;\n fileContent: string | null;\n fileLoading: boolean;\n fileError: string | null;\n expandedDirs: Set<string>;\n filter: string;\n setFilter: (filter: string) => void;\n selectFile: (path: string) => void;\n toggleDir: (path: string) => void;\n refresh: () => void;\n}\n\nexport function useFileBrowser({\n client,\n sessionId,\n}: UseFileBrowserOptions): UseFileBrowserReturn {\n const [files, setFiles] = useState<FileEntry[]>([]);\n const [source, setSource] = useState<string | null>(null);\n const [loading, setLoading] = useState(true);\n const [selectedPath, setSelectedPath] = useState<string | null>(null);\n const [fileContent, setFileContent] = useState<string | null>(null);\n const [fileLoading, setFileLoading] = useState(false);\n const [fileError, setFileError] = useState<string | null>(null);\n const [expandedDirs, setExpandedDirs] = useState<Set<string>>(new Set());\n const [filter, setFilter] = useState('');\n\n const fetchFiles = useCallback(async () => {\n setLoading(true);\n try {\n const data = await client.getSessionFiles(sessionId);\n setFiles(data.files || []);\n setSource(data.source || null);\n // Auto-expand top-level directories\n const topDirs = new Set<string>();\n for (const f of data.files || []) {\n const first = f.path.split('/')[0];\n if (f.path.includes('/')) topDirs.add(first);\n }\n setExpandedDirs(topDirs);\n } catch {\n // Silently fail\n } finally {\n setLoading(false);\n }\n }, [client, sessionId]);\n\n useEffect(() => {\n fetchFiles();\n }, [fetchFiles]);\n\n const selectFile = useCallback(async (path: string) => {\n setSelectedPath(path);\n setFileContent(null);\n setFileError(null);\n\n const ext = path.split('.').pop()?.toLowerCase();\n const imageExts = new Set(['png', 'jpg', 'jpeg', 'gif', 'svg', 'webp', 'ico']);\n if (imageExts.has(ext || '')) return;\n\n setFileLoading(true);\n try {\n const data = await client.getSessionFile(sessionId, path);\n setFileContent(data.content || '');\n } catch (err) {\n setFileError('Failed to load file content');\n } finally {\n setFileLoading(false);\n }\n }, [client, sessionId]);\n\n const toggleDir = useCallback((path: string) => {\n setExpandedDirs((prev) => {\n const next = new Set(prev);\n if (next.has(path)) next.delete(path);\n else next.add(path);\n return next;\n });\n }, []);\n\n return {\n files,\n source,\n loading,\n selectedPath,\n fileContent,\n fileLoading,\n fileError,\n expandedDirs,\n filter,\n setFilter,\n selectFile,\n toggleDir,\n refresh: fetchFiles,\n };\n}\n","import type { AshClient } from '@ash-ai/sdk';\nimport { cn } from '../utils.js';\nimport { PlaygroundProvider, usePlaygroundContext } from '../context/PlaygroundContext.js';\nimport { PlaygroundHeader } from './PlaygroundHeader.js';\nimport { Chat } from './Chat.js';\nimport { SessionHistory } from './SessionHistory.js';\nimport { Terminal } from './Terminal.js';\nimport { FileBrowser } from './FileBrowser.js';\nimport { BottomPanels } from './BottomPanels.js';\nimport { useTerminal } from '../hooks/useTerminal.js';\nimport { useFileBrowser } from '../hooks/useFileBrowser.js';\n\nexport interface PlaygroundProps {\n client: AshClient;\n defaultAgent?: string;\n className?: string;\n}\n\nfunction PlaygroundInner({ className }: { className?: string }) {\n const ctx = usePlaygroundContext();\n const {\n client,\n chat,\n agents,\n sessions,\n health,\n fileUpload,\n selectedAgent,\n setSelectedAgent,\n showHistory,\n setShowHistory,\n terminalOpen,\n setTerminalOpen,\n filesOpen,\n setFilesOpen,\n } = ctx;\n\n const selectedAgentObj = agents.agents.find((a) => (a.slug || a.name) === selectedAgent);\n const isActive = chat.sessionId !== null;\n\n return (\n <div className={cn('flex flex-col', className)}>\n {/* Header */}\n <PlaygroundHeader\n agents={agents.agents}\n selectedAgent={selectedAgent}\n onAgentChange={setSelectedAgent}\n runtimeConnected={health.connected}\n showHistory={showHistory}\n onToggleHistory={() => setShowHistory(!showHistory)}\n sessionId={chat.sessionId}\n onNewChat={chat.startNewChat}\n />\n\n {/* Main area */}\n <div className=\"flex flex-1 gap-4 min-h-0\">\n {/* History sidebar */}\n {showHistory && (\n <SessionHistory\n sessions={sessions.sessions}\n activeSessionId={chat.sessionId}\n onSelectSession={(s) => {\n chat.loadSession(s.id);\n setShowHistory(false);\n }}\n />\n )}\n\n {/* Chat + panels */}\n <div className=\"flex-1 flex flex-col min-w-0 gap-0\">\n <Chat\n messages={chat.messages}\n input={chat.input}\n onInputChange={chat.setInput}\n onSend={chat.send}\n sending={chat.sending}\n loading={chat.loading}\n error={chat.error}\n isActive={isActive}\n agentName={selectedAgentObj?.name}\n attachedFiles={chat.attachedFiles}\n onFileSelect={fileUpload.handleFileSelect}\n onRemoveFile={fileUpload.removeFile}\n className={cn(\n 'rounded-lg border border-white/10 bg-white/[0.02]',\n terminalOpen && chat.sessionId ? 'flex-1 min-h-0' : 'flex-1'\n )}\n />\n\n {/* Terminal panel */}\n {chat.sessionId && (\n <div className={cn(\n 'shrink-0 transition-all',\n terminalOpen ? 'h-64' : 'h-0'\n )}>\n {terminalOpen && (\n <TerminalPanel\n client={client}\n sessionId={chat.sessionId}\n />\n )}\n </div>\n )}\n\n {/* Files panel */}\n {chat.sessionId && (\n <div className={cn(\n 'shrink-0 transition-all',\n filesOpen ? 'h-72' : 'h-0'\n )}>\n {filesOpen && (\n <FileBrowserPanel\n client={client}\n sessionId={chat.sessionId}\n />\n )}\n </div>\n )}\n\n {/* Bottom toggles */}\n {chat.sessionId && (\n <BottomPanels\n terminalOpen={terminalOpen}\n onToggleTerminal={() => setTerminalOpen(!terminalOpen)}\n filesOpen={filesOpen}\n onToggleFiles={() => setFilesOpen(!filesOpen)}\n />\n )}\n </div>\n </div>\n </div>\n );\n}\n\n/** Internal wrapper that connects the Terminal component with the useTerminal hook */\nfunction TerminalPanel({ client, sessionId }: { client: AshClient; sessionId: string }) {\n const { logs, connected, clearLogs } = useTerminal({ client, sessionId });\n return (\n <Terminal\n logs={logs}\n connected={connected}\n onClear={clearLogs}\n className=\"h-full rounded-t-none border-t-0\"\n />\n );\n}\n\n/** Internal wrapper that connects the FileBrowser component with the useFileBrowser hook */\nfunction FileBrowserPanel({ client, sessionId }: { client: AshClient; sessionId: string }) {\n const fb = useFileBrowser({ client, sessionId });\n return (\n <FileBrowser\n files={fb.files}\n source={fb.source}\n loading={fb.loading}\n selectedPath={fb.selectedPath}\n fileContent={fb.fileContent}\n fileLoading={fb.fileLoading}\n fileError={fb.fileError}\n expandedDirs={fb.expandedDirs}\n filter={fb.filter}\n onFilterChange={fb.setFilter}\n onSelectFile={fb.selectFile}\n onToggleDir={fb.toggleDir}\n onRefresh={fb.refresh}\n className=\"h-full border-t border-white/10\"\n />\n );\n}\n\nexport function Playground({ client, defaultAgent, className }: PlaygroundProps) {\n return (\n <PlaygroundProvider client={client} defaultAgent={defaultAgent}>\n <PlaygroundInner className={className} />\n </PlaygroundProvider>\n );\n}\n"],"mappings":"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","names":["Terminal","import_react","import_react","import_react","import_react","import_react","import_jsx_runtime","import_jsx_runtime","import_jsx_runtime","import_react","import_react","import_jsx_runtime","import_jsx_runtime","import_jsx_runtime","import_react","import_jsx_runtime","import_jsx_runtime","import_jsx_runtime","import_react","import_jsx_runtime","Terminal","import_react","import_jsx_runtime","import_jsx_runtime","import_jsx_runtime","import_react","import_react","import_jsx_runtime","Terminal"]}
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/utils.ts","../src/context/PlaygroundContext.tsx","../src/hooks/usePlaygroundChat.ts","../src/hooks/useAgents.ts","../src/hooks/useSessions.ts","../src/hooks/useHealthCheck.ts","../src/hooks/useFileUpload.ts","../src/icons.tsx","../src/components/StatusIndicator.tsx","../src/components/PlaygroundHeader.tsx","../src/components/ChatMessages.tsx","../src/components/ToolCallBlock.tsx","../src/components/ChatMessage.tsx","../src/components/ChatInput.tsx","../src/components/Chat.tsx","../src/components/SessionHistory.tsx","../src/components/Terminal.tsx","../src/components/FileBrowser.tsx","../src/components/FileTree.tsx","../src/components/BottomPanels.tsx","../src/hooks/useTerminal.ts","../src/hooks/useFileBrowser.ts","../src/components/Playground.tsx"],"sourcesContent":["// Components\nexport { Playground } from './components/Playground.js';\nexport type { PlaygroundProps } from './components/Playground.js';\n\nexport { Chat } from './components/Chat.js';\nexport type { ChatProps } from './components/Chat.js';\n\nexport { ChatMessages } from './components/ChatMessages.js';\nexport type { ChatMessagesProps } from './components/ChatMessages.js';\n\nexport { ChatInput } from './components/ChatInput.js';\nexport type { ChatInputProps } from './components/ChatInput.js';\n\nexport { ChatMessage } from './components/ChatMessage.js';\nexport type { ChatMessageProps } from './components/ChatMessage.js';\n\nexport { ToolCallBlock, ThinkingBlock } from './components/ToolCallBlock.js';\n\nexport { Terminal } from './components/Terminal.js';\nexport type { TerminalProps } from './components/Terminal.js';\n\nexport { FileBrowser } from './components/FileBrowser.js';\nexport type { FileBrowserProps } from './components/FileBrowser.js';\n\nexport { FileTree } from './components/FileTree.js';\nexport type { FileTreeProps } from './components/FileTree.js';\n\nexport { SessionHistory } from './components/SessionHistory.js';\nexport type { SessionHistoryProps } from './components/SessionHistory.js';\n\nexport { StatusIndicator } from './components/StatusIndicator.js';\nexport type { StatusIndicatorProps } from './components/StatusIndicator.js';\n\nexport { PlaygroundHeader } from './components/PlaygroundHeader.js';\nexport type { PlaygroundHeaderProps } from './components/PlaygroundHeader.js';\n\nexport { BottomPanels } from './components/BottomPanels.js';\nexport type { BottomPanelsProps } from './components/BottomPanels.js';\n\n// Context\nexport { PlaygroundProvider, usePlaygroundContext } from './context/PlaygroundContext.js';\nexport type { PlaygroundContextValue, PlaygroundProviderProps } from './context/PlaygroundContext.js';\n\n// Hooks\nexport {\n usePlaygroundChat,\n useTerminal,\n useFileBrowser,\n useFileUpload,\n useAgents,\n useSessions,\n useHealthCheck,\n} from './hooks/index.js';\n\nexport type {\n UsePlaygroundChatOptions,\n UsePlaygroundChatReturn,\n UseTerminalOptions,\n UseTerminalReturn,\n UseFileBrowserOptions,\n UseFileBrowserReturn,\n UseFileUploadOptions,\n UseFileUploadReturn,\n UseAgentsOptions,\n UseAgentsReturn,\n UseSessionsOptions,\n UseSessionsReturn,\n UseHealthCheckOptions,\n UseHealthCheckReturn,\n} from './hooks/index.js';\n\n// Types\nexport type { ChatMessage as ChatMessageType, ToolCall, AttachedFile, TreeNode, LogEntry } from './types.js';\n\n// Utils\nexport { cn, formatBytes, formatTime, buildFileTree, parseContentBlocks, isImageFile, getFileLanguage } from './utils.js';\n","import { clsx, type ClassValue } from 'clsx';\nimport { twMerge } from 'tailwind-merge';\nimport type { TreeNode, ToolCall } from './types.js';\n\nexport function cn(...inputs: ClassValue[]): string {\n return twMerge(clsx(inputs));\n}\n\nexport function formatBytes(bytes: number): string {\n if (bytes === 0) return '0 B';\n const k = 1024;\n const sizes = ['B', 'KB', 'MB', 'GB'];\n const i = Math.floor(Math.log(bytes) / Math.log(k));\n return parseFloat((bytes / Math.pow(k, i)).toFixed(1)) + ' ' + sizes[i];\n}\n\nexport function formatTime(ts: string): string {\n return new Date(ts).toLocaleTimeString('en-US', { hour12: false, hour: '2-digit', minute: '2-digit' });\n}\n\nexport function formatTimestamp(ts: string): string {\n return new Date(ts).toLocaleTimeString('en-US', {\n hour12: false,\n hour: '2-digit',\n minute: '2-digit',\n second: '2-digit',\n });\n}\n\nexport function buildFileTree(files: Array<{ path: string; size: number; modifiedAt: string }>): TreeNode[] {\n const root: TreeNode[] = [];\n\n for (const file of files) {\n const parts = file.path.split('/');\n let current = root;\n\n for (let i = 0; i < parts.length; i++) {\n const name = parts[i];\n const isLast = i === parts.length - 1;\n const partialPath = parts.slice(0, i + 1).join('/');\n\n let existing = current.find((n) => n.name === name && n.isDir === !isLast);\n if (!existing) {\n existing = {\n name,\n path: partialPath,\n isDir: !isLast,\n size: isLast ? file.size : undefined,\n modifiedAt: isLast ? file.modifiedAt : undefined,\n children: [],\n };\n current.push(existing);\n }\n current = existing.children;\n }\n }\n\n function sortNodes(nodes: TreeNode[]) {\n nodes.sort((a, b) => {\n if (a.isDir !== b.isDir) return a.isDir ? -1 : 1;\n return a.name.localeCompare(b.name);\n });\n for (const n of nodes) {\n if (n.children.length > 0) sortNodes(n.children);\n }\n }\n\n sortNodes(root);\n return root;\n}\n\n/**\n * Unwrap a message envelope object into content blocks or plain text.\n * Handles Claude Code conversation formats like:\n * { type: \"user\", content: \"hello\" }\n * { type: \"assistant\", message: { content: [...blocks] } }\n * { type: \"result\", result: \"text\" }\n */\nfunction unwrapMessageObject(obj: Record<string, unknown>): unknown {\n if (obj.message && typeof obj.message === 'object') {\n const msg = obj.message as Record<string, unknown>;\n if (Array.isArray(msg.content)) return msg.content;\n }\n if (Array.isArray(obj.content)) return obj.content;\n if (typeof obj.content === 'string') return obj.content;\n if (typeof obj.result === 'string') return obj.result;\n return '';\n}\n\n/**\n * Parse content blocks (from Anthropic SDK format) into text + tool calls + thinking.\n * Handles both JSON string content and pre-parsed arrays, as well as\n * wrapped message envelopes from Claude Code conversations.\n */\nexport function parseContentBlocks(content: unknown): { text: string; toolCalls: ToolCall[]; thinking: string[] } {\n let blocks: unknown[] | null = null;\n\n if (typeof content === 'string') {\n try {\n const parsed = JSON.parse(content);\n if (Array.isArray(parsed)) {\n blocks = parsed;\n } else if (parsed && typeof parsed === 'object') {\n return parseContentBlocks(unwrapMessageObject(parsed));\n }\n } catch {\n return { text: content, toolCalls: [], thinking: [] };\n }\n } else if (Array.isArray(content)) {\n blocks = content;\n } else if (content && typeof content === 'object') {\n return parseContentBlocks(unwrapMessageObject(content as Record<string, unknown>));\n }\n\n if (!blocks) {\n return { text: typeof content === 'string' ? content : '', toolCalls: [], thinking: [] };\n }\n\n let text = '';\n const toolCalls: ToolCall[] = [];\n const thinking: string[] = [];\n\n for (const block of blocks) {\n const b = block as Record<string, unknown>;\n if (b.type === 'text' && typeof b.text === 'string') {\n text += (text ? '\\n' : '') + b.text;\n } else if (b.type === 'tool_use') {\n toolCalls.push({\n id: (b.id as string) || `tool-${toolCalls.length}`,\n name: (b.name as string) || 'unknown',\n input: b.input,\n state: 'completed',\n });\n } else if (b.type === 'tool_result') {\n const match = toolCalls.find((tc) => tc.id === (b.tool_use_id as string));\n if (match) {\n match.output = b.content;\n match.isError = (b.is_error as boolean) ?? false;\n match.state = b.is_error ? 'error' : 'completed';\n }\n } else if (b.type === 'thinking') {\n const t = (b.thinking as string) || (b.text as string) || '';\n if (t) thinking.push(t);\n }\n }\n\n return { text, toolCalls, thinking };\n}\n\nconst IMAGE_EXTS = new Set(['png', 'jpg', 'jpeg', 'gif', 'svg', 'webp', 'ico']);\n\nexport function isImageFile(name: string): boolean {\n const ext = name.split('.').pop()?.toLowerCase();\n return IMAGE_EXTS.has(ext || '');\n}\n\nexport function getFileLanguage(name: string): string {\n const ext = name.split('.').pop()?.toLowerCase();\n const map: Record<string, string> = {\n ts: 'typescript', tsx: 'typescript', js: 'javascript', jsx: 'javascript',\n py: 'python', rs: 'rust', go: 'go', rb: 'ruby',\n json: 'json', yaml: 'yaml', yml: 'yaml', toml: 'toml',\n md: 'markdown', sh: 'bash', bash: 'bash', css: 'css',\n html: 'html', sql: 'sql', xml: 'xml',\n };\n return map[ext || ''] || 'text';\n}\n","import { createContext, useContext, useState, useCallback } from 'react';\nimport type { AshClient, Agent, Session } from '@ash-ai/sdk';\nimport { usePlaygroundChat, type UsePlaygroundChatReturn } from '../hooks/usePlaygroundChat.js';\nimport { useAgents, type UseAgentsReturn } from '../hooks/useAgents.js';\nimport { useSessions, type UseSessionsReturn } from '../hooks/useSessions.js';\nimport { useHealthCheck, type UseHealthCheckReturn } from '../hooks/useHealthCheck.js';\nimport { useFileUpload, type UseFileUploadReturn } from '../hooks/useFileUpload.js';\n\nexport interface PlaygroundContextValue {\n client: AshClient;\n chat: UsePlaygroundChatReturn;\n agents: UseAgentsReturn;\n sessions: UseSessionsReturn;\n health: UseHealthCheckReturn;\n fileUpload: UseFileUploadReturn;\n selectedAgent: string;\n setSelectedAgent: (slug: string) => void;\n showHistory: boolean;\n setShowHistory: (show: boolean) => void;\n terminalOpen: boolean;\n setTerminalOpen: (open: boolean) => void;\n filesOpen: boolean;\n setFilesOpen: (open: boolean) => void;\n}\n\nconst PlaygroundCtx = createContext<PlaygroundContextValue | null>(null);\n\nexport function usePlaygroundContext(): PlaygroundContextValue {\n const ctx = useContext(PlaygroundCtx);\n if (!ctx) throw new Error('usePlaygroundContext must be used within <PlaygroundProvider>');\n return ctx;\n}\n\nexport interface PlaygroundProviderProps {\n client: AshClient;\n defaultAgent?: string;\n children: React.ReactNode;\n}\n\nexport function PlaygroundProvider({ client, defaultAgent, children }: PlaygroundProviderProps) {\n const [selectedAgent, setSelectedAgentRaw] = useState(defaultAgent || '');\n const [showHistory, setShowHistory] = useState(false);\n const [terminalOpen, setTerminalOpen] = useState(false);\n const [filesOpen, setFilesOpen] = useState(false);\n\n const agentsHook = useAgents({ client });\n const health = useHealthCheck({ client });\n\n // Auto-select first agent if none provided\n const resolvedAgent = selectedAgent || agentsHook.agents[0]?.slug || agentsHook.agents[0]?.name || '';\n\n const chat = usePlaygroundChat({\n client,\n agentSlug: resolvedAgent,\n });\n\n const sessions = useSessions({\n client,\n agent: resolvedAgent,\n enabled: showHistory,\n });\n\n const fileUpload = useFileUpload({\n client,\n onFilesChange: chat.setAttachedFiles,\n onError: (err) => {\n // Surface upload errors as chat errors\n chat.setMessages((prev) => [\n ...prev,\n { id: `err-${Date.now()}`, role: 'system', content: err },\n ]);\n },\n });\n\n const setSelectedAgent = useCallback((slug: string) => {\n setSelectedAgentRaw(slug);\n chat.startNewChat();\n }, [chat]);\n\n const value: PlaygroundContextValue = {\n client,\n chat,\n agents: agentsHook,\n sessions,\n health,\n fileUpload,\n selectedAgent: resolvedAgent,\n setSelectedAgent,\n showHistory,\n setShowHistory,\n terminalOpen,\n setTerminalOpen,\n filesOpen,\n setFilesOpen,\n };\n\n return <PlaygroundCtx.Provider value={value}>{children}</PlaygroundCtx.Provider>;\n}\n","import { useState, useCallback, useRef } from 'react';\nimport type { AshClient } from '@ash-ai/sdk';\nimport type { ChatMessage, ToolCall, AttachedFile } from '../types.js';\n\nexport interface UsePlaygroundChatOptions {\n client: AshClient;\n agentSlug: string;\n initialSessionId?: string;\n onSessionStart?: (sessionId: string) => void;\n onError?: (error: string) => void;\n}\n\nexport interface UsePlaygroundChatReturn {\n messages: ChatMessage[];\n input: string;\n setInput: (input: string) => void;\n sending: boolean;\n loading: boolean;\n error: string | null;\n sessionId: string | null;\n attachedFiles: AttachedFile[];\n setAttachedFiles: React.Dispatch<React.SetStateAction<AttachedFile[]>>;\n send: () => Promise<void>;\n loadSession: (sessionId: string) => Promise<void>;\n startNewChat: () => void;\n setMessages: React.Dispatch<React.SetStateAction<ChatMessage[]>>;\n}\n\nexport function usePlaygroundChat({\n client,\n agentSlug,\n initialSessionId,\n onSessionStart,\n onError,\n}: UsePlaygroundChatOptions): UsePlaygroundChatReturn {\n const [messages, setMessages] = useState<ChatMessage[]>([]);\n const [input, setInput] = useState('');\n const [sending, setSending] = useState(false);\n const [loading, setLoading] = useState(false);\n const [error, setError] = useState<string | null>(null);\n const [sessionId, setSessionId] = useState<string | null>(initialSessionId ?? null);\n const [attachedFiles, setAttachedFiles] = useState<AttachedFile[]>([]);\n const sendingRef = useRef(false);\n\n const startNewChat = useCallback(() => {\n setSessionId(null);\n setMessages([]);\n setAttachedFiles([]);\n setError(null);\n }, []);\n\n const loadSession = useCallback(async (sid: string) => {\n setSessionId(sid);\n setLoading(true);\n setError(null);\n\n try {\n const sdkMessages = await client.listMessages(sid);\n const msgs: ChatMessage[] = [];\n\n for (let i = 0; i < sdkMessages.length; i++) {\n const m = sdkMessages[i];\n let text = '';\n const tools: ToolCall[] = [];\n\n let parsed: unknown;\n try {\n parsed = JSON.parse(m.content);\n } catch {\n parsed = m.content;\n }\n\n const data = parsed as Record<string, any>;\n\n // Assistant message with content blocks\n if (data.type === 'assistant' && Array.isArray(data.message?.content)) {\n for (const b of data.message.content) {\n if (b.type === 'text' && b.text) {\n text += (text ? '\\n' : '') + b.text;\n } else if (b.type === 'tool_use') {\n tools.push({\n id: b.id || `tool-${tools.length}`,\n name: b.name || 'unknown',\n input: b.input,\n state: 'completed',\n });\n }\n }\n }\n\n // Tool result message\n if (data.type === 'user' && data.tool_use_result) {\n const r = data.tool_use_result;\n const match = tools.find((tc) => tc.id === r.tool_use_id) ||\n (msgs.length > 0 ? msgs[msgs.length - 1].toolCalls?.find((tc) => tc.id === r.tool_use_id) : undefined);\n if (match) {\n match.output = r.stdout ?? r.content;\n match.isError = r.is_error ?? false;\n match.state = r.is_error ? 'error' : 'completed';\n }\n continue; // Tool results get merged into the previous assistant message\n }\n\n // User message\n if (data.type === 'user' && !data.tool_use_result) {\n const content = Array.isArray(data.content)\n ? data.content.filter((b: any) => b.type === 'text').map((b: any) => b.text).join('\\n')\n : typeof data.content === 'string' ? data.content : '';\n if (content) {\n msgs.push({\n id: m.id || `msg-${i}`,\n role: 'user',\n content,\n timestamp: m.createdAt,\n });\n }\n continue;\n }\n\n // Result message (turn complete)\n if (data.type === 'result' && typeof data.result === 'string') {\n text = data.result;\n }\n\n if (text || tools.length > 0) {\n msgs.push({\n id: m.id || `msg-${i}`,\n role: m.role === 'user' ? 'user' : 'assistant',\n content: text,\n toolCalls: tools.length > 0 ? tools : undefined,\n timestamp: m.createdAt,\n });\n }\n }\n setMessages(msgs);\n } catch {\n setMessages([{ id: 'err', role: 'system', content: 'Failed to load session messages.' }]);\n } finally {\n setLoading(false);\n }\n }, [client]);\n\n const send = useCallback(async () => {\n const textContent = input.trim();\n const readyFiles = attachedFiles.filter((f) => !f.uploading);\n if ((!textContent && readyFiles.length === 0) || !agentSlug || sendingRef.current) return;\n\n let content = textContent;\n if (readyFiles.length > 0) {\n const fileRefs = readyFiles.map((f) => `[Attached file: ${f.filename}](${f.url})`).join('\\n');\n content = content ? `${content}\\n\\n${fileRefs}` : fileRefs;\n }\n\n // Create session on-the-fly if none exists\n let activeSessionId = sessionId;\n if (!activeSessionId) {\n setSending(true);\n sendingRef.current = true;\n setError(null);\n try {\n const session = await client.createSession(agentSlug);\n activeSessionId = session.id;\n setSessionId(activeSessionId);\n onSessionStart?.(activeSessionId);\n } catch (err) {\n const msg = err instanceof Error ? err.message : 'Failed to create session';\n setError(msg);\n onError?.(msg);\n setSending(false);\n sendingRef.current = false;\n return;\n }\n }\n\n setInput('');\n setAttachedFiles([]);\n\n const userMsg: ChatMessage = {\n id: `user-${Date.now()}`,\n role: 'user',\n content,\n timestamp: new Date().toISOString(),\n };\n setMessages((prev) => [...prev, userMsg]);\n setSending(true);\n sendingRef.current = true;\n\n const assistantId = `assistant-${Date.now()}`;\n setMessages((prev) => [...prev, { id: assistantId, role: 'assistant', content: '', isStreaming: true }]);\n\n try {\n let fullContent = '';\n const toolCalls: ToolCall[] = [];\n\n for await (const event of client.sendMessageStream(activeSessionId, content, { includePartialMessages: true })) {\n if (event.type === 'text_delta') {\n const delta = (event.data as { delta: string }).delta || '';\n fullContent += delta;\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, content: fullContent, toolCalls: [...toolCalls], isStreaming: true } : m\n ));\n } else if (event.type === 'tool_use') {\n const data = event.data as { id: string; name: string; input: unknown };\n const tc: ToolCall = {\n id: data.id || `tool-${Date.now()}-${toolCalls.length}`,\n name: data.name || 'unknown',\n input: data.input,\n state: 'running',\n };\n toolCalls.push(tc);\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, content: fullContent, toolCalls: [...toolCalls], isStreaming: true } : m\n ));\n } else if (event.type === 'tool_result') {\n const data = event.data as { tool_use_id: string; content: unknown; is_error?: boolean };\n const matchIdx = toolCalls.findIndex((tc) => tc.id === data.tool_use_id);\n if (matchIdx !== -1) {\n toolCalls[matchIdx] = {\n ...toolCalls[matchIdx],\n output: data.content,\n isError: data.is_error ?? false,\n state: data.is_error ? 'error' : 'completed',\n };\n } else {\n toolCalls.push({\n id: data.tool_use_id || `result-${Date.now()}`,\n name: 'tool_result',\n input: undefined,\n output: data.content,\n isError: data.is_error ?? false,\n state: data.is_error ? 'error' : 'completed',\n });\n }\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, content: fullContent, toolCalls: [...toolCalls], isStreaming: true } : m\n ));\n } else if (event.type === 'turn_complete' || event.type === 'done') {\n const data = event.data as { result?: string };\n if (!fullContent && data.result) {\n fullContent = data.result;\n }\n for (const tc of toolCalls) {\n if (tc.state === 'running' || tc.state === 'pending') tc.state = 'completed';\n }\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, content: fullContent || '(no response)', toolCalls: [...toolCalls], isStreaming: false, timestamp: new Date().toISOString() } : m\n ));\n } else if (event.type === 'error') {\n const data = event.data as { error: string };\n const errText = data.error || 'Unknown error';\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, role: 'system' as const, content: `Error: ${errText}`, isStreaming: false } : m\n ));\n }\n }\n\n // Finalize\n for (const tc of toolCalls) {\n if (tc.state === 'running' || tc.state === 'pending') tc.state = 'completed';\n }\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId && m.isStreaming\n ? { ...m, content: fullContent || '(no response)', toolCalls: toolCalls.length > 0 ? [...toolCalls] : undefined, isStreaming: false, timestamp: new Date().toISOString() }\n : m\n ));\n } catch (err) {\n const errMsg = err instanceof Error ? err.message : 'Failed to send';\n setMessages((prev) => prev.map((m) =>\n m.id === assistantId ? { ...m, role: 'system' as const, content: `Error: ${errMsg}`, isStreaming: false } : m\n ));\n } finally {\n setSending(false);\n sendingRef.current = false;\n }\n }, [input, attachedFiles, sessionId, agentSlug, client, onSessionStart, onError]);\n\n return {\n messages,\n input,\n setInput,\n sending,\n loading,\n error,\n sessionId,\n attachedFiles,\n setAttachedFiles,\n send,\n loadSession,\n startNewChat,\n setMessages,\n };\n}\n","import { useEffect, useState } from 'react';\nimport type { AshClient, Agent } from '@ash-ai/sdk';\n\nexport interface UseAgentsOptions {\n client: AshClient;\n}\n\nexport interface UseAgentsReturn {\n agents: Agent[];\n loading: boolean;\n error: string | null;\n refresh: () => void;\n}\n\nexport function useAgents({ client }: UseAgentsOptions): UseAgentsReturn {\n const [agents, setAgents] = useState<Agent[]>([]);\n const [loading, setLoading] = useState(true);\n const [error, setError] = useState<string | null>(null);\n\n const fetch_ = async () => {\n setLoading(true);\n setError(null);\n try {\n const result = await client.listAgents();\n setAgents(result);\n } catch (err) {\n setError(err instanceof Error ? err.message : 'Failed to fetch agents');\n } finally {\n setLoading(false);\n }\n };\n\n useEffect(() => {\n fetch_();\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n\n return { agents, loading, error, refresh: fetch_ };\n}\n","import { useEffect, useState, useCallback } from 'react';\nimport type { AshClient, Session } from '@ash-ai/sdk';\n\nexport interface UseSessionsOptions {\n client: AshClient;\n agent?: string;\n limit?: number;\n /** If false, don't auto-fetch on mount. */\n enabled?: boolean;\n}\n\nexport interface UseSessionsReturn {\n sessions: Session[];\n loading: boolean;\n error: string | null;\n refresh: () => void;\n}\n\nexport function useSessions({\n client,\n agent,\n limit = 20,\n enabled = true,\n}: UseSessionsOptions): UseSessionsReturn {\n const [sessions, setSessions] = useState<Session[]>([]);\n const [loading, setLoading] = useState(false);\n const [error, setError] = useState<string | null>(null);\n\n const fetch_ = useCallback(async () => {\n setLoading(true);\n setError(null);\n try {\n const result = await client.listSessions({ agent, limit });\n setSessions(result);\n } catch (err) {\n setError(err instanceof Error ? err.message : 'Failed to fetch sessions');\n } finally {\n setLoading(false);\n }\n }, [client, agent, limit]);\n\n useEffect(() => {\n if (enabled) fetch_();\n }, [enabled, fetch_]);\n\n return { sessions, loading, error, refresh: fetch_ };\n}\n","import { useEffect, useState } from 'react';\nimport type { AshClient } from '@ash-ai/sdk';\n\nexport interface UseHealthCheckOptions {\n client: AshClient;\n}\n\nexport interface UseHealthCheckReturn {\n connected: boolean | null;\n refresh: () => void;\n}\n\nexport function useHealthCheck({ client }: UseHealthCheckOptions): UseHealthCheckReturn {\n const [connected, setConnected] = useState<boolean | null>(null);\n\n const check = async () => {\n try {\n await client.health();\n setConnected(true);\n } catch {\n setConnected(false);\n }\n };\n\n useEffect(() => {\n check();\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n\n return { connected, refresh: check };\n}\n","import { useCallback } from 'react';\nimport type { AshClient } from '@ash-ai/sdk';\nimport type { AttachedFile } from '../types.js';\n\nexport interface UseFileUploadOptions {\n client: AshClient;\n onFilesChange: React.Dispatch<React.SetStateAction<AttachedFile[]>>;\n onError?: (error: string) => void;\n}\n\nexport interface UseFileUploadReturn {\n handleFileSelect: (e: React.ChangeEvent<HTMLInputElement>) => Promise<void>;\n removeFile: (fileId: string) => void;\n}\n\nexport function useFileUpload({\n client,\n onFilesChange,\n onError,\n}: UseFileUploadOptions): UseFileUploadReturn {\n const handleFileSelect = useCallback(async (e: React.ChangeEvent<HTMLInputElement>) => {\n const files = e.target.files;\n if (!files || files.length === 0) return;\n\n for (const file of Array.from(files)) {\n const tempId = `uploading-${Date.now()}-${Math.random().toString(36).slice(2)}`;\n onFilesChange((prev) => [...prev, { id: tempId, filename: file.name, url: '', uploading: true }]);\n\n try {\n // Read file as base64\n const base64 = await new Promise<string>((resolve, reject) => {\n const reader = new FileReader();\n reader.onload = () => {\n const result = reader.result as string;\n resolve(result.split(',')[1]);\n };\n reader.onerror = () => reject(new Error('Failed to read file'));\n reader.readAsDataURL(file);\n });\n\n // Upload via SDK\n const uploaded = await client.uploadFile({\n filename: file.name,\n content: base64,\n mimeType: file.type || undefined,\n ttl: '24h',\n });\n\n // Get download URL\n const url = await client.getFileUrl(uploaded.id);\n\n onFilesChange((prev) =>\n prev.map((f) => f.id === tempId ? { id: uploaded.id, filename: file.name, url, uploading: false } : f)\n );\n } catch {\n onFilesChange((prev) => prev.filter((f) => f.id !== tempId));\n onError?.(`Failed to upload ${file.name}`);\n }\n }\n\n // Reset input so the same file can be re-selected\n e.target.value = '';\n }, [client, onFilesChange, onError]);\n\n const removeFile = useCallback((fileId: string) => {\n onFilesChange((prev) => prev.filter((f) => f.id !== fileId));\n }, [onFilesChange]);\n\n return { handleFileSelect, removeFile };\n}\n","import type { SVGProps } from 'react';\n\ntype IconProps = SVGProps<SVGSVGElement>;\n\nfunction icon(d: string, opts?: { fill?: boolean; viewBox?: string }) {\n const Component = (props: IconProps) => (\n <svg\n xmlns=\"http://www.w3.org/2000/svg\"\n width=\"24\"\n height=\"24\"\n viewBox={opts?.viewBox ?? '0 0 24 24'}\n fill={opts?.fill ? 'currentColor' : 'none'}\n stroke=\"currentColor\"\n strokeWidth=\"2\"\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n {...props}\n >\n <path d={d} />\n </svg>\n );\n return Component;\n}\n\n// Multi-path icons need custom components\nexport const Brain = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M12 5a3 3 0 1 0-5.997.125 4 4 0 0 0-2.526 5.77 4 4 0 0 0 .556 6.588A4 4 0 1 0 12 18Z\" />\n <path d=\"M12 5a3 3 0 1 1 5.997.125 4 4 0 0 1 2.526 5.77 4 4 0 0 1-.556 6.588A4 4 0 1 1 12 18Z\" />\n <path d=\"M15 13a4.5 4.5 0 0 1-3-4 4.5 4.5 0 0 1-3 4\" />\n <path d=\"M17.599 6.5a3 3 0 0 0 .399-1.375\" />\n <path d=\"M6.003 5.125A3 3 0 0 0 6.401 6.5\" />\n <path d=\"M3.477 10.896a4 4 0 0 1 .585-.396\" />\n <path d=\"M19.938 10.5a4 4 0 0 1 .585.396\" />\n <path d=\"M6 18a4 4 0 0 1-1.967-.516\" />\n <path d=\"M19.967 17.484A4 4 0 0 1 18 18\" />\n </svg>\n);\n\nexport const Bot = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M12 8V4H8\" />\n <rect width=\"16\" height=\"12\" x=\"4\" y=\"8\" rx=\"2\" />\n <path d=\"M2 14h2\" />\n <path d=\"M20 14h2\" />\n <path d=\"M15 13v2\" />\n <path d=\"M9 13v2\" />\n </svg>\n);\n\nexport const User = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M19 21v-2a4 4 0 0 0-4-4H9a4 4 0 0 0-4 4v2\" />\n <circle cx=\"12\" cy=\"7\" r=\"4\" />\n </svg>\n);\n\nexport const Send = icon('m22 2-7 20-4-9-9-4Z M22 2 11 13');\n\nexport const MessageSquare = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M21 15a2 2 0 0 1-2 2H7l-4 4V5a2 2 0 0 1 2-2h14a2 2 0 0 1 2 2z\" />\n </svg>\n);\n\nexport const Terminal = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <polyline points=\"4 17 10 11 4 5\" />\n <line x1=\"12\" x2=\"20\" y1=\"19\" y2=\"19\" />\n </svg>\n);\n\nexport const FolderOpen = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"m6 14 1.5-2.9A2 2 0 0 1 9.24 10H20a2 2 0 0 1 1.94 2.5l-1.54 6a2 2 0 0 1-1.95 1.5H4a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h3.9a2 2 0 0 1 1.69.9l.81 1.2a2 2 0 0 0 1.67.9H18a2 2 0 0 1 2 2v2\" />\n </svg>\n);\n\nexport const Folder = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M20 20a2 2 0 0 0 2-2V8a2 2 0 0 0-2-2h-7.9a2 2 0 0 1-1.69-.9L9.6 3.9A2 2 0 0 0 7.93 3H4a2 2 0 0 0-2 2v13a2 2 0 0 0 2 2Z\" />\n </svg>\n);\n\nexport const FileText = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M15 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7Z\" />\n <path d=\"M14 2v4a2 2 0 0 0 2 2h4\" />\n <path d=\"M10 9H8\" />\n <path d=\"M16 13H8\" />\n <path d=\"M16 17H8\" />\n </svg>\n);\n\nexport const FileCode = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M15 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7Z\" />\n <path d=\"M14 2v4a2 2 0 0 0 2 2h4\" />\n <path d=\"m10 13-2 2 2 2\" />\n <path d=\"m14 17 2-2-2-2\" />\n </svg>\n);\n\nexport const FileJson = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M15 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7Z\" />\n <path d=\"M14 2v4a2 2 0 0 0 2 2h4\" />\n <path d=\"M10 12a1 1 0 0 0-1 1v1a1 1 0 0 1-1 1 1 1 0 0 1 1 1v1a1 1 0 0 0 1 1\" />\n <path d=\"M14 18a1 1 0 0 0 1-1v-1a1 1 0 0 1 1-1 1 1 0 0 1-1-1v-1a1 1 0 0 0-1-1\" />\n </svg>\n);\n\nexport const ImageIcon = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <rect width=\"18\" height=\"18\" x=\"3\" y=\"3\" rx=\"2\" ry=\"2\" />\n <circle cx=\"9\" cy=\"9\" r=\"2\" />\n <path d=\"m21 15-3.086-3.086a2 2 0 0 0-2.828 0L6 21\" />\n </svg>\n);\n\nexport const Loader2 = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M21 12a9 9 0 1 1-6.219-8.56\" />\n </svg>\n);\n\nexport const ChevronDown = icon('m6 9 6 6 6-6');\nexport const ChevronUp = icon('m18 15-6-6-6 6');\nexport const ChevronRight = icon('m9 18 6-6-6-6');\n\nexport const Plus = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M5 12h14\" />\n <path d=\"M12 5v14\" />\n </svg>\n);\n\nexport const X = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M18 6 6 18\" />\n <path d=\"m6 6 12 12\" />\n </svg>\n);\n\nexport const Paperclip = icon('m21.44 11.05-9.19 9.19a6 6 0 0 1-8.49-8.49l8.57-8.57A4 4 0 1 1 18 8.84l-8.59 8.57a2 2 0 0 1-2.83-2.83l8.49-8.48');\n\nexport const Clock = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <circle cx=\"12\" cy=\"12\" r=\"10\" />\n <polyline points=\"12 6 12 12 16 14\" />\n </svg>\n);\n\nexport const Wifi = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M12 20h.01\" />\n <path d=\"M2 8.82a15 15 0 0 1 20 0\" />\n <path d=\"M5 12.859a10 10 0 0 1 14 0\" />\n <path d=\"M8.5 16.429a5 5 0 0 1 7 0\" />\n </svg>\n);\n\nexport const WifiOff = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M12 20h.01\" />\n <path d=\"M8.5 16.429a5 5 0 0 1 7 0\" />\n <path d=\"M5 12.859a10 10 0 0 1 5.17-2.69\" />\n <path d=\"M19 12.859a10 10 0 0 0-2.007-1.523\" />\n <path d=\"M2 8.82a15 15 0 0 1 4.177-2.643\" />\n <path d=\"M22 8.82a15 15 0 0 0-11.288-3.764\" />\n <path d=\"m2 2 20 20\" />\n </svg>\n);\n\nexport const Wrench = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z\" />\n </svg>\n);\n\nexport const CheckCircle2 = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <circle cx=\"12\" cy=\"12\" r=\"10\" />\n <path d=\"m9 12 2 2 4-4\" />\n </svg>\n);\n\nexport const XCircle = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <circle cx=\"12\" cy=\"12\" r=\"10\" />\n <path d=\"m15 9-6 6\" />\n <path d=\"m9 9 6 6\" />\n </svg>\n);\n\nexport const Search = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <circle cx=\"11\" cy=\"11\" r=\"8\" />\n <path d=\"m21 21-4.3-4.3\" />\n </svg>\n);\n\nexport const Trash2 = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M3 6h18\" />\n <path d=\"M19 6v14c0 1-1 2-2 2H7c-1 0-2-1-2-2V6\" />\n <path d=\"M8 6V4c0-1 1-2 2-2h4c1 0 2 1 2 2v2\" />\n <line x1=\"10\" x2=\"10\" y1=\"11\" y2=\"17\" />\n <line x1=\"14\" x2=\"14\" y1=\"11\" y2=\"17\" />\n </svg>\n);\n\nexport const ArrowDown = icon('M12 5v14 m7-7-7 7-7-7');\n\nexport const Download = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4\" />\n <polyline points=\"7 10 12 15 17 10\" />\n <line x1=\"12\" x2=\"12\" y1=\"15\" y2=\"3\" />\n </svg>\n);\n\nexport const RefreshCw = (props: IconProps) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"24\" height=\"24\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2\" strokeLinecap=\"round\" strokeLinejoin=\"round\" {...props}>\n <path d=\"M3 12a9 9 0 0 1 9-9 9.75 9.75 0 0 1 6.74 2.74L21 8\" />\n <path d=\"M21 3v5h-5\" />\n <path d=\"M21 12a9 9 0 0 1-9 9 9.75 9.75 0 0 1-6.74-2.74L3 16\" />\n <path d=\"M8 16H3v5\" />\n </svg>\n);\n\n/** Returns the appropriate file icon component for a given filename */\nexport function getFileIcon(name: string): typeof FileText {\n const ext = name.split('.').pop()?.toLowerCase();\n if (['ts', 'tsx', 'js', 'jsx', 'py', 'rs', 'go', 'rb', 'sh', 'bash'].includes(ext || ''))\n return FileCode;\n if (['json', 'yaml', 'yml', 'toml'].includes(ext || ''))\n return FileJson;\n if (['png', 'jpg', 'jpeg', 'gif', 'svg', 'webp', 'ico'].includes(ext || ''))\n return ImageIcon;\n return FileText;\n}\n","import { cn } from '../utils.js';\nimport { Wifi, WifiOff } from '../icons.js';\n\nexport interface StatusIndicatorProps {\n connected: boolean | null;\n className?: string;\n}\n\nexport function StatusIndicator({ connected, className }: StatusIndicatorProps) {\n if (connected === null) return null;\n\n return (\n <div className={cn(\n 'flex items-center gap-1.5 rounded-full px-2.5 py-1 text-[10px] font-medium border',\n connected\n ? 'bg-green-500/10 text-green-400 border-green-500/20'\n : 'bg-red-500/10 text-red-400 border-red-500/20',\n className,\n )}>\n {connected\n ? <><Wifi className=\"h-3 w-3\" /> Runtime connected</>\n : <><WifiOff className=\"h-3 w-3\" /> Runtime disconnected</>\n }\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport type { Agent } from '@ash-ai/sdk';\nimport { StatusIndicator } from './StatusIndicator.js';\nimport { Clock, Plus } from '../icons.js';\n\nexport interface PlaygroundHeaderProps {\n agents: Agent[];\n selectedAgent: string;\n onAgentChange: (slug: string) => void;\n runtimeConnected: boolean | null;\n showHistory: boolean;\n onToggleHistory: () => void;\n sessionId: string | null;\n onNewChat: () => void;\n className?: string;\n}\n\nexport function PlaygroundHeader({\n agents,\n selectedAgent,\n onAgentChange,\n runtimeConnected,\n showHistory,\n onToggleHistory,\n sessionId,\n onNewChat,\n className,\n}: PlaygroundHeaderProps) {\n return (\n <div className={cn('shrink-0 flex items-center justify-between border-b border-white/10 pb-3 mb-4', className)}>\n <div className=\"flex items-center gap-3\">\n <div className=\"flex items-center gap-2 text-xs font-medium text-white/40 uppercase tracking-wider\">\n <span className=\"w-1.5 h-1.5 rounded-full bg-accent animate-pulse\" />\n PLAYGROUND\n </div>\n\n <select\n value={selectedAgent}\n onChange={(e) => onAgentChange(e.target.value)}\n className=\"rounded-lg border border-white/10 bg-white/5 px-3 py-1.5 text-sm text-white focus:border-accent/50 focus:outline-none\"\n >\n <option value=\"\" disabled>Select agent...</option>\n {agents.map((a) => (\n <option key={a.id} value={a.slug || a.name}>{a.name}</option>\n ))}\n </select>\n\n <StatusIndicator connected={runtimeConnected} />\n </div>\n\n <div className=\"flex items-center gap-2\">\n <button\n onClick={onToggleHistory}\n className={cn(\n 'flex items-center gap-1.5 px-3 py-1.5 rounded-lg text-xs font-medium border transition-all',\n showHistory\n ? 'bg-accent/10 text-accent border-accent/30'\n : 'bg-white/5 text-white/50 border-white/10 hover:bg-white/10'\n )}\n >\n <Clock className=\"h-3 w-3\" />\n History\n </button>\n {selectedAgent && (\n <button\n onClick={onNewChat}\n className={cn(\n 'flex items-center gap-1.5 px-3 py-1.5 rounded-lg text-xs font-medium border transition-all',\n !sessionId\n ? 'bg-accent/10 text-accent border-accent/30'\n : 'bg-white/5 text-white/50 border-white/10 hover:bg-white/10'\n )}\n >\n <Plus className=\"h-3 w-3\" />\n New Chat\n </button>\n )}\n </div>\n </div>\n );\n}\n","import { useEffect, useRef } from 'react';\nimport type { ChatMessage as ChatMessageType } from '../types.js';\nimport { ChatMessage } from './ChatMessage.js';\nimport { MessageSquare } from '../icons.js';\n\nexport interface ChatMessagesProps {\n messages: ChatMessageType[];\n className?: string;\n}\n\nexport function ChatMessages({ messages, className }: ChatMessagesProps) {\n const chatRef = useRef<HTMLDivElement>(null);\n\n useEffect(() => {\n if (chatRef.current) {\n chatRef.current.scrollTo({ top: chatRef.current.scrollHeight, behavior: 'smooth' });\n }\n }, [messages]);\n\n return (\n <div ref={chatRef} className={className ?? 'flex-1 overflow-auto p-4 space-y-3 scrollbar-thin'}>\n {messages.length === 0 ? (\n <div className=\"flex h-full flex-col items-center justify-center text-center\">\n <MessageSquare className=\"mb-3 h-8 w-8 text-white/20\" />\n <p className=\"text-sm text-white/40\">No messages yet</p>\n <p className=\"mt-1 text-xs text-white/30\">Send a message to start the conversation</p>\n </div>\n ) : (\n messages.map((msg) => <ChatMessage key={msg.id} message={msg} />)\n )}\n </div>\n );\n}\n","import { useState } from 'react';\nimport { cn } from '../utils.js';\nimport type { ToolCall } from '../types.js';\nimport { Brain, Wrench, CheckCircle2, XCircle, Loader2, ChevronDown, ChevronRight } from '../icons.js';\n\nexport function ThinkingBlock({ thinking }: { thinking: string[] }) {\n const [open, setOpen] = useState(false);\n const combined = thinking.join('\\n\\n');\n\n return (\n <div className=\"my-2 rounded-lg border border-amber-500/20 bg-amber-500/[0.03] overflow-hidden\">\n <button\n onClick={() => setOpen(!open)}\n className=\"flex w-full items-center gap-2 px-3 py-2 text-left hover:bg-amber-500/5 transition-colors\"\n >\n <Brain className=\"h-3.5 w-3.5 shrink-0 text-amber-500/60\" />\n <span className=\"text-xs font-medium text-amber-400/70\">Thinking</span>\n <span className=\"ml-auto flex items-center gap-1.5\">\n {open ? (\n <ChevronDown className=\"h-3 w-3 text-white/30\" />\n ) : (\n <ChevronRight className=\"h-3 w-3 text-white/30\" />\n )}\n </span>\n </button>\n {open && (\n <div className=\"border-t border-amber-500/10 px-3 py-2\">\n <pre className=\"whitespace-pre-wrap text-xs text-white/50 leading-relaxed max-h-96 overflow-y-auto\">\n {combined}\n </pre>\n </div>\n )}\n </div>\n );\n}\n\nexport function ToolCallBlock({ tool }: { tool: ToolCall }) {\n const [open, setOpen] = useState(false);\n\n const isRunning = tool.state === 'running' || tool.state === 'pending';\n const isError = tool.state === 'error';\n const isDone = tool.state === 'completed';\n\n return (\n <div className=\"my-2 rounded-lg border border-white/10 bg-white/[0.03] overflow-hidden\">\n <button\n onClick={() => setOpen(!open)}\n className=\"flex w-full items-center gap-2 px-3 py-2 text-left hover:bg-white/5 transition-colors\"\n >\n <Wrench className=\"h-3.5 w-3.5 shrink-0 text-white/40\" />\n <span className=\"text-xs font-medium text-white/70 truncate\">{tool.name}</span>\n <span className=\"ml-auto flex items-center gap-1.5\">\n {isRunning && (\n <span className=\"flex items-center gap-1 rounded-full bg-blue-500/10 border border-blue-500/20 px-2 py-0.5 text-[10px] font-medium text-blue-400\">\n <Loader2 className=\"h-3 w-3 animate-spin\" />\n Running\n </span>\n )}\n {isDone && (\n <span className=\"flex items-center gap-1 rounded-full bg-green-500/10 border border-green-500/20 px-2 py-0.5 text-[10px] font-medium text-green-400\">\n <CheckCircle2 className=\"h-3 w-3\" />\n Done\n </span>\n )}\n {isError && (\n <span className=\"flex items-center gap-1 rounded-full bg-red-500/10 border border-red-500/20 px-2 py-0.5 text-[10px] font-medium text-red-400\">\n <XCircle className=\"h-3 w-3\" />\n Error\n </span>\n )}\n {open ? (\n <ChevronDown className=\"h-3 w-3 text-white/30\" />\n ) : (\n <ChevronRight className=\"h-3 w-3 text-white/30\" />\n )}\n </span>\n </button>\n {open && (\n <div className=\"border-t border-white/10 px-3 py-2 space-y-2\">\n {tool.input != null && (\n <div>\n <div className=\"text-[10px] font-medium text-white/30 uppercase tracking-wider mb-1\">\n Input\n </div>\n <pre className=\"rounded-md bg-black/30 px-3 py-2 text-[11px] text-white/60 overflow-x-auto max-h-48 scrollbar-thin\">\n {typeof tool.input === 'string' ? tool.input : JSON.stringify(tool.input, null, 2)}\n </pre>\n </div>\n )}\n {tool.output != null && (\n <div>\n <div className=\"text-[10px] font-medium text-white/30 uppercase tracking-wider mb-1\">\n {isError ? 'Error' : 'Output'}\n </div>\n <pre\n className={cn(\n 'rounded-md px-3 py-2 text-[11px] overflow-x-auto max-h-64 scrollbar-thin',\n isError ? 'bg-red-500/10 text-red-400' : 'bg-black/30 text-white/60'\n )}\n >\n {typeof tool.output === 'string'\n ? tool.output\n : JSON.stringify(tool.output, null, 2)}\n </pre>\n </div>\n )}\n </div>\n )}\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport { formatTime } from '../utils.js';\nimport type { ChatMessage as ChatMessageType } from '../types.js';\nimport { Bot, User } from '../icons.js';\nimport { ToolCallBlock, ThinkingBlock } from './ToolCallBlock.js';\n\nexport interface ChatMessageProps {\n message: ChatMessageType;\n}\n\nexport function ChatMessage({ message: msg }: ChatMessageProps) {\n const isUser = msg.role === 'user';\n const isSystem = msg.role === 'system';\n\n if (isSystem) {\n return (\n <div className=\"flex justify-center\">\n <span className=\"max-w-lg rounded-xl bg-red-500/10 border border-red-500/20 px-4 py-2 text-xs text-red-400\">{msg.content}</span>\n </div>\n );\n }\n\n return (\n <div className={cn('flex gap-3', isUser ? 'flex-row-reverse' : 'flex-row')}>\n <div className={cn(\n 'flex h-8 w-8 shrink-0 items-center justify-center rounded-full',\n isUser ? 'bg-accent/20' : 'bg-white/10'\n )}>\n {isUser ? <User className=\"h-4 w-4 text-accent\" /> : <Bot className=\"h-4 w-4 text-white/60\" />}\n </div>\n <div className={cn(\n 'max-w-[75%] rounded-2xl px-4 py-2.5',\n isUser ? 'bg-accent/10 border border-accent/20 text-white' : 'bg-white/5 border border-white/10 text-white/80'\n )}>\n {/* Thinking */}\n {msg.thinking && msg.thinking.length > 0 && (\n <ThinkingBlock thinking={msg.thinking} />\n )}\n {/* Text content */}\n {msg.content && (\n <div className=\"whitespace-pre-wrap text-sm leading-relaxed\">\n {msg.content}\n {msg.isStreaming && !msg.toolCalls?.some((tc) => tc.state === 'running') && (\n <span className=\"ml-1 inline-block h-4 w-0.5 animate-pulse bg-accent align-text-bottom\" />\n )}\n </div>\n )}\n {/* Tool calls */}\n {msg.toolCalls && msg.toolCalls.length > 0 && (\n <div className={cn(msg.content && 'mt-2')}>\n {msg.toolCalls.map((tc) => (\n <ToolCallBlock key={tc.id} tool={tc} />\n ))}\n {msg.isStreaming && msg.toolCalls.some((tc) => tc.state === 'running') && (\n <span className=\"ml-1 inline-block h-4 w-0.5 animate-pulse bg-accent align-text-bottom\" />\n )}\n </div>\n )}\n {/* Streaming cursor when no content yet */}\n {msg.isStreaming && !msg.content && (!msg.toolCalls || msg.toolCalls.length === 0) && (\n <span className=\"inline-block h-4 w-0.5 animate-pulse bg-accent align-text-bottom\" />\n )}\n {msg.timestamp && (\n <div className=\"mt-1 text-right text-xs text-white/30\">{formatTime(msg.timestamp)}</div>\n )}\n </div>\n </div>\n );\n}\n","import { useRef } from 'react';\nimport { cn } from '../utils.js';\nimport type { AttachedFile } from '../types.js';\nimport { Send, Paperclip, Loader2, X } from '../icons.js';\n\nexport interface ChatInputProps {\n input: string;\n onInputChange: (value: string) => void;\n onSend: () => void;\n sending: boolean;\n disabled?: boolean;\n placeholder?: string;\n attachedFiles?: AttachedFile[];\n onFileSelect?: (e: React.ChangeEvent<HTMLInputElement>) => void;\n onRemoveFile?: (fileId: string) => void;\n className?: string;\n}\n\nexport function ChatInput({\n input,\n onInputChange,\n onSend,\n sending,\n disabled,\n placeholder = 'Send a message...',\n attachedFiles = [],\n onFileSelect,\n onRemoveFile,\n className,\n}: ChatInputProps) {\n const textareaRef = useRef<HTMLTextAreaElement>(null);\n const fileInputRef = useRef<HTMLInputElement>(null);\n\n const handleKeyDown = (e: React.KeyboardEvent) => {\n if (e.key === 'Enter' && !e.shiftKey) {\n e.preventDefault();\n onSend();\n }\n };\n\n const readyFiles = attachedFiles.filter((f) => !f.uploading);\n const canSend = (input.trim() || readyFiles.length > 0) && !sending && !disabled;\n\n return (\n <div className={cn('shrink-0 border-t border-white/10 p-4', className)}>\n {/* Attached files chips */}\n {attachedFiles.length > 0 && (\n <div className=\"mb-2 flex flex-wrap gap-2\">\n {attachedFiles.map((file) => (\n <div\n key={file.id}\n className={cn(\n 'flex items-center gap-1.5 rounded-lg border px-2.5 py-1 text-xs',\n file.uploading\n ? 'border-white/10 bg-white/5 text-white/40'\n : 'border-accent/20 bg-accent/5 text-accent'\n )}\n >\n {file.uploading ? (\n <Loader2 className=\"h-3 w-3 animate-spin\" />\n ) : (\n <Paperclip className=\"h-3 w-3\" />\n )}\n <span className=\"max-w-[180px] truncate\">{file.filename}</span>\n {!file.uploading && onRemoveFile && (\n <button\n onClick={() => onRemoveFile(file.id)}\n className=\"ml-0.5 rounded-full p-0.5 hover:bg-white/10 transition-colors\"\n >\n <X className=\"h-3 w-3\" />\n </button>\n )}\n </div>\n ))}\n </div>\n )}\n\n <div className=\"flex items-end gap-3\">\n {/* Hidden file input */}\n {onFileSelect && (\n <>\n <input\n ref={fileInputRef}\n type=\"file\"\n multiple\n onChange={onFileSelect}\n className=\"hidden\"\n />\n <button\n onClick={() => fileInputRef.current?.click()}\n disabled={sending || disabled}\n className={cn(\n 'flex h-11 w-11 shrink-0 items-center justify-center rounded-xl border transition-colors',\n 'border-white/10 bg-white/5 text-white/40 hover:bg-white/10 hover:text-white/60',\n (sending || disabled) && 'opacity-50 cursor-not-allowed'\n )}\n title=\"Attach files\"\n >\n <Paperclip className=\"h-4 w-4\" />\n </button>\n </>\n )}\n <textarea\n ref={textareaRef}\n value={input}\n onChange={(e) => {\n onInputChange(e.target.value);\n const el = e.target;\n el.style.height = 'auto';\n el.style.height = Math.min(el.scrollHeight, 160) + 'px';\n }}\n onKeyDown={handleKeyDown}\n placeholder={placeholder}\n rows={1}\n className={cn(\n 'w-full resize-none rounded-xl border bg-white/5 px-4 py-3 text-sm text-white',\n 'border-white/10 placeholder:text-white/40',\n 'focus:border-accent/50 focus:outline-none focus:ring-0',\n )}\n />\n <button\n onClick={onSend}\n disabled={!canSend}\n className={cn(\n 'flex h-11 w-11 shrink-0 items-center justify-center rounded-xl transition-colors',\n canSend\n ? 'bg-accent text-white hover:bg-accent/90'\n : 'bg-white/5 text-white/20 cursor-not-allowed'\n )}\n >\n {sending ? <Loader2 className=\"h-4 w-4 animate-spin\" /> : <Send className=\"h-4 w-4\" />}\n </button>\n </div>\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport type { ChatMessage, AttachedFile } from '../types.js';\nimport { ChatMessages } from './ChatMessages.js';\nimport { ChatInput } from './ChatInput.js';\nimport { MessageSquare, Bot, Loader2 } from '../icons.js';\n\nexport interface ChatProps {\n messages: ChatMessage[];\n input: string;\n onInputChange: (value: string) => void;\n onSend: () => void;\n sending: boolean;\n loading?: boolean;\n error?: string | null;\n /** Whether an active session exists */\n isActive: boolean;\n agentName?: string;\n attachedFiles?: AttachedFile[];\n onFileSelect?: (e: React.ChangeEvent<HTMLInputElement>) => void;\n onRemoveFile?: (fileId: string) => void;\n className?: string;\n}\n\nexport function Chat({\n messages,\n input,\n onInputChange,\n onSend,\n sending,\n loading,\n error,\n isActive,\n agentName,\n attachedFiles,\n onFileSelect,\n onRemoveFile,\n className,\n}: ChatProps) {\n return (\n <div className={cn('flex flex-col overflow-hidden', className)}>\n {loading ? (\n <div className=\"flex flex-1 items-center justify-center\">\n <Loader2 className=\"mr-2 h-5 w-5 animate-spin text-white/40\" />\n <span className=\"text-sm text-white/50\">Loading session...</span>\n </div>\n ) : !isActive ? (\n <div className=\"flex flex-1 flex-col items-center justify-center text-center px-8\">\n <div className=\"mb-4 flex h-16 w-16 items-center justify-center rounded-2xl bg-accent/10 border border-accent/20\">\n <MessageSquare className=\"h-8 w-8 text-accent\" />\n </div>\n <h2 className=\"text-xl font-semibold text-white\">Agent Playground</h2>\n <p className=\"mt-2 max-w-md text-sm text-white/50\">\n {agentName\n ? `Start a new conversation with ${agentName}, or resume a past session from History.`\n : 'Select an agent above to get started.'}\n </p>\n {agentName && (\n <div className=\"mt-4 inline-flex items-center gap-2 rounded-full bg-white/10 px-4 py-2 text-sm text-white/70\">\n <Bot className=\"h-4 w-4 text-accent\" />\n {agentName}\n </div>\n )}\n </div>\n ) : (\n <ChatMessages messages={messages} />\n )}\n\n {/* Error banner */}\n {error && (\n <div className=\"shrink-0 mx-4 mb-2 rounded-xl border border-red-500/20 bg-red-500/10 px-4 py-2.5 text-sm text-red-400\">\n {error}\n </div>\n )}\n\n {/* Input */}\n {agentName && (\n <ChatInput\n input={input}\n onInputChange={onInputChange}\n onSend={onSend}\n sending={sending}\n placeholder={isActive ? 'Send a message...' : 'Send a message to start a new session...'}\n attachedFiles={attachedFiles}\n onFileSelect={onFileSelect}\n onRemoveFile={onRemoveFile}\n />\n )}\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport type { Session } from '@ash-ai/sdk';\n\nexport interface SessionHistoryProps {\n sessions: Session[];\n activeSessionId: string | null;\n onSelectSession: (session: Session) => void;\n className?: string;\n}\n\nexport function SessionHistory({ sessions, activeSessionId, onSelectSession, className }: SessionHistoryProps) {\n return (\n <div className={cn('w-64 shrink-0 rounded-lg border border-white/10 bg-white/[0.02] flex flex-col overflow-hidden', className)}>\n <div className=\"px-3 py-2 border-b border-white/10 text-xs font-medium text-white/40 uppercase tracking-wider\">\n Recent Sessions\n </div>\n <div className=\"flex-1 overflow-auto scrollbar-thin\">\n {sessions.length === 0 ? (\n <p className=\"px-3 py-6 text-center text-xs text-white/30\">No sessions yet</p>\n ) : (\n sessions.map((s) => (\n <button\n key={s.id}\n onClick={() => onSelectSession(s)}\n className={cn(\n 'w-full text-left px-3 py-2.5 border-b border-white/5 hover:bg-white/5 transition-colors',\n activeSessionId === s.id && 'border-l-2 border-l-accent bg-accent/5'\n )}\n >\n <div className=\"text-xs font-medium text-white truncate\">{s.agentName}</div>\n <div className=\"text-[10px] text-white/30 mt-0.5\">\n {s.createdAt ? new Date(s.createdAt).toLocaleDateString() : 'No events'}\n <span className=\"mx-1 text-white/15\">|</span>\n <span className={cn(\n s.status === 'active' ? 'text-green-400' : 'text-white/30'\n )}>{s.status}</span>\n </div>\n </button>\n ))\n )}\n </div>\n </div>\n );\n}\n","import { useEffect, useState, useRef, useCallback } from 'react';\nimport { cn } from '../utils.js';\nimport { formatTimestamp } from '../utils.js';\nimport type { LogEntry } from '../types.js';\nimport {\n Terminal as TerminalIcon,\n Search,\n Trash2,\n ArrowDown,\n Wifi,\n WifiOff,\n Clock,\n} from '../icons.js';\n\nconst levelColors: Record<string, string> = {\n stdout: 'text-green-300',\n stderr: 'text-red-400',\n system: 'text-white/40',\n};\n\nexport interface TerminalProps {\n logs: LogEntry[];\n connected: boolean | null;\n onClear?: () => void;\n className?: string;\n}\n\nexport function Terminal({ logs, connected, onClear, className }: TerminalProps) {\n const [filter, setFilter] = useState('');\n const [showTimestamps, setShowTimestamps] = useState(false);\n const [autoScroll, setAutoScroll] = useState(true);\n const containerRef = useRef<HTMLDivElement>(null);\n\n useEffect(() => {\n if (autoScroll && containerRef.current) {\n containerRef.current.scrollTop = containerRef.current.scrollHeight;\n }\n }, [logs, autoScroll]);\n\n const handleScroll = useCallback(() => {\n if (!containerRef.current) return;\n const { scrollTop, scrollHeight, clientHeight } = containerRef.current;\n const atBottom = scrollHeight - scrollTop - clientHeight < 40;\n setAutoScroll(atBottom);\n }, []);\n\n const scrollToBottom = () => {\n if (containerRef.current) {\n containerRef.current.scrollTop = containerRef.current.scrollHeight;\n setAutoScroll(true);\n }\n };\n\n const filteredLogs = filter\n ? logs.filter((l) => l.text.toLowerCase().includes(filter.toLowerCase()))\n : logs;\n\n return (\n <div className={cn('flex flex-col bg-[#0d1117] rounded-lg border border-white/10 overflow-hidden', className)}>\n {/* Toolbar */}\n <div className=\"flex items-center gap-2 border-b border-white/10 px-3 py-2 bg-[#161b22]\">\n <TerminalIcon className=\"h-3.5 w-3.5 text-white/50\" />\n <span className=\"text-xs font-medium text-white/60\">Terminal</span>\n\n <div className={cn(\n 'ml-1 flex items-center gap-1 rounded-full px-2 py-0.5 text-[10px] font-medium',\n connected === true ? 'text-green-400' : connected === false ? 'text-red-400' : 'text-white/30'\n )}>\n {connected === true ? (\n <><Wifi className=\"h-2.5 w-2.5\" /> Live</>\n ) : connected === false ? (\n <><WifiOff className=\"h-2.5 w-2.5\" /> Disconnected</>\n ) : (\n 'Connecting...'\n )}\n </div>\n\n <div className=\"flex-1\" />\n\n <span className=\"text-[10px] text-white/30\">\n {filteredLogs.length.toLocaleString()} line{filteredLogs.length !== 1 ? 's' : ''}\n </span>\n\n <button\n onClick={() => setShowTimestamps(!showTimestamps)}\n className={cn(\n 'rounded p-1 text-white/40 hover:bg-white/10 hover:text-white/70 transition-colors',\n showTimestamps && 'bg-white/10 text-white/70'\n )}\n title=\"Toggle timestamps\"\n >\n <Clock className=\"h-3 w-3\" />\n </button>\n\n <div className=\"relative\">\n <Search className=\"absolute left-2 top-1/2 h-3 w-3 -translate-y-1/2 text-white/30\" />\n <input\n type=\"text\"\n value={filter}\n onChange={(e) => setFilter(e.target.value)}\n placeholder=\"Filter...\"\n className=\"h-6 w-32 rounded border border-white/10 bg-white/5 pl-7 pr-2 text-[11px] text-white placeholder:text-white/30 focus:border-white/20 focus:outline-none\"\n />\n </div>\n\n {!autoScroll && (\n <button\n onClick={scrollToBottom}\n className=\"rounded p-1 text-white/40 hover:bg-white/10 hover:text-white/70 transition-colors\"\n title=\"Scroll to bottom\"\n >\n <ArrowDown className=\"h-3 w-3\" />\n </button>\n )}\n\n {onClear && (\n <button\n onClick={onClear}\n className=\"rounded p-1 text-white/40 hover:bg-white/10 hover:text-white/70 transition-colors\"\n title=\"Clear\"\n >\n <Trash2 className=\"h-3 w-3\" />\n </button>\n )}\n </div>\n\n {/* Log content */}\n <div\n ref={containerRef}\n onScroll={handleScroll}\n className=\"flex-1 overflow-auto p-3 font-mono text-xs leading-5 scrollbar-thin min-h-[120px]\"\n >\n {filteredLogs.length === 0 ? (\n <div className=\"flex h-full items-center justify-center text-white/20 text-xs\">\n {logs.length === 0 ? 'Waiting for sandbox output...' : 'No matching lines'}\n </div>\n ) : (\n filteredLogs.map((entry, i) => (\n <div key={`${entry.index}-${i}`} className=\"flex hover:bg-white/5 rounded px-1 -mx-1\">\n {showTimestamps && (\n <span className=\"mr-3 shrink-0 select-none text-white/20\">\n {formatTimestamp(entry.ts)}\n </span>\n )}\n <span className={cn(\n 'whitespace-pre-wrap break-all',\n levelColors[entry.level] || 'text-white/60'\n )}>\n {entry.text}\n </span>\n </div>\n ))\n )}\n </div>\n </div>\n );\n}\n","import { useRef } from 'react';\nimport { cn } from '../utils.js';\nimport { formatBytes, isImageFile, buildFileTree } from '../utils.js';\nimport type { TreeNode } from '../types.js';\nimport { FileTree } from './FileTree.js';\nimport { FolderOpen, FileText, Search, RefreshCw, Download, Loader2, X } from '../icons.js';\n\nexport interface FileBrowserProps {\n files: Array<{ path: string; size: number; modifiedAt: string }>;\n source?: string | null;\n loading: boolean;\n selectedPath: string | null;\n fileContent: string | null;\n fileLoading: boolean;\n fileError: string | null;\n expandedDirs: Set<string>;\n filter: string;\n onFilterChange: (filter: string) => void;\n onSelectFile: (path: string) => void;\n onToggleDir: (path: string) => void;\n onRefresh: () => void;\n /** Base URL for file downloads/images. Will append `/${path}` */\n fileBaseUrl?: string;\n className?: string;\n}\n\nexport function FileBrowser({\n files,\n source,\n loading,\n selectedPath,\n fileContent,\n fileLoading,\n fileError,\n expandedDirs,\n filter,\n onFilterChange,\n onSelectFile,\n onToggleDir,\n onRefresh,\n fileBaseUrl,\n className,\n}: FileBrowserProps) {\n const contentRef = useRef<HTMLPreElement>(null);\n\n if (loading) {\n return (\n <div className={cn('flex items-center justify-center py-12', className)}>\n <Loader2 className=\"mr-2 h-4 w-4 animate-spin text-white/40\" />\n <span className=\"text-sm text-white/50\">Loading files...</span>\n </div>\n );\n }\n\n if (files.length === 0) {\n return (\n <div className={cn('flex flex-col items-center justify-center py-12 text-center', className)}>\n <FolderOpen className=\"mb-3 h-10 w-10 text-white/20\" />\n <p className=\"text-sm font-medium text-white/50\">No files in workspace</p>\n <p className=\"mt-1 text-xs text-white/40\">\n Files created by the agent will appear here\n </p>\n </div>\n );\n }\n\n const filteredFiles = filter\n ? files.filter((f) => f.path.toLowerCase().includes(filter.toLowerCase()))\n : files;\n\n const tree = buildFileTree(filteredFiles);\n const selectedFile = files.find((f) => f.path === selectedPath);\n const downloadUrl = fileBaseUrl && selectedPath ? `${fileBaseUrl}/${selectedPath}` : undefined;\n\n return (\n <div className={cn('flex flex-col h-full', className)}>\n {/* Toolbar */}\n <div className=\"flex items-center gap-2 border-b border-white/10 px-3 py-2 shrink-0\">\n {source && (\n <span className={cn(\n 'rounded-full px-2 py-0.5 text-[10px] font-medium border',\n source === 'sandbox'\n ? 'bg-green-500/10 text-green-400 border-green-500/20'\n : 'bg-white/5 text-white/40 border-white/10'\n )}>\n {source}\n </span>\n )}\n <span className=\"text-xs text-white/40\">{files.length} files</span>\n <div className=\"flex-1\" />\n <div className=\"relative\">\n <Search className=\"absolute left-2 top-1/2 h-3 w-3 -translate-y-1/2 text-white/30\" />\n <input\n type=\"text\"\n value={filter}\n onChange={(e) => onFilterChange(e.target.value)}\n placeholder=\"Filter...\"\n className=\"w-40 rounded-md border border-white/10 bg-white/5 pl-7 pr-2 py-1 text-xs text-white placeholder:text-white/30 focus:border-accent/50 focus:outline-none\"\n />\n {filter && (\n <button\n onClick={() => onFilterChange('')}\n className=\"absolute right-1.5 top-1/2 -translate-y-1/2 text-white/30 hover:text-white\"\n >\n <X className=\"h-3 w-3\" />\n </button>\n )}\n </div>\n <button\n onClick={onRefresh}\n className=\"rounded-md p-1 text-white/40 hover:bg-white/5 hover:text-white transition-colors\"\n title=\"Refresh\"\n >\n <RefreshCw className=\"h-3.5 w-3.5\" />\n </button>\n </div>\n\n {/* Two-panel layout */}\n <div className=\"flex flex-1 min-h-0\">\n {/* File tree */}\n <div className=\"w-64 shrink-0 border-r border-white/10 overflow-y-auto scrollbar-thin\">\n <FileTree\n nodes={tree}\n selectedPath={selectedPath}\n expandedDirs={expandedDirs}\n onSelectFile={onSelectFile}\n onToggleDir={onToggleDir}\n />\n </div>\n\n {/* File content viewer */}\n <div className=\"flex-1 min-w-0 flex flex-col overflow-hidden\">\n {!selectedPath ? (\n <div className=\"flex flex-1 items-center justify-center text-center\">\n <div>\n <FileText className=\"mx-auto mb-2 h-8 w-8 text-white/15\" />\n <p className=\"text-xs text-white/30\">Select a file to view its contents</p>\n </div>\n </div>\n ) : (\n <>\n {/* File header */}\n <div className=\"flex items-center justify-between border-b border-white/10 px-4 py-2 shrink-0\">\n <div className=\"flex items-center gap-2 min-w-0\">\n <span className=\"font-mono text-xs text-white/60 truncate\">{selectedPath}</span>\n {selectedFile && (\n <span className=\"text-[10px] text-white/30 shrink-0\">\n {formatBytes(selectedFile.size)}\n </span>\n )}\n </div>\n {downloadUrl && (\n <a\n href={downloadUrl}\n download\n className=\"rounded-md p-1.5 text-white/40 hover:bg-white/5 hover:text-white transition-colors shrink-0\"\n title=\"Download\"\n >\n <Download className=\"h-3.5 w-3.5\" />\n </a>\n )}\n </div>\n\n {/* Content */}\n <div className=\"flex-1 overflow-auto bg-[#0d1117]\">\n {fileLoading ? (\n <div className=\"flex items-center justify-center py-12\">\n <Loader2 className=\"mr-2 h-4 w-4 animate-spin text-white/40\" />\n <span className=\"text-xs text-white/50\">Loading...</span>\n </div>\n ) : fileError ? (\n <div className=\"flex flex-col items-center justify-center py-12 text-center px-4\">\n <p className=\"text-xs text-white/40\">{fileError}</p>\n {downloadUrl && (\n <a\n href={downloadUrl}\n download\n className=\"mt-2 text-xs text-accent hover:underline\"\n >\n Download file\n </a>\n )}\n </div>\n ) : isImageFile(selectedPath) ? (\n <div className=\"flex items-center justify-center p-4\">\n {downloadUrl && (\n <img\n src={downloadUrl}\n alt={selectedPath}\n className=\"max-w-full max-h-[60vh] object-contain rounded\"\n />\n )}\n </div>\n ) : (\n <pre\n ref={contentRef}\n className=\"p-4 text-xs font-mono text-white/70 leading-relaxed whitespace-pre-wrap break-words\"\n >\n {fileContent}\n </pre>\n )}\n </div>\n </>\n )}\n </div>\n </div>\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport type { TreeNode } from '../types.js';\nimport { FolderOpen, Folder, ChevronDown, ChevronRight, getFileIcon } from '../icons.js';\n\nexport interface FileTreeProps {\n nodes: TreeNode[];\n selectedPath: string | null;\n expandedDirs: Set<string>;\n onSelectFile: (path: string) => void;\n onToggleDir: (path: string) => void;\n}\n\nfunction TreeItem({\n node,\n depth,\n selectedPath,\n expandedDirs,\n onSelectFile,\n onToggleDir,\n}: {\n node: TreeNode;\n depth: number;\n selectedPath: string | null;\n expandedDirs: Set<string>;\n onSelectFile: (path: string) => void;\n onToggleDir: (path: string) => void;\n}) {\n const isExpanded = expandedDirs.has(node.path);\n const isSelected = selectedPath === node.path;\n const Icon = node.isDir ? (isExpanded ? FolderOpen : Folder) : getFileIcon(node.name);\n\n return (\n <>\n <button\n onClick={() => node.isDir ? onToggleDir(node.path) : onSelectFile(node.path)}\n className={cn(\n 'flex items-center gap-1.5 w-full text-left py-1 pr-2 text-xs transition-colors hover:bg-white/5',\n isSelected && !node.isDir && 'bg-accent/10 text-accent',\n !isSelected && 'text-white/60'\n )}\n style={{ paddingLeft: `${depth * 16 + 8}px` }}\n >\n {node.isDir ? (\n isExpanded ? (\n <ChevronDown className=\"h-3 w-3 shrink-0 text-white/30\" />\n ) : (\n <ChevronRight className=\"h-3 w-3 shrink-0 text-white/30\" />\n )\n ) : (\n <span className=\"w-3\" />\n )}\n <Icon className={cn(\n 'h-3.5 w-3.5 shrink-0',\n node.isDir ? 'text-accent' : 'text-white/40'\n )} />\n <span className=\"truncate\">{node.name}</span>\n {node.isDir && node.children.length > 0 && (\n <span className=\"ml-auto text-[10px] text-white/20 shrink-0\">{node.children.length}</span>\n )}\n </button>\n {node.isDir && isExpanded && node.children.map((child) => (\n <TreeItem\n key={child.path}\n node={child}\n depth={depth + 1}\n selectedPath={selectedPath}\n expandedDirs={expandedDirs}\n onSelectFile={onSelectFile}\n onToggleDir={onToggleDir}\n />\n ))}\n </>\n );\n}\n\nexport function FileTree({ nodes, selectedPath, expandedDirs, onSelectFile, onToggleDir }: FileTreeProps) {\n return (\n <div className=\"overflow-y-auto scrollbar-thin\">\n {nodes.map((node) => (\n <TreeItem\n key={node.path}\n node={node}\n depth={0}\n selectedPath={selectedPath}\n expandedDirs={expandedDirs}\n onSelectFile={onSelectFile}\n onToggleDir={onToggleDir}\n />\n ))}\n </div>\n );\n}\n","import { cn } from '../utils.js';\nimport { Terminal as TerminalIcon, FolderOpen, ChevronDown, ChevronUp } from '../icons.js';\n\nexport interface BottomPanelsProps {\n terminalOpen: boolean;\n onToggleTerminal: () => void;\n filesOpen: boolean;\n onToggleFiles: () => void;\n className?: string;\n}\n\nexport function BottomPanels({\n terminalOpen,\n onToggleTerminal,\n filesOpen,\n onToggleFiles,\n className,\n}: BottomPanelsProps) {\n return (\n <div className={cn('flex border-t border-white/10 bg-[#161b22] rounded-b-lg', className)}>\n <button\n onClick={onToggleTerminal}\n className={cn(\n 'flex flex-1 items-center justify-center gap-1.5 py-1 text-[10px] font-medium transition-colors',\n terminalOpen\n ? 'text-accent hover:text-accent/80'\n : 'text-white/40 hover:text-white/60 hover:bg-[#1c2128]'\n )}\n >\n <TerminalIcon className=\"h-3 w-3\" />\n Terminal\n {terminalOpen ? <ChevronDown className=\"h-3 w-3\" /> : <ChevronUp className=\"h-3 w-3\" />}\n </button>\n <div className=\"w-px bg-white/10\" />\n <button\n onClick={onToggleFiles}\n className={cn(\n 'flex flex-1 items-center justify-center gap-1.5 py-1 text-[10px] font-medium transition-colors',\n filesOpen\n ? 'text-accent hover:text-accent/80'\n : 'text-white/40 hover:text-white/60 hover:bg-[#1c2128]'\n )}\n >\n <FolderOpen className=\"h-3 w-3\" />\n Files\n {filesOpen ? <ChevronDown className=\"h-3 w-3\" /> : <ChevronUp className=\"h-3 w-3\" />}\n </button>\n </div>\n );\n}\n","import { useEffect, useState, useRef, useCallback } from 'react';\nimport type { AshClient } from '@ash-ai/sdk';\nimport type { LogEntry } from '../types.js';\n\nexport interface UseTerminalOptions {\n client: AshClient;\n sessionId: string;\n /** If true, fetch all logs once (no polling). Used for ended sessions. */\n historical?: boolean;\n /** Polling interval in ms. Defaults to 500. */\n pollInterval?: number;\n}\n\nexport interface UseTerminalReturn {\n logs: LogEntry[];\n connected: boolean | null;\n clearLogs: () => void;\n}\n\nexport function useTerminal({\n client,\n sessionId,\n historical,\n pollInterval = 500,\n}: UseTerminalOptions): UseTerminalReturn {\n const [logs, setLogs] = useState<LogEntry[]>([]);\n const [connected, setConnected] = useState<boolean | null>(null);\n const lastIndexRef = useRef(-1);\n const pollingRef = useRef<ReturnType<typeof setInterval> | null>(null);\n\n const fetchLogs = useCallback(async () => {\n try {\n const afterOpt = lastIndexRef.current >= 0 ? { after: lastIndexRef.current } : undefined;\n const data = await client.getSessionLogs(sessionId, afterOpt);\n setConnected(true);\n\n if (data.logs && data.logs.length > 0) {\n setLogs((prev) => [...prev, ...data.logs]);\n lastIndexRef.current = data.logs[data.logs.length - 1].index;\n }\n } catch {\n setConnected(false);\n }\n }, [client, sessionId]);\n\n useEffect(() => {\n setLogs([]);\n lastIndexRef.current = -1;\n setConnected(null);\n\n fetchLogs();\n\n if (!historical) {\n pollingRef.current = setInterval(fetchLogs, pollInterval);\n return () => {\n if (pollingRef.current) clearInterval(pollingRef.current);\n };\n }\n }, [sessionId, historical, pollInterval, fetchLogs]);\n\n const clearLogs = useCallback(() => {\n setLogs([]);\n }, []);\n\n return { logs, connected, clearLogs };\n}\n","import { useEffect, useState, useCallback } from 'react';\nimport type { AshClient, FileEntry } from '@ash-ai/sdk';\n\nexport interface UseFileBrowserOptions {\n client: AshClient;\n sessionId: string;\n}\n\nexport interface UseFileBrowserReturn {\n files: FileEntry[];\n source: string | null;\n loading: boolean;\n selectedPath: string | null;\n fileContent: string | null;\n fileLoading: boolean;\n fileError: string | null;\n expandedDirs: Set<string>;\n filter: string;\n setFilter: (filter: string) => void;\n selectFile: (path: string) => void;\n toggleDir: (path: string) => void;\n refresh: () => void;\n}\n\nexport function useFileBrowser({\n client,\n sessionId,\n}: UseFileBrowserOptions): UseFileBrowserReturn {\n const [files, setFiles] = useState<FileEntry[]>([]);\n const [source, setSource] = useState<string | null>(null);\n const [loading, setLoading] = useState(true);\n const [selectedPath, setSelectedPath] = useState<string | null>(null);\n const [fileContent, setFileContent] = useState<string | null>(null);\n const [fileLoading, setFileLoading] = useState(false);\n const [fileError, setFileError] = useState<string | null>(null);\n const [expandedDirs, setExpandedDirs] = useState<Set<string>>(new Set());\n const [filter, setFilter] = useState('');\n\n const fetchFiles = useCallback(async () => {\n setLoading(true);\n try {\n const data = await client.getSessionFiles(sessionId);\n setFiles(data.files || []);\n setSource(data.source || null);\n // Auto-expand top-level directories\n const topDirs = new Set<string>();\n for (const f of data.files || []) {\n const first = f.path.split('/')[0];\n if (f.path.includes('/')) topDirs.add(first);\n }\n setExpandedDirs(topDirs);\n } catch {\n // Silently fail\n } finally {\n setLoading(false);\n }\n }, [client, sessionId]);\n\n useEffect(() => {\n fetchFiles();\n }, [fetchFiles]);\n\n const selectFile = useCallback(async (path: string) => {\n setSelectedPath(path);\n setFileContent(null);\n setFileError(null);\n\n const ext = path.split('.').pop()?.toLowerCase();\n const imageExts = new Set(['png', 'jpg', 'jpeg', 'gif', 'svg', 'webp', 'ico']);\n if (imageExts.has(ext || '')) return;\n\n setFileLoading(true);\n try {\n const data = await client.getSessionFile(sessionId, path);\n setFileContent(data.content || '');\n } catch (err) {\n setFileError('Failed to load file content');\n } finally {\n setFileLoading(false);\n }\n }, [client, sessionId]);\n\n const toggleDir = useCallback((path: string) => {\n setExpandedDirs((prev) => {\n const next = new Set(prev);\n if (next.has(path)) next.delete(path);\n else next.add(path);\n return next;\n });\n }, []);\n\n return {\n files,\n source,\n loading,\n selectedPath,\n fileContent,\n fileLoading,\n fileError,\n expandedDirs,\n filter,\n setFilter,\n selectFile,\n toggleDir,\n refresh: fetchFiles,\n };\n}\n","import type { AshClient } from '@ash-ai/sdk';\nimport { cn } from '../utils.js';\nimport { PlaygroundProvider, usePlaygroundContext } from '../context/PlaygroundContext.js';\nimport { PlaygroundHeader } from './PlaygroundHeader.js';\nimport { Chat } from './Chat.js';\nimport { SessionHistory } from './SessionHistory.js';\nimport { Terminal } from './Terminal.js';\nimport { FileBrowser } from './FileBrowser.js';\nimport { BottomPanels } from './BottomPanels.js';\nimport { useTerminal } from '../hooks/useTerminal.js';\nimport { useFileBrowser } from '../hooks/useFileBrowser.js';\n\nexport interface PlaygroundProps {\n client: AshClient;\n defaultAgent?: string;\n className?: string;\n}\n\nfunction PlaygroundInner({ className }: { className?: string }) {\n const ctx = usePlaygroundContext();\n const {\n client,\n chat,\n agents,\n sessions,\n health,\n fileUpload,\n selectedAgent,\n setSelectedAgent,\n showHistory,\n setShowHistory,\n terminalOpen,\n setTerminalOpen,\n filesOpen,\n setFilesOpen,\n } = ctx;\n\n const selectedAgentObj = agents.agents.find((a) => (a.slug || a.name) === selectedAgent);\n const isActive = chat.sessionId !== null;\n\n return (\n <div className={cn('flex flex-col', className)}>\n {/* Header */}\n <PlaygroundHeader\n agents={agents.agents}\n selectedAgent={selectedAgent}\n onAgentChange={setSelectedAgent}\n runtimeConnected={health.connected}\n showHistory={showHistory}\n onToggleHistory={() => setShowHistory(!showHistory)}\n sessionId={chat.sessionId}\n onNewChat={chat.startNewChat}\n />\n\n {/* Main area */}\n <div className=\"flex flex-1 gap-4 min-h-0\">\n {/* History sidebar */}\n {showHistory && (\n <SessionHistory\n sessions={sessions.sessions}\n activeSessionId={chat.sessionId}\n onSelectSession={(s) => {\n chat.loadSession(s.id);\n setShowHistory(false);\n }}\n />\n )}\n\n {/* Chat + panels */}\n <div className=\"flex-1 flex flex-col min-w-0 gap-0\">\n <Chat\n messages={chat.messages}\n input={chat.input}\n onInputChange={chat.setInput}\n onSend={chat.send}\n sending={chat.sending}\n loading={chat.loading}\n error={chat.error}\n isActive={isActive}\n agentName={selectedAgentObj?.name}\n attachedFiles={chat.attachedFiles}\n onFileSelect={fileUpload.handleFileSelect}\n onRemoveFile={fileUpload.removeFile}\n className={cn(\n 'rounded-lg border border-white/10 bg-white/[0.02]',\n terminalOpen && chat.sessionId ? 'flex-1 min-h-0' : 'flex-1'\n )}\n />\n\n {/* Terminal panel */}\n {chat.sessionId && (\n <div className={cn(\n 'shrink-0 transition-all',\n terminalOpen ? 'h-64' : 'h-0'\n )}>\n {terminalOpen && (\n <TerminalPanel\n client={client}\n sessionId={chat.sessionId}\n />\n )}\n </div>\n )}\n\n {/* Files panel */}\n {chat.sessionId && (\n <div className={cn(\n 'shrink-0 transition-all',\n filesOpen ? 'h-72' : 'h-0'\n )}>\n {filesOpen && (\n <FileBrowserPanel\n client={client}\n sessionId={chat.sessionId}\n />\n )}\n </div>\n )}\n\n {/* Bottom toggles */}\n {chat.sessionId && (\n <BottomPanels\n terminalOpen={terminalOpen}\n onToggleTerminal={() => setTerminalOpen(!terminalOpen)}\n filesOpen={filesOpen}\n onToggleFiles={() => setFilesOpen(!filesOpen)}\n />\n )}\n </div>\n </div>\n </div>\n );\n}\n\n/** Internal wrapper that connects the Terminal component with the useTerminal hook */\nfunction TerminalPanel({ client, sessionId }: { client: AshClient; sessionId: string }) {\n const { logs, connected, clearLogs } = useTerminal({ client, sessionId });\n return (\n <Terminal\n logs={logs}\n connected={connected}\n onClear={clearLogs}\n className=\"h-full rounded-t-none border-t-0\"\n />\n );\n}\n\n/** Internal wrapper that connects the FileBrowser component with the useFileBrowser hook */\nfunction FileBrowserPanel({ client, sessionId }: { client: AshClient; sessionId: string }) {\n const fb = useFileBrowser({ client, sessionId });\n return (\n <FileBrowser\n files={fb.files}\n source={fb.source}\n loading={fb.loading}\n selectedPath={fb.selectedPath}\n fileContent={fb.fileContent}\n fileLoading={fb.fileLoading}\n fileError={fb.fileError}\n expandedDirs={fb.expandedDirs}\n filter={fb.filter}\n onFilterChange={fb.setFilter}\n onSelectFile={fb.selectFile}\n onToggleDir={fb.toggleDir}\n onRefresh={fb.refresh}\n className=\"h-full border-t border-white/10\"\n />\n );\n}\n\nexport function Playground({ client, defaultAgent, className }: PlaygroundProps) {\n return (\n <PlaygroundProvider client={client} defaultAgent={defaultAgent}>\n <PlaygroundInner className={className} />\n </PlaygroundProvider>\n );\n}\n"],"mappings":"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","names":["Terminal","import_react","import_react","import_react","import_react","import_react","import_jsx_runtime","import_jsx_runtime","import_jsx_runtime","import_react","import_react","import_jsx_runtime","import_jsx_runtime","import_jsx_runtime","import_react","import_jsx_runtime","import_jsx_runtime","import_jsx_runtime","import_react","import_jsx_runtime","Terminal","import_react","import_jsx_runtime","import_jsx_runtime","import_jsx_runtime","import_react","import_react","import_jsx_runtime","Terminal"]}
|