veryfront 0.1.216 → 0.1.217
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/esm/cli/commands/generate/integration-generator-helpers.d.ts +35 -0
- package/esm/cli/commands/generate/integration-generator-helpers.d.ts.map +1 -0
- package/esm/cli/commands/generate/integration-generator-helpers.js +123 -0
- package/esm/cli/commands/generate/integration-generator.d.ts +1 -2
- package/esm/cli/commands/generate/integration-generator.d.ts.map +1 -1
- package/esm/cli/commands/generate/integration-generator.js +1 -123
- package/esm/cli/commands/knowledge/command-helpers.d.ts +48 -0
- package/esm/cli/commands/knowledge/command-helpers.d.ts.map +1 -0
- package/esm/cli/commands/knowledge/command-helpers.js +216 -0
- package/esm/cli/commands/knowledge/command.d.ts +11 -16
- package/esm/cli/commands/knowledge/command.d.ts.map +1 -1
- package/esm/cli/commands/knowledge/command.js +25 -212
- package/esm/cli/mcp/remote-file-tool-helpers.d.ts +5 -0
- package/esm/cli/mcp/remote-file-tool-helpers.d.ts.map +1 -0
- package/esm/cli/mcp/remote-file-tool-helpers.js +22 -0
- package/esm/cli/mcp/remote-file-tools.d.ts.map +1 -1
- package/esm/cli/mcp/remote-file-tools.js +1 -22
- package/esm/cli/templates/integration-loader-helpers.d.ts +8 -0
- package/esm/cli/templates/integration-loader-helpers.d.ts.map +1 -0
- package/esm/cli/templates/integration-loader-helpers.js +29 -0
- package/esm/cli/templates/integration-loader.d.ts.map +1 -1
- package/esm/cli/templates/integration-loader.js +5 -21
- package/esm/cli/templates/manifest.d.ts +1 -0
- package/esm/cli/templates/manifest.js +2 -1
- package/esm/deno.js +2 -2
- package/esm/src/agent/runtime/index.d.ts.map +1 -1
- package/esm/src/agent/runtime/index.js +48 -90
- package/esm/src/chat/ag-ui-helpers.d.ts +17 -0
- package/esm/src/chat/ag-ui-helpers.d.ts.map +1 -0
- package/esm/src/chat/ag-ui-helpers.js +111 -0
- package/esm/src/chat/ag-ui.d.ts.map +1 -1
- package/esm/src/chat/ag-ui.js +1 -111
- package/esm/src/config/schemas/config.schema.d.ts +1 -0
- package/esm/src/config/schemas/config.schema.d.ts.map +1 -1
- package/esm/src/config/schemas/config.schema.js +11 -0
- package/esm/src/config/schemas/index.d.ts +11 -1
- package/esm/src/config/schemas/index.d.ts.map +1 -1
- package/esm/src/errors/error-registry-helpers.d.ts +6 -0
- package/esm/src/errors/error-registry-helpers.d.ts.map +1 -0
- package/esm/src/errors/error-registry-helpers.js +9 -0
- package/esm/src/errors/error-registry.d.ts.map +1 -1
- package/esm/src/errors/error-registry.js +4 -3
- package/esm/src/extensions/factory-loader.d.ts +29 -0
- package/esm/src/extensions/factory-loader.d.ts.map +1 -0
- package/esm/src/extensions/factory-loader.js +63 -0
- package/esm/src/extensions/index.d.ts +16 -0
- package/esm/src/extensions/index.d.ts.map +1 -1
- package/esm/src/extensions/index.js +16 -0
- package/esm/src/extensions/orchestrate.d.ts +54 -0
- package/esm/src/extensions/orchestrate.d.ts.map +1 -0
- package/esm/src/extensions/orchestrate.js +116 -0
- package/esm/src/html/styles-builder/plugin-loader.d.ts.map +1 -1
- package/esm/src/html/styles-builder/plugin-loader.js +23 -0
- package/esm/src/html/styles-builder/tailwind-plugin-allowlist.d.ts +29 -0
- package/esm/src/html/styles-builder/tailwind-plugin-allowlist.d.ts.map +1 -0
- package/esm/src/html/styles-builder/tailwind-plugin-allowlist.js +48 -0
- package/esm/src/modules/react-loader/ssr-module-loader/loader-helpers.d.ts +15 -0
- package/esm/src/modules/react-loader/ssr-module-loader/loader-helpers.d.ts.map +1 -0
- package/esm/src/modules/react-loader/ssr-module-loader/loader-helpers.js +22 -0
- package/esm/src/modules/react-loader/ssr-module-loader/loader.d.ts +0 -2
- package/esm/src/modules/react-loader/ssr-module-loader/loader.d.ts.map +1 -1
- package/esm/src/modules/react-loader/ssr-module-loader/loader.js +4 -24
- package/esm/src/platform/adapters/fs/veryfront/adapter-helpers.d.ts +19 -0
- package/esm/src/platform/adapters/fs/veryfront/adapter-helpers.d.ts.map +1 -0
- package/esm/src/platform/adapters/fs/veryfront/adapter-helpers.js +26 -0
- package/esm/src/platform/adapters/fs/veryfront/adapter.d.ts.map +1 -1
- package/esm/src/platform/adapters/fs/veryfront/adapter.js +4 -20
- package/esm/src/platform/adapters/fs/veryfront/read-operations-helpers.d.ts +1 -0
- package/esm/src/platform/adapters/fs/veryfront/read-operations-helpers.d.ts.map +1 -1
- package/esm/src/platform/adapters/fs/veryfront/read-operations-helpers.js +3 -0
- package/esm/src/platform/adapters/fs/veryfront/read-operations.d.ts.map +1 -1
- package/esm/src/platform/adapters/fs/veryfront/read-operations.js +4 -7
- package/esm/src/platform/adapters/fs/veryfront/websocket-manager-helpers.d.ts +28 -0
- package/esm/src/platform/adapters/fs/veryfront/websocket-manager-helpers.d.ts.map +1 -0
- package/esm/src/platform/adapters/fs/veryfront/websocket-manager-helpers.js +41 -0
- package/esm/src/platform/adapters/fs/veryfront/websocket-manager.d.ts +1 -4
- package/esm/src/platform/adapters/fs/veryfront/websocket-manager.d.ts.map +1 -1
- package/esm/src/platform/adapters/fs/veryfront/websocket-manager.js +7 -40
- package/esm/src/provider/runtime-loader/tool-input-status.d.ts +17 -0
- package/esm/src/provider/runtime-loader/tool-input-status.d.ts.map +1 -0
- package/esm/src/provider/runtime-loader/tool-input-status.js +155 -0
- package/esm/src/provider/runtime-loader.d.ts +2 -3
- package/esm/src/provider/runtime-loader.d.ts.map +1 -1
- package/esm/src/provider/runtime-loader.js +2 -155
- package/esm/src/rendering/orchestrator/pipeline-helpers.d.ts +8 -0
- package/esm/src/rendering/orchestrator/pipeline-helpers.d.ts.map +1 -0
- package/esm/src/rendering/orchestrator/pipeline-helpers.js +20 -0
- package/esm/src/rendering/orchestrator/pipeline.d.ts +0 -3
- package/esm/src/rendering/orchestrator/pipeline.d.ts.map +1 -1
- package/esm/src/rendering/orchestrator/pipeline.js +4 -22
- package/esm/src/routing/api/module-loader/loader-helpers.d.ts +10 -0
- package/esm/src/routing/api/module-loader/loader-helpers.d.ts.map +1 -0
- package/esm/src/routing/api/module-loader/loader-helpers.js +62 -0
- package/esm/src/routing/api/module-loader/loader.d.ts +1 -1
- package/esm/src/routing/api/module-loader/loader.d.ts.map +1 -1
- package/esm/src/routing/api/module-loader/loader.js +2 -60
- package/esm/src/server/bootstrap.d.ts +22 -2
- package/esm/src/server/bootstrap.d.ts.map +1 -1
- package/esm/src/server/bootstrap.js +67 -5
- package/esm/src/server/dev-ui/manifest.d.ts +2 -0
- package/esm/src/server/dev-ui/manifest.js +3 -1
- package/esm/src/server/handlers/request/api/project-discovery.d.ts.map +1 -1
- package/esm/src/server/handlers/request/api/project-discovery.js +14 -8
- package/esm/src/server/production-server.js +1 -1
- package/esm/src/server/services/rsc/endpoints/rsc-bundles.generated.d.ts.map +1 -1
- package/esm/src/server/services/rsc/endpoints/rsc-bundles.generated.js +2 -2
- package/esm/src/studio/bridge/bridge-bundle.generated.d.ts.map +1 -1
- package/esm/src/studio/bridge/bridge-bundle.generated.js +1 -1
- package/esm/src/tool/index.d.ts +1 -1
- package/esm/src/tool/index.d.ts.map +1 -1
- package/esm/src/tool/types.d.ts +20 -0
- package/esm/src/tool/types.d.ts.map +1 -1
- package/esm/src/utils/version-constant.d.ts +1 -1
- package/esm/src/utils/version-constant.js +1 -1
- package/package.json +1 -1
- package/src/cli/commands/generate/integration-generator-helpers.ts +185 -0
- package/src/cli/commands/generate/integration-generator.ts +12 -168
- package/src/cli/commands/knowledge/command-helpers.ts +295 -0
- package/src/cli/commands/knowledge/command.ts +33 -259
- package/src/cli/mcp/remote-file-tool-helpers.ts +27 -0
- package/src/cli/mcp/remote-file-tools.ts +6 -28
- package/src/cli/templates/integration-loader-helpers.ts +49 -0
- package/src/cli/templates/integration-loader.ts +10 -28
- package/src/cli/templates/manifest.js +2 -1
- package/src/deno.js +2 -2
- package/src/src/agent/runtime/index.ts +77 -94
- package/src/src/chat/ag-ui-helpers.ts +139 -0
- package/src/src/chat/ag-ui.ts +11 -139
- package/src/src/config/schemas/config.schema.ts +11 -0
- package/src/src/config/schemas/index.ts +15 -1
- package/src/src/errors/error-registry-helpers.ts +23 -0
- package/src/src/errors/error-registry.ts +8 -3
- package/src/src/extensions/factory-loader.ts +76 -0
- package/src/src/extensions/index.ts +20 -0
- package/src/src/extensions/orchestrate.ts +184 -0
- package/src/src/html/styles-builder/plugin-loader.ts +32 -0
- package/src/src/html/styles-builder/tailwind-plugin-allowlist.ts +51 -0
- package/src/src/modules/react-loader/ssr-module-loader/loader-helpers.ts +37 -0
- package/src/src/modules/react-loader/ssr-module-loader/loader.ts +8 -39
- package/src/src/platform/adapters/fs/veryfront/adapter-helpers.ts +43 -0
- package/src/src/platform/adapters/fs/veryfront/adapter.ts +8 -22
- package/src/src/platform/adapters/fs/veryfront/read-operations-helpers.ts +4 -0
- package/src/src/platform/adapters/fs/veryfront/read-operations.ts +4 -7
- package/src/src/platform/adapters/fs/veryfront/websocket-manager-helpers.ts +73 -0
- package/src/src/platform/adapters/fs/veryfront/websocket-manager.ts +29 -44
- package/src/src/provider/runtime-loader/tool-input-status.ts +210 -0
- package/src/src/provider/runtime-loader.ts +6 -203
- package/src/src/rendering/orchestrator/pipeline-helpers.ts +35 -0
- package/src/src/rendering/orchestrator/pipeline.ts +8 -35
- package/src/src/routing/api/module-loader/loader-helpers.ts +68 -0
- package/src/src/routing/api/module-loader/loader.ts +8 -65
- package/src/src/server/bootstrap.ts +88 -7
- package/src/src/server/dev-ui/manifest.js +3 -1
- package/src/src/server/handlers/request/api/project-discovery.ts +19 -8
- package/src/src/server/production-server.ts +1 -1
- package/src/src/server/services/rsc/endpoints/rsc-bundles.generated.ts +2 -2
- package/src/src/studio/bridge/bridge-bundle.generated.ts +1 -1
- package/src/src/tool/index.ts +1 -0
- package/src/src/tool/types.ts +21 -0
- package/src/src/utils/version-constant.ts +1 -1
|
@@ -11,7 +11,8 @@ export default {
|
|
|
11
11
|
"dashboard/App.tsx": "import { useEffect, useState } from \"react\";\nimport { Header } from \"./components/Header.tsx\";\nimport { TabNav } from \"./components/TabNav.tsx\";\nimport { AgentTab } from \"./components/AgentTab.tsx\";\nimport { ServerTab } from \"./components/ServerTab.tsx\";\nimport { RuntimeTab } from \"./components/RuntimeTab.tsx\";\nimport { FilesTab } from \"./components/FilesTab.tsx\";\nimport { ErrorsTab } from \"./components/ErrorsTab.tsx\";\nimport { ConfigTab } from \"./components/ConfigTab.tsx\";\nimport { APITab } from \"./components/APITab.tsx\";\n\nexport interface Tool {\n id: string;\n type: string;\n description: string;\n schema: { properties?: Record<string, unknown>; required?: string[] } | null;\n mcp: { enabled: boolean };\n}\n\nexport interface Resource {\n id: string;\n pattern: string;\n description: string;\n mcp: { enabled: boolean };\n}\n\nexport interface Prompt {\n id: string;\n description: string;\n}\n\nexport interface Agent {\n id: string;\n description: string;\n model: string;\n system: string | null;\n tools: Record<string, boolean>;\n memory: { type: string; maxTokens: number } | null;\n streaming: boolean;\n maxSteps: number | null;\n}\n\nexport interface FileItem {\n name: string;\n type: \"file\" | \"directory\";\n path: string;\n}\n\nexport interface Handler {\n name: string;\n priority: number;\n patterns: Array<{ pattern: string; exact?: boolean; prefix?: boolean; method?: string }>;\n enabled: string;\n}\n\nexport type TabId = \"agent\" | \"server\" | \"runtime\" | \"files\" | \"errors\" | \"config\" | \"api\";\n\nconst TABS: Array<{ id: TabId; label: string }> = [\n { id: \"agent\", label: \"Agent\" },\n { id: \"server\", label: \"Server\" },\n { id: \"runtime\", label: \"Runtime\" },\n { id: \"files\", label: \"Files\" },\n { id: \"errors\", label: \"Errors\" },\n { id: \"config\", label: \"Config\" },\n { id: \"api\", label: \"API\" },\n];\n\nasync function fetchJson(url: string): Promise<unknown> {\n const res = await fetch(url);\n return res.json();\n}\n\nexport function App(): JSX.Element {\n const [currentTab, setCurrentTab] = useState<TabId>(\"agent\");\n const [tools, setTools] = useState<Tool[]>([]);\n const [resources, setResources] = useState<Resource[]>([]);\n const [prompts, setPrompts] = useState<Prompt[]>([]);\n const [agents, setAgents] = useState<Agent[]>([]);\n\n useEffect((): void => {\n async function fetchData(): Promise<void> {\n try {\n const [t, r, p, a] = await Promise.all([\n fetchJson(\"/_dev/api/tools\"),\n fetchJson(\"/_dev/api/resources\"),\n fetchJson(\"/_dev/api/prompts\"),\n fetchJson(\"/_dev/api/agents\"),\n ]);\n\n const asRecord = (v: unknown): Record<string, unknown> =>\n v && typeof v === \"object\" ? (v as Record<string, unknown>) : {};\n setTools((asRecord(t).tools as Tool[]) ?? []);\n setResources((asRecord(r).resources as Resource[]) ?? []);\n setPrompts((asRecord(p).prompts as Prompt[]) ?? []);\n setAgents((asRecord(a).agents as Agent[]) ?? []);\n } catch (e) {\n console.error(\"Failed to fetch data:\", e);\n }\n }\n\n void fetchData();\n }, []);\n\n return (\n <div className=\"min-h-screen bg-gray-50\">\n <Header />\n <TabNav tabs={TABS} currentTab={currentTab} onTabChange={setCurrentTab} />\n\n <div className=\"tab-content\">\n {currentTab === \"agent\" && (\n <AgentTab tools={tools} resources={resources} prompts={prompts} agents={agents} />\n )}\n {currentTab === \"server\" && <ServerTab />}\n {currentTab === \"runtime\" && <RuntimeTab />}\n {currentTab === \"files\" && <FilesTab />}\n {currentTab === \"errors\" && <ErrorsTab />}\n {currentTab === \"config\" && <ConfigTab />}\n {currentTab === \"api\" && <APITab />}\n </div>\n </div>\n );\n}\n",
|
|
12
12
|
"dashboard/components/AgentsTab.tsx": "import { useMemo, useState } from \"react\";\nimport type { Agent, Tool } from \"../App.tsx\";\nimport { Card } from \"./Card.tsx\";\nimport { Sidebar } from \"./Sidebar.tsx\";\nimport { DetailHeader, EmptyState, TwoColumnLayout } from \"./shared.tsx\";\n\ninterface AgentsTabProps {\n agents: Agent[];\n tools: Tool[];\n onNavigateToMCP: (subTab: \"tools\" | \"resources\" | \"prompts\", itemId: string) => void;\n}\n\nexport function AgentsTab({ agents, tools, onNavigateToMCP }: AgentsTabProps): React.JSX.Element {\n const [selectedId, setSelectedId] = useState<string | null>(null);\n const [search, setSearch] = useState(\"\");\n\n const filteredAgents = useMemo(() => {\n const searchLower = search.toLowerCase();\n return agents.filter((a) => a.id.toLowerCase().includes(searchLower));\n }, [agents, search]);\n\n const selectedAgent = useMemo(() => {\n if (!selectedId) return undefined;\n return agents.find((a) => a.id === selectedId);\n }, [agents, selectedId]);\n\n return (\n <TwoColumnLayout\n sidebar={\n <Sidebar\n search={search}\n onSearchChange={setSearch}\n items={filteredAgents.map((a) => ({ id: a.id, label: a.id }))}\n selectedId={selectedId}\n onSelect={setSelectedId}\n emptyMessage=\"No agents registered\"\n />\n }\n >\n {selectedAgent\n ? <AgentDetail agent={selectedAgent} tools={tools} onNavigateToMCP={onNavigateToMCP} />\n : <EmptyState message=\"Select an agent\" />}\n </TwoColumnLayout>\n );\n}\n\ninterface AgentDetailProps {\n agent: Agent;\n tools: Tool[];\n onNavigateToMCP: (subTab: \"tools\" | \"resources\" | \"prompts\", itemId: string) => void;\n}\n\nfunction AgentDetail({ agent, tools, onNavigateToMCP }: AgentDetailProps): React.JSX.Element {\n const toolIds = Object.keys(agent.tools ?? {}).filter((k) => agent.tools?.[k]);\n\n return (\n <div>\n <DetailHeader title={agent.id} description={agent.description ?? \"No description\"} />\n\n <Card title=\"Configuration\" className=\"mb-6\">\n <table className=\"w-full text-sm\">\n <tbody>\n <ConfigRow label=\"Model\" value={agent.model} />\n <ConfigRow label=\"Streaming\" value={agent.streaming ? \"Enabled\" : \"Disabled\"} />\n <ConfigRow label=\"Max Steps\" value={agent.maxSteps ?? \"Default\"} last />\n </tbody>\n </table>\n </Card>\n\n {agent.system\n ? (\n <Card title=\"System Prompt\" className=\"mb-6\">\n <div className=\"p-4\">\n <pre className=\"text-sm text-gray-700 whitespace-pre-wrap font-mono bg-gray-50 p-3 rounded-lg max-h-64 overflow-auto\">\n {agent.system}\n </pre>\n </div>\n </Card>\n )\n : null}\n\n <Card title={`Tools (${toolIds.length})`} className=\"mb-6\">\n <div className=\"p-3\">\n {toolIds.length === 0\n ? <span className=\"text-sm text-gray-400\">No tools configured</span>\n : (\n <div className=\"flex flex-wrap gap-1.5\">\n {toolIds.map((id) => {\n const exists = tools.some((t) => t.id === id);\n const onClick = exists ? () => onNavigateToMCP(\"tools\", id) : undefined;\n\n return <Badge key={id} label={id} exists={exists} onClick={onClick} />;\n })}\n </div>\n )}\n </div>\n </Card>\n\n {agent.memory\n ? (\n <Card title=\"Memory\">\n <table className=\"w-full text-sm\">\n <tbody>\n <ConfigRow label=\"Type\" value={agent.memory.type || \"-\"} />\n <ConfigRow label=\"Max Tokens\" value={agent.memory.maxTokens || \"-\"} last />\n </tbody>\n </table>\n </Card>\n )\n : null}\n </div>\n );\n}\n\nfunction ConfigRow({\n label,\n value,\n last,\n}: {\n label: string;\n value: string | number;\n last?: boolean;\n}): React.JSX.Element {\n return (\n <tr className={last ? \"\" : \"border-b\"}>\n <td className=\"px-3 py-2.5 w-28 font-medium text-gray-600\">{label}</td>\n <td className=\"px-3 py-2.5 text-gray-900\">{value}</td>\n </tr>\n );\n}\n\nfunction Badge({\n label,\n exists,\n onClick,\n}: {\n label: string;\n exists: boolean;\n onClick?: () => void;\n}): React.JSX.Element {\n const base = \"px-2.5 py-1 text-xs font-medium rounded transition-colors\";\n\n if (!exists) {\n return <span className={`${base} bg-gray-100 text-gray-400`}>{label} (not found)</span>;\n }\n\n return (\n <button\n type=\"button\"\n onClick={onClick}\n className={`${base} bg-sky-50 text-sky-600 hover:bg-sky-500 hover:text-white cursor-pointer`}\n >\n {label}\n </button>\n );\n}\n",
|
|
13
13
|
"dashboard/components/Sidebar.tsx": "interface SidebarProps {\n search: string;\n onSearchChange: (value: string) => void;\n subTabs?: { id: string; label: string }[];\n currentSubTab?: string;\n onSubTabChange?: (id: string) => void;\n items: { id: string; label: string; bold?: boolean }[];\n selectedId: string | null;\n onSelect: (id: string) => void;\n emptyMessage: string;\n onBack?: () => void;\n backLabel?: string;\n}\n\nexport function Sidebar({\n search,\n onSearchChange,\n subTabs,\n currentSubTab,\n onSubTabChange,\n items,\n selectedId,\n onSelect,\n emptyMessage,\n onBack,\n backLabel,\n}: SidebarProps): React.ReactElement {\n const showSubTabs = subTabs && onSubTabChange;\n\n return (\n <aside className=\"bg-white border-r border-gray-200 flex flex-col overflow-hidden\">\n <div className=\"p-3 border-b border-gray-100\">\n <input\n type=\"text\"\n value={search}\n onChange={(e) => onSearchChange(e.target.value)}\n placeholder=\"Search...\"\n className=\"w-full px-2.5 py-1.5 bg-gray-50 border border-gray-200 rounded text-sm focus:outline-none focus:border-sky-500 focus:bg-white placeholder:text-gray-400\"\n />\n </div>\n\n {showSubTabs\n ? (\n <div className=\"flex px-3 py-2 gap-0.5 border-b border-gray-100\">\n {subTabs.map((tab) => {\n const isActive = currentSubTab === tab.id;\n\n return (\n <button\n type=\"button\"\n key={tab.id}\n onClick={() => onSubTabChange(tab.id)}\n className={`px-2.5 py-1 text-[11px] font-medium rounded transition-colors ${\n isActive\n ? \"bg-sky-50 text-sky-600\"\n : \"text-gray-400 hover:bg-gray-50 hover:text-gray-600\"\n }`}\n >\n {tab.label}\n </button>\n );\n })}\n </div>\n )\n : null}\n\n <div className=\"flex-1 overflow-y-auto p-1.5\">\n {onBack\n ? (\n <button\n type=\"button\"\n onClick={onBack}\n className=\"w-full px-2.5 py-2 text-sm text-sky-600 rounded hover:bg-gray-50 flex items-center gap-1.5 text-left\"\n >\n <span className=\"w-1.5 h-1.5 rounded-full bg-sky-500\" />\n {backLabel ?? \".. (back)\"}\n </button>\n )\n : null}\n\n {items.length === 0\n ? (\n <div className=\"flex items-center justify-center py-8 text-gray-400 text-sm\">\n {emptyMessage}\n </div>\n )\n : (\n items.map((item) => {\n const isSelected = selectedId === item.id;\n\n return (\n <button\n type=\"button\"\n key={item.id}\n onClick={() => onSelect(item.id)}\n className={`w-full px-2.5 py-2 text-sm rounded flex items-center gap-1.5 text-left transition-colors ${\n isSelected\n ? \"bg-sky-500 text-white\"\n : \"text-gray-600 hover:bg-gray-50 hover:text-gray-900\"\n } ${item.bold ? \"font-semibold\" : \"\"}`}\n >\n <span\n className={`w-1.5 h-1.5 rounded-full flex-shrink-0 ${\n isSelected ? \"bg-white\" : \"bg-current opacity-30\"\n }`}\n />\n {item.label}\n </button>\n );\n })\n )}\n </div>\n </aside>\n );\n}\n",
|
|
14
|
-
"dashboard/components/WorkflowsTab.tsx": "import { useEffect, useState } from \"react\";\nimport type { Agent, Tool } from \"../App.tsx\";\nimport { Sidebar } from \"./Sidebar.tsx\";\nimport { Card } from \"./Card.tsx\";\nimport { ActionButton, DetailHeader, EmptyState, ResultBox, TwoColumnLayout } from \"./shared.tsx\";\n\ninterface NodeInfo {\n id: string;\n type: string;\n agent?: string;\n tool?: string;\n dependsOn?: string[];\n children?: string[];\n message?: string;\n}\n\ninterface WorkflowMetadata {\n id: string;\n description?: string;\n version?: string;\n timeout?: string | number;\n nodeCount: number;\n nodeTypes: string[];\n nodes: NodeInfo[];\n agentRefs: string[];\n toolRefs: string[];\n hasInputSchema: boolean;\n hasOutputSchema: boolean;\n inputSchemaJson?: Record<string, unknown>;\n registeredAt: string;\n}\n\ninterface WorkflowsTabProps {\n workflows: WorkflowMetadata[];\n agents: Agent[];\n tools: Tool[];\n onNavigateToAgent?: (agentId: string) => void;\n onNavigateToTool?: (toolId: string) => void;\n}\n\ninterface NodeTypeStyle {\n badge: string;\n node: string;\n}\n\nconst DEFAULT_NODE_TYPE_STYLE: NodeTypeStyle = {\n badge: \"bg-gray-100 text-gray-600\",\n node: \"bg-gray-50 border-gray-200 text-gray-700\",\n};\n\nconst NODE_TYPE_STYLES: Record<string, NodeTypeStyle> = {\n step: {\n badge: \"bg-blue-50 text-blue-600\",\n node: \"bg-blue-50 border-blue-200 text-blue-700\",\n },\n parallel: {\n badge: \"bg-green-50 text-green-600\",\n node: \"bg-green-50 border-green-200 text-green-700\",\n },\n branch: {\n badge: \"bg-yellow-50 text-yellow-700\",\n node: \"bg-yellow-50 border-yellow-200 text-yellow-700\",\n },\n wait: {\n badge: \"bg-orange-50 text-orange-600\",\n node: \"bg-orange-50 border-orange-200 text-orange-700\",\n },\n};\n\nfunction getNodeTypeStyle(type: string): NodeTypeStyle {\n return NODE_TYPE_STYLES[type] ?? DEFAULT_NODE_TYPE_STYLE;\n}\n\nexport function WorkflowsTab({\n workflows,\n agents,\n tools,\n onNavigateToAgent,\n onNavigateToTool,\n}: WorkflowsTabProps): React.ReactElement {\n const [selectedId, setSelectedId] = useState<string | null>(null);\n const [search, setSearch] = useState(\"\");\n\n const searchLower = search.toLowerCase();\n const filteredWorkflows = workflows.filter((wf) => wf.id.toLowerCase().includes(searchLower));\n const selectedWorkflow = workflows.find((wf) => wf.id === selectedId);\n\n const sidebar = (\n <Sidebar\n search={search}\n onSearchChange={setSearch}\n items={filteredWorkflows.map((wf) => ({\n id: wf.id,\n label: wf.id,\n badge: wf.nodeCount > 0 ? `${wf.nodeCount} nodes` : \"dynamic\",\n }))}\n selectedId={selectedId}\n onSelect={setSelectedId}\n emptyMessage=\"No workflows registered\"\n />\n );\n\n return (\n <TwoColumnLayout sidebar={sidebar}>\n {selectedWorkflow\n ? (\n <WorkflowDetail\n workflow={selectedWorkflow}\n agents={agents}\n tools={tools}\n onNavigateToAgent={onNavigateToAgent}\n onNavigateToTool={onNavigateToTool}\n />\n )\n : <EmptyState message=\"Select a workflow to inspect\" />}\n </TwoColumnLayout>\n );\n}\n\nfunction WorkflowDetail({\n workflow,\n agents,\n tools,\n onNavigateToAgent,\n onNavigateToTool,\n}: {\n workflow: WorkflowMetadata;\n agents: Agent[];\n tools: Tool[];\n onNavigateToAgent?: (agentId: string) => void;\n onNavigateToTool?: (toolId: string) => void;\n}): React.ReactElement {\n const agentMap = new Map(agents.map((a) => [a.id, a]));\n const toolMap = new Map(tools.map((t) => [t.id, t]));\n\n function getNodeTypeBadgeClass(type: string): string {\n return getNodeTypeStyle(type).badge;\n }\n\n return (\n <div>\n <DetailHeader title={workflow.id} description={workflow.description || \"No description\"} />\n\n <div className=\"grid grid-cols-2 md:grid-cols-4 gap-4 mb-6\">\n <Card className=\"p-4\">\n <div className=\"text-2xl font-bold text-gray-900\">{workflow.nodeCount || \"dynamic\"}</div>\n <div className=\"text-xs text-gray-500 uppercase tracking-wide\">Nodes</div>\n </Card>\n <Card className=\"p-4\">\n <div className=\"text-2xl font-bold text-gray-900\">{workflow.agentRefs.length}</div>\n <div className=\"text-xs text-gray-500 uppercase tracking-wide\">Agents</div>\n </Card>\n <Card className=\"p-4\">\n <div className=\"text-2xl font-bold text-gray-900\">{workflow.toolRefs.length}</div>\n <div className=\"text-xs text-gray-500 uppercase tracking-wide\">Tools</div>\n </Card>\n <Card className=\"p-4\">\n <div className=\"text-lg font-bold text-gray-900\">{workflow.timeout || \"-\"}</div>\n <div className=\"text-xs text-gray-500 uppercase tracking-wide\">Timeout</div>\n </Card>\n </div>\n\n {workflow.nodeTypes.length > 0\n ? (\n <Card title=\"Node Types\" className=\"mb-6\">\n <div className=\"p-4 flex flex-wrap gap-2\">\n {workflow.nodeTypes.map((type) => (\n <span\n key={type}\n className=\"px-2.5 py-1 bg-purple-50 text-purple-700 text-sm font-medium rounded-full\"\n >\n {type}\n </span>\n ))}\n </div>\n </Card>\n )\n : null}\n\n <Card title=\"Workflow Steps\" className=\"mb-6\">\n {workflow.nodes.length > 0\n ? (\n <div className=\"divide-y\">\n {workflow.nodes.map((node, index) => {\n const agentId = node.agent;\n const toolId = node.tool;\n\n return (\n <div key={node.id} className=\"p-4\">\n <div className=\"flex items-start gap-4\">\n <div className=\"flex-shrink-0 w-8 h-8 rounded-full bg-sky-100 text-sky-700 flex items-center justify-center text-sm font-medium\">\n {index + 1}\n </div>\n\n <div className=\"flex-1 min-w-0\">\n <div className=\"flex items-center gap-2 mb-1\">\n <code className=\"text-sm font-medium text-gray-900\">{node.id}</code>\n <span\n className={`px-1.5 py-0.5 text-[10px] font-semibold uppercase rounded ${\n getNodeTypeBadgeClass(\n node.type,\n )\n }`}\n >\n {node.type}\n </span>\n </div>\n\n <div className=\"text-sm text-gray-600 space-y-1\">\n {agentId\n ? (\n <div className=\"flex items-center gap-2\">\n <span className=\"text-gray-400\">Agent:</span>\n {agentMap.has(agentId)\n ? (\n <button\n type=\"button\"\n onClick={() => onNavigateToAgent?.(agentId)}\n className=\"text-sky-600 hover:underline\"\n >\n {agentId}\n </button>\n )\n : <span className=\"text-red-500\">{agentId} (not found)</span>}\n </div>\n )\n : null}\n\n {toolId\n ? (\n <div className=\"flex items-center gap-2\">\n <span className=\"text-gray-400\">Tool:</span>\n {toolMap.has(toolId)\n ? (\n <button\n type=\"button\"\n onClick={() => onNavigateToTool?.(toolId)}\n className=\"text-sky-600 hover:underline\"\n >\n {toolId}\n </button>\n )\n : <span className=\"text-red-500\">{toolId} (not found)</span>}\n </div>\n )\n : null}\n\n {node.dependsOn?.length\n ? (\n <div className=\"flex items-center gap-2\">\n <span className=\"text-gray-400\">Depends on:</span>\n <span className=\"text-gray-600\">{node.dependsOn.join(\", \")}</span>\n </div>\n )\n : null}\n\n {node.children?.length\n ? (\n <div className=\"flex items-center gap-2\">\n <span className=\"text-gray-400\">Contains:</span>\n <span className=\"text-gray-600\">{node.children.join(\", \")}</span>\n </div>\n )\n : null}\n\n {node.message\n ? (\n <div className=\"flex items-start gap-2\">\n <span className=\"text-gray-400\">Message:</span>\n <span className=\"text-gray-600 italic\">\"{node.message}\"</span>\n </div>\n )\n : null}\n </div>\n </div>\n </div>\n </div>\n );\n })}\n </div>\n )\n : (\n <div className=\"p-8 text-center text-gray-400\">\n <div className=\"mb-2\">Dynamic steps</div>\n <div className=\"text-sm text-gray-500\">\n This workflow uses a function to generate steps at runtime\n </div>\n </div>\n )}\n </Card>\n\n {workflow.nodes.length > 0\n ? (\n <Card title=\"Workflow Flow\" className=\"mb-6\">\n <div className=\"p-4 font-mono text-sm bg-gray-50 overflow-x-auto\">\n <WorkflowDAG nodes={workflow.nodes} />\n </div>\n </Card>\n )\n : null}\n\n <div className=\"grid grid-cols-1 md:grid-cols-2 gap-6\">\n <Card title={`Agents Used (${workflow.agentRefs.length})`}>\n {workflow.agentRefs.length > 0\n ? (\n <div className=\"divide-y\">\n {workflow.agentRefs.map((agentId) => {\n const agent = agentMap.get(agentId);\n return (\n <div key={agentId} className=\"p-3 flex items-center justify-between\">\n <div>\n <button\n type=\"button\"\n onClick={() => onNavigateToAgent?.(agentId)}\n className=\"text-sm text-sky-600 hover:underline font-medium\"\n >\n {agentId}\n </button>\n {agent ? <div className=\"text-xs text-gray-500\">{agent.model}</div> : null}\n </div>\n {agent\n ? <span className=\"w-2 h-2 rounded-full bg-green-500\" title=\"Found\" />\n : <span className=\"w-2 h-2 rounded-full bg-red-500\" title=\"Not found\" />}\n </div>\n );\n })}\n </div>\n )\n : <div className=\"p-4 text-center text-gray-400 text-sm\">No agents referenced</div>}\n </Card>\n\n <Card title={`Tools Used (${workflow.toolRefs.length})`}>\n {workflow.toolRefs.length > 0\n ? (\n <div className=\"divide-y\">\n {workflow.toolRefs.map((toolId) => {\n const tool = toolMap.get(toolId);\n return (\n <div key={toolId} className=\"p-3 flex items-center justify-between\">\n <div>\n <button\n type=\"button\"\n onClick={() => onNavigateToTool?.(toolId)}\n className=\"text-sm text-sky-600 hover:underline font-medium\"\n >\n {toolId}\n </button>\n {tool\n ? (\n <div className=\"text-xs text-gray-500 truncate max-w-[200px]\">\n {tool.description}\n </div>\n )\n : null}\n </div>\n {tool\n ? <span className=\"w-2 h-2 rounded-full bg-green-500\" title=\"Found\" />\n : <span className=\"w-2 h-2 rounded-full bg-red-500\" title=\"Not found\" />}\n </div>\n );\n })}\n </div>\n )\n : <div className=\"p-4 text-center text-gray-400 text-sm\">No tools referenced</div>}\n </Card>\n </div>\n\n <Card title=\"Schema\" className=\"mt-6\">\n <div className=\"p-4 flex gap-4\">\n <div className=\"flex items-center gap-2\">\n <span\n className={`w-3 h-3 rounded-full ${\n workflow.hasInputSchema ? \"bg-green-500\" : \"bg-gray-300\"\n }`}\n />\n <span className=\"text-sm text-gray-600\">Input Schema</span>\n </div>\n <div className=\"flex items-center gap-2\">\n <span\n className={`w-3 h-3 rounded-full ${\n workflow.hasOutputSchema ? \"bg-green-500\" : \"bg-gray-300\"\n }`}\n />\n <span className=\"text-sm text-gray-600\">Output Schema</span>\n </div>\n </div>\n </Card>\n\n <WorkflowExecutor workflowId={workflow.id} inputSchema={workflow.inputSchemaJson} />\n </div>\n );\n}\n\nfunction generateExampleFromSchema(schema?: Record<string, unknown>): Record<string, unknown> {\n if (!schema || schema.type !== \"object\") return {};\n\n const properties = schema.properties as Record<string, Record<string, unknown>> | undefined;\n if (!properties) return {};\n\n const example: Record<string, unknown> = {};\n\n for (const [name, prop] of Object.entries(properties)) {\n if (prop.default !== undefined) {\n example[name] = prop.default;\n continue;\n }\n\n if (Array.isArray(prop.enum) && prop.enum.length > 0) {\n example[name] = prop.enum[0];\n continue;\n }\n\n const nameLower = name.toLowerCase();\n\n switch (prop.type) {\n case \"string\":\n if (nameLower.includes(\"url\") || nameLower.includes(\"uri\")) {\n example[name] = \"https://example.com/data\";\n } else if (nameLower.includes(\"email\")) {\n example[name] = \"user@example.com\";\n } else {\n example[name] = `example-${name}`;\n }\n break;\n case \"number\":\n case \"integer\":\n example[name] = 1;\n break;\n case \"boolean\":\n example[name] = true;\n break;\n case \"array\":\n example[name] = [];\n break;\n case \"object\":\n example[name] = generateExampleFromSchema(prop as Record<string, unknown>);\n break;\n default:\n example[name] = null;\n }\n }\n\n return example;\n}\n\nfunction WorkflowExecutor({\n workflowId,\n inputSchema,\n}: {\n workflowId: string;\n inputSchema?: Record<string, unknown>;\n}): React.ReactElement {\n const [input, setInput] = useState<string>(() => {\n const example = generateExampleFromSchema(inputSchema);\n return JSON.stringify(example, null, 2);\n });\n\n const [result, setResult] = useState<\n {\n success: boolean;\n data: string;\n duration?: number;\n runId?: string;\n status?: string;\n } | null\n >(null);\n\n const [loading, setLoading] = useState(false);\n\n useEffect(() => {\n const example = generateExampleFromSchema(inputSchema);\n setInput(JSON.stringify(example, null, 2));\n setResult(null);\n }, [workflowId, inputSchema]);\n\n async function startWorkflow(): Promise<void> {\n let parsed: unknown;\n try {\n parsed = JSON.parse(input);\n } catch (e) {\n setResult({ success: false, data: (e as Error).message });\n return;\n }\n\n setLoading(true);\n setResult(null);\n\n try {\n const res = await fetch(\"/_dev/api/start-workflow\", {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({ workflowId, input: parsed }),\n });\n\n const d = await res.json();\n\n if (d.error) {\n setResult({\n success: false,\n data: d.error + (d.hint ? `\\n\\n${d.hint}` : \"\"),\n });\n return;\n }\n\n setResult({\n success: true,\n data: JSON.stringify(d.result, null, 2),\n duration: d.duration,\n runId: d.runId,\n status: d.status,\n });\n } catch (e) {\n setResult({ success: false, data: (e as Error).message });\n } finally {\n setLoading(false);\n }\n }\n\n return (\n <Card title=\"Start Workflow\" className=\"mt-6\">\n <div className=\"p-4\">\n <label className=\"block text-xs font-medium uppercase tracking-wide text-gray-600 mb-1\">\n Input (JSON)\n </label>\n <textarea\n value={input}\n onChange={(e) => setInput(e.target.value)}\n placeholder='{\"topic\": \"AI Safety\", \"requiresApproval\": false}'\n className=\"w-full px-3 py-2 bg-gray-50 border border-gray-200 rounded text-sm font-mono focus:outline-none focus:border-sky-500 focus:bg-white min-h-[80px] resize-y\"\n />\n <ActionButton onClick={startWorkflow} loading={loading} loadingText=\"Running...\">\n Start\n </ActionButton>\n\n {result\n ? (\n <div>\n {result.runId\n ? (\n <div className=\"mt-2 text-xs text-gray-500\">\n Run ID: <code className=\"text-sky-600\">{result.runId}</code>\n {result.status\n ? (\n <span className=\"ml-2\">\n Status:{\" \"}\n <span\n className={result.status === \"completed\"\n ? \"text-green-600\"\n : \"text-yellow-600\"}\n >\n {result.status}\n </span>\n </span>\n )\n : null}\n </div>\n )\n : null}\n\n <ResultBox\n success={result.success}\n label={result.success ? \"Result\" : \"Error\"}\n duration={result.duration}\n >\n {result.data}\n </ResultBox>\n </div>\n )\n : null}\n </div>\n </Card>\n );\n}\n\nfunction WorkflowDAG({ nodes }: { nodes: NodeInfo[] }): React.ReactElement {\n if (nodes.length === 0) {\n return (\n <div className=\"text-gray-400 text-center py-4\">(dynamic - steps generated at runtime)</div>\n );\n }\n\n const dependsOnMap = new Map<string, string[]>();\n const dependentsMap = new Map<string, string[]>();\n\n for (const node of nodes) {\n dependsOnMap.set(node.id, node.dependsOn || []);\n dependentsMap.set(node.id, []);\n }\n\n for (const node of nodes) {\n for (const dep of node.dependsOn || []) {\n dependentsMap.get(dep)?.push(node.id);\n }\n }\n\n const rootNodes = nodes.filter((n) => !n.dependsOn?.length);\n\n const levels = new Map<string, number>();\n const queue = rootNodes.map((n) => n.id);\n\n for (const id of queue) levels.set(id, 0);\n\n while (queue.length > 0) {\n const current = queue.shift();\n if (!current) continue;\n\n for (const dependent of dependentsMap.get(current) || []) {\n const deps = dependsOnMap.get(dependent) || [];\n if (levels.has(dependent) || !deps.every((d) => levels.has(d))) continue;\n\n const maxDepLevel = Math.max(...deps.map((d) => levels.get(d) ?? 0));\n levels.set(dependent, maxDepLevel + 1);\n queue.push(dependent);\n }\n }\n\n const levelGroups = new Map<number, NodeInfo[]>();\n for (const node of nodes) {\n const level = levels.get(node.id) ?? 0;\n const group = levelGroups.get(level);\n if (group) group.push(node);\n else levelGroups.set(level, [node]);\n }\n\n const maxLevel = Math.max(...Array.from(levels.values()), 0);\n\n function getNodeStyle(type: string): string {\n return getNodeTypeStyle(type).node;\n }\n\n return (\n <div className=\"flex flex-col items-center gap-2\">\n {Array.from({ length: maxLevel + 1 }, (_, level) => {\n const nodesAtLevel = levelGroups.get(level) || [];\n const isParallel = nodesAtLevel.length > 1;\n\n return (\n <div key={level}>\n {level > 0\n ? (\n <div className=\"flex justify-center py-1\">\n <svg width=\"24\" height=\"20\" viewBox=\"0 0 24 20\" className=\"text-gray-400\">\n <path\n d=\"M12 0 L12 14 M6 10 L12 16 L18 10\"\n stroke=\"currentColor\"\n strokeWidth=\"2\"\n fill=\"none\"\n />\n </svg>\n </div>\n )\n : null}\n\n <div className={`flex gap-3 ${isParallel ? \"items-start\" : \"justify-center\"}`}>\n {isParallel\n ? (\n <div className=\"flex items-center text-gray-400 text-xs font-mono self-center\">\n [\n </div>\n )\n : null}\n\n {nodesAtLevel.map((node, idx) => (\n <div key={node.id} className=\"flex items-center gap-2\">\n <div\n className={`px-3 py-2 rounded-lg border text-sm font-medium ${\n getNodeStyle(\n node.type,\n )\n }`}\n >\n <div className=\"font-semibold\">{node.id}</div>\n {node.tool\n ? <div className=\"text-xs opacity-75 mt-0.5\">tool: {node.tool}</div>\n : null}\n {node.agent\n ? <div className=\"text-xs opacity-75 mt-0.5\">agent: {node.agent}</div>\n : null}\n </div>\n\n {isParallel && idx < nodesAtLevel.length - 1\n ? <div className=\"text-gray-400 text-xs font-mono\">,</div>\n : null}\n </div>\n ))}\n\n {isParallel\n ? (\n <div className=\"flex items-center text-gray-400 text-xs font-mono self-center\">\n ]\n </div>\n )\n : null}\n </div>\n </div>\n );\n })}\n </div>\n );\n}\n",
|
|
14
|
+
"dashboard/components/WorkflowsTab.helpers.ts": "export interface NodeTypeStyle {\n badge: string;\n node: string;\n}\n\nconst DEFAULT_NODE_TYPE_STYLE: NodeTypeStyle = {\n badge: \"bg-gray-100 text-gray-600\",\n node: \"bg-gray-50 border-gray-200 text-gray-700\",\n};\n\nconst NODE_TYPE_STYLES: Record<string, NodeTypeStyle> = {\n step: {\n badge: \"bg-blue-50 text-blue-600\",\n node: \"bg-blue-50 border-blue-200 text-blue-700\",\n },\n parallel: {\n badge: \"bg-green-50 text-green-600\",\n node: \"bg-green-50 border-green-200 text-green-700\",\n },\n branch: {\n badge: \"bg-yellow-50 text-yellow-700\",\n node: \"bg-yellow-50 border-yellow-200 text-yellow-700\",\n },\n wait: {\n badge: \"bg-orange-50 text-orange-600\",\n node: \"bg-orange-50 border-orange-200 text-orange-700\",\n },\n};\n\nexport function getNodeTypeStyle(type: string): NodeTypeStyle {\n return NODE_TYPE_STYLES[type] ?? DEFAULT_NODE_TYPE_STYLE;\n}\n\nexport function filterItemsByIdSearch<T extends { id: string }>(items: T[], search: string): T[] {\n const searchLower = search.toLowerCase();\n return items.filter((item) => item.id.toLowerCase().includes(searchLower));\n}\n\nexport function generateExampleFromSchema(\n schema?: Record<string, unknown>,\n): Record<string, unknown> {\n if (!schema || schema.type !== \"object\") return {};\n\n const properties = schema.properties as Record<string, Record<string, unknown>> | undefined;\n if (!properties) return {};\n\n const example: Record<string, unknown> = {};\n\n for (const [name, prop] of Object.entries(properties)) {\n if (prop.default !== undefined) {\n example[name] = prop.default;\n continue;\n }\n\n if (Array.isArray(prop.enum) && prop.enum.length > 0) {\n example[name] = prop.enum[0];\n continue;\n }\n\n const nameLower = name.toLowerCase();\n\n switch (prop.type) {\n case \"string\":\n if (nameLower.includes(\"url\") || nameLower.includes(\"uri\")) {\n example[name] = \"https://example.com/data\";\n } else if (nameLower.includes(\"email\")) {\n example[name] = \"user@example.com\";\n } else {\n example[name] = `example-${name}`;\n }\n break;\n case \"number\":\n case \"integer\":\n example[name] = 1;\n break;\n case \"boolean\":\n example[name] = true;\n break;\n case \"array\":\n example[name] = [];\n break;\n case \"object\":\n example[name] = generateExampleFromSchema(prop as Record<string, unknown>);\n break;\n default:\n example[name] = null;\n }\n }\n\n return example;\n}\n",
|
|
15
|
+
"dashboard/components/WorkflowsTab.tsx": "import { useEffect, useState } from \"react\";\nimport type { Agent, Tool } from \"../App.tsx\";\nimport { Sidebar } from \"./Sidebar.tsx\";\nimport { Card } from \"./Card.tsx\";\nimport { ActionButton, DetailHeader, EmptyState, ResultBox, TwoColumnLayout } from \"./shared.tsx\";\nimport {\n filterItemsByIdSearch,\n generateExampleFromSchema,\n getNodeTypeStyle,\n} from \"./WorkflowsTab.helpers.ts\";\n\ninterface NodeInfo {\n id: string;\n type: string;\n agent?: string;\n tool?: string;\n dependsOn?: string[];\n children?: string[];\n message?: string;\n}\n\ninterface WorkflowMetadata {\n id: string;\n description?: string;\n version?: string;\n timeout?: string | number;\n nodeCount: number;\n nodeTypes: string[];\n nodes: NodeInfo[];\n agentRefs: string[];\n toolRefs: string[];\n hasInputSchema: boolean;\n hasOutputSchema: boolean;\n inputSchemaJson?: Record<string, unknown>;\n registeredAt: string;\n}\n\ninterface WorkflowsTabProps {\n workflows: WorkflowMetadata[];\n agents: Agent[];\n tools: Tool[];\n onNavigateToAgent?: (agentId: string) => void;\n onNavigateToTool?: (toolId: string) => void;\n}\n\nexport function WorkflowsTab({\n workflows,\n agents,\n tools,\n onNavigateToAgent,\n onNavigateToTool,\n}: WorkflowsTabProps): React.ReactElement {\n const [selectedId, setSelectedId] = useState<string | null>(null);\n const [search, setSearch] = useState(\"\");\n\n const filteredWorkflows = filterItemsByIdSearch(workflows, search);\n const selectedWorkflow = workflows.find((wf) => wf.id === selectedId);\n\n const sidebar = (\n <Sidebar\n search={search}\n onSearchChange={setSearch}\n items={filteredWorkflows.map((wf) => ({\n id: wf.id,\n label: wf.id,\n badge: wf.nodeCount > 0 ? `${wf.nodeCount} nodes` : \"dynamic\",\n }))}\n selectedId={selectedId}\n onSelect={setSelectedId}\n emptyMessage=\"No workflows registered\"\n />\n );\n\n return (\n <TwoColumnLayout sidebar={sidebar}>\n {selectedWorkflow\n ? (\n <WorkflowDetail\n workflow={selectedWorkflow}\n agents={agents}\n tools={tools}\n onNavigateToAgent={onNavigateToAgent}\n onNavigateToTool={onNavigateToTool}\n />\n )\n : <EmptyState message=\"Select a workflow to inspect\" />}\n </TwoColumnLayout>\n );\n}\n\nfunction WorkflowDetail({\n workflow,\n agents,\n tools,\n onNavigateToAgent,\n onNavigateToTool,\n}: {\n workflow: WorkflowMetadata;\n agents: Agent[];\n tools: Tool[];\n onNavigateToAgent?: (agentId: string) => void;\n onNavigateToTool?: (toolId: string) => void;\n}): React.ReactElement {\n const agentMap = new Map(agents.map((a) => [a.id, a]));\n const toolMap = new Map(tools.map((t) => [t.id, t]));\n\n function getNodeTypeBadgeClass(type: string): string {\n return getNodeTypeStyle(type).badge;\n }\n\n return (\n <div>\n <DetailHeader title={workflow.id} description={workflow.description || \"No description\"} />\n\n <div className=\"grid grid-cols-2 md:grid-cols-4 gap-4 mb-6\">\n <Card className=\"p-4\">\n <div className=\"text-2xl font-bold text-gray-900\">{workflow.nodeCount || \"dynamic\"}</div>\n <div className=\"text-xs text-gray-500 uppercase tracking-wide\">Nodes</div>\n </Card>\n <Card className=\"p-4\">\n <div className=\"text-2xl font-bold text-gray-900\">{workflow.agentRefs.length}</div>\n <div className=\"text-xs text-gray-500 uppercase tracking-wide\">Agents</div>\n </Card>\n <Card className=\"p-4\">\n <div className=\"text-2xl font-bold text-gray-900\">{workflow.toolRefs.length}</div>\n <div className=\"text-xs text-gray-500 uppercase tracking-wide\">Tools</div>\n </Card>\n <Card className=\"p-4\">\n <div className=\"text-lg font-bold text-gray-900\">{workflow.timeout || \"-\"}</div>\n <div className=\"text-xs text-gray-500 uppercase tracking-wide\">Timeout</div>\n </Card>\n </div>\n\n {workflow.nodeTypes.length > 0\n ? (\n <Card title=\"Node Types\" className=\"mb-6\">\n <div className=\"p-4 flex flex-wrap gap-2\">\n {workflow.nodeTypes.map((type) => (\n <span\n key={type}\n className=\"px-2.5 py-1 bg-purple-50 text-purple-700 text-sm font-medium rounded-full\"\n >\n {type}\n </span>\n ))}\n </div>\n </Card>\n )\n : null}\n\n <Card title=\"Workflow Steps\" className=\"mb-6\">\n {workflow.nodes.length > 0\n ? (\n <div className=\"divide-y\">\n {workflow.nodes.map((node, index) => {\n const agentId = node.agent;\n const toolId = node.tool;\n\n return (\n <div key={node.id} className=\"p-4\">\n <div className=\"flex items-start gap-4\">\n <div className=\"flex-shrink-0 w-8 h-8 rounded-full bg-sky-100 text-sky-700 flex items-center justify-center text-sm font-medium\">\n {index + 1}\n </div>\n\n <div className=\"flex-1 min-w-0\">\n <div className=\"flex items-center gap-2 mb-1\">\n <code className=\"text-sm font-medium text-gray-900\">{node.id}</code>\n <span\n className={`px-1.5 py-0.5 text-[10px] font-semibold uppercase rounded ${\n getNodeTypeBadgeClass(\n node.type,\n )\n }`}\n >\n {node.type}\n </span>\n </div>\n\n <div className=\"text-sm text-gray-600 space-y-1\">\n {agentId\n ? (\n <div className=\"flex items-center gap-2\">\n <span className=\"text-gray-400\">Agent:</span>\n {agentMap.has(agentId)\n ? (\n <button\n type=\"button\"\n onClick={() => onNavigateToAgent?.(agentId)}\n className=\"text-sky-600 hover:underline\"\n >\n {agentId}\n </button>\n )\n : <span className=\"text-red-500\">{agentId} (not found)</span>}\n </div>\n )\n : null}\n\n {toolId\n ? (\n <div className=\"flex items-center gap-2\">\n <span className=\"text-gray-400\">Tool:</span>\n {toolMap.has(toolId)\n ? (\n <button\n type=\"button\"\n onClick={() => onNavigateToTool?.(toolId)}\n className=\"text-sky-600 hover:underline\"\n >\n {toolId}\n </button>\n )\n : <span className=\"text-red-500\">{toolId} (not found)</span>}\n </div>\n )\n : null}\n\n {node.dependsOn?.length\n ? (\n <div className=\"flex items-center gap-2\">\n <span className=\"text-gray-400\">Depends on:</span>\n <span className=\"text-gray-600\">{node.dependsOn.join(\", \")}</span>\n </div>\n )\n : null}\n\n {node.children?.length\n ? (\n <div className=\"flex items-center gap-2\">\n <span className=\"text-gray-400\">Contains:</span>\n <span className=\"text-gray-600\">{node.children.join(\", \")}</span>\n </div>\n )\n : null}\n\n {node.message\n ? (\n <div className=\"flex items-start gap-2\">\n <span className=\"text-gray-400\">Message:</span>\n <span className=\"text-gray-600 italic\">\"{node.message}\"</span>\n </div>\n )\n : null}\n </div>\n </div>\n </div>\n </div>\n );\n })}\n </div>\n )\n : (\n <div className=\"p-8 text-center text-gray-400\">\n <div className=\"mb-2\">Dynamic steps</div>\n <div className=\"text-sm text-gray-500\">\n This workflow uses a function to generate steps at runtime\n </div>\n </div>\n )}\n </Card>\n\n {workflow.nodes.length > 0\n ? (\n <Card title=\"Workflow Flow\" className=\"mb-6\">\n <div className=\"p-4 font-mono text-sm bg-gray-50 overflow-x-auto\">\n <WorkflowDAG nodes={workflow.nodes} />\n </div>\n </Card>\n )\n : null}\n\n <div className=\"grid grid-cols-1 md:grid-cols-2 gap-6\">\n <Card title={`Agents Used (${workflow.agentRefs.length})`}>\n {workflow.agentRefs.length > 0\n ? (\n <div className=\"divide-y\">\n {workflow.agentRefs.map((agentId) => {\n const agent = agentMap.get(agentId);\n return (\n <div key={agentId} className=\"p-3 flex items-center justify-between\">\n <div>\n <button\n type=\"button\"\n onClick={() => onNavigateToAgent?.(agentId)}\n className=\"text-sm text-sky-600 hover:underline font-medium\"\n >\n {agentId}\n </button>\n {agent ? <div className=\"text-xs text-gray-500\">{agent.model}</div> : null}\n </div>\n {agent\n ? <span className=\"w-2 h-2 rounded-full bg-green-500\" title=\"Found\" />\n : <span className=\"w-2 h-2 rounded-full bg-red-500\" title=\"Not found\" />}\n </div>\n );\n })}\n </div>\n )\n : <div className=\"p-4 text-center text-gray-400 text-sm\">No agents referenced</div>}\n </Card>\n\n <Card title={`Tools Used (${workflow.toolRefs.length})`}>\n {workflow.toolRefs.length > 0\n ? (\n <div className=\"divide-y\">\n {workflow.toolRefs.map((toolId) => {\n const tool = toolMap.get(toolId);\n return (\n <div key={toolId} className=\"p-3 flex items-center justify-between\">\n <div>\n <button\n type=\"button\"\n onClick={() => onNavigateToTool?.(toolId)}\n className=\"text-sm text-sky-600 hover:underline font-medium\"\n >\n {toolId}\n </button>\n {tool\n ? (\n <div className=\"text-xs text-gray-500 truncate max-w-[200px]\">\n {tool.description}\n </div>\n )\n : null}\n </div>\n {tool\n ? <span className=\"w-2 h-2 rounded-full bg-green-500\" title=\"Found\" />\n : <span className=\"w-2 h-2 rounded-full bg-red-500\" title=\"Not found\" />}\n </div>\n );\n })}\n </div>\n )\n : <div className=\"p-4 text-center text-gray-400 text-sm\">No tools referenced</div>}\n </Card>\n </div>\n\n <Card title=\"Schema\" className=\"mt-6\">\n <div className=\"p-4 flex gap-4\">\n <div className=\"flex items-center gap-2\">\n <span\n className={`w-3 h-3 rounded-full ${\n workflow.hasInputSchema ? \"bg-green-500\" : \"bg-gray-300\"\n }`}\n />\n <span className=\"text-sm text-gray-600\">Input Schema</span>\n </div>\n <div className=\"flex items-center gap-2\">\n <span\n className={`w-3 h-3 rounded-full ${\n workflow.hasOutputSchema ? \"bg-green-500\" : \"bg-gray-300\"\n }`}\n />\n <span className=\"text-sm text-gray-600\">Output Schema</span>\n </div>\n </div>\n </Card>\n\n <WorkflowExecutor workflowId={workflow.id} inputSchema={workflow.inputSchemaJson} />\n </div>\n );\n}\n\nfunction WorkflowExecutor({\n workflowId,\n inputSchema,\n}: {\n workflowId: string;\n inputSchema?: Record<string, unknown>;\n}): React.ReactElement {\n const [input, setInput] = useState<string>(() => {\n const example = generateExampleFromSchema(inputSchema);\n return JSON.stringify(example, null, 2);\n });\n\n const [result, setResult] = useState<\n {\n success: boolean;\n data: string;\n duration?: number;\n runId?: string;\n status?: string;\n } | null\n >(null);\n\n const [loading, setLoading] = useState(false);\n\n useEffect(() => {\n const example = generateExampleFromSchema(inputSchema);\n setInput(JSON.stringify(example, null, 2));\n setResult(null);\n }, [workflowId, inputSchema]);\n\n async function startWorkflow(): Promise<void> {\n let parsed: unknown;\n try {\n parsed = JSON.parse(input);\n } catch (e) {\n setResult({ success: false, data: (e as Error).message });\n return;\n }\n\n setLoading(true);\n setResult(null);\n\n try {\n const res = await fetch(\"/_dev/api/start-workflow\", {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({ workflowId, input: parsed }),\n });\n\n const d = await res.json();\n\n if (d.error) {\n setResult({\n success: false,\n data: d.error + (d.hint ? `\\n\\n${d.hint}` : \"\"),\n });\n return;\n }\n\n setResult({\n success: true,\n data: JSON.stringify(d.result, null, 2),\n duration: d.duration,\n runId: d.runId,\n status: d.status,\n });\n } catch (e) {\n setResult({ success: false, data: (e as Error).message });\n } finally {\n setLoading(false);\n }\n }\n\n return (\n <Card title=\"Start Workflow\" className=\"mt-6\">\n <div className=\"p-4\">\n <label className=\"block text-xs font-medium uppercase tracking-wide text-gray-600 mb-1\">\n Input (JSON)\n </label>\n <textarea\n value={input}\n onChange={(e) => setInput(e.target.value)}\n placeholder='{\"topic\": \"AI Safety\", \"requiresApproval\": false}'\n className=\"w-full px-3 py-2 bg-gray-50 border border-gray-200 rounded text-sm font-mono focus:outline-none focus:border-sky-500 focus:bg-white min-h-[80px] resize-y\"\n />\n <ActionButton onClick={startWorkflow} loading={loading} loadingText=\"Running...\">\n Start\n </ActionButton>\n\n {result\n ? (\n <div>\n {result.runId\n ? (\n <div className=\"mt-2 text-xs text-gray-500\">\n Run ID: <code className=\"text-sky-600\">{result.runId}</code>\n {result.status\n ? (\n <span className=\"ml-2\">\n Status:{\" \"}\n <span\n className={result.status === \"completed\"\n ? \"text-green-600\"\n : \"text-yellow-600\"}\n >\n {result.status}\n </span>\n </span>\n )\n : null}\n </div>\n )\n : null}\n\n <ResultBox\n success={result.success}\n label={result.success ? \"Result\" : \"Error\"}\n duration={result.duration}\n >\n {result.data}\n </ResultBox>\n </div>\n )\n : null}\n </div>\n </Card>\n );\n}\n\nfunction WorkflowDAG({ nodes }: { nodes: NodeInfo[] }): React.ReactElement {\n if (nodes.length === 0) {\n return (\n <div className=\"text-gray-400 text-center py-4\">(dynamic - steps generated at runtime)</div>\n );\n }\n\n const dependsOnMap = new Map<string, string[]>();\n const dependentsMap = new Map<string, string[]>();\n\n for (const node of nodes) {\n dependsOnMap.set(node.id, node.dependsOn || []);\n dependentsMap.set(node.id, []);\n }\n\n for (const node of nodes) {\n for (const dep of node.dependsOn || []) {\n dependentsMap.get(dep)?.push(node.id);\n }\n }\n\n const rootNodes = nodes.filter((n) => !n.dependsOn?.length);\n\n const levels = new Map<string, number>();\n const queue = rootNodes.map((n) => n.id);\n\n for (const id of queue) levels.set(id, 0);\n\n while (queue.length > 0) {\n const current = queue.shift();\n if (!current) continue;\n\n for (const dependent of dependentsMap.get(current) || []) {\n const deps = dependsOnMap.get(dependent) || [];\n if (levels.has(dependent) || !deps.every((d) => levels.has(d))) continue;\n\n const maxDepLevel = Math.max(...deps.map((d) => levels.get(d) ?? 0));\n levels.set(dependent, maxDepLevel + 1);\n queue.push(dependent);\n }\n }\n\n const levelGroups = new Map<number, NodeInfo[]>();\n for (const node of nodes) {\n const level = levels.get(node.id) ?? 0;\n const group = levelGroups.get(level);\n if (group) group.push(node);\n else levelGroups.set(level, [node]);\n }\n\n const maxLevel = Math.max(...Array.from(levels.values()), 0);\n\n function getNodeStyle(type: string): string {\n return getNodeTypeStyle(type).node;\n }\n\n return (\n <div className=\"flex flex-col items-center gap-2\">\n {Array.from({ length: maxLevel + 1 }, (_, level) => {\n const nodesAtLevel = levelGroups.get(level) || [];\n const isParallel = nodesAtLevel.length > 1;\n\n return (\n <div key={level}>\n {level > 0\n ? (\n <div className=\"flex justify-center py-1\">\n <svg width=\"24\" height=\"20\" viewBox=\"0 0 24 20\" className=\"text-gray-400\">\n <path\n d=\"M12 0 L12 14 M6 10 L12 16 L18 10\"\n stroke=\"currentColor\"\n strokeWidth=\"2\"\n fill=\"none\"\n />\n </svg>\n </div>\n )\n : null}\n\n <div className={`flex gap-3 ${isParallel ? \"items-start\" : \"justify-center\"}`}>\n {isParallel\n ? (\n <div className=\"flex items-center text-gray-400 text-xs font-mono self-center\">\n [\n </div>\n )\n : null}\n\n {nodesAtLevel.map((node, idx) => (\n <div key={node.id} className=\"flex items-center gap-2\">\n <div\n className={`px-3 py-2 rounded-lg border text-sm font-medium ${\n getNodeStyle(\n node.type,\n )\n }`}\n >\n <div className=\"font-semibold\">{node.id}</div>\n {node.tool\n ? <div className=\"text-xs opacity-75 mt-0.5\">tool: {node.tool}</div>\n : null}\n {node.agent\n ? <div className=\"text-xs opacity-75 mt-0.5\">agent: {node.agent}</div>\n : null}\n </div>\n\n {isParallel && idx < nodesAtLevel.length - 1\n ? <div className=\"text-gray-400 text-xs font-mono\">,</div>\n : null}\n </div>\n ))}\n\n {isParallel\n ? (\n <div className=\"flex items-center text-gray-400 text-xs font-mono self-center\">\n ]\n </div>\n )\n : null}\n </div>\n </div>\n );\n })}\n </div>\n );\n}\n",
|
|
15
16
|
"dashboard/components/shared.tsx": "import type { ReactNode } from \"react\";\n\ninterface EmptyStateProps {\n message: string;\n}\n\nexport function EmptyState({ message }: EmptyStateProps): ReactNode {\n return (\n <div className=\"flex flex-col items-center justify-center py-12 text-gray-400\">\n <div className=\"w-10 h-10 border border-gray-200 rounded-lg mb-3 flex items-center justify-center bg-white\">\n <div className=\"w-3.5 h-3.5 border-2 border-gray-200 rounded\" />\n </div>\n <p className=\"text-sm\">{message}</p>\n </div>\n );\n}\n\nfunction LoadingSpinner(): ReactNode {\n return (\n <div className=\"w-4 h-4 border-2 border-gray-200 border-t-sky-500 rounded-full animate-spin\" />\n );\n}\n\ninterface LoadingStateProps {\n message?: string;\n}\n\nexport function LoadingState({ message = \"Loading...\" }: LoadingStateProps): ReactNode {\n return (\n <div className=\"p-4 flex items-center gap-2 text-sm text-gray-400\">\n <LoadingSpinner />\n {message}\n </div>\n );\n}\n\ninterface ErrorStateProps {\n error: string;\n}\n\nexport function ErrorState({ error }: ErrorStateProps): ReactNode {\n return <div className=\"p-4 text-sm text-red-600\">Error: {error}</div>;\n}\n\ninterface ResultBoxProps {\n success: boolean;\n label: string;\n duration?: number;\n children: ReactNode;\n}\n\nexport function ResultBox({ success, label, duration, children }: ResultBoxProps): ReactNode {\n const headerClassName = success ? \"bg-green-50 text-green-700\" : \"bg-red-50 text-red-700\";\n\n return (\n <div className=\"mt-4 border rounded overflow-hidden\">\n <div className={`px-3 py-2 text-xs font-medium flex items-center gap-2 ${headerClassName}`}>\n {label}\n {duration !== undefined && (\n <span className=\"ml-auto text-gray-400 font-normal\">{duration}ms</span>\n )}\n </div>\n <pre className=\"p-3 text-xs font-mono text-gray-600 overflow-auto max-h-60 whitespace-pre-wrap\">\n {children}\n </pre>\n </div>\n );\n}\n\ninterface ActionButtonProps {\n onClick: () => void;\n disabled?: boolean;\n loading?: boolean;\n loadingText?: string;\n children: ReactNode;\n}\n\nexport function ActionButton({\n onClick,\n disabled,\n loading,\n loadingText,\n children,\n}: ActionButtonProps): ReactNode {\n return (\n <button\n type=\"button\"\n onClick={onClick}\n disabled={disabled || loading}\n className=\"mt-3 px-4 py-2 bg-sky-500 text-white text-sm font-medium rounded hover:bg-sky-600 disabled:opacity-50\"\n >\n {loading ? loadingText : children}\n </button>\n );\n}\n\ninterface DetailHeaderProps {\n title: string;\n description?: string;\n}\n\nexport function DetailHeader({ title, description }: DetailHeaderProps): ReactNode {\n return (\n <div className=\"mb-6\">\n <h1 className=\"text-lg font-semibold tracking-tight\">{title}</h1>\n {description && <p className=\"text-sm text-gray-500\">{description}</p>}\n </div>\n );\n}\n\ninterface PageLayoutProps {\n title: string;\n description?: string;\n children: ReactNode;\n}\n\nexport function PageLayout({ title, description, children }: PageLayoutProps): ReactNode {\n return (\n <div className=\"h-[calc(100vh-89px)] overflow-y-auto\">\n <main className=\"p-5 bg-gray-50 max-w-5xl\">\n <DetailHeader title={title} description={description} />\n {children}\n </main>\n </div>\n );\n}\n\ninterface TwoColumnLayoutProps {\n sidebar: ReactNode;\n children: ReactNode;\n}\n\nexport function TwoColumnLayout({ sidebar, children }: TwoColumnLayoutProps): ReactNode {\n return (\n <div className=\"grid grid-cols-[240px_1fr] h-[calc(100vh-89px)]\">\n {sidebar}\n <main className=\"overflow-y-auto p-5 bg-gray-50\">{children}</main>\n </div>\n );\n}\n\nexport function formatSize(bytes: number): string {\n if (bytes < 1024) return `${bytes} B`;\n if (bytes < 1024 * 1024) return `${(bytes / 1024).toFixed(1)} KB`;\n return `${(bytes / (1024 * 1024)).toFixed(1)} MB`;\n}\n",
|
|
16
17
|
"dashboard/components/Card.tsx": "import type { ReactNode } from \"react\";\n\ninterface CardProps {\n title?: string;\n titleRight?: ReactNode;\n children: ReactNode;\n className?: string;\n}\n\nexport function Card({\n title,\n titleRight,\n children,\n className = \"\",\n}: CardProps): ReactNode {\n return (\n <div\n className={`bg-white border border-gray-200 rounded-md shadow-sm overflow-hidden ${className}`}\n >\n {title && (\n <div className=\"px-4 py-3 border-b border-gray-100 flex items-center justify-between\">\n <span className=\"text-[11px] font-semibold uppercase tracking-wide text-gray-500\">\n {title}\n </span>\n {titleRight}\n </div>\n )}\n {children}\n </div>\n );\n}\n",
|
|
17
18
|
"dashboard/components/TabNav.tsx": "import type { TabId } from \"../App.tsx\";\n\ninterface TabNavProps {\n tabs: { id: TabId; label: string }[];\n currentTab: TabId;\n onTabChange: (tab: TabId) => void;\n}\n\nexport function TabNav({ tabs, currentTab, onTabChange }: TabNavProps): JSX.Element {\n return (\n <nav className=\"bg-white border-b border-gray-200 px-5 flex gap-0.5\">\n {tabs.map((tab) => {\n const isActive = currentTab === tab.id;\n\n let className = \"px-3 py-2.5 text-xs font-medium border-b-2 -mb-px transition-colors \";\n if (isActive) {\n className += \"text-sky-500 border-sky-500\";\n } else {\n className += \"text-gray-400 border-transparent hover:text-gray-600\";\n }\n\n return (\n <button\n key={tab.id}\n type=\"button\"\n className={className}\n onClick={() => onTabChange(tab.id)}\n >\n {tab.label}\n </button>\n );\n })}\n </nav>\n );\n}\n",
|
|
@@ -23,6 +24,7 @@ export default {
|
|
|
23
24
|
"dashboard/components/FilesTab.tsx": "import { useEffect, useMemo, useState } from \"react\";\nimport type { FileItem } from \"../App.tsx\";\nimport { Card } from \"./Card.tsx\";\nimport { Sidebar } from \"./Sidebar.tsx\";\nimport { DetailHeader, ErrorState, formatSize, LoadingState, TwoColumnLayout } from \"./shared.tsx\";\n\nexport function FilesTab(): React.ReactElement {\n const [currentPath, setCurrentPath] = useState(\"\");\n const [files, setFiles] = useState<FileItem[]>([]);\n const [selectedFile, setSelectedFile] = useState<string | null>(null);\n const [search, setSearch] = useState(\"\");\n const [loading, setLoading] = useState(true);\n\n useEffect(() => {\n async function loadFiles(path: string): Promise<void> {\n setLoading(true);\n try {\n const res = await fetch(`/_dev/api/files?path=${encodeURIComponent(path)}`);\n const data = await res.json();\n setFiles(data.files ?? []);\n } catch (e) {\n console.error(\"Failed to load files:\", e);\n setFiles([]);\n } finally {\n setLoading(false);\n }\n }\n\n void loadFiles(currentPath);\n }, [currentPath]);\n\n const filteredFiles = useMemo((): FileItem[] => {\n if (!search) return files;\n const q = search.toLowerCase();\n return files.filter((f) => f.name.toLowerCase().includes(q));\n }, [files, search]);\n\n function handleSelect(id: string): void {\n const file = files.find((f) => f.path === id);\n if (!file) return;\n\n if (file.type !== \"directory\") {\n setSelectedFile(file.path);\n return;\n }\n\n setCurrentPath(file.path);\n setSelectedFile(null);\n setSearch(\"\");\n }\n\n function handleBack(): void {\n setCurrentPath(currentPath.split(\"/\").slice(0, -1).join(\"/\"));\n setSelectedFile(null);\n }\n\n const sidebar = (\n <Sidebar\n search={search}\n onSearchChange={setSearch}\n items={filteredFiles.map((f) => ({\n id: f.path,\n label: f.type === \"directory\" ? `${f.name}/` : f.name,\n bold: f.type === \"directory\",\n }))}\n selectedId={selectedFile}\n onSelect={handleSelect}\n emptyMessage={loading ? \"Loading...\" : \"No files found\"}\n onBack={currentPath && !search ? handleBack : undefined}\n />\n );\n\n return (\n <TwoColumnLayout sidebar={sidebar}>\n {selectedFile\n ? <FileDetail path={selectedFile} />\n : <DirectoryInfo path={currentPath} fileCount={files.length} />}\n </TwoColumnLayout>\n );\n}\n\nfunction DirectoryInfo(\n { path, fileCount }: { path: string; fileCount: number },\n): React.ReactElement {\n return (\n <div>\n <DetailHeader title={path || \"Project Root\"} description={`${fileCount} items`} />\n <Card>\n <div className=\"p-4 text-sm text-gray-400\">Select a file to view its contents</div>\n </Card>\n </div>\n );\n}\n\ninterface FileContent {\n content?: string;\n lines?: number;\n size?: number;\n isBinary?: boolean;\n message?: string;\n error?: string;\n}\n\nfunction FileDetail({ path }: { path: string }): React.ReactElement {\n const [content, setContent] = useState<FileContent | null>(null);\n const [loading, setLoading] = useState(true);\n\n const filename = useMemo((): string => path.split(\"/\").pop() ?? \"\", [path]);\n const ext = useMemo((): string => path.split(\".\").pop()?.toLowerCase() ?? \"\", [path]);\n\n useEffect(() => {\n async function loadContent(): Promise<void> {\n setLoading(true);\n try {\n const res = await fetch(`/_dev/api/file-content?path=${encodeURIComponent(path)}`);\n const data = await res.json();\n setContent(data);\n } catch (e: unknown) {\n const message = e instanceof Error ? e.message : String(e);\n setContent({ error: message });\n } finally {\n setLoading(false);\n }\n }\n loadContent();\n }, [path]);\n\n const title = !loading && content?.content !== undefined ? \"Contents\" : undefined;\n const titleRight = content?.lines\n ? <span className=\"text-[11px] text-gray-400 font-normal\">{content.lines} lines</span>\n : undefined;\n\n let body: React.ReactNode = null;\n if (loading) {\n body = <LoadingState message=\"Loading file contents...\" />;\n } else if (content?.error) {\n body = <ErrorState error={content.error} />;\n } else if (content?.isBinary) {\n body = <div className=\"p-4 text-sm text-gray-400\">{content.message}</div>;\n } else if (content?.content !== undefined) {\n body = (\n <pre className=\"p-3 text-xs font-mono text-gray-600 overflow-auto max-h-[500px] whitespace-pre-wrap bg-gray-50\">\n {content.content}\n </pre>\n );\n }\n\n return (\n <div>\n <DetailHeader title={filename} description={path} />\n\n <Card title=\"File Info\" className=\"mb-4\">\n <table className=\"w-full text-sm\">\n <tbody>\n <tr className=\"border-b\">\n <td className=\"px-3 py-2.5 w-24 font-medium text-gray-600\">Path</td>\n <td className=\"px-3 py-2.5 text-gray-900\">{path}</td>\n </tr>\n <tr className=\"border-b\">\n <td className=\"px-3 py-2.5 font-medium text-gray-600\">Extension</td>\n <td className=\"px-3 py-2.5 text-gray-900\">{ext}</td>\n </tr>\n {content?.lines\n ? (\n <tr className=\"border-b\">\n <td className=\"px-3 py-2.5 font-medium text-gray-600\">Lines</td>\n <td className=\"px-3 py-2.5 text-gray-900\">{content.lines}</td>\n </tr>\n )\n : null}\n {content?.size\n ? (\n <tr>\n <td className=\"px-3 py-2.5 font-medium text-gray-600\">Size</td>\n <td className=\"px-3 py-2.5 text-gray-900\">{formatSize(content.size)}</td>\n </tr>\n )\n : null}\n </tbody>\n </table>\n </Card>\n\n <Card title={title} titleRight={titleRight}>\n {body}\n </Card>\n </div>\n );\n}\n",
|
|
24
25
|
"dashboard/components/APITab.tsx": "export function APITab(): JSX.Element {\n return (\n <div className=\"h-[calc(100vh-89px)] overflow-y-auto\">\n <main className=\"bg-gray-50 p-5\">\n <div className=\"mb-6\">\n <h1 className=\"text-lg font-semibold tracking-tight\">API Documentation</h1>\n <p className=\"text-sm text-gray-500\">\n Interactive API docs powered by Scalar.{\" \"}\n <a\n href=\"/_docs\"\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n className=\"text-sky-500 hover:text-sky-600\"\n >\n Open in new tab\n </a>\n </p>\n </div>\n\n <div className=\"overflow-hidden rounded-md border border-gray-200 bg-white shadow-sm\">\n <iframe\n src=\"/_docs\"\n className=\"w-full border-0\"\n style={{ height: \"calc(100vh - 180px)\" }}\n />\n </div>\n </main>\n </div>\n );\n}\n",
|
|
25
26
|
"dashboard/components/AgentTab.tsx": "import { useEffect, useState } from \"react\";\nimport type { Agent, Prompt, Resource, Tool } from \"../App.tsx\";\nimport { MCPTab } from \"./MCPTab.tsx\";\nimport { AgentsTab } from \"./AgentsTab.tsx\";\nimport { WorkflowsTab } from \"./WorkflowsTab.tsx\";\nimport { Card } from \"./Card.tsx\";\nimport { ErrorState, LoadingState, PageLayout } from \"./shared.tsx\";\n\ntype SubTab = \"mcp\" | \"agents\" | \"workflows\" | \"providers\";\n\ninterface Provider {\n name: string;\n configured: boolean;\n}\n\ninterface NodeInfo {\n id: string;\n type: string;\n agent?: string;\n tool?: string;\n dependsOn?: string[];\n children?: string[];\n message?: string;\n}\n\ninterface WorkflowMetadata {\n id: string;\n description?: string;\n version?: string;\n timeout?: string | number;\n nodeCount: number;\n nodeTypes: string[];\n nodes: NodeInfo[];\n agentRefs: string[];\n toolRefs: string[];\n hasInputSchema: boolean;\n hasOutputSchema: boolean;\n inputSchemaJson?: Record<string, unknown>;\n registeredAt: string;\n}\n\ninterface AgentTabProps {\n tools: Tool[];\n resources: Resource[];\n prompts: Prompt[];\n agents: Agent[];\n}\n\nexport function AgentTab({\n tools,\n resources,\n prompts,\n agents,\n}: AgentTabProps): React.ReactElement {\n const [subTab, setSubTab] = useState<SubTab>(\"mcp\");\n\n const [providers, setProviders] = useState<Provider[]>([]);\n const [providersLoading, setProvidersLoading] = useState(true);\n const [providersError, setProvidersError] = useState<string | null>(null);\n\n const [workflows, setWorkflows] = useState<WorkflowMetadata[]>([]);\n const [workflowsLoading, setWorkflowsLoading] = useState(true);\n const [workflowsError, setWorkflowsError] = useState<string | null>(null);\n\n useEffect(() => {\n async function loadProviders(): Promise<void> {\n try {\n const res = await fetch(\"/_dev/api/infrastructure\");\n const d = await res.json();\n setProviders(d.providers ?? []);\n setProvidersError(null);\n } catch (e: unknown) {\n setProvidersError(e instanceof Error ? e.message : String(e));\n } finally {\n setProvidersLoading(false);\n }\n }\n\n async function loadWorkflows(): Promise<void> {\n try {\n const res = await fetch(\"/_dev/api/workflows\");\n const d = await res.json();\n setWorkflows(d.workflows ?? []);\n setWorkflowsError(null);\n } catch (e: unknown) {\n setWorkflowsError(e instanceof Error ? e.message : String(e));\n } finally {\n setWorkflowsLoading(false);\n }\n }\n\n loadProviders();\n loadWorkflows();\n }, []);\n\n function navigateToMCP(mcpSubTab: \"tools\" | \"resources\" | \"prompts\", itemId: string): void {\n setSubTab(\"mcp\");\n globalThis.dispatchEvent(\n new CustomEvent(\"mcp-navigate\", { detail: { subTab: mcpSubTab, itemId } }),\n );\n }\n\n const mcpCount = tools.length + resources.length + prompts.length;\n const configuredProvidersCount = providers.filter((p) => p.configured).length;\n\n return (\n <div className=\"min-h-screen\">\n <div className=\"bg-white border-b\">\n <div className=\"px-6 py-4\">\n <div className=\"mb-3\">\n <h1 className=\"text-xl font-semibold text-gray-900\">Agent</h1>\n <p className=\"text-sm text-gray-500\">MCP, agents, workflows, and providers</p>\n </div>\n <div className=\"flex gap-1 border border-gray-200 rounded-lg p-1 bg-gray-50 w-fit\">\n <TabButton\n active={subTab === \"mcp\"}\n onClick={() => setSubTab(\"mcp\")}\n label={`MCP (${mcpCount})`}\n />\n <TabButton\n active={subTab === \"agents\"}\n onClick={() => setSubTab(\"agents\")}\n label={`Agents (${agents.length})`}\n />\n <TabButton\n active={subTab === \"workflows\"}\n onClick={() => setSubTab(\"workflows\")}\n label={`Workflows (${workflows.length})`}\n />\n <TabButton\n active={subTab === \"providers\"}\n onClick={() => setSubTab(\"providers\")}\n label={`Providers (${configuredProvidersCount})`}\n />\n </div>\n </div>\n </div>\n\n {subTab === \"mcp\" && <MCPTab tools={tools} resources={resources} prompts={prompts} />}\n\n {subTab === \"agents\" && (\n <AgentsTab agents={agents} tools={tools} onNavigateToMCP={navigateToMCP} />\n )}\n\n {subTab === \"workflows\" && (\n <WorkflowsSection\n loading={workflowsLoading}\n error={workflowsError}\n workflows={workflows}\n agents={agents}\n tools={tools}\n onNavigateToTool={(toolId) => navigateToMCP(\"tools\", toolId)}\n onNavigateToAgent={() => {\n setSubTab(\"agents\");\n // AgentsTab will need to handle this\n }}\n />\n )}\n\n {subTab === \"providers\" && (\n <ProvidersSection providers={providers} loading={providersLoading} error={providersError} />\n )}\n </div>\n );\n}\n\nfunction TabButton({\n active,\n onClick,\n label,\n}: {\n active: boolean;\n onClick: () => void;\n label: string;\n}): React.ReactElement {\n const className = `px-3 py-1.5 text-sm font-medium rounded-md transition-colors ${\n active ? \"bg-white text-sky-600 shadow-sm\" : \"text-gray-500 hover:text-gray-700\"\n }`;\n\n return (\n <button type=\"button\" onClick={onClick} className={className}>\n {label}\n </button>\n );\n}\n\nfunction WorkflowsSection({\n loading,\n error,\n workflows,\n agents,\n tools,\n onNavigateToAgent,\n onNavigateToTool,\n}: {\n loading: boolean;\n error: string | null;\n workflows: WorkflowMetadata[];\n agents: Agent[];\n tools: Tool[];\n onNavigateToAgent: (agentId: string) => void;\n onNavigateToTool: (toolId: string) => void;\n}): React.ReactElement {\n if (loading) {\n return (\n <PageLayout title=\"\" description=\"\">\n <Card>\n <LoadingState message=\"Loading workflows...\" />\n </Card>\n </PageLayout>\n );\n }\n\n if (error) {\n return (\n <PageLayout title=\"\" description=\"\">\n <Card>\n <ErrorState error={error} />\n </Card>\n </PageLayout>\n );\n }\n\n return (\n <WorkflowsTab\n workflows={workflows}\n agents={agents}\n tools={tools}\n onNavigateToAgent={onNavigateToAgent}\n onNavigateToTool={onNavigateToTool}\n />\n );\n}\n\nfunction ProvidersSection({\n providers,\n loading,\n error,\n}: {\n providers: Provider[];\n loading: boolean;\n error: string | null;\n}): React.ReactElement {\n if (loading) {\n return (\n <PageLayout title=\"\" description=\"\">\n <Card>\n <LoadingState message=\"Loading providers...\" />\n </Card>\n </PageLayout>\n );\n }\n\n if (error) {\n return (\n <PageLayout title=\"\" description=\"\">\n <Card>\n <ErrorState error={error} />\n </Card>\n </PageLayout>\n );\n }\n\n const configured: Provider[] = [];\n const notConfigured: Provider[] = [];\n\n for (const provider of providers) {\n if (provider.configured) {\n configured.push(provider);\n } else {\n notConfigured.push(provider);\n }\n }\n\n return (\n <div className=\"max-w-7xl mx-auto px-6 py-6\">\n <div className=\"grid grid-cols-1 md:grid-cols-3 gap-4 mb-6\">\n <Card className=\"p-4\">\n <div className=\"text-2xl font-bold text-gray-900\">{configured.length}</div>\n <div className=\"text-sm text-gray-500\">Configured</div>\n </Card>\n <Card className=\"p-4\">\n <div className=\"text-2xl font-bold text-gray-400\">{notConfigured.length}</div>\n <div className=\"text-sm text-gray-500\">Not Configured</div>\n </Card>\n <Card className=\"p-4\">\n <div className=\"text-2xl font-bold text-gray-900\">{providers.length}</div>\n <div className=\"text-sm text-gray-500\">Total Available</div>\n </Card>\n </div>\n\n <Card title=\"AGENT PROVIDERS\">\n <table className=\"w-full text-sm\">\n <thead>\n <tr className=\"bg-gray-50 border-b\">\n <th className=\"text-left px-3 py-2 text-[10px] font-semibold uppercase tracking-wide text-gray-500\">\n Provider\n </th>\n <th className=\"text-left px-3 py-2 text-[10px] font-semibold uppercase tracking-wide text-gray-500\">\n Status\n </th>\n <th className=\"text-left px-3 py-2 text-[10px] font-semibold uppercase tracking-wide text-gray-500\">\n API Key\n </th>\n </tr>\n </thead>\n <tbody>\n {providers.map((provider) => {\n const status = provider.configured\n ? {\n className: \"inline-flex items-center gap-1.5 text-green-600\",\n dotClassName: \"w-2 h-2 rounded-full bg-green-500\",\n label: \"Ready\",\n apiKey: <span className=\"text-green-600\">(set)</span>,\n }\n : {\n className: \"inline-flex items-center gap-1.5 text-gray-400\",\n dotClassName: \"w-2 h-2 rounded-full bg-gray-300\",\n label: \"Not configured\",\n apiKey: <span className=\"text-gray-400\">(not set)</span>,\n };\n\n return (\n <tr key={provider.name} className=\"border-b last:border-0\">\n <td className=\"px-3 py-3\">\n <code className=\"text-sm text-sky-600 font-medium\">{provider.name}</code>\n </td>\n <td className=\"px-3 py-3\">\n <span className={status.className}>\n <span className={status.dotClassName} />\n {status.label}\n </span>\n </td>\n <td className=\"px-3 py-3 text-gray-500 text-sm\">{status.apiKey}</td>\n </tr>\n );\n })}\n </tbody>\n </table>\n </Card>\n </div>\n );\n}\n",
|
|
27
|
+
"dashboard/components/WorkflowsTab.helpers.test.ts": "import { assertEquals } from \"#veryfront/testing/assert.ts\";\nimport { describe, it } from \"#veryfront/testing/bdd.ts\";\nimport {\n filterItemsByIdSearch,\n generateExampleFromSchema,\n getNodeTypeStyle,\n} from \"./WorkflowsTab.helpers.ts\";\n\ndescribe(\"WorkflowsTab helpers\", () => {\n it(\"returns configured node styles and falls back for unknown types\", () => {\n assertEquals(getNodeTypeStyle(\"step\"), {\n badge: \"bg-blue-50 text-blue-600\",\n node: \"bg-blue-50 border-blue-200 text-blue-700\",\n });\n assertEquals(getNodeTypeStyle(\"unknown\"), {\n badge: \"bg-gray-100 text-gray-600\",\n node: \"bg-gray-50 border-gray-200 text-gray-700\",\n });\n });\n\n it(\"filters items by id using case-insensitive search\", () => {\n const items = [{ id: \"Alpha\" }, { id: \"beta\" }, { id: \"gamma\" }];\n assertEquals(filterItemsByIdSearch(items, \"A\"), [{ id: \"Alpha\" }, { id: \"beta\" }, {\n id: \"gamma\",\n }]);\n assertEquals(filterItemsByIdSearch(items, \"BET\"), [{ id: \"beta\" }]);\n });\n\n it(\"generates examples from nested schemas\", () => {\n assertEquals(\n generateExampleFromSchema({\n type: \"object\",\n properties: {\n email: { type: \"string\" },\n url: { type: \"string\" },\n count: { type: \"integer\" },\n enabled: { type: \"boolean\" },\n mode: { enum: [\"fast\", \"slow\"] },\n nested: {\n type: \"object\",\n properties: {\n name: { type: \"string\", default: \"preset\" },\n },\n },\n tags: { type: \"array\" },\n },\n }),\n {\n email: \"user@example.com\",\n url: \"https://example.com/data\",\n count: 1,\n enabled: true,\n mode: \"fast\",\n nested: { name: \"preset\" },\n tags: [],\n },\n );\n });\n});\n",
|
|
26
28
|
"dashboard/components/Header.tsx": "export function Header(): JSX.Element {\n return (\n <header className=\"bg-white border-b border-gray-200 px-5 h-12 flex items-center sticky top-0 z-50\">\n <div className=\"flex items-center gap-2\">\n <div className=\"w-6 h-6 bg-sky-500 rounded flex items-center justify-center text-white font-bold text-xs\">\n V\n </div>\n <span className=\"font-semibold text-sm tracking-tight\">Dev</span>\n </div>\n </header>\n );\n}\n",
|
|
27
29
|
"dashboard/index.tsx": "import { App } from \"./App.tsx\";\nimport { mountReactApp } from \"../shared/mount-react-app.tsx\";\n\nmountReactApp(<App />);\n"
|
|
28
30
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"project-discovery.d.ts","sourceRoot":"","sources":["../../../../../../src/src/server/handlers/request/api/project-discovery.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"project-discovery.d.ts","sourceRoot":"","sources":["../../../../../../src/src/server/handlers/request/api/project-discovery.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAC;AAuErD;;;;;GAKG;AACH,wBAAsB,sBAAsB,CAAC,GAAG,EAAE,cAAc,GAAG,OAAO,CAAC,IAAI,CAAC,CAmE/E"}
|
|
@@ -12,16 +12,19 @@ const logger = serverLogger.component("api-wrapper");
|
|
|
12
12
|
* allows retry on failure (the key is deleted if discovery rejects).
|
|
13
13
|
*/
|
|
14
14
|
const discoveredProjects = new Map();
|
|
15
|
+
function isDiscoveryEnabled(discovery) {
|
|
16
|
+
return discovery?.enabled ?? true;
|
|
17
|
+
}
|
|
15
18
|
function buildDiscoveryConfig(ctx) {
|
|
16
19
|
const discoveryConfig = ctx.config?.ai;
|
|
17
|
-
const
|
|
20
|
+
const toolDiscovery = discoveryConfig?.tools?.discovery;
|
|
21
|
+
const agentDiscovery = discoveryConfig?.agents?.discovery;
|
|
22
|
+
const skillDiscovery = discoveryConfig?.skills?.discovery;
|
|
18
23
|
return {
|
|
19
24
|
baseDir: ctx.projectDir,
|
|
20
|
-
toolDirs:
|
|
21
|
-
agentDirs:
|
|
22
|
-
skillDirs:
|
|
23
|
-
? (discoveryConfig?.skills?.discovery?.paths ?? ["skills"])
|
|
24
|
-
: [],
|
|
25
|
+
toolDirs: isDiscoveryEnabled(toolDiscovery) ? (toolDiscovery?.paths ?? ["tools"]) : [],
|
|
26
|
+
agentDirs: isDiscoveryEnabled(agentDiscovery) ? (agentDiscovery?.paths ?? ["agents"]) : [],
|
|
27
|
+
skillDirs: isDiscoveryEnabled(skillDiscovery) ? (skillDiscovery?.paths ?? ["skills"]) : [],
|
|
25
28
|
resourceDirs: ["resources"],
|
|
26
29
|
promptDirs: ["prompts"],
|
|
27
30
|
workflowDirs: ["workflows"],
|
|
@@ -76,7 +79,10 @@ export async function ensureProjectDiscovery(ctx) {
|
|
|
76
79
|
clearTranspileCache();
|
|
77
80
|
agentRegistry.clear();
|
|
78
81
|
toolRegistry.clear();
|
|
79
|
-
const
|
|
82
|
+
const discoveryOptions = buildDiscoveryConfig(ctx);
|
|
83
|
+
const result = await discoverAll(discoveryOptions);
|
|
84
|
+
const shouldWarnOnEmptyAiDiscovery = discoveryOptions.toolDirs.length > 0 ||
|
|
85
|
+
discoveryOptions.agentDirs.length > 0;
|
|
80
86
|
const logData = {
|
|
81
87
|
projectSlug: ctx.projectSlug,
|
|
82
88
|
releaseId: ctx.releaseId,
|
|
@@ -84,7 +90,7 @@ export async function ensureProjectDiscovery(ctx) {
|
|
|
84
90
|
tools: result.tools.size,
|
|
85
91
|
errors: result.errors.length,
|
|
86
92
|
};
|
|
87
|
-
if (result.agents.size === 0 && result.tools.size === 0) {
|
|
93
|
+
if (result.agents.size === 0 && result.tools.size === 0 && shouldWarnOnEmptyAiDiscovery) {
|
|
88
94
|
logger.warn("Primitive discovery found 0 agents and 0 tools", {
|
|
89
95
|
...logData,
|
|
90
96
|
errorMessages: result.errors.map((e) => e.error.message).slice(0, 5),
|
|
@@ -285,7 +285,7 @@ if (globalThis[Symbol.for("import-meta-ponyfill-esmodule")](import.meta).main) {
|
|
|
285
285
|
// Phase 3: Stop accepting new connections and clean up
|
|
286
286
|
stopMemoryMonitoring();
|
|
287
287
|
requestTracker.shutdown();
|
|
288
|
-
bootstrap.dispose?.();
|
|
288
|
+
await bootstrap.dispose?.();
|
|
289
289
|
shutdownController.abort();
|
|
290
290
|
await server.stop();
|
|
291
291
|
await shutdownOTLP();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"rsc-bundles.generated.d.ts","sourceRoot":"","sources":["../../../../../../src/src/server/services/rsc/endpoints/rsc-bundles.generated.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,eAAO,MAAM,kBAAkB,EAAE,MACmorB,CAAC;AAErqrB,eAAO,MAAM,iBAAiB,EAAE,
|
|
1
|
+
{"version":3,"file":"rsc-bundles.generated.d.ts","sourceRoot":"","sources":["../../../../../../src/src/server/services/rsc/endpoints/rsc-bundles.generated.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,eAAO,MAAM,kBAAkB,EAAE,MACmorB,CAAC;AAErqrB,eAAO,MAAM,iBAAiB,EAAE,MACiqiB,CAAC"}
|
|
@@ -5,5 +5,5 @@
|
|
|
5
5
|
* Do not edit manually — run `deno task generate` to regenerate.
|
|
6
6
|
* @module
|
|
7
7
|
*/
|
|
8
|
-
export const CLIENT_BOOT_BUNDLE = 'var B=Object.defineProperty;var Y=(t,e,o)=>e in t?B(t,e,{enumerable:!0,configurable:!0,writable:!0,value:o}):t[e]=o;var d=(t,e,o)=>Y(t,typeof e!="symbol"?e+"":e,o);var W="3.2.3";function q(t,e,o,n){let s=[];if(n?.external?.length&&s.push(`external=${n.external.join(",")}`),s.push(`target=${n?.target??"es2022"}`),n?.deps){let g=Object.entries(n.deps).map(([a,h])=>`${a}@${h}`).join(",");s.push(`deps=${g}`)}let c=e?`@${e}`:"",l=o??"",u=s.length?`?${s.join("&")}`:"";return`https://esm.sh/${t}${c}${l}${u}`}function R(t,e,o,n=!1){return q(t,e,o,{external:n?["react"]:void 0,deps:{csstype:W}})}var X="19.1.1",f=X;function N(t=f){return{react:R("react",t),"react-dom":R("react-dom",t,void 0,!0),"react-dom/client":R("react-dom",t,"/client",!0),"react-dom/server":R("react-dom",t,"/server",!0),"react/jsx-runtime":R("react",t,"/jsx-runtime",!0),"react/jsx-dev-runtime":R("react",t,"/jsx-dev-runtime",!0)}}function A(t=f){return N(t).react}function D(t=f){return N(t)["react-dom/client"]}function J(t){return t.replaceAll("+","-").replaceAll("/","_").replaceAll("=","")}function v(t){return J(btoa(t))}var Nt=Object.freeze({react:"","react-dom":"","react-dom/client":"","react-dom/server":"","react/jsx-runtime":"","react/jsx-dev-runtime":""});function I(t,e){if(!e)return!1;if(Object.prototype.hasOwnProperty.call(e,t))return!0;for(let o of Object.keys(e))if(o.endsWith("/")&&t.startsWith(o))return!0;return!1}function K(t){try{return JSON.parse(t)?.imports??{}}catch{return{}}}function L(t=document){let e=t.querySelector(\'script[type="importmap"]\');return e?.textContent?K(e.textContent):{}}var i="/_veryfront",S={RSC:`${i}/rsc/`,FS:`${i}/fs/`,MODULES:`${i}/modules/`,PAGES:`${i}/pages/`,DATA:`${i}/data/`,LIB:`${i}/lib/`,CHUNKS:`${i}/chunks/`,CLIENT:`${i}/client/`},b={HMR_RUNTIME:`${i}/hmr-runtime.js`,HMR:`${i}/hmr.js`,HYDRATE:`${i}/hydrate.js`,ERROR_OVERLAY:`${i}/error-overlay.js`,DEV_LOADER:`${i}/dev-loader.js`,CLIENT_LOG:`${i}/log`,CLIENT_JS:`${i}/client.js`,ROUTER_JS:`${i}/router.js`,PREFETCH_JS:`${i}/prefetch.js`,MANIFEST_JSON:`${i}/manifest.json`,APP_JS:`${i}/app.js`,RSC_CLIENT:`${i}/rsc/client.js`,RSC_MANIFEST:`${i}/rsc/manifest`,RSC_STREAM:`${i}/rsc/stream`,RSC_PAYLOAD:`${i}/rsc/payload`,RSC_RENDER:`${i}/rsc/render`,RSC_PAGE:`${i}/rsc/page`,RSC_MODULE:`${i}/rsc/module`,RSC_DOM:`${i}/rsc/dom.js`,RSC_HYDRATOR:`${i}/rsc/hydrator.js`,RSC_HYDRATE_CLIENT:`${i}/rsc/hydrate-client.js`,LIB_CHAT_REACT:`${i}/lib/chat/react.js`,LIB_CHAT_COMPONENTS:`${i}/lib/chat/components.js`,LIB_CHAT_PRIMITIVES:`${i}/lib/chat/primitives.js`};var Q={ROOT:".veryfront",CACHE:".veryfront/cache",KV:".veryfront/kv",LOGS:".veryfront/logs",TMP:".veryfront/tmp"},bt=Q.CACHE;var Mt={HMR_RUNTIME:b.HMR_RUNTIME,ERROR_OVERLAY:b.ERROR_OVERLAY};var m=S.RSC,M=S.FS,U="veryfront-hydration-data",y="rsc-root";function P(t=document){try{let e=t.getElementById(U);return e?JSON.parse(e.textContent||"{}"):null}catch(e){return console.debug?.("[RSC] hydration data parse failed",e),null}}function V(t){return t?.clientModuleStrategy?t.clientModuleStrategy:t?.dev?"fs":"rsc-module"}function tt(t){return`${M}${v(t)}.js`}function et(t,e){let o=e?`&v=${encodeURIComponent(e)}`:"";return`${m}module?rel=${encodeURIComponent(t)}${o}`}function w(t){if(t.strategy==="fs"){let e=t.absPath??t.rel;return e?tt(e):null}return et(t.rel,t.version)}function F(t=document,e=f){let o=L(t);return{react:I("react",o)?"react":A(e),reactDomClient:I("react-dom/client",o)?"react-dom/client":D(e)}}function r(t){return{...t,create(e){return new C(e?.message||e?.detail||t.title,{slug:t.slug,category:t.category,status:e?.status??t.status,title:t.title,suggestion:t.suggestion,detail:e?.detail,cause:e?.cause,instance:e?.instance,context:e?.context})}}}var C=class extends Error{constructor(o,n){super(o);d(this,"slug");d(this,"category");d(this,"status");d(this,"title");d(this,"suggestion");d(this,"detail");d(this,"cause");d(this,"instance");d(this,"context");this.name="VeryfrontError",this.slug=n.slug,this.category=n.category,this.status=n.status,this.title=n.title,this.suggestion=n.suggestion,this.detail=n.detail,this.cause=n.cause,this.instance=n.instance,this.context=n.context}toRFC9457(){return{type:`https://veryfront.com/docs/errors/${this.slug}`,title:this.title,status:this.status,detail:this.detail,instance:this.instance,category:this.category,suggestion:this.suggestion,cause:typeof this.cause=="string"?this.cause:void 0}}getDocsUrl(){return`https://veryfront.com/docs/errors/${this.slug}`}};var qt=r({slug:"config-not-found",category:"CONFIG",status:404,title:"Configuration file not found",suggestion:"Run \'vf init\' to create a configuration file"}),zt=r({slug:"config-invalid",category:"CONFIG",status:400,title:"Invalid configuration format",suggestion:"Check your veryfront.config.ts for syntax errors"}),Xt=r({slug:"config-parse-error",category:"CONFIG",status:400,title:"Failed to parse configuration",suggestion:"Ensure your configuration file is valid TypeScript/JSON"}),Jt=r({slug:"config-validation-error",category:"CONFIG",status:422,title:"Configuration validation failed",suggestion:"Check the configuration against the schema requirements"}),Kt=r({slug:"config-type-error",category:"CONFIG",status:400,title:"Configuration type mismatch",suggestion:"Ensure configuration values match expected types"}),Zt=r({slug:"import-map-invalid",category:"CONFIG",status:400,title:"Invalid import map configuration",suggestion:"Check your import map syntax and paths"}),Qt=r({slug:"cors-config-invalid",category:"CONFIG",status:400,title:"Invalid CORS configuration",suggestion:"Review CORS settings in your configuration"}),te=r({slug:"config-validation-failed",category:"CONFIG",status:400,title:"Configuration validation failed",suggestion:"Check configuration values against requirements"}),ee=r({slug:"build-failed",category:"BUILD",status:500,title:"Build process failed",suggestion:"Check the build output for specific errors"}),re=r({slug:"bundle-error",category:"BUILD",status:500,title:"Bundle generation failed",suggestion:"Review bundler output for details"}),oe=r({slug:"typescript-error",category:"BUILD",status:500,title:"TypeScript compilation error",suggestion:"Fix TypeScript errors shown in the output"}),ne=r({slug:"mdx-compile-error",category:"BUILD",status:500,title:"MDX compilation failed",suggestion:"Check your MDX file syntax"}),se=r({slug:"asset-optimization-error",category:"BUILD",status:500,title:"Asset optimization failed",suggestion:"Check asset file formats and paths"}),ie=r({slug:"ssg-generation-error",category:"BUILD",status:500,title:"Static site generation failed",suggestion:"Review SSG configuration and data fetching"}),ae=r({slug:"sourcemap-error",category:"BUILD",status:500,title:"Source map generation failed",suggestion:"Check source map configuration"}),ce=r({slug:"compilation-error",category:"BUILD",status:500,title:"Compilation failed",suggestion:"Review compiler output for specific errors"}),ue=r({slug:"hydration-mismatch",category:"RUNTIME",status:500,title:"Client/server hydration mismatch",suggestion:"Ensure server and client render the same content"}),le=r({slug:"render-error",category:"RUNTIME",status:500,title:"Component render failed",suggestion:"Check component for runtime errors"}),ge=r({slug:"component-error",category:"RUNTIME",status:500,title:"Component execution error",suggestion:"Review component logic and props"}),de=r({slug:"layout-not-found",category:"RUNTIME",status:404,title:"Layout component not found",suggestion:"Ensure layout file exists at the expected path"}),pe=r({slug:"page-not-found",category:"RUNTIME",status:404,title:"Page component not found",suggestion:"Check that the page file exists in the routes directory"}),Re=r({slug:"api-error",category:"RUNTIME",status:500,title:"API route handler error",suggestion:"Review API route handler for errors"}),me=r({slug:"middleware-error",category:"RUNTIME",status:500,title:"Middleware execution error",suggestion:"Check middleware function for errors"}),Ee=r({slug:"route-conflict",category:"ROUTE",status:409,title:"Conflicting route definitions",suggestion:"Rename or reorganize conflicting route files"}),fe=r({slug:"invalid-route-file",category:"ROUTE",status:400,title:"Invalid route file structure",suggestion:"Ensure route file exports required functions"}),ye=r({slug:"route-handler-invalid",category:"ROUTE",status:400,title:"Invalid route handler export",suggestion:"Export a valid handler function from the route file"}),_e=r({slug:"dynamic-route-error",category:"ROUTE",status:500,title:"Dynamic route parsing failed",suggestion:"Check dynamic route segment syntax"}),Oe=r({slug:"route-params-error",category:"ROUTE",status:400,title:"Route parameters invalid",suggestion:"Validate route parameter values"}),xe=r({slug:"api-route-error",category:"ROUTE",status:500,title:"API route definition error",suggestion:"Review API route configuration"}),he=r({slug:"module-not-found",category:"MODULE",status:404,title:"Module could not be resolved",suggestion:"Check the import path and ensure the module is installed"}),Ie=r({slug:"import-resolution-error",category:"MODULE",status:500,title:"Import path resolution failed",suggestion:"Verify import paths and module configuration"}),Se=r({slug:"circular-dependency",category:"MODULE",status:500,title:"Circular dependency detected",suggestion:"Refactor imports to break the circular dependency"}),Ce=r({slug:"invalid-import",category:"MODULE",status:400,title:"Invalid import statement",suggestion:"Fix import syntax or path"}),Te=r({slug:"dependency-missing",category:"MODULE",status:404,title:"Required dependency not installed",suggestion:"Install the missing dependency with your package manager"}),Ne=r({slug:"version-mismatch",category:"MODULE",status:409,title:"Dependency version mismatch",suggestion:"Update dependencies to compatible versions"}),Ae=r({slug:"port-in-use",category:"SERVER",status:409,title:"Server port already in use",suggestion:"Use a different port or stop the process using this port"}),De=r({slug:"server-start-error",category:"SERVER",status:500,title:"Server failed to start",suggestion:"Check server configuration and port availability"}),ve=r({slug:"cache-error",category:"SERVER",status:500,title:"Cache operation failed",suggestion:"Clear the cache and try again"}),Le=r({slug:"file-watch-error",category:"SERVER",status:500,title:"File watcher error",suggestion:"Restart the development server"}),be=r({slug:"request-error",category:"SERVER",status:500,title:"HTTP request handling error",suggestion:"Check request handler and middleware"}),Me=r({slug:"service-overloaded",category:"SERVER",status:503,title:"Service overloaded",suggestion:"Reduce load or scale up resources"}),Ue=r({slug:"cache-path-mismatch",category:"SERVER",status:500,title:"Cache path mismatch",suggestion:"Clear the cache directory and rebuild"}),Pe=r({slug:"network-error",category:"SERVER",status:502,title:"Network operation failed",suggestion:"Check network connectivity and retry"}),Ve=r({slug:"api-client-error",category:"SERVER",status:500,title:"API client request failed",suggestion:"Check API connectivity and authentication"}),we=r({slug:"token-storage-error",category:"SERVER",status:500,title:"Token storage operation failed",suggestion:"Check token storage backend and credentials"}),Fe=r({slug:"cache-invariant-violation",category:"SERVER",status:500,title:"Cache path invariant violated",suggestion:"Clear the cache and rebuild"}),He=r({slug:"release-not-found",category:"SERVER",status:404,title:"No active release found",suggestion:"Deploy the project to create a release for this environment"}),$e=r({slug:"fallback-exhausted",category:"SERVER",status:500,title:"Primary and fallback operations both failed",suggestion:"Check service availability and connectivity"}),ke=r({slug:"client-boundary-violation",category:"BOUNDARY",status:400,title:"Client boundary rule violation",suggestion:"Add \'use client\' directive or move code to a client component"}),Ge=r({slug:"server-only-in-client",category:"BOUNDARY",status:400,title:"Server-only code in client component",suggestion:"Move server-only code to a server component"}),je=r({slug:"client-only-in-server",category:"BOUNDARY",status:400,title:"Client-only code in server component",suggestion:"Move client-only code to a client component"}),Be=r({slug:"invalid-use-client",category:"BOUNDARY",status:400,title:"Invalid \'use client\' directive",suggestion:"Place \'use client\' at the top of the file"}),Ye=r({slug:"invalid-use-server",category:"BOUNDARY",status:400,title:"Invalid \'use server\' directive",suggestion:"Place \'use server\' at the top of the file or function"}),We=r({slug:"rsc-payload-error",category:"BOUNDARY",status:500,title:"RSC payload serialization error",suggestion:"Ensure props are serializable (no functions, symbols, etc.)"}),qe=r({slug:"hmr-error",category:"DEV",status:500,title:"Hot module replacement error",suggestion:"Restart the development server"}),ze=r({slug:"dev-server-error",category:"DEV",status:500,title:"Development server error",suggestion:"Check the dev server logs and restart"}),Xe=r({slug:"fast-refresh-error",category:"DEV",status:500,title:"Fast refresh failed",suggestion:"Save the file again or restart the dev server"}),Je=r({slug:"error-overlay-error",category:"DEV",status:500,title:"Error overlay failed",suggestion:"Check browser console for details"}),Ke=r({slug:"source-map-error",category:"DEV",status:500,title:"Source map loading error",suggestion:"Rebuild or clear cache"}),Ze=r({slug:"deployment-error",category:"DEPLOY",status:500,title:"Deployment process failed",suggestion:"Check deployment logs for details"}),Qe=r({slug:"platform-error",category:"DEPLOY",status:500,title:"Platform-specific error",suggestion:"Check platform documentation and requirements"}),tr=r({slug:"env-var-missing",category:"DEPLOY",status:500,title:"Required environment variable missing",suggestion:"Set the required environment variable"}),er=r({slug:"production-build-required",category:"DEPLOY",status:400,title:"Production build required",suggestion:"Run \'vf build\' before deploying"}),rr=r({slug:"agent-error",category:"AGENT",status:500,title:"Agent operation error",suggestion:"Check agent configuration and logs"}),or=r({slug:"agent-not-found",category:"AGENT",status:404,title:"Agent not found",suggestion:"Verify the agent ID exists"}),nr=r({slug:"agent-timeout",category:"AGENT",status:408,title:"Agent operation timed out",suggestion:"Increase timeout or simplify the request"}),sr=r({slug:"agent-intent-error",category:"AGENT",status:400,title:"Agent intent parsing error",suggestion:"Rephrase the request more clearly"}),ir=r({slug:"orchestration-error",category:"AGENT",status:500,title:"Multi-agent orchestration error",suggestion:"Check agent coordination logic"}),ar=r({slug:"cost-limit-exceeded",category:"AGENT",status:429,title:"Cost limit exceeded",suggestion:"Wait for the budget period to reset or increase the limit"}),cr=r({slug:"unknown-error",category:"GENERAL",status:500,title:"Unknown/unclassified error",suggestion:"Check logs for more details"}),ur=r({slug:"permission-denied",category:"GENERAL",status:403,title:"File/resource permission denied",suggestion:"Check file permissions and access rights"}),lr=r({slug:"file-not-found",category:"GENERAL",status:404,title:"File not found",suggestion:"Verify the file path exists"}),gr=r({slug:"resource-not-found",category:"GENERAL",status:404,title:"Requested resource not found",suggestion:"Verify the referenced resource ID or name exists"}),dr=r({slug:"invalid-argument",category:"GENERAL",status:400,title:"Invalid function argument",suggestion:"Check argument types and values"}),pr=r({slug:"timeout-error",category:"GENERAL",status:408,title:"Operation timed out",suggestion:"Increase timeout or optimize the operation"}),Rr=r({slug:"initialization-error",category:"GENERAL",status:500,title:"Initialization failed",suggestion:"Check initialization requirements and dependencies"}),mr=r({slug:"not-supported",category:"GENERAL",status:501,title:"Feature not supported",suggestion:"Check documentation for supported features"}),H=r({slug:"security-violation",category:"GENERAL",status:403,title:"Security violation detected",suggestion:"Check for path traversal or unauthorized access attempts"}),Er=r({slug:"input-validation-failed",category:"GENERAL",status:400,title:"Input validation failed",suggestion:"Check request input against validation rules"});var rt=[{pattern:/<script[^>]*>[\\s\\S]*?<\\/script>/gi,name:"inline script"},{pattern:/javascript:/gi,name:"javascript: URL"},{pattern:/\\bon\\w+\\s*=/gi,name:"event handler attribute"},{pattern:/data:\\s*text\\/html/gi,name:"data: HTML URL"}];function ot(){let t=globalThis;return t.__VERYFRONT_DEV__===!0||t.Deno?.env?.get?.("VERYFRONT_ENV")==="development"}function _(t,e={}){let{strict:o=!1,warn:n=!0}=e;for(let{pattern:s,name:c}of rt)if(s.lastIndex=0,!!s.test(t)&&(n&&console.warn(`[Security] Suspicious ${c} detected in server HTML`),o||!ot()))throw H.create({detail:`Potentially unsafe HTML: ${c} detected`});return t}var E=class{constructor(e,o){this.prefix=e;this.level=o}log(e,o,n,...s){this.level>e||o?.(n,...s)}debug(e,...o){this.log(0,console.debug,`[${this.prefix}] DEBUG: ${e}`,...o)}info(e,...o){this.log(1,console.log,`[${this.prefix}] ${e}`,...o)}warn(e,...o){this.log(2,console.warn,`[${this.prefix}] WARN: ${e}`,...o)}error(e,...o){this.log(3,console.error,`[${this.prefix}] ERROR: ${e}`,...o)}};function nt(){if(typeof window>"u")return 2;let t=globalThis;return t.__VERYFRONT_DEV__||t.__RSC_DEV__?t.__VERYFRONT_DEBUG__||t.__RSC_DEBUG__?0:1:2}var x=nt(),p=new E("RSC",x),hr=new E("PREFETCH",x),Ir=new E("HYDRATE",x),Sr=new E("VERYFRONT",x);function O(t,e){let o=e==="root"?y:`rsc-slot-${e}`,n=t.getElementById(o);if(n)return n;let s=t.createElement("div");return s.id=o,t.body.appendChild(s),s}function st(t,e){if(e.type!=="slot")return;let o=O(t,e.id);o.innerHTML=_(String(e.html??""))}function $(t,e){let o=e.split(`\n`),n=o.pop()??"";for(let s of o){let c=s.trim();if(!c)continue;let l;try{l=JSON.parse(c)}catch(g){p.debug("[client-dom] malformed NDJSON line",{line:c,error:g instanceof Error?g.message:String(g)});continue}if(!l||typeof l!="object")continue;let u=l;if(u.type==="slot"){st(t,u);try{ct(t,u.id||"root")}catch(g){p.debug("[client-dom] hydration optional failed",g)}}}return n}function it(t){return new Promise((e,o)=>{let n=()=>o(new DOMException("aborted","AbortError"));if(t.aborted){n();return}t.addEventListener("abort",n,{once:!0})})}async function k(t,e=document,o){let n="body"in t?t:null,s=n?.body??t;if(!s)return;let c=s.getReader(),l=new TextDecoder,u="",g=!1;try{for(;;){if(o?.aborted)throw new DOMException("aborted","AbortError");let a=c.read(),{done:h,value:j}=o?await Promise.race([a,it(o)]):await a;if(h){g=!0;break}u+=l.decode(j,{stream:!0}),u=$(e,u)}u&&$(e,`${u}\n`)}catch(a){throw a instanceof Error&&a.name==="AbortError"||p.debug("[client-dom] consumeNdjsonStream error",a),a}finally{try{await c.cancel()}catch(a){g||p.debug("[client-dom] reader.cancel failed",a)}try{c.releaseLock()}catch(a){p.debug("[client-dom] reader.releaseLock failed",a)}if(typeof s.cancel=="function")try{await s.cancel()}catch(a){p.debug("[client-dom] stream.cancel failed",a)}if(typeof n?.body?.cancel=="function")try{await n.body.cancel()}catch(a){p.debug("[client-dom] response.body.cancel failed",a)}}}function at(t,e){let o=O(t,e),n=[],s=c=>{let l=c;l.dataset?.clientRef&&n.push(l);for(let u of c.children)s(u)};return s(o),n}function ct(t,e){let o=at(t,e);for(let n of o){let s=n.dataset?.clientRef;s&&(n.dataset.hydrated="true",p.debug("[client-dom] marked for hydration",s))}}async function ut(){let t=F(document),[e,o]=await Promise.all([import(t.react),import(t.reactDomClient)]);return{React:e,ReactDOM:o}}var lt=new Set(["SCRIPT","STYLE","NOSCRIPT","TEMPLATE"]);function G(t){let e=t.getAttribute("style")??"";return t.hasAttribute("data-veryfront-head")||t.hasAttribute("hidden")||/(?:^|;)\\s*display\\s*:\\s*none(?:\\s*;|$)/i.test(e)||lt.has(t.tagName.toUpperCase())}function gt(t,e){return t.find(o=>o.tagName.toUpperCase()==="DIV"&&!!o.getAttribute("class")?.trim()&&!G(o))??t.find(o=>!G(o))??e}function dt(t,e){return e?.pagePath?!1:!!t.getElementById(y)}async function pt(t){try{let e=await fetch(m+"stream"+t);if(!e.ok||!e.body)return!1;let o=new AbortController;return addEventListener("pagehide",()=>o.abort(),{once:!0}),await k(e,document,o.signal),!0}catch(e){return console.debug?.("[RSC] tryStream failed",e),!1}}async function T(){try{(await import(m+"hydrate.js")).bootHydration?.()}catch(t){console.debug?.("[RSC] hydrate import failed",t)}}async function Rt(t,e){try{let{React:o,ReactDOM:n}=await ut(),s=w({strategy:e,rel:t});if(!s)return!1;console.debug?.("[RSC] Loading component from:",s);let l=(await import(s)).default;if(typeof l!="function")return console.debug?.("[RSC] Page component is not a function"),!1;let u=gt(Array.from(document.body.children),document.body);return n.hydrateRoot(u,o.createElement(l,{}),{identifierPrefix:"vf",onRecoverableError:()=>{}}),console.debug?.("[RSC] Page component hydrated successfully"),!0}catch(o){return console.error("[RSC] Page hydration failed",o),!1}}async function mt(t){try{let e=await fetch(m+"payload"+t);if(!e.ok)return!1;let o=await e.json();if(o?.slots){for(let[n,s]of Object.entries(o.slots))O(document,n).innerHTML=_(String(s||""));return!0}return O(document,y).innerHTML=_(String(o?.html||"")),!0}catch(e){return console.debug?.("[RSC] payload fetch failed",e),!1}}async function Et(){try{let t=globalThis.window?.location.search??"",e=P(document),o=e?.pagePath,n=V(e);if(o){console.debug?.("[RSC] Found page component in hydration data:",o),await Rt(o,n)&&console.debug?.("[RSC] Client component hydrated successfully");return}if(!dt(document,e))return;if(await pt(t)){await T();return}if(await mt(t)){await T();return}await T()}catch(t){console.error("[RSC] boot failed",t)}}if(typeof document<"u"){let t=()=>{Et()};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",t,{once:!0}):t()}export{Et as boot,gt as selectHydrationRoot,dt as shouldAttemptRSCTransport};\n';
|
|
9
|
-
export const CLIENT_DOM_BUNDLE = 'var A=Object.defineProperty;var x=(r,t,o)=>t in r?A(r,t,{enumerable:!0,configurable:!0,writable:!0,value:o}):r[t]=o;var u=(r,t,o)=>x(r,typeof t!="symbol"?t+"":t,o);function e(r){return{...r,create(t){return new f(t?.message||t?.detail||r.title,{slug:r.slug,category:r.category,status:t?.status??r.status,title:r.title,suggestion:r.suggestion,detail:t?.detail,cause:t?.cause,instance:t?.instance,context:t?.context})}}}var f=class extends Error{constructor(o,n){super(o);u(this,"slug");u(this,"category");u(this,"status");u(this,"title");u(this,"suggestion");u(this,"detail");u(this,"cause");u(this,"instance");u(this,"context");this.name="VeryfrontError",this.slug=n.slug,this.category=n.category,this.status=n.status,this.title=n.title,this.suggestion=n.suggestion,this.detail=n.detail,this.cause=n.cause,this.instance=n.instance,this.context=n.context}toRFC9457(){return{type:`https://veryfront.com/docs/errors/${this.slug}`,title:this.title,status:this.status,detail:this.detail,instance:this.instance,category:this.category,suggestion:this.suggestion,cause:typeof this.cause=="string"?this.cause:void 0}}getDocsUrl(){return`https://veryfront.com/docs/errors/${this.slug}`}};var $=e({slug:"config-not-found",category:"CONFIG",status:404,title:"Configuration file not found",suggestion:"Run \'vf init\' to create a configuration file"}),B=e({slug:"config-invalid",category:"CONFIG",status:400,title:"Invalid configuration format",suggestion:"Check your veryfront.config.ts for syntax errors"}),Y=e({slug:"config-parse-error",category:"CONFIG",status:400,title:"Failed to parse configuration",suggestion:"Ensure your configuration file is valid TypeScript/JSON"}),j=e({slug:"config-validation-error",category:"CONFIG",status:422,title:"Configuration validation failed",suggestion:"Check the configuration against the schema requirements"}),q=e({slug:"config-type-error",category:"CONFIG",status:400,title:"Configuration type mismatch",suggestion:"Ensure configuration values match expected types"}),z=e({slug:"import-map-invalid",category:"CONFIG",status:400,title:"Invalid import map configuration",suggestion:"Check your import map syntax and paths"}),W=e({slug:"cors-config-invalid",category:"CONFIG",status:400,title:"Invalid CORS configuration",suggestion:"Review CORS settings in your configuration"}),X=e({slug:"config-validation-failed",category:"CONFIG",status:400,title:"Configuration validation failed",suggestion:"Check configuration values against requirements"}),J=e({slug:"build-failed",category:"BUILD",status:500,title:"Build process failed",suggestion:"Check the build output for specific errors"}),K=e({slug:"bundle-error",category:"BUILD",status:500,title:"Bundle generation failed",suggestion:"Review bundler output for details"}),Z=e({slug:"typescript-error",category:"BUILD",status:500,title:"TypeScript compilation error",suggestion:"Fix TypeScript errors shown in the output"}),Q=e({slug:"mdx-compile-error",category:"BUILD",status:500,title:"MDX compilation failed",suggestion:"Check your MDX file syntax"}),ee=e({slug:"asset-optimization-error",category:"BUILD",status:500,title:"Asset optimization failed",suggestion:"Check asset file formats and paths"}),te=e({slug:"ssg-generation-error",category:"BUILD",status:500,title:"Static site generation failed",suggestion:"Review SSG configuration and data fetching"}),re=e({slug:"sourcemap-error",category:"BUILD",status:500,title:"Source map generation failed",suggestion:"Check source map configuration"}),oe=e({slug:"compilation-error",category:"BUILD",status:500,title:"Compilation failed",suggestion:"Review compiler output for specific errors"}),se=e({slug:"hydration-mismatch",category:"RUNTIME",status:500,title:"Client/server hydration mismatch",suggestion:"Ensure server and client render the same content"}),ne=e({slug:"render-error",category:"RUNTIME",status:500,title:"Component render failed",suggestion:"Check component for runtime errors"}),ie=e({slug:"component-error",category:"RUNTIME",status:500,title:"Component execution error",suggestion:"Review component logic and props"}),ae=e({slug:"layout-not-found",category:"RUNTIME",status:404,title:"Layout component not found",suggestion:"Ensure layout file exists at the expected path"}),ce=e({slug:"page-not-found",category:"RUNTIME",status:404,title:"Page component not found",suggestion:"Check that the page file exists in the routes directory"}),le=e({slug:"api-error",category:"RUNTIME",status:500,title:"API route handler error",suggestion:"Review API route handler for errors"}),ue=e({slug:"middleware-error",category:"RUNTIME",status:500,title:"Middleware execution error",suggestion:"Check middleware function for errors"}),ge=e({slug:"route-conflict",category:"ROUTE",status:409,title:"Conflicting route definitions",suggestion:"Rename or reorganize conflicting route files"}),de=e({slug:"invalid-route-file",category:"ROUTE",status:400,title:"Invalid route file structure",suggestion:"Ensure route file exports required functions"}),pe=e({slug:"route-handler-invalid",category:"ROUTE",status:400,title:"Invalid route handler export",suggestion:"Export a valid handler function from the route file"}),Ee=e({slug:"dynamic-route-error",category:"ROUTE",status:500,title:"Dynamic route parsing failed",suggestion:"Check dynamic route segment syntax"}),Re=e({slug:"route-params-error",category:"ROUTE",status:400,title:"Route parameters invalid",suggestion:"Validate route parameter values"}),fe=e({slug:"api-route-error",category:"ROUTE",status:500,title:"API route definition error",suggestion:"Review API route configuration"}),me=e({slug:"module-not-found",category:"MODULE",status:404,title:"Module could not be resolved",suggestion:"Check the import path and ensure the module is installed"}),_e=e({slug:"import-resolution-error",category:"MODULE",status:500,title:"Import path resolution failed",suggestion:"Verify import paths and module configuration"}),ye=e({slug:"circular-dependency",category:"MODULE",status:500,title:"Circular dependency detected",suggestion:"Refactor imports to break the circular dependency"}),Oe=e({slug:"invalid-import",category:"MODULE",status:400,title:"Invalid import statement",suggestion:"Fix import syntax or path"}),Te=e({slug:"dependency-missing",category:"MODULE",status:404,title:"Required dependency not installed",suggestion:"Install the missing dependency with your package manager"}),he=e({slug:"version-mismatch",category:"MODULE",status:409,title:"Dependency version mismatch",suggestion:"Update dependencies to compatible versions"}),Ie=e({slug:"port-in-use",category:"SERVER",status:409,title:"Server port already in use",suggestion:"Use a different port or stop the process using this port"}),ve=e({slug:"server-start-error",category:"SERVER",status:500,title:"Server failed to start",suggestion:"Check server configuration and port availability"}),Ne=e({slug:"cache-error",category:"SERVER",status:500,title:"Cache operation failed",suggestion:"Clear the cache and try again"}),Ae=e({slug:"file-watch-error",category:"SERVER",status:500,title:"File watcher error",suggestion:"Restart the development server"}),xe=e({slug:"request-error",category:"SERVER",status:500,title:"HTTP request handling error",suggestion:"Check request handler and middleware"}),Ce=e({slug:"service-overloaded",category:"SERVER",status:503,title:"Service overloaded",suggestion:"Reduce load or scale up resources"}),Se=e({slug:"cache-path-mismatch",category:"SERVER",status:500,title:"Cache path mismatch",suggestion:"Clear the cache directory and rebuild"}),De=e({slug:"network-error",category:"SERVER",status:502,title:"Network operation failed",suggestion:"Check network connectivity and retry"}),Le=e({slug:"api-client-error",category:"SERVER",status:500,title:"API client request failed",suggestion:"Check API connectivity and authentication"}),Ue=e({slug:"token-storage-error",category:"SERVER",status:500,title:"Token storage operation failed",suggestion:"Check token storage backend and credentials"}),be=e({slug:"cache-invariant-violation",category:"SERVER",status:500,title:"Cache path invariant violated",suggestion:"Clear the cache and rebuild"}),Me=e({slug:"release-not-found",category:"SERVER",status:404,title:"No active release found",suggestion:"Deploy the project to create a release for this environment"}),Pe=e({slug:"fallback-exhausted",category:"SERVER",status:500,title:"Primary and fallback operations both failed",suggestion:"Check service availability and connectivity"}),Ve=e({slug:"client-boundary-violation",category:"BOUNDARY",status:400,title:"Client boundary rule violation",suggestion:"Add \'use client\' directive or move code to a client component"}),Fe=e({slug:"server-only-in-client",category:"BOUNDARY",status:400,title:"Server-only code in client component",suggestion:"Move server-only code to a server component"}),ke=e({slug:"client-only-in-server",category:"BOUNDARY",status:400,title:"Client-only code in server component",suggestion:"Move client-only code to a client component"}),we=e({slug:"invalid-use-client",category:"BOUNDARY",status:400,title:"Invalid \'use client\' directive",suggestion:"Place \'use client\' at the top of the file"}),Ge=e({slug:"invalid-use-server",category:"BOUNDARY",status:400,title:"Invalid \'use server\' directive",suggestion:"Place \'use server\' at the top of the file or function"}),He=e({slug:"rsc-payload-error",category:"BOUNDARY",status:500,title:"RSC payload serialization error",suggestion:"Ensure props are serializable (no functions, symbols, etc.)"}),$e=e({slug:"hmr-error",category:"DEV",status:500,title:"Hot module replacement error",suggestion:"Restart the development server"}),Be=e({slug:"dev-server-error",category:"DEV",status:500,title:"Development server error",suggestion:"Check the dev server logs and restart"}),Ye=e({slug:"fast-refresh-error",category:"DEV",status:500,title:"Fast refresh failed",suggestion:"Save the file again or restart the dev server"}),je=e({slug:"error-overlay-error",category:"DEV",status:500,title:"Error overlay failed",suggestion:"Check browser console for details"}),qe=e({slug:"source-map-error",category:"DEV",status:500,title:"Source map loading error",suggestion:"Rebuild or clear cache"}),ze=e({slug:"deployment-error",category:"DEPLOY",status:500,title:"Deployment process failed",suggestion:"Check deployment logs for details"}),We=e({slug:"platform-error",category:"DEPLOY",status:500,title:"Platform-specific error",suggestion:"Check platform documentation and requirements"}),Xe=e({slug:"env-var-missing",category:"DEPLOY",status:500,title:"Required environment variable missing",suggestion:"Set the required environment variable"}),Je=e({slug:"production-build-required",category:"DEPLOY",status:400,title:"Production build required",suggestion:"Run \'vf build\' before deploying"}),Ke=e({slug:"agent-error",category:"AGENT",status:500,title:"Agent operation error",suggestion:"Check agent configuration and logs"}),Ze=e({slug:"agent-not-found",category:"AGENT",status:404,title:"Agent not found",suggestion:"Verify the agent ID exists"}),Qe=e({slug:"agent-timeout",category:"AGENT",status:408,title:"Agent operation timed out",suggestion:"Increase timeout or simplify the request"}),et=e({slug:"agent-intent-error",category:"AGENT",status:400,title:"Agent intent parsing error",suggestion:"Rephrase the request more clearly"}),tt=e({slug:"orchestration-error",category:"AGENT",status:500,title:"Multi-agent orchestration error",suggestion:"Check agent coordination logic"}),rt=e({slug:"cost-limit-exceeded",category:"AGENT",status:429,title:"Cost limit exceeded",suggestion:"Wait for the budget period to reset or increase the limit"}),ot=e({slug:"unknown-error",category:"GENERAL",status:500,title:"Unknown/unclassified error",suggestion:"Check logs for more details"}),st=e({slug:"permission-denied",category:"GENERAL",status:403,title:"File/resource permission denied",suggestion:"Check file permissions and access rights"}),nt=e({slug:"file-not-found",category:"GENERAL",status:404,title:"File not found",suggestion:"Verify the file path exists"}),it=e({slug:"resource-not-found",category:"GENERAL",status:404,title:"Requested resource not found",suggestion:"Verify the referenced resource ID or name exists"}),at=e({slug:"invalid-argument",category:"GENERAL",status:400,title:"Invalid function argument",suggestion:"Check argument types and values"}),ct=e({slug:"timeout-error",category:"GENERAL",status:408,title:"Operation timed out",suggestion:"Increase timeout or optimize the operation"}),lt=e({slug:"initialization-error",category:"GENERAL",status:500,title:"Initialization failed",suggestion:"Check initialization requirements and dependencies"}),ut=e({slug:"not-supported",category:"GENERAL",status:501,title:"Feature not supported",suggestion:"Check documentation for supported features"}),_=e({slug:"security-violation",category:"GENERAL",status:403,title:"Security violation detected",suggestion:"Check for path traversal or unauthorized access attempts"}),gt=e({slug:"input-validation-failed",category:"GENERAL",status:400,title:"Input validation failed",suggestion:"Check request input against validation rules"});var C=[{pattern:/<script[^>]*>[\\s\\S]*?<\\/script>/gi,name:"inline script"},{pattern:/javascript:/gi,name:"javascript: URL"},{pattern:/\\bon\\w+\\s*=/gi,name:"event handler attribute"},{pattern:/data:\\s*text\\/html/gi,name:"data: HTML URL"}];function S(){let r=globalThis;return r.__VERYFRONT_DEV__===!0||r.Deno?.env?.get?.("VERYFRONT_ENV")==="development"}function y(r,t={}){let{strict:o=!1,warn:n=!0}=t;for(let{pattern:i,name:c}of C)if(i.lastIndex=0,!!i.test(r)&&(n&&console.warn(`[Security] Suspicious ${c} detected in server HTML`),o||!S()))throw _.create({detail:`Potentially unsafe HTML: ${c} detected`});return r}var E=class{constructor(t,o){this.prefix=t;this.level=o}log(t,o,n,...i){this.level>t||o?.(n,...i)}debug(t,...o){this.log(0,console.debug,`[${this.prefix}] DEBUG: ${t}`,...o)}info(t,...o){this.log(1,console.log,`[${this.prefix}] ${t}`,...o)}warn(t,...o){this.log(2,console.warn,`[${this.prefix}] WARN: ${t}`,...o)}error(t,...o){this.log(3,console.error,`[${this.prefix}] ERROR: ${t}`,...o)}};function D(){if(typeof window>"u")return 2;let r=globalThis;return r.__VERYFRONT_DEV__||r.__RSC_DEV__?r.__VERYFRONT_DEBUG__||r.__RSC_DEBUG__?0:1:2}var R=D(),d=new E("RSC",R),mt=new E("PREFETCH",R),_t=new E("HYDRATE",R),yt=new E("VERYFRONT",R);var s="/_veryfront",m={RSC:`${s}/rsc/`,FS:`${s}/fs/`,MODULES:`${s}/modules/`,PAGES:`${s}/pages/`,DATA:`${s}/data/`,LIB:`${s}/lib/`,CHUNKS:`${s}/chunks/`,CLIENT:`${s}/client/`},O={HMR_RUNTIME:`${s}/hmr-runtime.js`,HMR:`${s}/hmr.js`,HYDRATE:`${s}/hydrate.js`,ERROR_OVERLAY:`${s}/error-overlay.js`,DEV_LOADER:`${s}/dev-loader.js`,CLIENT_LOG:`${s}/log`,CLIENT_JS:`${s}/client.js`,ROUTER_JS:`${s}/router.js`,PREFETCH_JS:`${s}/prefetch.js`,MANIFEST_JSON:`${s}/manifest.json`,APP_JS:`${s}/app.js`,RSC_CLIENT:`${s}/rsc/client.js`,RSC_MANIFEST:`${s}/rsc/manifest`,RSC_STREAM:`${s}/rsc/stream`,RSC_PAYLOAD:`${s}/rsc/payload`,RSC_RENDER:`${s}/rsc/render`,RSC_PAGE:`${s}/rsc/page`,RSC_MODULE:`${s}/rsc/module`,RSC_DOM:`${s}/rsc/dom.js`,RSC_HYDRATOR:`${s}/rsc/hydrator.js`,RSC_HYDRATE_CLIENT:`${s}/rsc/hydrate-client.js`,LIB_CHAT_REACT:`${s}/lib/chat/react.js`,LIB_CHAT_COMPONENTS:`${s}/lib/chat/components.js`,LIB_CHAT_PRIMITIVES:`${s}/lib/chat/primitives.js`};var U={ROOT:".veryfront",CACHE:".veryfront/cache",KV:".veryfront/kv",LOGS:".veryfront/logs",TMP:".veryfront/tmp"},vt=U.CACHE;var Nt={HMR_RUNTIME:O.HMR_RUNTIME,ERROR_OVERLAY:O.ERROR_OVERLAY};var St=m.RSC,Dt=m.FS;var T="rsc-root";function I(r,t){let o=t==="root"?T:`rsc-slot-${t}`,n=r.getElementById(o);if(n)return n;let i=r.createElement("div");return i.id=o,r.body.appendChild(i),i}function b(r,t){if(t.type!=="slot")return;let o=I(r,t.id);o.innerHTML=y(String(t.html??""))}function h(r,t){let o=t.split(`\n`),n=o.pop()??"";for(let i of o){let c=i.trim();if(!c)continue;let g;try{g=JSON.parse(c)}catch(p){d.debug("[client-dom] malformed NDJSON line",{line:c,error:p instanceof Error?p.message:String(p)});continue}if(!g||typeof g!="object")continue;let l=g;if(l.type==="slot"){b(r,l);try{V(r,l.id||"root")}catch(p){d.debug("[client-dom] hydration optional failed",p)}}}return n}function M(r){return new Promise((t,o)=>{let n=()=>o(new DOMException("aborted","AbortError"));if(r.aborted){n();return}r.addEventListener("abort",n,{once:!0})})}async function Pt(r,t=document,o){let n="body"in r?r:null,i=n?.body??r;if(!i)return;let c=i.getReader(),g=new TextDecoder,l="",p=!1;try{for(;;){if(o?.aborted)throw new DOMException("aborted","AbortError");let a=c.read(),{done:v,value:N}=o?await Promise.race([a,M(o)]):await a;if(v){p=!0;break}l+=g.decode(N,{stream:!0}),l=h(t,l)}l&&h(t,`${l}\n`)}catch(a){throw a instanceof Error&&a.name==="AbortError"||d.debug("[client-dom] consumeNdjsonStream error",a),a}finally{try{await c.cancel()}catch(a){p||d.debug("[client-dom] reader.cancel failed",a)}try{c.releaseLock()}catch(a){d.debug("[client-dom] reader.releaseLock failed",a)}if(typeof i.cancel=="function")try{await i.cancel()}catch(a){d.debug("[client-dom] stream.cancel failed",a)}if(typeof n?.body?.cancel=="function")try{await n.body.cancel()}catch(a){d.debug("[client-dom] response.body.cancel failed",a)}}}function P(r,t){let o=I(r,t),n=[],i=c=>{let g=c;g.dataset?.clientRef&&n.push(g);for(let l of c.children)i(l)};return i(o),n}function V(r,t){let o=P(r,t);for(let n of o){let i=n.dataset?.clientRef;i&&(n.dataset.hydrated="true",d.debug("[client-dom] marked for hydration",i))}}export{Pt as consumeNdjsonStream,I as getContainer};\n';
|
|
8
|
+
export const CLIENT_BOOT_BUNDLE = 'var B=Object.defineProperty;var Y=(t,e,o)=>e in t?B(t,e,{enumerable:!0,configurable:!0,writable:!0,value:o}):t[e]=o;var d=(t,e,o)=>Y(t,typeof e!="symbol"?e+"":e,o);var W="3.2.3";function q(t,e,o,n){let s=[];if(n?.external?.length&&s.push(`external=${n.external.join(",")}`),s.push(`target=${n?.target??"es2022"}`),n?.deps){let g=Object.entries(n.deps).map(([a,h])=>`${a}@${h}`).join(",");s.push(`deps=${g}`)}let c=e?`@${e}`:"",l=o??"",u=s.length?`?${s.join("&")}`:"";return`https://esm.sh/${t}${c}${l}${u}`}function R(t,e,o,n=!1){return q(t,e,o,{external:n?["react"]:void 0,deps:{csstype:W}})}var X="19.1.1",f=X;function N(t=f){return{react:R("react",t),"react-dom":R("react-dom",t,void 0,!0),"react-dom/client":R("react-dom",t,"/client",!0),"react-dom/server":R("react-dom",t,"/server",!0),"react/jsx-runtime":R("react",t,"/jsx-runtime",!0),"react/jsx-dev-runtime":R("react",t,"/jsx-dev-runtime",!0)}}function A(t=f){return N(t).react}function D(t=f){return N(t)["react-dom/client"]}function J(t){return t.replaceAll("+","-").replaceAll("/","_").replaceAll("=","")}function v(t){return J(btoa(t))}var Nt=Object.freeze({react:"","react-dom":"","react-dom/client":"","react-dom/server":"","react/jsx-runtime":"","react/jsx-dev-runtime":""});function S(t,e){if(!e)return!1;if(Object.prototype.hasOwnProperty.call(e,t))return!0;for(let o of Object.keys(e))if(o.endsWith("/")&&t.startsWith(o))return!0;return!1}function K(t){try{return JSON.parse(t)?.imports??{}}catch{return{}}}function L(t=document){let e=t.querySelector(\'script[type="importmap"]\');return e?.textContent?K(e.textContent):{}}var i="/_veryfront",I={RSC:`${i}/rsc/`,FS:`${i}/fs/`,MODULES:`${i}/modules/`,PAGES:`${i}/pages/`,DATA:`${i}/data/`,LIB:`${i}/lib/`,CHUNKS:`${i}/chunks/`,CLIENT:`${i}/client/`},b={HMR_RUNTIME:`${i}/hmr-runtime.js`,HMR:`${i}/hmr.js`,HYDRATE:`${i}/hydrate.js`,ERROR_OVERLAY:`${i}/error-overlay.js`,DEV_LOADER:`${i}/dev-loader.js`,CLIENT_LOG:`${i}/log`,CLIENT_JS:`${i}/client.js`,ROUTER_JS:`${i}/router.js`,PREFETCH_JS:`${i}/prefetch.js`,MANIFEST_JSON:`${i}/manifest.json`,APP_JS:`${i}/app.js`,RSC_CLIENT:`${i}/rsc/client.js`,RSC_MANIFEST:`${i}/rsc/manifest`,RSC_STREAM:`${i}/rsc/stream`,RSC_PAYLOAD:`${i}/rsc/payload`,RSC_RENDER:`${i}/rsc/render`,RSC_PAGE:`${i}/rsc/page`,RSC_MODULE:`${i}/rsc/module`,RSC_DOM:`${i}/rsc/dom.js`,RSC_HYDRATOR:`${i}/rsc/hydrator.js`,RSC_HYDRATE_CLIENT:`${i}/rsc/hydrate-client.js`,LIB_CHAT_REACT:`${i}/lib/chat/react.js`,LIB_CHAT_COMPONENTS:`${i}/lib/chat/components.js`,LIB_CHAT_PRIMITIVES:`${i}/lib/chat/primitives.js`};var Q={ROOT:".veryfront",CACHE:".veryfront/cache",KV:".veryfront/kv",LOGS:".veryfront/logs",TMP:".veryfront/tmp"},bt=Q.CACHE;var Mt={HMR_RUNTIME:b.HMR_RUNTIME,ERROR_OVERLAY:b.ERROR_OVERLAY};var m=I.RSC,M=I.FS,U="veryfront-hydration-data",y="rsc-root";function P(t=document){try{let e=t.getElementById(U);return e?JSON.parse(e.textContent||"{}"):null}catch(e){return console.debug?.("[RSC] hydration data parse failed",e),null}}function V(t){return t?.clientModuleStrategy?t.clientModuleStrategy:t?.dev?"fs":"rsc-module"}function tt(t){return`${M}${v(t)}.js`}function et(t,e){let o=e?`&v=${encodeURIComponent(e)}`:"";return`${m}module?rel=${encodeURIComponent(t)}${o}`}function w(t){if(t.strategy==="fs"){let e=t.absPath??t.rel;return e?tt(e):null}return et(t.rel,t.version)}function F(t=document,e=f){let o=L(t);return{react:S("react",o)?"react":A(e),reactDomClient:S("react-dom/client",o)?"react-dom/client":D(e)}}function r(t){return{...t,create(e){return new C(e?.message||e?.detail||t.title,{slug:t.slug,category:t.category,status:e?.status??t.status,title:t.title,suggestion:t.suggestion,detail:e?.detail,cause:e?.cause,instance:e?.instance,context:e?.context})}}}var C=class extends Error{constructor(o,n){super(o);d(this,"slug");d(this,"category");d(this,"status");d(this,"title");d(this,"suggestion");d(this,"detail");d(this,"cause");d(this,"instance");d(this,"context");this.name="VeryfrontError",this.slug=n.slug,this.category=n.category,this.status=n.status,this.title=n.title,this.suggestion=n.suggestion,this.detail=n.detail,this.cause=n.cause,this.instance=n.instance,this.context=n.context}toRFC9457(){return{type:`https://veryfront.com/docs/errors/${this.slug}`,title:this.title,status:this.status,detail:this.detail,instance:this.instance,category:this.category,suggestion:this.suggestion,cause:typeof this.cause=="string"?this.cause:void 0}}getDocsUrl(){return`https://veryfront.com/docs/errors/${this.slug}`}};var Zt=r({slug:"config-not-found",category:"CONFIG",status:404,title:"Configuration file not found",suggestion:"Run \'vf init\' to create a configuration file"}),Qt=r({slug:"config-invalid",category:"CONFIG",status:400,title:"Invalid configuration format",suggestion:"Check your veryfront.config.ts for syntax errors"}),te=r({slug:"config-parse-error",category:"CONFIG",status:400,title:"Failed to parse configuration",suggestion:"Ensure your configuration file is valid TypeScript/JSON"}),ee=r({slug:"config-validation-error",category:"CONFIG",status:422,title:"Configuration validation failed",suggestion:"Check the configuration against the schema requirements"}),re=r({slug:"config-type-error",category:"CONFIG",status:400,title:"Configuration type mismatch",suggestion:"Ensure configuration values match expected types"}),oe=r({slug:"import-map-invalid",category:"CONFIG",status:400,title:"Invalid import map configuration",suggestion:"Check your import map syntax and paths"}),ne=r({slug:"cors-config-invalid",category:"CONFIG",status:400,title:"Invalid CORS configuration",suggestion:"Review CORS settings in your configuration"}),se=r({slug:"config-validation-failed",category:"CONFIG",status:400,title:"Configuration validation failed",suggestion:"Check configuration values against requirements"}),ie=r({slug:"build-failed",category:"BUILD",status:500,title:"Build process failed",suggestion:"Check the build output for specific errors"}),ae=r({slug:"bundle-error",category:"BUILD",status:500,title:"Bundle generation failed",suggestion:"Review bundler output for details"}),ce=r({slug:"typescript-error",category:"BUILD",status:500,title:"TypeScript compilation error",suggestion:"Fix TypeScript errors shown in the output"}),ue=r({slug:"mdx-compile-error",category:"BUILD",status:500,title:"MDX compilation failed",suggestion:"Check your MDX file syntax"}),le=r({slug:"asset-optimization-error",category:"BUILD",status:500,title:"Asset optimization failed",suggestion:"Check asset file formats and paths"}),ge=r({slug:"ssg-generation-error",category:"BUILD",status:500,title:"Static site generation failed",suggestion:"Review SSG configuration and data fetching"}),de=r({slug:"sourcemap-error",category:"BUILD",status:500,title:"Source map generation failed",suggestion:"Check source map configuration"}),pe=r({slug:"compilation-error",category:"BUILD",status:500,title:"Compilation failed",suggestion:"Review compiler output for specific errors"}),Re=r({slug:"hydration-mismatch",category:"RUNTIME",status:500,title:"Client/server hydration mismatch",suggestion:"Ensure server and client render the same content"}),me=r({slug:"render-error",category:"RUNTIME",status:500,title:"Component render failed",suggestion:"Check component for runtime errors"}),Ee=r({slug:"component-error",category:"RUNTIME",status:500,title:"Component execution error",suggestion:"Review component logic and props"}),fe=r({slug:"layout-not-found",category:"RUNTIME",status:404,title:"Layout component not found",suggestion:"Ensure layout file exists at the expected path"}),ye=r({slug:"page-not-found",category:"RUNTIME",status:404,title:"Page component not found",suggestion:"Check that the page file exists in the routes directory"}),_e=r({slug:"api-error",category:"RUNTIME",status:500,title:"API route handler error",suggestion:"Review API route handler for errors"}),Oe=r({slug:"middleware-error",category:"RUNTIME",status:500,title:"Middleware execution error",suggestion:"Check middleware function for errors"}),xe=r({slug:"route-conflict",category:"ROUTE",status:409,title:"Conflicting route definitions",suggestion:"Rename or reorganize conflicting route files"}),he=r({slug:"invalid-route-file",category:"ROUTE",status:400,title:"Invalid route file structure",suggestion:"Ensure route file exports required functions"}),Se=r({slug:"route-handler-invalid",category:"ROUTE",status:400,title:"Invalid route handler export",suggestion:"Export a valid handler function from the route file"}),Ie=r({slug:"dynamic-route-error",category:"ROUTE",status:500,title:"Dynamic route parsing failed",suggestion:"Check dynamic route segment syntax"}),Ce=r({slug:"route-params-error",category:"ROUTE",status:400,title:"Route parameters invalid",suggestion:"Validate route parameter values"}),Te=r({slug:"api-route-error",category:"ROUTE",status:500,title:"API route definition error",suggestion:"Review API route configuration"}),Ne=r({slug:"module-not-found",category:"MODULE",status:404,title:"Module could not be resolved",suggestion:"Check the import path and ensure the module is installed"}),Ae=r({slug:"import-resolution-error",category:"MODULE",status:500,title:"Import path resolution failed",suggestion:"Verify import paths and module configuration"}),De=r({slug:"circular-dependency",category:"MODULE",status:500,title:"Circular dependency detected",suggestion:"Refactor imports to break the circular dependency"}),ve=r({slug:"invalid-import",category:"MODULE",status:400,title:"Invalid import statement",suggestion:"Fix import syntax or path"}),Le=r({slug:"dependency-missing",category:"MODULE",status:404,title:"Required dependency not installed",suggestion:"Install the missing dependency with your package manager"}),be=r({slug:"version-mismatch",category:"MODULE",status:409,title:"Dependency version mismatch",suggestion:"Update dependencies to compatible versions"}),Me=r({slug:"port-in-use",category:"SERVER",status:409,title:"Server port already in use",suggestion:"Use a different port or stop the process using this port"}),Ue=r({slug:"server-start-error",category:"SERVER",status:500,title:"Server failed to start",suggestion:"Check server configuration and port availability"}),Pe=r({slug:"cache-error",category:"SERVER",status:500,title:"Cache operation failed",suggestion:"Clear the cache and try again"}),Ve=r({slug:"file-watch-error",category:"SERVER",status:500,title:"File watcher error",suggestion:"Restart the development server"}),we=r({slug:"request-error",category:"SERVER",status:500,title:"HTTP request handling error",suggestion:"Check request handler and middleware"}),Fe=r({slug:"service-overloaded",category:"SERVER",status:503,title:"Service overloaded",suggestion:"Reduce load or scale up resources"}),He=r({slug:"cache-path-mismatch",category:"SERVER",status:500,title:"Cache path mismatch",suggestion:"Clear the cache directory and rebuild"}),$e=r({slug:"network-error",category:"SERVER",status:502,title:"Network operation failed",suggestion:"Check network connectivity and retry"}),ke=r({slug:"api-client-error",category:"SERVER",status:500,title:"API client request failed",suggestion:"Check API connectivity and authentication"}),Ge=r({slug:"token-storage-error",category:"SERVER",status:500,title:"Token storage operation failed",suggestion:"Check token storage backend and credentials"}),je=r({slug:"cache-invariant-violation",category:"SERVER",status:500,title:"Cache path invariant violated",suggestion:"Clear the cache and rebuild"}),Be=r({slug:"release-not-found",category:"SERVER",status:404,title:"No active release found",suggestion:"Deploy the project to create a release for this environment"}),Ye=r({slug:"fallback-exhausted",category:"SERVER",status:500,title:"Primary and fallback operations both failed",suggestion:"Check service availability and connectivity"}),We=r({slug:"client-boundary-violation",category:"BOUNDARY",status:400,title:"Client boundary rule violation",suggestion:"Add \'use client\' directive or move code to a client component"}),qe=r({slug:"server-only-in-client",category:"BOUNDARY",status:400,title:"Server-only code in client component",suggestion:"Move server-only code to a server component"}),ze=r({slug:"client-only-in-server",category:"BOUNDARY",status:400,title:"Client-only code in server component",suggestion:"Move client-only code to a client component"}),Xe=r({slug:"invalid-use-client",category:"BOUNDARY",status:400,title:"Invalid \'use client\' directive",suggestion:"Place \'use client\' at the top of the file"}),Je=r({slug:"invalid-use-server",category:"BOUNDARY",status:400,title:"Invalid \'use server\' directive",suggestion:"Place \'use server\' at the top of the file or function"}),Ke=r({slug:"rsc-payload-error",category:"BOUNDARY",status:500,title:"RSC payload serialization error",suggestion:"Ensure props are serializable (no functions, symbols, etc.)"}),Ze=r({slug:"hmr-error",category:"DEV",status:500,title:"Hot module replacement error",suggestion:"Restart the development server"}),Qe=r({slug:"dev-server-error",category:"DEV",status:500,title:"Development server error",suggestion:"Check the dev server logs and restart"}),tr=r({slug:"fast-refresh-error",category:"DEV",status:500,title:"Fast refresh failed",suggestion:"Save the file again or restart the dev server"}),er=r({slug:"error-overlay-error",category:"DEV",status:500,title:"Error overlay failed",suggestion:"Check browser console for details"}),rr=r({slug:"source-map-error",category:"DEV",status:500,title:"Source map loading error",suggestion:"Rebuild or clear cache"}),or=r({slug:"deployment-error",category:"DEPLOY",status:500,title:"Deployment process failed",suggestion:"Check deployment logs for details"}),nr=r({slug:"platform-error",category:"DEPLOY",status:500,title:"Platform-specific error",suggestion:"Check platform documentation and requirements"}),sr=r({slug:"env-var-missing",category:"DEPLOY",status:500,title:"Required environment variable missing",suggestion:"Set the required environment variable"}),ir=r({slug:"production-build-required",category:"DEPLOY",status:400,title:"Production build required",suggestion:"Run \'vf build\' before deploying"}),ar=r({slug:"agent-error",category:"AGENT",status:500,title:"Agent operation error",suggestion:"Check agent configuration and logs"}),cr=r({slug:"agent-not-found",category:"AGENT",status:404,title:"Agent not found",suggestion:"Verify the agent ID exists"}),ur=r({slug:"agent-timeout",category:"AGENT",status:408,title:"Agent operation timed out",suggestion:"Increase timeout or simplify the request"}),lr=r({slug:"agent-intent-error",category:"AGENT",status:400,title:"Agent intent parsing error",suggestion:"Rephrase the request more clearly"}),gr=r({slug:"orchestration-error",category:"AGENT",status:500,title:"Multi-agent orchestration error",suggestion:"Check agent coordination logic"}),dr=r({slug:"cost-limit-exceeded",category:"AGENT",status:429,title:"Cost limit exceeded",suggestion:"Wait for the budget period to reset or increase the limit"}),pr=r({slug:"unknown-error",category:"GENERAL",status:500,title:"Unknown/unclassified error",suggestion:"Check logs for more details"}),Rr=r({slug:"permission-denied",category:"GENERAL",status:403,title:"File/resource permission denied",suggestion:"Check file permissions and access rights"}),mr=r({slug:"file-not-found",category:"GENERAL",status:404,title:"File not found",suggestion:"Verify the file path exists"}),Er=r({slug:"resource-not-found",category:"GENERAL",status:404,title:"Requested resource not found",suggestion:"Verify the referenced resource ID or name exists"}),fr=r({slug:"invalid-argument",category:"GENERAL",status:400,title:"Invalid function argument",suggestion:"Check argument types and values"}),yr=r({slug:"timeout-error",category:"GENERAL",status:408,title:"Operation timed out",suggestion:"Increase timeout or optimize the operation"}),_r=r({slug:"initialization-error",category:"GENERAL",status:500,title:"Initialization failed",suggestion:"Check initialization requirements and dependencies"}),Or=r({slug:"not-supported",category:"GENERAL",status:501,title:"Feature not supported",suggestion:"Check documentation for supported features"}),H=r({slug:"security-violation",category:"GENERAL",status:403,title:"Security violation detected",suggestion:"Check for path traversal or unauthorized access attempts"}),xr=r({slug:"input-validation-failed",category:"GENERAL",status:400,title:"Input validation failed",suggestion:"Check request input against validation rules"});var rt=[{pattern:/<script[^>]*>[\\s\\S]*?<\\/script>/gi,name:"inline script"},{pattern:/javascript:/gi,name:"javascript: URL"},{pattern:/\\bon\\w+\\s*=/gi,name:"event handler attribute"},{pattern:/data:\\s*text\\/html/gi,name:"data: HTML URL"}];function ot(){let t=globalThis;return t.__VERYFRONT_DEV__===!0||t.Deno?.env?.get?.("VERYFRONT_ENV")==="development"}function _(t,e={}){let{strict:o=!1,warn:n=!0}=e;for(let{pattern:s,name:c}of rt)if(s.lastIndex=0,!!s.test(t)&&(n&&console.warn(`[Security] Suspicious ${c} detected in server HTML`),o||!ot()))throw H.create({detail:`Potentially unsafe HTML: ${c} detected`});return t}var E=class{constructor(e,o){this.prefix=e;this.level=o}log(e,o,n,...s){this.level>e||o?.(n,...s)}debug(e,...o){this.log(0,console.debug,`[${this.prefix}] DEBUG: ${e}`,...o)}info(e,...o){this.log(1,console.log,`[${this.prefix}] ${e}`,...o)}warn(e,...o){this.log(2,console.warn,`[${this.prefix}] WARN: ${e}`,...o)}error(e,...o){this.log(3,console.error,`[${this.prefix}] ERROR: ${e}`,...o)}};function nt(){if(typeof window>"u")return 2;let t=globalThis;return t.__VERYFRONT_DEV__||t.__RSC_DEV__?t.__VERYFRONT_DEBUG__||t.__RSC_DEBUG__?0:1:2}var x=nt(),p=new E("RSC",x),Nr=new E("PREFETCH",x),Ar=new E("HYDRATE",x),Dr=new E("VERYFRONT",x);function O(t,e){let o=e==="root"?y:`rsc-slot-${e}`,n=t.getElementById(o);if(n)return n;let s=t.createElement("div");return s.id=o,t.body.appendChild(s),s}function st(t,e){if(e.type!=="slot")return;let o=O(t,e.id);o.innerHTML=_(String(e.html??""))}function $(t,e){let o=e.split(`\n`),n=o.pop()??"";for(let s of o){let c=s.trim();if(!c)continue;let l;try{l=JSON.parse(c)}catch(g){p.debug("[client-dom] malformed NDJSON line",{line:c,error:g instanceof Error?g.message:String(g)});continue}if(!l||typeof l!="object")continue;let u=l;if(u.type==="slot"){st(t,u);try{ct(t,u.id||"root")}catch(g){p.debug("[client-dom] hydration optional failed",g)}}}return n}function it(t){return new Promise((e,o)=>{let n=()=>o(new DOMException("aborted","AbortError"));if(t.aborted){n();return}t.addEventListener("abort",n,{once:!0})})}async function k(t,e=document,o){let n="body"in t?t:null,s=n?.body??t;if(!s)return;let c=s.getReader(),l=new TextDecoder,u="",g=!1;try{for(;;){if(o?.aborted)throw new DOMException("aborted","AbortError");let a=c.read(),{done:h,value:j}=o?await Promise.race([a,it(o)]):await a;if(h){g=!0;break}u+=l.decode(j,{stream:!0}),u=$(e,u)}u&&$(e,`${u}\n`)}catch(a){throw a instanceof Error&&a.name==="AbortError"||p.debug("[client-dom] consumeNdjsonStream error",a),a}finally{try{await c.cancel()}catch(a){g||p.debug("[client-dom] reader.cancel failed",a)}try{c.releaseLock()}catch(a){p.debug("[client-dom] reader.releaseLock failed",a)}if(typeof s.cancel=="function")try{await s.cancel()}catch(a){p.debug("[client-dom] stream.cancel failed",a)}if(typeof n?.body?.cancel=="function")try{await n.body.cancel()}catch(a){p.debug("[client-dom] response.body.cancel failed",a)}}}function at(t,e){let o=O(t,e),n=[],s=c=>{let l=c;l.dataset?.clientRef&&n.push(l);for(let u of c.children)s(u)};return s(o),n}function ct(t,e){let o=at(t,e);for(let n of o){let s=n.dataset?.clientRef;s&&(n.dataset.hydrated="true",p.debug("[client-dom] marked for hydration",s))}}async function ut(){let t=F(document),[e,o]=await Promise.all([import(t.react),import(t.reactDomClient)]);return{React:e,ReactDOM:o}}var lt=new Set(["SCRIPT","STYLE","NOSCRIPT","TEMPLATE"]);function G(t){let e=t.getAttribute("style")??"";return t.hasAttribute("data-veryfront-head")||t.hasAttribute("hidden")||/(?:^|;)\\s*display\\s*:\\s*none(?:\\s*;|$)/i.test(e)||lt.has(t.tagName.toUpperCase())}function gt(t,e){return t.find(o=>o.tagName.toUpperCase()==="DIV"&&!!o.getAttribute("class")?.trim()&&!G(o))??t.find(o=>!G(o))??e}function dt(t,e){return e?.pagePath?!1:!!t.getElementById(y)}async function pt(t){try{let e=await fetch(m+"stream"+t);if(!e.ok||!e.body)return!1;let o=new AbortController;return addEventListener("pagehide",()=>o.abort(),{once:!0}),await k(e,document,o.signal),!0}catch(e){return console.debug?.("[RSC] tryStream failed",e),!1}}async function T(){try{(await import(m+"hydrate.js")).bootHydration?.()}catch(t){console.debug?.("[RSC] hydrate import failed",t)}}async function Rt(t,e){try{let{React:o,ReactDOM:n}=await ut(),s=w({strategy:e,rel:t});if(!s)return!1;console.debug?.("[RSC] Loading component from:",s);let l=(await import(s)).default;if(typeof l!="function")return console.debug?.("[RSC] Page component is not a function"),!1;let u=gt(Array.from(document.body.children),document.body);return n.hydrateRoot(u,o.createElement(l,{}),{identifierPrefix:"vf",onRecoverableError:()=>{}}),console.debug?.("[RSC] Page component hydrated successfully"),!0}catch(o){return console.error("[RSC] Page hydration failed",o),!1}}async function mt(t){try{let e=await fetch(m+"payload"+t);if(!e.ok)return!1;let o=await e.json();if(o?.slots){for(let[n,s]of Object.entries(o.slots))O(document,n).innerHTML=_(String(s||""));return!0}return O(document,y).innerHTML=_(String(o?.html||"")),!0}catch(e){return console.debug?.("[RSC] payload fetch failed",e),!1}}async function Et(){try{let t=globalThis.window?.location.search??"",e=P(document),o=e?.pagePath,n=V(e);if(o){console.debug?.("[RSC] Found page component in hydration data:",o),await Rt(o,n)&&console.debug?.("[RSC] Client component hydrated successfully");return}if(!dt(document,e))return;if(await pt(t)){await T();return}if(await mt(t)){await T();return}await T()}catch(t){console.error("[RSC] boot failed",t)}}if(typeof document<"u"){let t=()=>{Et()};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",t,{once:!0}):t()}export{Et as boot,gt as selectHydrationRoot,dt as shouldAttemptRSCTransport};\n';
|
|
9
|
+
export const CLIENT_DOM_BUNDLE = 'var N=Object.defineProperty;var A=(r,t,o)=>t in r?N(r,t,{enumerable:!0,configurable:!0,writable:!0,value:o}):r[t]=o;var u=(r,t,o)=>A(r,typeof t!="symbol"?t+"":t,o);function e(r){return{...r,create(t){return new f(t?.message||t?.detail||r.title,{slug:r.slug,category:r.category,status:t?.status??r.status,title:r.title,suggestion:r.suggestion,detail:t?.detail,cause:t?.cause,instance:t?.instance,context:t?.context})}}}var f=class extends Error{constructor(o,n){super(o);u(this,"slug");u(this,"category");u(this,"status");u(this,"title");u(this,"suggestion");u(this,"detail");u(this,"cause");u(this,"instance");u(this,"context");this.name="VeryfrontError",this.slug=n.slug,this.category=n.category,this.status=n.status,this.title=n.title,this.suggestion=n.suggestion,this.detail=n.detail,this.cause=n.cause,this.instance=n.instance,this.context=n.context}toRFC9457(){return{type:`https://veryfront.com/docs/errors/${this.slug}`,title:this.title,status:this.status,detail:this.detail,instance:this.instance,category:this.category,suggestion:this.suggestion,cause:typeof this.cause=="string"?this.cause:void 0}}getDocsUrl(){return`https://veryfront.com/docs/errors/${this.slug}`}};var z=e({slug:"config-not-found",category:"CONFIG",status:404,title:"Configuration file not found",suggestion:"Run \'vf init\' to create a configuration file"}),W=e({slug:"config-invalid",category:"CONFIG",status:400,title:"Invalid configuration format",suggestion:"Check your veryfront.config.ts for syntax errors"}),X=e({slug:"config-parse-error",category:"CONFIG",status:400,title:"Failed to parse configuration",suggestion:"Ensure your configuration file is valid TypeScript/JSON"}),J=e({slug:"config-validation-error",category:"CONFIG",status:422,title:"Configuration validation failed",suggestion:"Check the configuration against the schema requirements"}),K=e({slug:"config-type-error",category:"CONFIG",status:400,title:"Configuration type mismatch",suggestion:"Ensure configuration values match expected types"}),Z=e({slug:"import-map-invalid",category:"CONFIG",status:400,title:"Invalid import map configuration",suggestion:"Check your import map syntax and paths"}),Q=e({slug:"cors-config-invalid",category:"CONFIG",status:400,title:"Invalid CORS configuration",suggestion:"Review CORS settings in your configuration"}),ee=e({slug:"config-validation-failed",category:"CONFIG",status:400,title:"Configuration validation failed",suggestion:"Check configuration values against requirements"}),te=e({slug:"build-failed",category:"BUILD",status:500,title:"Build process failed",suggestion:"Check the build output for specific errors"}),re=e({slug:"bundle-error",category:"BUILD",status:500,title:"Bundle generation failed",suggestion:"Review bundler output for details"}),oe=e({slug:"typescript-error",category:"BUILD",status:500,title:"TypeScript compilation error",suggestion:"Fix TypeScript errors shown in the output"}),se=e({slug:"mdx-compile-error",category:"BUILD",status:500,title:"MDX compilation failed",suggestion:"Check your MDX file syntax"}),ne=e({slug:"asset-optimization-error",category:"BUILD",status:500,title:"Asset optimization failed",suggestion:"Check asset file formats and paths"}),ie=e({slug:"ssg-generation-error",category:"BUILD",status:500,title:"Static site generation failed",suggestion:"Review SSG configuration and data fetching"}),ae=e({slug:"sourcemap-error",category:"BUILD",status:500,title:"Source map generation failed",suggestion:"Check source map configuration"}),ce=e({slug:"compilation-error",category:"BUILD",status:500,title:"Compilation failed",suggestion:"Review compiler output for specific errors"}),le=e({slug:"hydration-mismatch",category:"RUNTIME",status:500,title:"Client/server hydration mismatch",suggestion:"Ensure server and client render the same content"}),ue=e({slug:"render-error",category:"RUNTIME",status:500,title:"Component render failed",suggestion:"Check component for runtime errors"}),ge=e({slug:"component-error",category:"RUNTIME",status:500,title:"Component execution error",suggestion:"Review component logic and props"}),de=e({slug:"layout-not-found",category:"RUNTIME",status:404,title:"Layout component not found",suggestion:"Ensure layout file exists at the expected path"}),pe=e({slug:"page-not-found",category:"RUNTIME",status:404,title:"Page component not found",suggestion:"Check that the page file exists in the routes directory"}),Ee=e({slug:"api-error",category:"RUNTIME",status:500,title:"API route handler error",suggestion:"Review API route handler for errors"}),Re=e({slug:"middleware-error",category:"RUNTIME",status:500,title:"Middleware execution error",suggestion:"Check middleware function for errors"}),fe=e({slug:"route-conflict",category:"ROUTE",status:409,title:"Conflicting route definitions",suggestion:"Rename or reorganize conflicting route files"}),ye=e({slug:"invalid-route-file",category:"ROUTE",status:400,title:"Invalid route file structure",suggestion:"Ensure route file exports required functions"}),me=e({slug:"route-handler-invalid",category:"ROUTE",status:400,title:"Invalid route handler export",suggestion:"Export a valid handler function from the route file"}),_e=e({slug:"dynamic-route-error",category:"ROUTE",status:500,title:"Dynamic route parsing failed",suggestion:"Check dynamic route segment syntax"}),Oe=e({slug:"route-params-error",category:"ROUTE",status:400,title:"Route parameters invalid",suggestion:"Validate route parameter values"}),Te=e({slug:"api-route-error",category:"ROUTE",status:500,title:"API route definition error",suggestion:"Review API route configuration"}),he=e({slug:"module-not-found",category:"MODULE",status:404,title:"Module could not be resolved",suggestion:"Check the import path and ensure the module is installed"}),Ie=e({slug:"import-resolution-error",category:"MODULE",status:500,title:"Import path resolution failed",suggestion:"Verify import paths and module configuration"}),ve=e({slug:"circular-dependency",category:"MODULE",status:500,title:"Circular dependency detected",suggestion:"Refactor imports to break the circular dependency"}),xe=e({slug:"invalid-import",category:"MODULE",status:400,title:"Invalid import statement",suggestion:"Fix import syntax or path"}),Ne=e({slug:"dependency-missing",category:"MODULE",status:404,title:"Required dependency not installed",suggestion:"Install the missing dependency with your package manager"}),Ae=e({slug:"version-mismatch",category:"MODULE",status:409,title:"Dependency version mismatch",suggestion:"Update dependencies to compatible versions"}),Ce=e({slug:"port-in-use",category:"SERVER",status:409,title:"Server port already in use",suggestion:"Use a different port or stop the process using this port"}),Se=e({slug:"server-start-error",category:"SERVER",status:500,title:"Server failed to start",suggestion:"Check server configuration and port availability"}),De=e({slug:"cache-error",category:"SERVER",status:500,title:"Cache operation failed",suggestion:"Clear the cache and try again"}),Le=e({slug:"file-watch-error",category:"SERVER",status:500,title:"File watcher error",suggestion:"Restart the development server"}),Ue=e({slug:"request-error",category:"SERVER",status:500,title:"HTTP request handling error",suggestion:"Check request handler and middleware"}),be=e({slug:"service-overloaded",category:"SERVER",status:503,title:"Service overloaded",suggestion:"Reduce load or scale up resources"}),Me=e({slug:"cache-path-mismatch",category:"SERVER",status:500,title:"Cache path mismatch",suggestion:"Clear the cache directory and rebuild"}),Pe=e({slug:"network-error",category:"SERVER",status:502,title:"Network operation failed",suggestion:"Check network connectivity and retry"}),Ve=e({slug:"api-client-error",category:"SERVER",status:500,title:"API client request failed",suggestion:"Check API connectivity and authentication"}),Fe=e({slug:"token-storage-error",category:"SERVER",status:500,title:"Token storage operation failed",suggestion:"Check token storage backend and credentials"}),ke=e({slug:"cache-invariant-violation",category:"SERVER",status:500,title:"Cache path invariant violated",suggestion:"Clear the cache and rebuild"}),we=e({slug:"release-not-found",category:"SERVER",status:404,title:"No active release found",suggestion:"Deploy the project to create a release for this environment"}),Ge=e({slug:"fallback-exhausted",category:"SERVER",status:500,title:"Primary and fallback operations both failed",suggestion:"Check service availability and connectivity"}),He=e({slug:"client-boundary-violation",category:"BOUNDARY",status:400,title:"Client boundary rule violation",suggestion:"Add \'use client\' directive or move code to a client component"}),$e=e({slug:"server-only-in-client",category:"BOUNDARY",status:400,title:"Server-only code in client component",suggestion:"Move server-only code to a server component"}),Be=e({slug:"client-only-in-server",category:"BOUNDARY",status:400,title:"Client-only code in server component",suggestion:"Move client-only code to a client component"}),Ye=e({slug:"invalid-use-client",category:"BOUNDARY",status:400,title:"Invalid \'use client\' directive",suggestion:"Place \'use client\' at the top of the file"}),je=e({slug:"invalid-use-server",category:"BOUNDARY",status:400,title:"Invalid \'use server\' directive",suggestion:"Place \'use server\' at the top of the file or function"}),qe=e({slug:"rsc-payload-error",category:"BOUNDARY",status:500,title:"RSC payload serialization error",suggestion:"Ensure props are serializable (no functions, symbols, etc.)"}),ze=e({slug:"hmr-error",category:"DEV",status:500,title:"Hot module replacement error",suggestion:"Restart the development server"}),We=e({slug:"dev-server-error",category:"DEV",status:500,title:"Development server error",suggestion:"Check the dev server logs and restart"}),Xe=e({slug:"fast-refresh-error",category:"DEV",status:500,title:"Fast refresh failed",suggestion:"Save the file again or restart the dev server"}),Je=e({slug:"error-overlay-error",category:"DEV",status:500,title:"Error overlay failed",suggestion:"Check browser console for details"}),Ke=e({slug:"source-map-error",category:"DEV",status:500,title:"Source map loading error",suggestion:"Rebuild or clear cache"}),Ze=e({slug:"deployment-error",category:"DEPLOY",status:500,title:"Deployment process failed",suggestion:"Check deployment logs for details"}),Qe=e({slug:"platform-error",category:"DEPLOY",status:500,title:"Platform-specific error",suggestion:"Check platform documentation and requirements"}),et=e({slug:"env-var-missing",category:"DEPLOY",status:500,title:"Required environment variable missing",suggestion:"Set the required environment variable"}),tt=e({slug:"production-build-required",category:"DEPLOY",status:400,title:"Production build required",suggestion:"Run \'vf build\' before deploying"}),rt=e({slug:"agent-error",category:"AGENT",status:500,title:"Agent operation error",suggestion:"Check agent configuration and logs"}),ot=e({slug:"agent-not-found",category:"AGENT",status:404,title:"Agent not found",suggestion:"Verify the agent ID exists"}),st=e({slug:"agent-timeout",category:"AGENT",status:408,title:"Agent operation timed out",suggestion:"Increase timeout or simplify the request"}),nt=e({slug:"agent-intent-error",category:"AGENT",status:400,title:"Agent intent parsing error",suggestion:"Rephrase the request more clearly"}),it=e({slug:"orchestration-error",category:"AGENT",status:500,title:"Multi-agent orchestration error",suggestion:"Check agent coordination logic"}),at=e({slug:"cost-limit-exceeded",category:"AGENT",status:429,title:"Cost limit exceeded",suggestion:"Wait for the budget period to reset or increase the limit"}),ct=e({slug:"unknown-error",category:"GENERAL",status:500,title:"Unknown/unclassified error",suggestion:"Check logs for more details"}),lt=e({slug:"permission-denied",category:"GENERAL",status:403,title:"File/resource permission denied",suggestion:"Check file permissions and access rights"}),ut=e({slug:"file-not-found",category:"GENERAL",status:404,title:"File not found",suggestion:"Verify the file path exists"}),gt=e({slug:"resource-not-found",category:"GENERAL",status:404,title:"Requested resource not found",suggestion:"Verify the referenced resource ID or name exists"}),dt=e({slug:"invalid-argument",category:"GENERAL",status:400,title:"Invalid function argument",suggestion:"Check argument types and values"}),pt=e({slug:"timeout-error",category:"GENERAL",status:408,title:"Operation timed out",suggestion:"Increase timeout or optimize the operation"}),Et=e({slug:"initialization-error",category:"GENERAL",status:500,title:"Initialization failed",suggestion:"Check initialization requirements and dependencies"}),Rt=e({slug:"not-supported",category:"GENERAL",status:501,title:"Feature not supported",suggestion:"Check documentation for supported features"}),m=e({slug:"security-violation",category:"GENERAL",status:403,title:"Security violation detected",suggestion:"Check for path traversal or unauthorized access attempts"}),ft=e({slug:"input-validation-failed",category:"GENERAL",status:400,title:"Input validation failed",suggestion:"Check request input against validation rules"});var C=[{pattern:/<script[^>]*>[\\s\\S]*?<\\/script>/gi,name:"inline script"},{pattern:/javascript:/gi,name:"javascript: URL"},{pattern:/\\bon\\w+\\s*=/gi,name:"event handler attribute"},{pattern:/data:\\s*text\\/html/gi,name:"data: HTML URL"}];function S(){let r=globalThis;return r.__VERYFRONT_DEV__===!0||r.Deno?.env?.get?.("VERYFRONT_ENV")==="development"}function _(r,t={}){let{strict:o=!1,warn:n=!0}=t;for(let{pattern:i,name:c}of C)if(i.lastIndex=0,!!i.test(r)&&(n&&console.warn(`[Security] Suspicious ${c} detected in server HTML`),o||!S()))throw m.create({detail:`Potentially unsafe HTML: ${c} detected`});return r}var E=class{constructor(t,o){this.prefix=t;this.level=o}log(t,o,n,...i){this.level>t||o?.(n,...i)}debug(t,...o){this.log(0,console.debug,`[${this.prefix}] DEBUG: ${t}`,...o)}info(t,...o){this.log(1,console.log,`[${this.prefix}] ${t}`,...o)}warn(t,...o){this.log(2,console.warn,`[${this.prefix}] WARN: ${t}`,...o)}error(t,...o){this.log(3,console.error,`[${this.prefix}] ERROR: ${t}`,...o)}};function D(){if(typeof window>"u")return 2;let r=globalThis;return r.__VERYFRONT_DEV__||r.__RSC_DEV__?r.__VERYFRONT_DEBUG__||r.__RSC_DEBUG__?0:1:2}var R=D(),d=new E("RSC",R),ht=new E("PREFETCH",R),It=new E("HYDRATE",R),vt=new E("VERYFRONT",R);var s="/_veryfront",y={RSC:`${s}/rsc/`,FS:`${s}/fs/`,MODULES:`${s}/modules/`,PAGES:`${s}/pages/`,DATA:`${s}/data/`,LIB:`${s}/lib/`,CHUNKS:`${s}/chunks/`,CLIENT:`${s}/client/`},O={HMR_RUNTIME:`${s}/hmr-runtime.js`,HMR:`${s}/hmr.js`,HYDRATE:`${s}/hydrate.js`,ERROR_OVERLAY:`${s}/error-overlay.js`,DEV_LOADER:`${s}/dev-loader.js`,CLIENT_LOG:`${s}/log`,CLIENT_JS:`${s}/client.js`,ROUTER_JS:`${s}/router.js`,PREFETCH_JS:`${s}/prefetch.js`,MANIFEST_JSON:`${s}/manifest.json`,APP_JS:`${s}/app.js`,RSC_CLIENT:`${s}/rsc/client.js`,RSC_MANIFEST:`${s}/rsc/manifest`,RSC_STREAM:`${s}/rsc/stream`,RSC_PAYLOAD:`${s}/rsc/payload`,RSC_RENDER:`${s}/rsc/render`,RSC_PAGE:`${s}/rsc/page`,RSC_MODULE:`${s}/rsc/module`,RSC_DOM:`${s}/rsc/dom.js`,RSC_HYDRATOR:`${s}/rsc/hydrator.js`,RSC_HYDRATE_CLIENT:`${s}/rsc/hydrate-client.js`,LIB_CHAT_REACT:`${s}/lib/chat/react.js`,LIB_CHAT_COMPONENTS:`${s}/lib/chat/components.js`,LIB_CHAT_PRIMITIVES:`${s}/lib/chat/primitives.js`};var U={ROOT:".veryfront",CACHE:".veryfront/cache",KV:".veryfront/kv",LOGS:".veryfront/logs",TMP:".veryfront/tmp"},St=U.CACHE;var Dt={HMR_RUNTIME:O.HMR_RUNTIME,ERROR_OVERLAY:O.ERROR_OVERLAY};var Mt=y.RSC,Pt=y.FS;var T="rsc-root";function I(r,t){let o=t==="root"?T:`rsc-slot-${t}`,n=r.getElementById(o);if(n)return n;let i=r.createElement("div");return i.id=o,r.body.appendChild(i),i}function b(r,t){if(t.type!=="slot")return;let o=I(r,t.id);o.innerHTML=_(String(t.html??""))}function h(r,t){let o=t.split(`\n`),n=o.pop()??"";for(let i of o){let c=i.trim();if(!c)continue;let g;try{g=JSON.parse(c)}catch(p){d.debug("[client-dom] malformed NDJSON line",{line:c,error:p instanceof Error?p.message:String(p)});continue}if(!g||typeof g!="object")continue;let l=g;if(l.type==="slot"){b(r,l);try{V(r,l.id||"root")}catch(p){d.debug("[client-dom] hydration optional failed",p)}}}return n}function M(r){return new Promise((t,o)=>{let n=()=>o(new DOMException("aborted","AbortError"));if(r.aborted){n();return}r.addEventListener("abort",n,{once:!0})})}async function Gt(r,t=document,o){let n="body"in r?r:null,i=n?.body??r;if(!i)return;let c=i.getReader(),g=new TextDecoder,l="",p=!1;try{for(;;){if(o?.aborted)throw new DOMException("aborted","AbortError");let a=c.read(),{done:v,value:x}=o?await Promise.race([a,M(o)]):await a;if(v){p=!0;break}l+=g.decode(x,{stream:!0}),l=h(t,l)}l&&h(t,`${l}\n`)}catch(a){throw a instanceof Error&&a.name==="AbortError"||d.debug("[client-dom] consumeNdjsonStream error",a),a}finally{try{await c.cancel()}catch(a){p||d.debug("[client-dom] reader.cancel failed",a)}try{c.releaseLock()}catch(a){d.debug("[client-dom] reader.releaseLock failed",a)}if(typeof i.cancel=="function")try{await i.cancel()}catch(a){d.debug("[client-dom] stream.cancel failed",a)}if(typeof n?.body?.cancel=="function")try{await n.body.cancel()}catch(a){d.debug("[client-dom] response.body.cancel failed",a)}}}function P(r,t){let o=I(r,t),n=[],i=c=>{let g=c;g.dataset?.clientRef&&n.push(g);for(let l of c.children)i(l)};return i(o),n}function V(r,t){let o=P(r,t);for(let n of o){let i=n.dataset?.clientRef;i&&(n.dataset.hydrated="true",d.debug("[client-dom] marked for hydration",i))}}export{Gt as consumeNdjsonStream,I as getContainer};\n';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"bridge-bundle.generated.d.ts","sourceRoot":"","sources":["../../../../src/src/studio/bridge/bridge-bundle.generated.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,eAAO,MAAM,oBAAoB,EAAE,
|
|
1
|
+
{"version":3,"file":"bridge-bundle.generated.d.ts","sourceRoot":"","sources":["../../../../src/src/studio/bridge/bridge-bundle.generated.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,eAAO,MAAM,oBAAoB,EAAE,MAAszpD,CAAC"}
|