@flanksource/clicky-ui 0.3.25 → 0.3.27
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/NOTICE.md +1 -0
- package/dist/ai.cjs +4 -0
- package/dist/ai.cjs.map +1 -1
- package/dist/ai.js +6 -2
- package/dist/ai.js.map +1 -1
- package/dist/chat.cjs +8 -0
- package/dist/chat.cjs.map +1 -1
- package/dist/chat.js +9 -1
- package/dist/chat.js.map +1 -1
- package/dist/comments/CommentCard.cjs +89 -14
- package/dist/comments/CommentCard.cjs.map +1 -1
- package/dist/comments/CommentCard.d.ts.map +1 -1
- package/dist/comments/CommentCard.js +90 -15
- package/dist/comments/CommentCard.js.map +1 -1
- package/dist/comments/CommentComposer.cjs +25 -2
- package/dist/comments/CommentComposer.cjs.map +1 -1
- package/dist/comments/CommentComposer.d.ts.map +1 -1
- package/dist/comments/CommentComposer.js +25 -2
- package/dist/comments/CommentComposer.js.map +1 -1
- package/dist/comments/CommentProvider.cjs +21 -14
- package/dist/comments/CommentProvider.cjs.map +1 -1
- package/dist/comments/CommentProvider.d.ts +1 -1
- package/dist/comments/CommentProvider.d.ts.map +1 -1
- package/dist/comments/CommentProvider.js +21 -14
- package/dist/comments/CommentProvider.js.map +1 -1
- package/dist/comments/CommentSidePanel.cjs +1 -1
- package/dist/comments/CommentSidePanel.cjs.map +1 -1
- package/dist/comments/CommentSidePanel.js +1 -1
- package/dist/comments/CommentSidePanel.js.map +1 -1
- package/dist/comments/comment-types.cjs.map +1 -1
- package/dist/comments/comment-types.d.ts +6 -0
- package/dist/comments/comment-types.d.ts.map +1 -1
- package/dist/comments/comment-types.js.map +1 -1
- package/dist/components/DimensionField.cjs +56 -0
- package/dist/components/DimensionField.cjs.map +1 -0
- package/dist/components/DimensionField.d.ts +17 -0
- package/dist/components/DimensionField.d.ts.map +1 -0
- package/dist/components/DimensionField.js +56 -0
- package/dist/components/DimensionField.js.map +1 -0
- package/dist/components.cjs +4 -0
- package/dist/components.cjs.map +1 -1
- package/dist/components.d.ts +2 -0
- package/dist/components.d.ts.map +1 -1
- package/dist/components.js +4 -0
- package/dist/components.js.map +1 -1
- package/dist/data/Clicky.cjs +4 -5
- package/dist/data/Clicky.cjs.map +1 -1
- package/dist/data/Clicky.d.ts.map +1 -1
- package/dist/data/Clicky.js +4 -5
- package/dist/data/Clicky.js.map +1 -1
- package/dist/data/FixtureEditor/fixture-frontmatter.cjs +4 -0
- package/dist/data/FixtureEditor/fixture-frontmatter.cjs.map +1 -1
- package/dist/data/FixtureEditor/fixture-frontmatter.d.ts.map +1 -1
- package/dist/data/FixtureEditor/fixture-frontmatter.js +4 -0
- package/dist/data/FixtureEditor/fixture-frontmatter.js.map +1 -1
- package/dist/data/TaskExecDetails.cjs +8 -3
- package/dist/data/TaskExecDetails.cjs.map +1 -1
- package/dist/data/TaskExecDetails.d.ts +4 -0
- package/dist/data/TaskExecDetails.d.ts.map +1 -1
- package/dist/data/TaskExecDetails.js +9 -4
- package/dist/data/TaskExecDetails.js.map +1 -1
- package/dist/data/TaskManagerButton.cjs +101 -7
- package/dist/data/TaskManagerButton.cjs.map +1 -1
- package/dist/data/TaskManagerButton.d.ts +6 -1
- package/dist/data/TaskManagerButton.d.ts.map +1 -1
- package/dist/data/TaskManagerButton.js +103 -9
- package/dist/data/TaskManagerButton.js.map +1 -1
- package/dist/data/TaskProcessDetails.cjs +2 -0
- package/dist/data/TaskProcessDetails.cjs.map +1 -1
- package/dist/data/TaskProcessDetails.d.ts.map +1 -1
- package/dist/data/TaskProcessDetails.js +2 -0
- package/dist/data/TaskProcessDetails.js.map +1 -1
- package/dist/data/TaskProgress.cjs +14 -4
- package/dist/data/TaskProgress.cjs.map +1 -1
- package/dist/data/TaskProgress.js +14 -4
- package/dist/data/TaskProgress.js.map +1 -1
- package/dist/data/TaskSnapshot.cjs.map +1 -1
- package/dist/data/TaskSnapshot.d.ts +1 -0
- package/dist/data/TaskSnapshot.d.ts.map +1 -1
- package/dist/data/TaskSnapshot.js.map +1 -1
- package/dist/data/ai/ChatWindow.cjs +18 -23
- package/dist/data/ai/ChatWindow.cjs.map +1 -1
- package/dist/data/ai/ChatWindow.d.ts +1 -1
- package/dist/data/ai/ChatWindow.d.ts.map +1 -1
- package/dist/data/ai/ChatWindow.js +19 -24
- package/dist/data/ai/ChatWindow.js.map +1 -1
- package/dist/data/ai/ChatWindow.preferences.cjs +12 -21
- package/dist/data/ai/ChatWindow.preferences.cjs.map +1 -1
- package/dist/data/ai/ChatWindow.preferences.d.ts +3 -2
- package/dist/data/ai/ChatWindow.preferences.d.ts.map +1 -1
- package/dist/data/ai/ChatWindow.preferences.js +12 -21
- package/dist/data/ai/ChatWindow.preferences.js.map +1 -1
- package/dist/data/ai/ChatWindow.tool-catalog.cjs +21 -38
- package/dist/data/ai/ChatWindow.tool-catalog.cjs.map +1 -1
- package/dist/data/ai/ChatWindow.tool-catalog.d.ts +5 -5
- package/dist/data/ai/ChatWindow.tool-catalog.d.ts.map +1 -1
- package/dist/data/ai/ChatWindow.tool-catalog.js +21 -38
- package/dist/data/ai/ChatWindow.tool-catalog.js.map +1 -1
- package/dist/data/ai/ChatWindow.types.d.ts +2 -2
- package/dist/data/ai/ChatWindow.types.d.ts.map +1 -1
- package/dist/data/ai/ChatWindowManager.cjs +2 -2
- package/dist/data/ai/ChatWindowManager.cjs.map +1 -1
- package/dist/data/ai/ChatWindowManager.js +2 -2
- package/dist/data/ai/ChatWindowManager.js.map +1 -1
- package/dist/data/ai/ChatWindowRequestBody.cjs +4 -2
- package/dist/data/ai/ChatWindowRequestBody.cjs.map +1 -1
- package/dist/data/ai/ChatWindowRequestBody.d.ts +15 -3
- package/dist/data/ai/ChatWindowRequestBody.d.ts.map +1 -1
- package/dist/data/ai/ChatWindowRequestBody.js +4 -2
- package/dist/data/ai/ChatWindowRequestBody.js.map +1 -1
- package/dist/data/ai/PromptRunEditor/index.cjs +2 -3
- package/dist/data/ai/PromptRunEditor/index.cjs.map +1 -1
- package/dist/data/ai/PromptRunEditor/index.d.ts.map +1 -1
- package/dist/data/ai/PromptRunEditor/index.js +2 -3
- package/dist/data/ai/PromptRunEditor/index.js.map +1 -1
- package/dist/data/ai/PromptRunEditor/model.cjs +1 -0
- package/dist/data/ai/PromptRunEditor/model.cjs.map +1 -1
- package/dist/data/ai/PromptRunEditor/model.d.ts +1 -1
- package/dist/data/ai/PromptRunEditor/model.d.ts.map +1 -1
- package/dist/data/ai/PromptRunEditor/model.js +1 -0
- package/dist/data/ai/PromptRunEditor/model.js.map +1 -1
- package/dist/data/ai/RuntimeModePicker.cjs +11 -9
- package/dist/data/ai/RuntimeModePicker.cjs.map +1 -1
- package/dist/data/ai/RuntimeModePicker.d.ts.map +1 -1
- package/dist/data/ai/RuntimeModePicker.js +12 -10
- package/dist/data/ai/RuntimeModePicker.js.map +1 -1
- package/dist/data/ai/SpecRuntimeEditor/ModelSection.cjs +5 -0
- package/dist/data/ai/SpecRuntimeEditor/ModelSection.cjs.map +1 -1
- package/dist/data/ai/SpecRuntimeEditor/ModelSection.d.ts.map +1 -1
- package/dist/data/ai/SpecRuntimeEditor/ModelSection.js +5 -0
- package/dist/data/ai/SpecRuntimeEditor/ModelSection.js.map +1 -1
- package/dist/data/ai/SpecRuntimeEditor.model.cjs +4 -0
- package/dist/data/ai/SpecRuntimeEditor.model.cjs.map +1 -1
- package/dist/data/ai/SpecRuntimeEditor.model.d.ts +2 -0
- package/dist/data/ai/SpecRuntimeEditor.model.d.ts.map +1 -1
- package/dist/data/ai/SpecRuntimeEditor.model.js +4 -0
- package/dist/data/ai/SpecRuntimeEditor.model.js.map +1 -1
- package/dist/data/ai/ToolPreferences.cjs +5 -5
- package/dist/data/ai/ToolPreferences.cjs.map +1 -1
- package/dist/data/ai/ToolPreferences.d.ts +6 -5
- package/dist/data/ai/ToolPreferences.d.ts.map +1 -1
- package/dist/data/ai/ToolPreferences.js +5 -5
- package/dist/data/ai/ToolPreferences.js.map +1 -1
- package/dist/data/ai/ToolPreferences.model.cjs +61 -37
- package/dist/data/ai/ToolPreferences.model.cjs.map +1 -1
- package/dist/data/ai/ToolPreferences.model.d.ts +32 -13
- package/dist/data/ai/ToolPreferences.model.d.ts.map +1 -1
- package/dist/data/ai/ToolPreferences.model.js +62 -38
- package/dist/data/ai/ToolPreferences.model.js.map +1 -1
- package/dist/data/ai/ToolPreferencesList.cjs +17 -20
- package/dist/data/ai/ToolPreferencesList.cjs.map +1 -1
- package/dist/data/ai/ToolPreferencesList.d.ts +16 -7
- package/dist/data/ai/ToolPreferencesList.d.ts.map +1 -1
- package/dist/data/ai/ToolPreferencesList.js +18 -21
- package/dist/data/ai/ToolPreferencesList.js.map +1 -1
- package/dist/data/ai/chat-window-context.cjs +1 -1
- package/dist/data/ai/chat-window-context.cjs.map +1 -1
- package/dist/data/ai/chat-window-context.d.ts +7 -7
- package/dist/data/ai/chat-window-context.d.ts.map +1 -1
- package/dist/data/ai/chat-window-context.js +1 -1
- package/dist/data/ai/chat-window-context.js.map +1 -1
- package/dist/data/ai/index.d.ts +3 -1
- package/dist/data/ai/index.d.ts.map +1 -1
- package/dist/data/chat/Chat.cjs +4 -2
- package/dist/data/chat/Chat.cjs.map +1 -1
- package/dist/data/chat/Chat.d.ts.map +1 -1
- package/dist/data/chat/Chat.js +4 -2
- package/dist/data/chat/Chat.js.map +1 -1
- package/dist/data/chat/Chat.runtime.cjs +14 -3
- package/dist/data/chat/Chat.runtime.cjs.map +1 -1
- package/dist/data/chat/Chat.runtime.d.ts.map +1 -1
- package/dist/data/chat/Chat.runtime.js +15 -4
- package/dist/data/chat/Chat.runtime.js.map +1 -1
- package/dist/data/chat/clickyOperationsToTools.cjs +2 -1
- package/dist/data/chat/clickyOperationsToTools.cjs.map +1 -1
- package/dist/data/chat/clickyOperationsToTools.d.ts.map +1 -1
- package/dist/data/chat/clickyOperationsToTools.js +2 -1
- package/dist/data/chat/clickyOperationsToTools.js.map +1 -1
- package/dist/data/chat/index.d.ts +2 -1
- package/dist/data/chat/index.d.ts.map +1 -1
- package/dist/data/chat/tool-policy.cjs +132 -0
- package/dist/data/chat/tool-policy.cjs.map +1 -0
- package/dist/data/chat/tool-policy.d.ts +81 -0
- package/dist/data/chat/tool-policy.d.ts.map +1 -0
- package/dist/data/chat/tool-policy.js +132 -0
- package/dist/data/chat/tool-policy.js.map +1 -0
- package/dist/data/chat/types.cjs +20 -0
- package/dist/data/chat/types.cjs.map +1 -1
- package/dist/data/chat/types.d.ts +22 -2
- package/dist/data/chat/types.d.ts.map +1 -1
- package/dist/data/chat/types.js +20 -0
- package/dist/data/chat/types.js.map +1 -1
- package/dist/data/debugConsoleSignal.cjs +64 -0
- package/dist/data/debugConsoleSignal.cjs.map +1 -0
- package/dist/data/debugConsoleSignal.d.ts +83 -0
- package/dist/data/debugConsoleSignal.d.ts.map +1 -0
- package/dist/data/debugConsoleSignal.js +64 -0
- package/dist/data/debugConsoleSignal.js.map +1 -0
- package/dist/data/har/HarPanel.cjs +20 -14
- package/dist/data/har/HarPanel.cjs.map +1 -1
- package/dist/data/har/HarPanel.d.ts.map +1 -1
- package/dist/data/har/HarPanel.js +20 -14
- package/dist/data/har/HarPanel.js.map +1 -1
- package/dist/data/har/types.d.ts +18 -0
- package/dist/data/har/types.d.ts.map +1 -1
- package/dist/data/query-browser/QueryBrowser.cjs +4 -42
- package/dist/data/query-browser/QueryBrowser.cjs.map +1 -1
- package/dist/data/query-browser/QueryBrowser.d.ts.map +1 -1
- package/dist/data/query-browser/QueryBrowser.js +5 -43
- package/dist/data/query-browser/QueryBrowser.js.map +1 -1
- package/dist/data/query-browser/QueryBrowser.types.cjs.map +1 -1
- package/dist/data/query-browser/QueryBrowser.types.d.ts +0 -1
- package/dist/data/query-browser/QueryBrowser.types.d.ts.map +1 -1
- package/dist/data/query-browser/QueryBrowser.types.js.map +1 -1
- package/dist/data/runtime/RuntimeBar.cjs +26 -41
- package/dist/data/runtime/RuntimeBar.cjs.map +1 -1
- package/dist/data/runtime/RuntimeBar.d.ts.map +1 -1
- package/dist/data/runtime/RuntimeBar.js +28 -43
- package/dist/data/runtime/RuntimeBar.js.map +1 -1
- package/dist/data/runtime/RuntimeBar.model.cjs +65 -0
- package/dist/data/runtime/RuntimeBar.model.cjs.map +1 -1
- package/dist/data/runtime/RuntimeBar.model.d.ts +11 -3
- package/dist/data/runtime/RuntimeBar.model.d.ts.map +1 -1
- package/dist/data/runtime/RuntimeBar.model.js +65 -0
- package/dist/data/runtime/RuntimeBar.model.js.map +1 -1
- package/dist/data/runtime/model-capabilities.cjs +8 -5
- package/dist/data/runtime/model-capabilities.cjs.map +1 -1
- package/dist/data/runtime/model-capabilities.d.ts +6 -1
- package/dist/data/runtime/model-capabilities.d.ts.map +1 -1
- package/dist/data/runtime/model-capabilities.js +8 -5
- package/dist/data/runtime/model-capabilities.js.map +1 -1
- package/dist/data/runtime/runtime-mode.cjs +17 -0
- package/dist/data/runtime/runtime-mode.cjs.map +1 -1
- package/dist/data/runtime/runtime-mode.d.ts +6 -0
- package/dist/data/runtime/runtime-mode.d.ts.map +1 -1
- package/dist/data/runtime/runtime-mode.js +17 -0
- package/dist/data/runtime/runtime-mode.js.map +1 -1
- package/dist/data/useDebugAction.cjs +29 -0
- package/dist/data/useDebugAction.cjs.map +1 -0
- package/dist/data/useDebugAction.d.ts +16 -0
- package/dist/data/useDebugAction.d.ts.map +1 -0
- package/dist/data/useDebugAction.js +29 -0
- package/dist/data/useDebugAction.js.map +1 -0
- package/dist/data/version-info.cjs +3 -3
- package/dist/data/version-info.js +3 -3
- package/dist/data.cjs +16 -8
- package/dist/data.cjs.map +1 -1
- package/dist/data.d.ts +3 -2
- package/dist/data.d.ts.map +1 -1
- package/dist/data.js +16 -8
- package/dist/devtools/DebugConsole.cjs +138 -0
- package/dist/devtools/DebugConsole.cjs.map +1 -0
- package/dist/devtools/DebugConsole.d.ts +23 -0
- package/dist/devtools/DebugConsole.d.ts.map +1 -0
- package/dist/devtools/DebugConsole.js +138 -0
- package/dist/devtools/DebugConsole.js.map +1 -0
- package/dist/devtools/DebugConsoleButton.cjs +59 -0
- package/dist/devtools/DebugConsoleButton.cjs.map +1 -0
- package/dist/devtools/DebugConsoleButton.d.ts +20 -0
- package/dist/devtools/DebugConsoleButton.d.ts.map +1 -0
- package/dist/devtools/DebugConsoleButton.js +59 -0
- package/dist/devtools/DebugConsoleButton.js.map +1 -0
- package/dist/devtools/DebugConsoleDock.cjs +112 -0
- package/dist/devtools/DebugConsoleDock.cjs.map +1 -0
- package/dist/devtools/DebugConsoleDock.d.ts +26 -0
- package/dist/devtools/DebugConsoleDock.d.ts.map +1 -0
- package/dist/devtools/DebugConsoleDock.js +112 -0
- package/dist/devtools/DebugConsoleDock.js.map +1 -0
- package/dist/devtools/ExecutionDetail.cjs +135 -0
- package/dist/devtools/ExecutionDetail.cjs.map +1 -0
- package/dist/devtools/ExecutionDetail.d.ts +19 -0
- package/dist/devtools/ExecutionDetail.d.ts.map +1 -0
- package/dist/devtools/ExecutionDetail.js +135 -0
- package/dist/devtools/ExecutionDetail.js.map +1 -0
- package/dist/devtools/debugClient.cjs +172 -0
- package/dist/devtools/debugClient.cjs.map +1 -0
- package/dist/devtools/debugClient.d.ts +98 -0
- package/dist/devtools/debugClient.d.ts.map +1 -0
- package/dist/devtools/debugClient.js +172 -0
- package/dist/devtools/debugClient.js.map +1 -0
- package/dist/devtools/debugStore.cjs +115 -0
- package/dist/devtools/debugStore.cjs.map +1 -0
- package/dist/devtools/debugStore.d.ts +83 -0
- package/dist/devtools/debugStore.d.ts.map +1 -0
- package/dist/devtools/debugStore.js +115 -0
- package/dist/devtools/debugStore.js.map +1 -0
- package/dist/devtools/dockState.cjs +51 -0
- package/dist/devtools/dockState.cjs.map +1 -0
- package/dist/devtools/dockState.d.ts +31 -0
- package/dist/devtools/dockState.d.ts.map +1 -0
- package/dist/devtools/dockState.js +51 -0
- package/dist/devtools/dockState.js.map +1 -0
- package/dist/devtools/tabs/ConsoleTab.cjs +36 -0
- package/dist/devtools/tabs/ConsoleTab.cjs.map +1 -0
- package/dist/devtools/tabs/ConsoleTab.d.ts +19 -0
- package/dist/devtools/tabs/ConsoleTab.d.ts.map +1 -0
- package/dist/devtools/tabs/ConsoleTab.js +36 -0
- package/dist/devtools/tabs/ConsoleTab.js.map +1 -0
- package/dist/devtools/tabs/InspectionCaches.cjs +150 -0
- package/dist/devtools/tabs/InspectionCaches.cjs.map +1 -0
- package/dist/devtools/tabs/InspectionCaches.d.ts +23 -0
- package/dist/devtools/tabs/InspectionCaches.d.ts.map +1 -0
- package/dist/devtools/tabs/InspectionCaches.js +150 -0
- package/dist/devtools/tabs/InspectionCaches.js.map +1 -0
- package/dist/devtools/tabs/InspectionTab.cjs +316 -0
- package/dist/devtools/tabs/InspectionTab.cjs.map +1 -0
- package/dist/devtools/tabs/InspectionTab.d.ts +27 -0
- package/dist/devtools/tabs/InspectionTab.d.ts.map +1 -0
- package/dist/devtools/tabs/InspectionTab.js +316 -0
- package/dist/devtools/tabs/InspectionTab.js.map +1 -0
- package/dist/devtools/tabs/NetworkTab.cjs +91 -0
- package/dist/devtools/tabs/NetworkTab.cjs.map +1 -0
- package/dist/devtools/tabs/NetworkTab.d.ts +20 -0
- package/dist/devtools/tabs/NetworkTab.d.ts.map +1 -0
- package/dist/devtools/tabs/NetworkTab.js +91 -0
- package/dist/devtools/tabs/NetworkTab.js.map +1 -0
- package/dist/devtools/tabs/QueriesTab.cjs +85 -0
- package/dist/devtools/tabs/QueriesTab.cjs.map +1 -0
- package/dist/devtools/tabs/QueriesTab.d.ts +24 -0
- package/dist/devtools/tabs/QueriesTab.d.ts.map +1 -0
- package/dist/devtools/tabs/QueriesTab.js +85 -0
- package/dist/devtools/tabs/QueriesTab.js.map +1 -0
- package/dist/devtools/types.cjs +26 -0
- package/dist/devtools/types.cjs.map +1 -0
- package/dist/devtools/types.d.ts +235 -0
- package/dist/devtools/types.d.ts.map +1 -0
- package/dist/devtools/types.js +26 -0
- package/dist/devtools/types.js.map +1 -0
- package/dist/devtools/useDebugStream.cjs +46 -0
- package/dist/devtools/useDebugStream.cjs.map +1 -0
- package/dist/devtools/useDebugStream.d.ts +23 -0
- package/dist/devtools/useDebugStream.d.ts.map +1 -0
- package/dist/devtools/useDebugStream.js +46 -0
- package/dist/devtools/useDebugStream.js.map +1 -0
- package/dist/devtools.cjs +51 -0
- package/dist/devtools.cjs.map +1 -0
- package/dist/devtools.d.ts +37 -0
- package/dist/devtools.d.ts.map +1 -0
- package/dist/devtools.js +51 -0
- package/dist/devtools.js.map +1 -0
- package/dist/icons/components/UiOpenScad.cjs +10 -0
- package/dist/icons/components/UiOpenScad.cjs.map +1 -0
- package/dist/icons/components/UiOpenScad.d.ts +9 -0
- package/dist/icons/components/UiOpenScad.d.ts.map +1 -0
- package/dist/icons/components/UiOpenScad.js +10 -0
- package/dist/icons/components/UiOpenScad.js.map +1 -0
- package/dist/icons/index.d.ts +1 -0
- package/dist/icons/index.d.ts.map +1 -1
- package/dist/icons/registry.cjs +2 -0
- package/dist/icons/registry.cjs.map +1 -1
- package/dist/icons/registry.d.ts.map +1 -1
- package/dist/icons/registry.js +2 -0
- package/dist/icons/registry.js.map +1 -1
- package/dist/icons.cjs +2 -0
- package/dist/icons.cjs.map +1 -1
- package/dist/icons.js +2 -0
- package/dist/icons.js.map +1 -1
- package/dist/index.cjs +20 -8
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +20 -8
- package/dist/index.js.map +1 -1
- package/dist/layout/AppShell.cjs +15 -10
- package/dist/layout/AppShell.cjs.map +1 -1
- package/dist/layout/AppShell.d.ts +11 -0
- package/dist/layout/AppShell.d.ts.map +1 -1
- package/dist/layout/AppShell.js +15 -10
- package/dist/layout/AppShell.js.map +1 -1
- package/dist/layout/AppShell.nav.cjs +170 -49
- package/dist/layout/AppShell.nav.cjs.map +1 -1
- package/dist/layout/AppShell.nav.d.ts.map +1 -1
- package/dist/layout/AppShell.nav.js +170 -49
- package/dist/layout/AppShell.nav.js.map +1 -1
- package/dist/overlay/CellActions.cjs +18 -124
- package/dist/overlay/CellActions.cjs.map +1 -1
- package/dist/overlay/CellActions.d.ts +1 -1
- package/dist/overlay/CellActions.d.ts.map +1 -1
- package/dist/overlay/CellActions.js +18 -124
- package/dist/overlay/CellActions.js.map +1 -1
- package/dist/overlay/ContextMenu.cjs +144 -0
- package/dist/overlay/ContextMenu.cjs.map +1 -0
- package/dist/overlay/ContextMenu.d.ts +8 -0
- package/dist/overlay/ContextMenu.d.ts.map +1 -0
- package/dist/overlay/ContextMenu.js +144 -0
- package/dist/overlay/ContextMenu.js.map +1 -0
- package/dist/profiles/connections/connectionBrowserModel.cjs +14 -65
- package/dist/profiles/connections/connectionBrowserModel.cjs.map +1 -1
- package/dist/profiles/connections/connectionBrowserModel.d.ts +35 -35
- package/dist/profiles/connections/connectionBrowserModel.d.ts.map +1 -1
- package/dist/profiles/connections/connectionBrowserModel.js +14 -65
- package/dist/profiles/connections/connectionBrowserModel.js.map +1 -1
- package/dist/profiles/connections/connectionQueryWorkspace.cjs +29 -9
- package/dist/profiles/connections/connectionQueryWorkspace.cjs.map +1 -1
- package/dist/profiles/connections/connectionQueryWorkspace.d.ts +3 -2
- package/dist/profiles/connections/connectionQueryWorkspace.d.ts.map +1 -1
- package/dist/profiles/connections/connectionQueryWorkspace.js +30 -10
- package/dist/profiles/connections/connectionQueryWorkspace.js.map +1 -1
- package/dist/profiles/connections/connectionQueryWorkspaceModel.cjs +15 -0
- package/dist/profiles/connections/connectionQueryWorkspaceModel.cjs.map +1 -1
- package/dist/profiles/connections/connectionQueryWorkspaceModel.d.ts +22 -1
- package/dist/profiles/connections/connectionQueryWorkspaceModel.d.ts.map +1 -1
- package/dist/profiles/connections/connectionQueryWorkspaceModel.js +15 -0
- package/dist/profiles/connections/connectionQueryWorkspaceModel.js.map +1 -1
- package/dist/profiles/connections/index.d.ts +1 -0
- package/dist/profiles/connections/index.d.ts.map +1 -1
- package/dist/profiles/connections/inspectionStatus.cjs +44 -0
- package/dist/profiles/connections/inspectionStatus.cjs.map +1 -0
- package/dist/profiles/connections/inspectionStatus.d.ts +5 -0
- package/dist/profiles/connections/inspectionStatus.d.ts.map +1 -0
- package/dist/profiles/connections/inspectionStatus.js +44 -0
- package/dist/profiles/connections/inspectionStatus.js.map +1 -0
- package/dist/profiles/connections/useInspection.cjs +123 -0
- package/dist/profiles/connections/useInspection.cjs.map +1 -0
- package/dist/profiles/connections/useInspection.d.ts +35 -0
- package/dist/profiles/connections/useInspection.d.ts.map +1 -0
- package/dist/profiles/connections/useInspection.js +123 -0
- package/dist/profiles/connections/useInspection.js.map +1 -0
- package/dist/profiles/editor/profileBuilderWorkspace.cjs +55 -23
- package/dist/profiles/editor/profileBuilderWorkspace.cjs.map +1 -1
- package/dist/profiles/editor/profileBuilderWorkspace.d.ts.map +1 -1
- package/dist/profiles/editor/profileBuilderWorkspace.js +56 -24
- package/dist/profiles/editor/profileBuilderWorkspace.js.map +1 -1
- package/dist/profiles/elasticsearch/esQueryBuilder.cjs +12 -3
- package/dist/profiles/elasticsearch/esQueryBuilder.cjs.map +1 -1
- package/dist/profiles/elasticsearch/esQueryBuilder.d.ts +2 -2
- package/dist/profiles/elasticsearch/esQueryBuilder.d.ts.map +1 -1
- package/dist/profiles/elasticsearch/esQueryBuilder.js +12 -3
- package/dist/profiles/elasticsearch/esQueryBuilder.js.map +1 -1
- package/dist/profiles/fields/profileFieldEditor.cjs +137 -22
- package/dist/profiles/fields/profileFieldEditor.cjs.map +1 -1
- package/dist/profiles/fields/profileFieldEditor.d.ts.map +1 -1
- package/dist/profiles/fields/profileFieldEditor.js +137 -22
- package/dist/profiles/fields/profileFieldEditor.js.map +1 -1
- package/dist/profiles/fields/profileFieldFilterEditor.cjs +171 -82
- package/dist/profiles/fields/profileFieldFilterEditor.cjs.map +1 -1
- package/dist/profiles/fields/profileFieldFilterEditor.d.ts +0 -9
- package/dist/profiles/fields/profileFieldFilterEditor.d.ts.map +1 -1
- package/dist/profiles/fields/profileFieldFilterEditor.js +174 -85
- package/dist/profiles/fields/profileFieldFilterEditor.js.map +1 -1
- package/dist/profiles/fields/profileFieldIcons.cjs +6 -3
- package/dist/profiles/fields/profileFieldIcons.cjs.map +1 -1
- package/dist/profiles/fields/profileFieldIcons.js +6 -3
- package/dist/profiles/fields/profileFieldIcons.js.map +1 -1
- package/dist/profiles/query/profileSampleFilterLookup.cjs +34 -0
- package/dist/profiles/query/profileSampleFilterLookup.cjs.map +1 -0
- package/dist/profiles/query/profileSampleFilterLookup.d.ts +12 -0
- package/dist/profiles/query/profileSampleFilterLookup.d.ts.map +1 -0
- package/dist/profiles/query/profileSampleFilterLookup.js +34 -0
- package/dist/profiles/query/profileSampleFilterLookup.js.map +1 -0
- package/dist/profiles/query/profileSamplePayload.cjs +6 -4
- package/dist/profiles/query/profileSamplePayload.cjs.map +1 -1
- package/dist/profiles/query/profileSamplePayload.d.ts +11 -4
- package/dist/profiles/query/profileSamplePayload.d.ts.map +1 -1
- package/dist/profiles/query/profileSamplePayload.js +6 -4
- package/dist/profiles/query/profileSamplePayload.js.map +1 -1
- package/dist/profiles/query/profileSampleResult.cjs +26 -0
- package/dist/profiles/query/profileSampleResult.cjs.map +1 -0
- package/dist/profiles/query/profileSampleResult.d.ts +11 -0
- package/dist/profiles/query/profileSampleResult.d.ts.map +1 -0
- package/dist/profiles/query/profileSampleResult.js +26 -0
- package/dist/profiles/query/profileSampleResult.js.map +1 -0
- package/dist/profiles/query/queryTargetPicker.cjs +5 -3
- package/dist/profiles/query/queryTargetPicker.cjs.map +1 -1
- package/dist/profiles/query/queryTargetPicker.d.ts +3 -2
- package/dist/profiles/query/queryTargetPicker.d.ts.map +1 -1
- package/dist/profiles/query/queryTargetPicker.js +5 -3
- package/dist/profiles/query/queryTargetPicker.js.map +1 -1
- package/dist/profiles/wizard/profileWizard.cjs +14 -5
- package/dist/profiles/wizard/profileWizard.cjs.map +1 -1
- package/dist/profiles/wizard/profileWizard.d.ts.map +1 -1
- package/dist/profiles/wizard/profileWizard.js +15 -6
- package/dist/profiles/wizard/profileWizard.js.map +1 -1
- package/dist/profiles/wizard/profileWizardModel.cjs +35 -6
- package/dist/profiles/wizard/profileWizardModel.cjs.map +1 -1
- package/dist/profiles/wizard/profileWizardModel.d.ts +29 -4
- package/dist/profiles/wizard/profileWizardModel.d.ts.map +1 -1
- package/dist/profiles/wizard/profileWizardModel.js +35 -6
- package/dist/profiles/wizard/profileWizardModel.js.map +1 -1
- package/dist/profiles/wizard/profileWizardQueryStep.cjs +44 -11
- package/dist/profiles/wizard/profileWizardQueryStep.cjs.map +1 -1
- package/dist/profiles/wizard/profileWizardQueryStep.d.ts.map +1 -1
- package/dist/profiles/wizard/profileWizardQueryStep.js +46 -13
- package/dist/profiles/wizard/profileWizardQueryStep.js.map +1 -1
- package/dist/profiles/wizard/profileWizardSteps.cjs +33 -2
- package/dist/profiles/wizard/profileWizardSteps.cjs.map +1 -1
- package/dist/profiles/wizard/profileWizardSteps.d.ts +11 -2
- package/dist/profiles/wizard/profileWizardSteps.d.ts.map +1 -1
- package/dist/profiles/wizard/profileWizardSteps.js +33 -2
- package/dist/profiles/wizard/profileWizardSteps.js.map +1 -1
- package/dist/profiles.cjs +8 -2
- package/dist/profiles.cjs.map +1 -1
- package/dist/profiles.js +10 -4
- package/dist/profiles.js.map +1 -1
- package/dist/rpc/FilterForm.cjs +21 -237
- package/dist/rpc/FilterForm.cjs.map +1 -1
- package/dist/rpc/FilterForm.d.ts +3 -1
- package/dist/rpc/FilterForm.d.ts.map +1 -1
- package/dist/rpc/FilterForm.js +21 -237
- package/dist/rpc/FilterForm.js.map +1 -1
- package/dist/rpc/FilterFormFields.cjs +240 -0
- package/dist/rpc/FilterFormFields.cjs.map +1 -0
- package/dist/rpc/FilterFormFields.d.ts +12 -0
- package/dist/rpc/FilterFormFields.d.ts.map +1 -0
- package/dist/rpc/FilterFormFields.js +240 -0
- package/dist/rpc/FilterFormFields.js.map +1 -0
- package/dist/rpc/router.cjs +3 -2
- package/dist/rpc/router.cjs.map +1 -1
- package/dist/rpc/router.d.ts.map +1 -1
- package/dist/rpc/router.js +3 -2
- package/dist/rpc/router.js.map +1 -1
- package/dist/rpc/types.cjs.map +1 -1
- package/dist/rpc/types.d.ts +3 -1
- package/dist/rpc/types.d.ts.map +1 -1
- package/dist/rpc/types.js.map +1 -1
- package/dist/styles.css +1 -1
- package/package.json +6 -1
- package/dist/data/query-info/QueryInfoDialog.cjs +0 -106
- package/dist/data/query-info/QueryInfoDialog.cjs.map +0 -1
- package/dist/data/query-info/QueryInfoDialog.d.ts +0 -16
- package/dist/data/query-info/QueryInfoDialog.d.ts.map +0 -1
- package/dist/data/query-info/QueryInfoDialog.js +0 -106
- package/dist/data/query-info/QueryInfoDialog.js.map +0 -1
- package/dist/data/query-info/index.d.ts +0 -4
- package/dist/data/query-info/index.d.ts.map +0 -1
- package/dist/data/query-info/queryInfo.cjs +0 -42
- package/dist/data/query-info/queryInfo.cjs.map +0 -1
- package/dist/data/query-info/queryInfo.d.ts +0 -45
- package/dist/data/query-info/queryInfo.d.ts.map +0 -1
- package/dist/data/query-info/queryInfo.js +0 -42
- package/dist/data/query-info/queryInfo.js.map +0 -1
- package/dist/data/query-info/useQueryInfo.cjs +0 -48
- package/dist/data/query-info/useQueryInfo.cjs.map +0 -1
- package/dist/data/query-info/useQueryInfo.d.ts +0 -26
- package/dist/data/query-info/useQueryInfo.d.ts.map +0 -1
- package/dist/data/query-info/useQueryInfo.js +0 -48
- package/dist/data/query-info/useQueryInfo.js.map +0 -1
|
@@ -8,6 +8,7 @@ const AI_RUNTIME_KEYS = /* @__PURE__ */ new Set([
|
|
|
8
8
|
"effort",
|
|
9
9
|
"id",
|
|
10
10
|
"model",
|
|
11
|
+
"mode",
|
|
11
12
|
"noCache",
|
|
12
13
|
"prompt",
|
|
13
14
|
"temperature"
|
|
@@ -18,6 +19,7 @@ const AI_MODEL_KEYS = /* @__PURE__ */ new Set([
|
|
|
18
19
|
"effort",
|
|
19
20
|
"id",
|
|
20
21
|
"model",
|
|
22
|
+
"mode",
|
|
21
23
|
"noCache",
|
|
22
24
|
"temperature"
|
|
23
25
|
]);
|
|
@@ -107,6 +109,8 @@ function aiToRuntime(ai) {
|
|
|
107
109
|
if (model) runtime.model = model;
|
|
108
110
|
const backend = stringValue(ai.backend);
|
|
109
111
|
if (backend) runtime.backend = backend;
|
|
112
|
+
const mode = stringValue(ai.mode);
|
|
113
|
+
if (mode) runtime.mode = mode;
|
|
110
114
|
const id = stringValue(ai.id);
|
|
111
115
|
if (id) runtime.id = id;
|
|
112
116
|
const effort = stringValue(ai.effort);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"fixture-frontmatter.cjs","sources":["../../../src/data/FixtureEditor/fixture-frontmatter.ts"],"sourcesContent":["import { parseDocument, stringify } from \"yaml\";\nimport {\n compactAISpecRuntime,\n type AISpecRuntimeEnvVar,\n type AISpecRuntimeValue,\n} from \"../ai/SpecRuntimeEditor.model\";\n\nexport type FixtureAIExtras = {\n maxConcurrent?: number;\n cacheTTL?: string;\n};\n\nexport type FixtureFrontmatterState = {\n runtime: AISpecRuntimeValue;\n aiExtras: FixtureAIExtras;\n};\n\nexport type FixtureFrontmatterApplyOptions = {\n /** Omit model/runtime knobs so a verification fixture inherits its parent runtime. */\n inheritModel?: boolean | undefined;\n};\n\nexport type FixtureFrontmatterParseResult =\n | {\n ok: true;\n hasFrontmatter: boolean;\n frontmatter: Record<string, unknown>;\n raw: string;\n body: string;\n }\n | {\n ok: false;\n hasFrontmatter: true;\n error: string;\n raw: string;\n body: string;\n };\n\nconst AI_RUNTIME_KEYS = new Set([\n \"backend\",\n \"budget\",\n \"effort\",\n \"id\",\n \"model\",\n \"noCache\",\n \"prompt\",\n \"temperature\",\n]);\n\nconst AI_MODEL_KEYS = new Set([\n \"backend\",\n \"budget\",\n \"effort\",\n \"id\",\n \"model\",\n \"noCache\",\n \"temperature\",\n]);\n\nconst AI_EXTRA_KEYS = new Set([\"maxConcurrent\", \"cacheTTL\"]);\n\nexport function parseFixtureFrontmatter(\n markdown: string,\n): FixtureFrontmatterParseResult {\n const split = splitMarkdownFrontmatter(markdown);\n if (!split.hasFrontmatter) {\n return {\n ok: true,\n hasFrontmatter: false,\n frontmatter: {},\n raw: \"\",\n body: markdown,\n };\n }\n if (!split.closed) {\n return {\n ok: false,\n hasFrontmatter: true,\n error: \"Frontmatter closing delimiter not found\",\n raw: split.raw,\n body: split.body,\n };\n }\n\n const parsed = parseYamlRecord(split.raw);\n if (!parsed.ok) {\n return {\n ok: false,\n hasFrontmatter: true,\n error: parsed.error,\n raw: split.raw,\n body: split.body,\n };\n }\n\n return {\n ok: true,\n hasFrontmatter: true,\n frontmatter: parsed.value,\n raw: split.raw,\n body: split.body,\n };\n}\n\nexport function fixtureFrontmatterState(\n frontmatter: Record<string, unknown>,\n): FixtureFrontmatterState {\n const ai = recordValue(frontmatter.ai);\n const runtime = aiToRuntime(ai);\n const envVars = envToRuntimeEnvVars(frontmatter.env);\n if (envVars.length > 0) {\n runtime.setup = { ...runtime.setup, envVars };\n }\n const aiExtras = aiToExtras(ai);\n return { runtime, aiExtras };\n}\n\nexport function applyFixtureFrontmatterState(\n markdown: string,\n state: FixtureFrontmatterState,\n options: FixtureFrontmatterApplyOptions = {},\n): string {\n const parsed = parseFixtureFrontmatter(markdown);\n const body = parsed.body;\n const existing = parsed.ok ? parsed.frontmatter : {};\n const frontmatter = frontmatterFromState(existing, state, options);\n return serializeFixtureFrontmatter(frontmatter, body);\n}\n\nexport function applyFixtureFrontmatterRaw(\n markdown: string,\n raw: string,\n): string {\n const split = splitMarkdownFrontmatter(markdown);\n const body = split.hasFrontmatter ? split.body : markdown;\n if (raw.trim() === \"\") return body;\n const normalizedRaw = raw.endsWith(\"\\n\") ? raw : `${raw}\\n`;\n return `---\\n${normalizedRaw}---\\n${body}`;\n}\n\nexport function frontmatterFromState(\n existing: Record<string, unknown>,\n state: FixtureFrontmatterState,\n options: FixtureFrontmatterApplyOptions = {},\n): Record<string, unknown> {\n const next = omitKeys(existing, [\"ai\", \"env\"]);\n const currentAI = recordValue(existing.ai);\n const ai = {\n ...omitControlledAIKeys(currentAI),\n ...runtimeToAI(state.runtime, options),\n ...compactAIExtras(state.aiExtras),\n };\n const env = runtimeEnvVarsToEnv(state.runtime.setup?.envVars);\n\n if (hasKeys(ai)) next.ai = ai;\n if (hasKeys(env)) next.env = env;\n return next;\n}\n\nfunction aiToRuntime(ai: Record<string, unknown>): AISpecRuntimeValue {\n const runtime: AISpecRuntimeValue = {};\n const model = stringValue(ai.model);\n if (model) runtime.model = model;\n const backend = stringValue(ai.backend);\n if (backend) runtime.backend = backend;\n const id = stringValue(ai.id);\n if (id) runtime.id = id;\n const effort = stringValue(ai.effort);\n if (effort) runtime.effort = effort;\n const temperature = numberValue(ai.temperature);\n if (temperature != null) runtime.temperature = temperature;\n if (ai.noCache === true) runtime.noCache = true;\n\n const budget = recordValue(ai.budget);\n const maxTokens = numberValue(ai.maxTokens) ?? numberValue(budget.maxTokens);\n const cost = numberValue(budget.cost);\n const maxTurns = numberValue(budget.maxTurns);\n const timeout = stringValue(budget.timeout);\n if (maxTokens != null || cost != null || maxTurns != null || timeout) {\n runtime.budget = {\n ...(cost != null ? { cost } : {}),\n ...(maxTokens != null ? { maxTokens } : {}),\n ...(maxTurns != null ? { maxTurns } : {}),\n ...(timeout ? { timeout } : {}),\n };\n }\n\n const prompt = promptToRuntimePrompt(ai.prompt);\n if (prompt) runtime.prompt = prompt;\n\n return runtime;\n}\n\nfunction runtimeToAI(\n runtime: AISpecRuntimeValue,\n options: FixtureFrontmatterApplyOptions = {},\n): Record<string, unknown> {\n const compact = compactAISpecRuntime(runtime);\n const ai: Record<string, unknown> = {};\n for (const key of AI_RUNTIME_KEYS) {\n if (options.inheritModel && AI_MODEL_KEYS.has(key)) continue;\n const value = (compact as Record<string, unknown>)[key];\n if (value != null && (key !== \"budget\" || hasKeys(recordValue(value)))) {\n ai[key] = value;\n }\n }\n const maxTokens = compact.budget?.maxTokens;\n if (maxTokens != null && !options.inheritModel) {\n delete ai.budget;\n ai.maxTokens = maxTokens;\n }\n return ai;\n}\n\nfunction promptToRuntimePrompt(\n value: unknown,\n): AISpecRuntimeValue[\"prompt\"] | undefined {\n if (typeof value === \"string\") {\n const user = stringValue(value);\n return user ? { user } : undefined;\n }\n const prompt = recordValue(value);\n const user = stringValue(prompt.user);\n const system = stringValue(prompt.system);\n const appendSystem = stringValue(prompt.appendSystem);\n const source = stringValue(prompt.source);\n const metadata = recordStringMap(prompt.metadata);\n const out = {\n ...(user ? { user } : {}),\n ...(system ? { system } : {}),\n ...(appendSystem ? { appendSystem } : {}),\n ...(source ? { source } : {}),\n ...(metadata ? { metadata } : {}),\n };\n return hasKeys(out) ? out : undefined;\n}\n\nfunction aiToExtras(ai: Record<string, unknown>): FixtureAIExtras {\n const maxConcurrent = numberValue(ai.maxConcurrent);\n const cacheTTL = stringValue(ai.cacheTTL);\n return {\n ...(maxConcurrent != null ? { maxConcurrent } : {}),\n ...(cacheTTL ? { cacheTTL } : {}),\n };\n}\n\nfunction compactAIExtras(extras: FixtureAIExtras): Record<string, unknown> {\n return {\n ...(numberValue(extras.maxConcurrent) != null\n ? { maxConcurrent: numberValue(extras.maxConcurrent) }\n : {}),\n ...(stringValue(extras.cacheTTL) ? { cacheTTL: stringValue(extras.cacheTTL) } : {}),\n };\n}\n\nfunction envToRuntimeEnvVars(value: unknown): AISpecRuntimeEnvVar[] {\n if (!isRecord(value)) return [];\n const envVars: AISpecRuntimeEnvVar[] = [];\n for (const [name, envValue] of Object.entries(value)) {\n const key = name.trim();\n if (!key || typeof envValue !== \"string\") continue;\n envVars.push({ name: key, value: envValue });\n }\n return envVars;\n}\n\nfunction runtimeEnvVarsToEnv(\n value: AISpecRuntimeEnvVar[] | undefined,\n): Record<string, unknown> {\n const env: Record<string, unknown> = {};\n for (const item of value ?? []) {\n const name = stringValue(item.name);\n if (!name) continue;\n const literal = typeof item.value === \"string\" ? item.value : undefined;\n const valueFrom =\n typeof item.valueFrom === \"string\" ? item.valueFrom : undefined;\n if (literal != null) env[name] = literal;\n else if (valueFrom) env[name] = valueFrom;\n }\n return env;\n}\n\nfunction serializeFixtureFrontmatter(\n frontmatter: Record<string, unknown>,\n body: string,\n): string {\n if (!hasKeys(frontmatter)) return body;\n const yaml = stringify(frontmatter, {\n lineWidth: 0,\n collectionStyle: \"block\",\n });\n const normalizedYaml = yaml.endsWith(\"\\n\") ? yaml : `${yaml}\\n`;\n return `---\\n${normalizedYaml}---\\n${body}`;\n}\n\nfunction splitMarkdownFrontmatter(markdown: string):\n | { hasFrontmatter: false }\n | { hasFrontmatter: true; closed: boolean; raw: string; body: string } {\n const lines = splitLinesWithEndings(markdown);\n if (stripLineEnding(lines[0] ?? \"\") !== \"---\") return { hasFrontmatter: false };\n\n for (let index = 1; index < lines.length; index += 1) {\n const line = stripLineEnding(lines[index] ?? \"\");\n if (line === \"---\" || line === \"...\") {\n return {\n hasFrontmatter: true,\n closed: true,\n raw: lines.slice(1, index).join(\"\"),\n body: lines.slice(index + 1).join(\"\"),\n };\n }\n }\n\n return {\n hasFrontmatter: true,\n closed: false,\n raw: lines.slice(1).join(\"\"),\n body: \"\",\n };\n}\n\nfunction splitLinesWithEndings(text: string): string[] {\n if (text === \"\") return [];\n const lines = text.match(/[^\\n]*(?:\\n|$)/g) ?? [];\n if (lines.at(-1) === \"\") lines.pop();\n return lines;\n}\n\nfunction stripLineEnding(line: string): string {\n return line.replace(/\\r?\\n$/, \"\").trim();\n}\n\nfunction parseYamlRecord(\n yaml: string,\n): { ok: true; value: Record<string, unknown> } | { ok: false; error: string } {\n if (yaml.trim() === \"\") return { ok: true, value: {} };\n const doc = parseDocument(yaml, { prettyErrors: false });\n const firstError = doc.errors[0];\n if (firstError) return { ok: false, error: firstError.message };\n const value = doc.toJSON();\n if (value == null) return { ok: true, value: {} };\n if (!isRecord(value)) return { ok: false, error: \"Frontmatter root must be an object\" };\n return { ok: true, value };\n}\n\nfunction omitControlledAIKeys(ai: Record<string, unknown>): Record<string, unknown> {\n const omitted = new Set([...AI_RUNTIME_KEYS, ...AI_EXTRA_KEYS, \"maxTokens\"]);\n return omitKeys(ai, [...omitted]);\n}\n\nfunction omitKeys(\n value: Record<string, unknown>,\n keys: readonly string[],\n): Record<string, unknown> {\n const omitted = new Set(keys);\n return Object.fromEntries(\n Object.entries(value).filter(([key]) => !omitted.has(key)),\n );\n}\n\nfunction recordValue(value: unknown): Record<string, unknown> {\n return isRecord(value) ? value : {};\n}\n\nfunction recordStringMap(value: unknown): Record<string, string> | undefined {\n if (!isRecord(value)) return undefined;\n const out: Record<string, string> = {};\n for (const [rawKey, rawValue] of Object.entries(value)) {\n const key = rawKey.trim();\n if (!key || typeof rawValue !== \"string\") continue;\n out[key] = rawValue;\n }\n return hasKeys(out) ? out : undefined;\n}\n\nfunction stringValue(value: unknown): string | undefined {\n return typeof value === \"string\" && value.trim() ? value.trim() : undefined;\n}\n\nfunction numberValue(value: unknown): number | undefined {\n return typeof value === \"number\" && Number.isFinite(value) ? value : undefined;\n}\n\nfunction hasKeys(value: Record<string, unknown>): boolean {\n return Object.keys(value).length > 0;\n}\n\nfunction isRecord(value: unknown): value is Record<string, unknown> {\n return typeof value === \"object\" && value != null && !Array.isArray(value);\n}\n"],"names":["compactAISpecRuntime","user","yaml","stringify","parseDocument"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"fixture-frontmatter.cjs","sources":["../../../src/data/FixtureEditor/fixture-frontmatter.ts"],"sourcesContent":["import { parseDocument, stringify } from \"yaml\";\nimport {\n compactAISpecRuntime,\n type AISpecRuntimeEnvVar,\n type AISpecRuntimeValue,\n} from \"../ai/SpecRuntimeEditor.model\";\n\nexport type FixtureAIExtras = {\n maxConcurrent?: number;\n cacheTTL?: string;\n};\n\nexport type FixtureFrontmatterState = {\n runtime: AISpecRuntimeValue;\n aiExtras: FixtureAIExtras;\n};\n\nexport type FixtureFrontmatterApplyOptions = {\n /** Omit model/runtime knobs so a verification fixture inherits its parent runtime. */\n inheritModel?: boolean | undefined;\n};\n\nexport type FixtureFrontmatterParseResult =\n | {\n ok: true;\n hasFrontmatter: boolean;\n frontmatter: Record<string, unknown>;\n raw: string;\n body: string;\n }\n | {\n ok: false;\n hasFrontmatter: true;\n error: string;\n raw: string;\n body: string;\n };\n\nconst AI_RUNTIME_KEYS = new Set([\n \"backend\",\n \"budget\",\n \"effort\",\n \"id\",\n \"model\",\n \"mode\",\n \"noCache\",\n \"prompt\",\n \"temperature\",\n]);\n\nconst AI_MODEL_KEYS = new Set([\n \"backend\",\n \"budget\",\n \"effort\",\n \"id\",\n \"model\",\n \"mode\",\n \"noCache\",\n \"temperature\",\n]);\n\nconst AI_EXTRA_KEYS = new Set([\"maxConcurrent\", \"cacheTTL\"]);\n\nexport function parseFixtureFrontmatter(\n markdown: string,\n): FixtureFrontmatterParseResult {\n const split = splitMarkdownFrontmatter(markdown);\n if (!split.hasFrontmatter) {\n return {\n ok: true,\n hasFrontmatter: false,\n frontmatter: {},\n raw: \"\",\n body: markdown,\n };\n }\n if (!split.closed) {\n return {\n ok: false,\n hasFrontmatter: true,\n error: \"Frontmatter closing delimiter not found\",\n raw: split.raw,\n body: split.body,\n };\n }\n\n const parsed = parseYamlRecord(split.raw);\n if (!parsed.ok) {\n return {\n ok: false,\n hasFrontmatter: true,\n error: parsed.error,\n raw: split.raw,\n body: split.body,\n };\n }\n\n return {\n ok: true,\n hasFrontmatter: true,\n frontmatter: parsed.value,\n raw: split.raw,\n body: split.body,\n };\n}\n\nexport function fixtureFrontmatterState(\n frontmatter: Record<string, unknown>,\n): FixtureFrontmatterState {\n const ai = recordValue(frontmatter.ai);\n const runtime = aiToRuntime(ai);\n const envVars = envToRuntimeEnvVars(frontmatter.env);\n if (envVars.length > 0) {\n runtime.setup = { ...runtime.setup, envVars };\n }\n const aiExtras = aiToExtras(ai);\n return { runtime, aiExtras };\n}\n\nexport function applyFixtureFrontmatterState(\n markdown: string,\n state: FixtureFrontmatterState,\n options: FixtureFrontmatterApplyOptions = {},\n): string {\n const parsed = parseFixtureFrontmatter(markdown);\n const body = parsed.body;\n const existing = parsed.ok ? parsed.frontmatter : {};\n const frontmatter = frontmatterFromState(existing, state, options);\n return serializeFixtureFrontmatter(frontmatter, body);\n}\n\nexport function applyFixtureFrontmatterRaw(\n markdown: string,\n raw: string,\n): string {\n const split = splitMarkdownFrontmatter(markdown);\n const body = split.hasFrontmatter ? split.body : markdown;\n if (raw.trim() === \"\") return body;\n const normalizedRaw = raw.endsWith(\"\\n\") ? raw : `${raw}\\n`;\n return `---\\n${normalizedRaw}---\\n${body}`;\n}\n\nexport function frontmatterFromState(\n existing: Record<string, unknown>,\n state: FixtureFrontmatterState,\n options: FixtureFrontmatterApplyOptions = {},\n): Record<string, unknown> {\n const next = omitKeys(existing, [\"ai\", \"env\"]);\n const currentAI = recordValue(existing.ai);\n const ai = {\n ...omitControlledAIKeys(currentAI),\n ...runtimeToAI(state.runtime, options),\n ...compactAIExtras(state.aiExtras),\n };\n const env = runtimeEnvVarsToEnv(state.runtime.setup?.envVars);\n\n if (hasKeys(ai)) next.ai = ai;\n if (hasKeys(env)) next.env = env;\n return next;\n}\n\nfunction aiToRuntime(ai: Record<string, unknown>): AISpecRuntimeValue {\n const runtime: AISpecRuntimeValue = {};\n const model = stringValue(ai.model);\n if (model) runtime.model = model;\n const backend = stringValue(ai.backend);\n if (backend) runtime.backend = backend;\n const mode = stringValue(ai.mode);\n if (mode) runtime.mode = mode;\n const id = stringValue(ai.id);\n if (id) runtime.id = id;\n const effort = stringValue(ai.effort);\n if (effort) runtime.effort = effort;\n const temperature = numberValue(ai.temperature);\n if (temperature != null) runtime.temperature = temperature;\n if (ai.noCache === true) runtime.noCache = true;\n\n const budget = recordValue(ai.budget);\n const maxTokens = numberValue(ai.maxTokens) ?? numberValue(budget.maxTokens);\n const cost = numberValue(budget.cost);\n const maxTurns = numberValue(budget.maxTurns);\n const timeout = stringValue(budget.timeout);\n if (maxTokens != null || cost != null || maxTurns != null || timeout) {\n runtime.budget = {\n ...(cost != null ? { cost } : {}),\n ...(maxTokens != null ? { maxTokens } : {}),\n ...(maxTurns != null ? { maxTurns } : {}),\n ...(timeout ? { timeout } : {}),\n };\n }\n\n const prompt = promptToRuntimePrompt(ai.prompt);\n if (prompt) runtime.prompt = prompt;\n\n return runtime;\n}\n\nfunction runtimeToAI(\n runtime: AISpecRuntimeValue,\n options: FixtureFrontmatterApplyOptions = {},\n): Record<string, unknown> {\n const compact = compactAISpecRuntime(runtime);\n const ai: Record<string, unknown> = {};\n for (const key of AI_RUNTIME_KEYS) {\n if (options.inheritModel && AI_MODEL_KEYS.has(key)) continue;\n const value = (compact as Record<string, unknown>)[key];\n if (value != null && (key !== \"budget\" || hasKeys(recordValue(value)))) {\n ai[key] = value;\n }\n }\n const maxTokens = compact.budget?.maxTokens;\n if (maxTokens != null && !options.inheritModel) {\n delete ai.budget;\n ai.maxTokens = maxTokens;\n }\n return ai;\n}\n\nfunction promptToRuntimePrompt(\n value: unknown,\n): AISpecRuntimeValue[\"prompt\"] | undefined {\n if (typeof value === \"string\") {\n const user = stringValue(value);\n return user ? { user } : undefined;\n }\n const prompt = recordValue(value);\n const user = stringValue(prompt.user);\n const system = stringValue(prompt.system);\n const appendSystem = stringValue(prompt.appendSystem);\n const source = stringValue(prompt.source);\n const metadata = recordStringMap(prompt.metadata);\n const out = {\n ...(user ? { user } : {}),\n ...(system ? { system } : {}),\n ...(appendSystem ? { appendSystem } : {}),\n ...(source ? { source } : {}),\n ...(metadata ? { metadata } : {}),\n };\n return hasKeys(out) ? out : undefined;\n}\n\nfunction aiToExtras(ai: Record<string, unknown>): FixtureAIExtras {\n const maxConcurrent = numberValue(ai.maxConcurrent);\n const cacheTTL = stringValue(ai.cacheTTL);\n return {\n ...(maxConcurrent != null ? { maxConcurrent } : {}),\n ...(cacheTTL ? { cacheTTL } : {}),\n };\n}\n\nfunction compactAIExtras(extras: FixtureAIExtras): Record<string, unknown> {\n return {\n ...(numberValue(extras.maxConcurrent) != null\n ? { maxConcurrent: numberValue(extras.maxConcurrent) }\n : {}),\n ...(stringValue(extras.cacheTTL) ? { cacheTTL: stringValue(extras.cacheTTL) } : {}),\n };\n}\n\nfunction envToRuntimeEnvVars(value: unknown): AISpecRuntimeEnvVar[] {\n if (!isRecord(value)) return [];\n const envVars: AISpecRuntimeEnvVar[] = [];\n for (const [name, envValue] of Object.entries(value)) {\n const key = name.trim();\n if (!key || typeof envValue !== \"string\") continue;\n envVars.push({ name: key, value: envValue });\n }\n return envVars;\n}\n\nfunction runtimeEnvVarsToEnv(\n value: AISpecRuntimeEnvVar[] | undefined,\n): Record<string, unknown> {\n const env: Record<string, unknown> = {};\n for (const item of value ?? []) {\n const name = stringValue(item.name);\n if (!name) continue;\n const literal = typeof item.value === \"string\" ? item.value : undefined;\n const valueFrom =\n typeof item.valueFrom === \"string\" ? item.valueFrom : undefined;\n if (literal != null) env[name] = literal;\n else if (valueFrom) env[name] = valueFrom;\n }\n return env;\n}\n\nfunction serializeFixtureFrontmatter(\n frontmatter: Record<string, unknown>,\n body: string,\n): string {\n if (!hasKeys(frontmatter)) return body;\n const yaml = stringify(frontmatter, {\n lineWidth: 0,\n collectionStyle: \"block\",\n });\n const normalizedYaml = yaml.endsWith(\"\\n\") ? yaml : `${yaml}\\n`;\n return `---\\n${normalizedYaml}---\\n${body}`;\n}\n\nfunction splitMarkdownFrontmatter(markdown: string):\n | { hasFrontmatter: false }\n | { hasFrontmatter: true; closed: boolean; raw: string; body: string } {\n const lines = splitLinesWithEndings(markdown);\n if (stripLineEnding(lines[0] ?? \"\") !== \"---\") return { hasFrontmatter: false };\n\n for (let index = 1; index < lines.length; index += 1) {\n const line = stripLineEnding(lines[index] ?? \"\");\n if (line === \"---\" || line === \"...\") {\n return {\n hasFrontmatter: true,\n closed: true,\n raw: lines.slice(1, index).join(\"\"),\n body: lines.slice(index + 1).join(\"\"),\n };\n }\n }\n\n return {\n hasFrontmatter: true,\n closed: false,\n raw: lines.slice(1).join(\"\"),\n body: \"\",\n };\n}\n\nfunction splitLinesWithEndings(text: string): string[] {\n if (text === \"\") return [];\n const lines = text.match(/[^\\n]*(?:\\n|$)/g) ?? [];\n if (lines.at(-1) === \"\") lines.pop();\n return lines;\n}\n\nfunction stripLineEnding(line: string): string {\n return line.replace(/\\r?\\n$/, \"\").trim();\n}\n\nfunction parseYamlRecord(\n yaml: string,\n): { ok: true; value: Record<string, unknown> } | { ok: false; error: string } {\n if (yaml.trim() === \"\") return { ok: true, value: {} };\n const doc = parseDocument(yaml, { prettyErrors: false });\n const firstError = doc.errors[0];\n if (firstError) return { ok: false, error: firstError.message };\n const value = doc.toJSON();\n if (value == null) return { ok: true, value: {} };\n if (!isRecord(value)) return { ok: false, error: \"Frontmatter root must be an object\" };\n return { ok: true, value };\n}\n\nfunction omitControlledAIKeys(ai: Record<string, unknown>): Record<string, unknown> {\n const omitted = new Set([...AI_RUNTIME_KEYS, ...AI_EXTRA_KEYS, \"maxTokens\"]);\n return omitKeys(ai, [...omitted]);\n}\n\nfunction omitKeys(\n value: Record<string, unknown>,\n keys: readonly string[],\n): Record<string, unknown> {\n const omitted = new Set(keys);\n return Object.fromEntries(\n Object.entries(value).filter(([key]) => !omitted.has(key)),\n );\n}\n\nfunction recordValue(value: unknown): Record<string, unknown> {\n return isRecord(value) ? value : {};\n}\n\nfunction recordStringMap(value: unknown): Record<string, string> | undefined {\n if (!isRecord(value)) return undefined;\n const out: Record<string, string> = {};\n for (const [rawKey, rawValue] of Object.entries(value)) {\n const key = rawKey.trim();\n if (!key || typeof rawValue !== \"string\") continue;\n out[key] = rawValue;\n }\n return hasKeys(out) ? out : undefined;\n}\n\nfunction stringValue(value: unknown): string | undefined {\n return typeof value === \"string\" && value.trim() ? value.trim() : undefined;\n}\n\nfunction numberValue(value: unknown): number | undefined {\n return typeof value === \"number\" && Number.isFinite(value) ? value : undefined;\n}\n\nfunction hasKeys(value: Record<string, unknown>): boolean {\n return Object.keys(value).length > 0;\n}\n\nfunction isRecord(value: unknown): value is Record<string, unknown> {\n return typeof value === \"object\" && value != null && !Array.isArray(value);\n}\n"],"names":["compactAISpecRuntime","user","yaml","stringify","parseDocument"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"fixture-frontmatter.d.ts","sourceRoot":"","sources":["../../../src/data/FixtureEditor/fixture-frontmatter.ts"],"names":[],"mappings":"AACA,OAAO,EAGL,KAAK,kBAAkB,EACxB,MAAM,+BAA+B,CAAC;AAEvC,MAAM,MAAM,eAAe,GAAG;IAC5B,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,uBAAuB,GAAG;IACpC,OAAO,EAAE,kBAAkB,CAAC;IAC5B,QAAQ,EAAE,eAAe,CAAC;CAC3B,CAAC;AAEF,MAAM,MAAM,8BAA8B,GAAG;IAC3C,sFAAsF;IACtF,YAAY,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC;CACpC,CAAC;AAEF,MAAM,MAAM,6BAA6B,GACrC;IACE,EAAE,EAAE,IAAI,CAAC;IACT,cAAc,EAAE,OAAO,CAAC;IACxB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACrC,GAAG,EAAE,MAAM,CAAC;IACZ,IAAI,EAAE,MAAM,CAAC;CACd,GACD;IACE,EAAE,EAAE,KAAK,CAAC;IACV,cAAc,EAAE,IAAI,CAAC;IACrB,KAAK,EAAE,MAAM,CAAC;IACd,GAAG,EAAE,MAAM,CAAC;IACZ,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;
|
|
1
|
+
{"version":3,"file":"fixture-frontmatter.d.ts","sourceRoot":"","sources":["../../../src/data/FixtureEditor/fixture-frontmatter.ts"],"names":[],"mappings":"AACA,OAAO,EAGL,KAAK,kBAAkB,EACxB,MAAM,+BAA+B,CAAC;AAEvC,MAAM,MAAM,eAAe,GAAG;IAC5B,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,uBAAuB,GAAG;IACpC,OAAO,EAAE,kBAAkB,CAAC;IAC5B,QAAQ,EAAE,eAAe,CAAC;CAC3B,CAAC;AAEF,MAAM,MAAM,8BAA8B,GAAG;IAC3C,sFAAsF;IACtF,YAAY,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC;CACpC,CAAC;AAEF,MAAM,MAAM,6BAA6B,GACrC;IACE,EAAE,EAAE,IAAI,CAAC;IACT,cAAc,EAAE,OAAO,CAAC;IACxB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACrC,GAAG,EAAE,MAAM,CAAC;IACZ,IAAI,EAAE,MAAM,CAAC;CACd,GACD;IACE,EAAE,EAAE,KAAK,CAAC;IACV,cAAc,EAAE,IAAI,CAAC;IACrB,KAAK,EAAE,MAAM,CAAC;IACd,GAAG,EAAE,MAAM,CAAC;IACZ,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;AA2BN,wBAAgB,uBAAuB,CACrC,QAAQ,EAAE,MAAM,GACf,6BAA6B,CAuC/B;AAED,wBAAgB,uBAAuB,CACrC,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACnC,uBAAuB,CASzB;AAED,wBAAgB,4BAA4B,CAC1C,QAAQ,EAAE,MAAM,EAChB,KAAK,EAAE,uBAAuB,EAC9B,OAAO,GAAE,8BAAmC,GAC3C,MAAM,CAMR;AAED,wBAAgB,0BAA0B,CACxC,QAAQ,EAAE,MAAM,EAChB,GAAG,EAAE,MAAM,GACV,MAAM,CAMR;AAED,wBAAgB,oBAAoB,CAClC,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACjC,KAAK,EAAE,uBAAuB,EAC9B,OAAO,GAAE,8BAAmC,GAC3C,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAazB"}
|
|
@@ -6,6 +6,7 @@ const AI_RUNTIME_KEYS = /* @__PURE__ */ new Set([
|
|
|
6
6
|
"effort",
|
|
7
7
|
"id",
|
|
8
8
|
"model",
|
|
9
|
+
"mode",
|
|
9
10
|
"noCache",
|
|
10
11
|
"prompt",
|
|
11
12
|
"temperature"
|
|
@@ -16,6 +17,7 @@ const AI_MODEL_KEYS = /* @__PURE__ */ new Set([
|
|
|
16
17
|
"effort",
|
|
17
18
|
"id",
|
|
18
19
|
"model",
|
|
20
|
+
"mode",
|
|
19
21
|
"noCache",
|
|
20
22
|
"temperature"
|
|
21
23
|
]);
|
|
@@ -105,6 +107,8 @@ function aiToRuntime(ai) {
|
|
|
105
107
|
if (model) runtime.model = model;
|
|
106
108
|
const backend = stringValue(ai.backend);
|
|
107
109
|
if (backend) runtime.backend = backend;
|
|
110
|
+
const mode = stringValue(ai.mode);
|
|
111
|
+
if (mode) runtime.mode = mode;
|
|
108
112
|
const id = stringValue(ai.id);
|
|
109
113
|
if (id) runtime.id = id;
|
|
110
114
|
const effort = stringValue(ai.effort);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"fixture-frontmatter.js","sources":["../../../src/data/FixtureEditor/fixture-frontmatter.ts"],"sourcesContent":["import { parseDocument, stringify } from \"yaml\";\nimport {\n compactAISpecRuntime,\n type AISpecRuntimeEnvVar,\n type AISpecRuntimeValue,\n} from \"../ai/SpecRuntimeEditor.model\";\n\nexport type FixtureAIExtras = {\n maxConcurrent?: number;\n cacheTTL?: string;\n};\n\nexport type FixtureFrontmatterState = {\n runtime: AISpecRuntimeValue;\n aiExtras: FixtureAIExtras;\n};\n\nexport type FixtureFrontmatterApplyOptions = {\n /** Omit model/runtime knobs so a verification fixture inherits its parent runtime. */\n inheritModel?: boolean | undefined;\n};\n\nexport type FixtureFrontmatterParseResult =\n | {\n ok: true;\n hasFrontmatter: boolean;\n frontmatter: Record<string, unknown>;\n raw: string;\n body: string;\n }\n | {\n ok: false;\n hasFrontmatter: true;\n error: string;\n raw: string;\n body: string;\n };\n\nconst AI_RUNTIME_KEYS = new Set([\n \"backend\",\n \"budget\",\n \"effort\",\n \"id\",\n \"model\",\n \"noCache\",\n \"prompt\",\n \"temperature\",\n]);\n\nconst AI_MODEL_KEYS = new Set([\n \"backend\",\n \"budget\",\n \"effort\",\n \"id\",\n \"model\",\n \"noCache\",\n \"temperature\",\n]);\n\nconst AI_EXTRA_KEYS = new Set([\"maxConcurrent\", \"cacheTTL\"]);\n\nexport function parseFixtureFrontmatter(\n markdown: string,\n): FixtureFrontmatterParseResult {\n const split = splitMarkdownFrontmatter(markdown);\n if (!split.hasFrontmatter) {\n return {\n ok: true,\n hasFrontmatter: false,\n frontmatter: {},\n raw: \"\",\n body: markdown,\n };\n }\n if (!split.closed) {\n return {\n ok: false,\n hasFrontmatter: true,\n error: \"Frontmatter closing delimiter not found\",\n raw: split.raw,\n body: split.body,\n };\n }\n\n const parsed = parseYamlRecord(split.raw);\n if (!parsed.ok) {\n return {\n ok: false,\n hasFrontmatter: true,\n error: parsed.error,\n raw: split.raw,\n body: split.body,\n };\n }\n\n return {\n ok: true,\n hasFrontmatter: true,\n frontmatter: parsed.value,\n raw: split.raw,\n body: split.body,\n };\n}\n\nexport function fixtureFrontmatterState(\n frontmatter: Record<string, unknown>,\n): FixtureFrontmatterState {\n const ai = recordValue(frontmatter.ai);\n const runtime = aiToRuntime(ai);\n const envVars = envToRuntimeEnvVars(frontmatter.env);\n if (envVars.length > 0) {\n runtime.setup = { ...runtime.setup, envVars };\n }\n const aiExtras = aiToExtras(ai);\n return { runtime, aiExtras };\n}\n\nexport function applyFixtureFrontmatterState(\n markdown: string,\n state: FixtureFrontmatterState,\n options: FixtureFrontmatterApplyOptions = {},\n): string {\n const parsed = parseFixtureFrontmatter(markdown);\n const body = parsed.body;\n const existing = parsed.ok ? parsed.frontmatter : {};\n const frontmatter = frontmatterFromState(existing, state, options);\n return serializeFixtureFrontmatter(frontmatter, body);\n}\n\nexport function applyFixtureFrontmatterRaw(\n markdown: string,\n raw: string,\n): string {\n const split = splitMarkdownFrontmatter(markdown);\n const body = split.hasFrontmatter ? split.body : markdown;\n if (raw.trim() === \"\") return body;\n const normalizedRaw = raw.endsWith(\"\\n\") ? raw : `${raw}\\n`;\n return `---\\n${normalizedRaw}---\\n${body}`;\n}\n\nexport function frontmatterFromState(\n existing: Record<string, unknown>,\n state: FixtureFrontmatterState,\n options: FixtureFrontmatterApplyOptions = {},\n): Record<string, unknown> {\n const next = omitKeys(existing, [\"ai\", \"env\"]);\n const currentAI = recordValue(existing.ai);\n const ai = {\n ...omitControlledAIKeys(currentAI),\n ...runtimeToAI(state.runtime, options),\n ...compactAIExtras(state.aiExtras),\n };\n const env = runtimeEnvVarsToEnv(state.runtime.setup?.envVars);\n\n if (hasKeys(ai)) next.ai = ai;\n if (hasKeys(env)) next.env = env;\n return next;\n}\n\nfunction aiToRuntime(ai: Record<string, unknown>): AISpecRuntimeValue {\n const runtime: AISpecRuntimeValue = {};\n const model = stringValue(ai.model);\n if (model) runtime.model = model;\n const backend = stringValue(ai.backend);\n if (backend) runtime.backend = backend;\n const id = stringValue(ai.id);\n if (id) runtime.id = id;\n const effort = stringValue(ai.effort);\n if (effort) runtime.effort = effort;\n const temperature = numberValue(ai.temperature);\n if (temperature != null) runtime.temperature = temperature;\n if (ai.noCache === true) runtime.noCache = true;\n\n const budget = recordValue(ai.budget);\n const maxTokens = numberValue(ai.maxTokens) ?? numberValue(budget.maxTokens);\n const cost = numberValue(budget.cost);\n const maxTurns = numberValue(budget.maxTurns);\n const timeout = stringValue(budget.timeout);\n if (maxTokens != null || cost != null || maxTurns != null || timeout) {\n runtime.budget = {\n ...(cost != null ? { cost } : {}),\n ...(maxTokens != null ? { maxTokens } : {}),\n ...(maxTurns != null ? { maxTurns } : {}),\n ...(timeout ? { timeout } : {}),\n };\n }\n\n const prompt = promptToRuntimePrompt(ai.prompt);\n if (prompt) runtime.prompt = prompt;\n\n return runtime;\n}\n\nfunction runtimeToAI(\n runtime: AISpecRuntimeValue,\n options: FixtureFrontmatterApplyOptions = {},\n): Record<string, unknown> {\n const compact = compactAISpecRuntime(runtime);\n const ai: Record<string, unknown> = {};\n for (const key of AI_RUNTIME_KEYS) {\n if (options.inheritModel && AI_MODEL_KEYS.has(key)) continue;\n const value = (compact as Record<string, unknown>)[key];\n if (value != null && (key !== \"budget\" || hasKeys(recordValue(value)))) {\n ai[key] = value;\n }\n }\n const maxTokens = compact.budget?.maxTokens;\n if (maxTokens != null && !options.inheritModel) {\n delete ai.budget;\n ai.maxTokens = maxTokens;\n }\n return ai;\n}\n\nfunction promptToRuntimePrompt(\n value: unknown,\n): AISpecRuntimeValue[\"prompt\"] | undefined {\n if (typeof value === \"string\") {\n const user = stringValue(value);\n return user ? { user } : undefined;\n }\n const prompt = recordValue(value);\n const user = stringValue(prompt.user);\n const system = stringValue(prompt.system);\n const appendSystem = stringValue(prompt.appendSystem);\n const source = stringValue(prompt.source);\n const metadata = recordStringMap(prompt.metadata);\n const out = {\n ...(user ? { user } : {}),\n ...(system ? { system } : {}),\n ...(appendSystem ? { appendSystem } : {}),\n ...(source ? { source } : {}),\n ...(metadata ? { metadata } : {}),\n };\n return hasKeys(out) ? out : undefined;\n}\n\nfunction aiToExtras(ai: Record<string, unknown>): FixtureAIExtras {\n const maxConcurrent = numberValue(ai.maxConcurrent);\n const cacheTTL = stringValue(ai.cacheTTL);\n return {\n ...(maxConcurrent != null ? { maxConcurrent } : {}),\n ...(cacheTTL ? { cacheTTL } : {}),\n };\n}\n\nfunction compactAIExtras(extras: FixtureAIExtras): Record<string, unknown> {\n return {\n ...(numberValue(extras.maxConcurrent) != null\n ? { maxConcurrent: numberValue(extras.maxConcurrent) }\n : {}),\n ...(stringValue(extras.cacheTTL) ? { cacheTTL: stringValue(extras.cacheTTL) } : {}),\n };\n}\n\nfunction envToRuntimeEnvVars(value: unknown): AISpecRuntimeEnvVar[] {\n if (!isRecord(value)) return [];\n const envVars: AISpecRuntimeEnvVar[] = [];\n for (const [name, envValue] of Object.entries(value)) {\n const key = name.trim();\n if (!key || typeof envValue !== \"string\") continue;\n envVars.push({ name: key, value: envValue });\n }\n return envVars;\n}\n\nfunction runtimeEnvVarsToEnv(\n value: AISpecRuntimeEnvVar[] | undefined,\n): Record<string, unknown> {\n const env: Record<string, unknown> = {};\n for (const item of value ?? []) {\n const name = stringValue(item.name);\n if (!name) continue;\n const literal = typeof item.value === \"string\" ? item.value : undefined;\n const valueFrom =\n typeof item.valueFrom === \"string\" ? item.valueFrom : undefined;\n if (literal != null) env[name] = literal;\n else if (valueFrom) env[name] = valueFrom;\n }\n return env;\n}\n\nfunction serializeFixtureFrontmatter(\n frontmatter: Record<string, unknown>,\n body: string,\n): string {\n if (!hasKeys(frontmatter)) return body;\n const yaml = stringify(frontmatter, {\n lineWidth: 0,\n collectionStyle: \"block\",\n });\n const normalizedYaml = yaml.endsWith(\"\\n\") ? yaml : `${yaml}\\n`;\n return `---\\n${normalizedYaml}---\\n${body}`;\n}\n\nfunction splitMarkdownFrontmatter(markdown: string):\n | { hasFrontmatter: false }\n | { hasFrontmatter: true; closed: boolean; raw: string; body: string } {\n const lines = splitLinesWithEndings(markdown);\n if (stripLineEnding(lines[0] ?? \"\") !== \"---\") return { hasFrontmatter: false };\n\n for (let index = 1; index < lines.length; index += 1) {\n const line = stripLineEnding(lines[index] ?? \"\");\n if (line === \"---\" || line === \"...\") {\n return {\n hasFrontmatter: true,\n closed: true,\n raw: lines.slice(1, index).join(\"\"),\n body: lines.slice(index + 1).join(\"\"),\n };\n }\n }\n\n return {\n hasFrontmatter: true,\n closed: false,\n raw: lines.slice(1).join(\"\"),\n body: \"\",\n };\n}\n\nfunction splitLinesWithEndings(text: string): string[] {\n if (text === \"\") return [];\n const lines = text.match(/[^\\n]*(?:\\n|$)/g) ?? [];\n if (lines.at(-1) === \"\") lines.pop();\n return lines;\n}\n\nfunction stripLineEnding(line: string): string {\n return line.replace(/\\r?\\n$/, \"\").trim();\n}\n\nfunction parseYamlRecord(\n yaml: string,\n): { ok: true; value: Record<string, unknown> } | { ok: false; error: string } {\n if (yaml.trim() === \"\") return { ok: true, value: {} };\n const doc = parseDocument(yaml, { prettyErrors: false });\n const firstError = doc.errors[0];\n if (firstError) return { ok: false, error: firstError.message };\n const value = doc.toJSON();\n if (value == null) return { ok: true, value: {} };\n if (!isRecord(value)) return { ok: false, error: \"Frontmatter root must be an object\" };\n return { ok: true, value };\n}\n\nfunction omitControlledAIKeys(ai: Record<string, unknown>): Record<string, unknown> {\n const omitted = new Set([...AI_RUNTIME_KEYS, ...AI_EXTRA_KEYS, \"maxTokens\"]);\n return omitKeys(ai, [...omitted]);\n}\n\nfunction omitKeys(\n value: Record<string, unknown>,\n keys: readonly string[],\n): Record<string, unknown> {\n const omitted = new Set(keys);\n return Object.fromEntries(\n Object.entries(value).filter(([key]) => !omitted.has(key)),\n );\n}\n\nfunction recordValue(value: unknown): Record<string, unknown> {\n return isRecord(value) ? value : {};\n}\n\nfunction recordStringMap(value: unknown): Record<string, string> | undefined {\n if (!isRecord(value)) return undefined;\n const out: Record<string, string> = {};\n for (const [rawKey, rawValue] of Object.entries(value)) {\n const key = rawKey.trim();\n if (!key || typeof rawValue !== \"string\") continue;\n out[key] = rawValue;\n }\n return hasKeys(out) ? out : undefined;\n}\n\nfunction stringValue(value: unknown): string | undefined {\n return typeof value === \"string\" && value.trim() ? value.trim() : undefined;\n}\n\nfunction numberValue(value: unknown): number | undefined {\n return typeof value === \"number\" && Number.isFinite(value) ? value : undefined;\n}\n\nfunction hasKeys(value: Record<string, unknown>): boolean {\n return Object.keys(value).length > 0;\n}\n\nfunction isRecord(value: unknown): value is Record<string, unknown> {\n return typeof value === \"object\" && value != null && !Array.isArray(value);\n}\n"],"names":["user"],"mappings":";;AAsCA,MAAM,sCAAsB,IAAI;AAAA,EAC9B;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,CAAC;AAED,MAAM,oCAAoB,IAAI;AAAA,EAC5B;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,CAAC;AAED,MAAM,gBAAgB,oBAAI,IAAI,CAAC,iBAAiB,UAAU,CAAC;AAEpD,SAAS,wBACd,UAC+B;AAC/B,QAAM,QAAQ,yBAAyB,QAAQ;AAC/C,MAAI,CAAC,MAAM,gBAAgB;AACzB,WAAO;AAAA,MACL,IAAI;AAAA,MACJ,gBAAgB;AAAA,MAChB,aAAa,CAAA;AAAA,MACb,KAAK;AAAA,MACL,MAAM;AAAA,IAAA;AAAA,EAEV;AACA,MAAI,CAAC,MAAM,QAAQ;AACjB,WAAO;AAAA,MACL,IAAI;AAAA,MACJ,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,KAAK,MAAM;AAAA,MACX,MAAM,MAAM;AAAA,IAAA;AAAA,EAEhB;AAEA,QAAM,SAAS,gBAAgB,MAAM,GAAG;AACxC,MAAI,CAAC,OAAO,IAAI;AACd,WAAO;AAAA,MACL,IAAI;AAAA,MACJ,gBAAgB;AAAA,MAChB,OAAO,OAAO;AAAA,MACd,KAAK,MAAM;AAAA,MACX,MAAM,MAAM;AAAA,IAAA;AAAA,EAEhB;AAEA,SAAO;AAAA,IACL,IAAI;AAAA,IACJ,gBAAgB;AAAA,IAChB,aAAa,OAAO;AAAA,IACpB,KAAK,MAAM;AAAA,IACX,MAAM,MAAM;AAAA,EAAA;AAEhB;AAEO,SAAS,wBACd,aACyB;AACzB,QAAM,KAAK,YAAY,YAAY,EAAE;AACrC,QAAM,UAAU,YAAY,EAAE;AAC9B,QAAM,UAAU,oBAAoB,YAAY,GAAG;AACnD,MAAI,QAAQ,SAAS,GAAG;AACtB,YAAQ,QAAQ,EAAE,GAAG,QAAQ,OAAO,QAAA;AAAA,EACtC;AACA,QAAM,WAAW,WAAW,EAAE;AAC9B,SAAO,EAAE,SAAS,SAAA;AACpB;AAEO,SAAS,6BACd,UACA,OACA,UAA0C,CAAA,GAClC;AACR,QAAM,SAAS,wBAAwB,QAAQ;AAC/C,QAAM,OAAO,OAAO;AACpB,QAAM,WAAW,OAAO,KAAK,OAAO,cAAc,CAAA;AAClD,QAAM,cAAc,qBAAqB,UAAU,OAAO,OAAO;AACjE,SAAO,4BAA4B,aAAa,IAAI;AACtD;AAEO,SAAS,2BACd,UACA,KACQ;AACR,QAAM,QAAQ,yBAAyB,QAAQ;AAC/C,QAAM,OAAO,MAAM,iBAAiB,MAAM,OAAO;AACjD,MAAI,IAAI,WAAW,GAAI,QAAO;AAC9B,QAAM,gBAAgB,IAAI,SAAS,IAAI,IAAI,MAAM,GAAG,GAAG;AAAA;AACvD,SAAO;AAAA,EAAQ,aAAa;AAAA,EAAQ,IAAI;AAC1C;AAEO,SAAS,qBACd,UACA,OACA,UAA0C,CAAA,GACjB;;AACzB,QAAM,OAAO,SAAS,UAAU,CAAC,MAAM,KAAK,CAAC;AAC7C,QAAM,YAAY,YAAY,SAAS,EAAE;AACzC,QAAM,KAAK;AAAA,IACT,GAAG,qBAAqB,SAAS;AAAA,IACjC,GAAG,YAAY,MAAM,SAAS,OAAO;AAAA,IACrC,GAAG,gBAAgB,MAAM,QAAQ;AAAA,EAAA;AAEnC,QAAM,MAAM,qBAAoB,WAAM,QAAQ,UAAd,mBAAqB,OAAO;AAE5D,MAAI,QAAQ,EAAE,EAAG,MAAK,KAAK;AAC3B,MAAI,QAAQ,GAAG,EAAG,MAAK,MAAM;AAC7B,SAAO;AACT;AAEA,SAAS,YAAY,IAAiD;AACpE,QAAM,UAA8B,CAAA;AACpC,QAAM,QAAQ,YAAY,GAAG,KAAK;AAClC,MAAI,eAAe,QAAQ;AAC3B,QAAM,UAAU,YAAY,GAAG,OAAO;AACtC,MAAI,iBAAiB,UAAU;AAC/B,QAAM,KAAK,YAAY,GAAG,EAAE;AAC5B,MAAI,YAAY,KAAK;AACrB,QAAM,SAAS,YAAY,GAAG,MAAM;AACpC,MAAI,gBAAgB,SAAS;AAC7B,QAAM,cAAc,YAAY,GAAG,WAAW;AAC9C,MAAI,eAAe,KAAM,SAAQ,cAAc;AAC/C,MAAI,GAAG,YAAY,KAAM,SAAQ,UAAU;AAE3C,QAAM,SAAS,YAAY,GAAG,MAAM;AACpC,QAAM,YAAY,YAAY,GAAG,SAAS,KAAK,YAAY,OAAO,SAAS;AAC3E,QAAM,OAAO,YAAY,OAAO,IAAI;AACpC,QAAM,WAAW,YAAY,OAAO,QAAQ;AAC5C,QAAM,UAAU,YAAY,OAAO,OAAO;AAC1C,MAAI,aAAa,QAAQ,QAAQ,QAAQ,YAAY,QAAQ,SAAS;AACpE,YAAQ,SAAS;AAAA,MACf,GAAI,QAAQ,OAAO,EAAE,KAAA,IAAS,CAAA;AAAA,MAC9B,GAAI,aAAa,OAAO,EAAE,UAAA,IAAc,CAAA;AAAA,MACxC,GAAI,YAAY,OAAO,EAAE,SAAA,IAAa,CAAA;AAAA,MACtC,GAAI,UAAU,EAAE,YAAY,CAAA;AAAA,IAAC;AAAA,EAEjC;AAEA,QAAM,SAAS,sBAAsB,GAAG,MAAM;AAC9C,MAAI,gBAAgB,SAAS;AAE7B,SAAO;AACT;AAEA,SAAS,YACP,SACA,UAA0C,IACjB;;AACzB,QAAM,UAAU,qBAAqB,OAAO;AAC5C,QAAM,KAA8B,CAAA;AACpC,aAAW,OAAO,iBAAiB;AACjC,QAAI,QAAQ,gBAAgB,cAAc,IAAI,GAAG,EAAG;AACpD,UAAM,QAAS,QAAoC,GAAG;AACtD,QAAI,SAAS,SAAS,QAAQ,YAAY,QAAQ,YAAY,KAAK,CAAC,IAAI;AACtE,SAAG,GAAG,IAAI;AAAA,IACZ;AAAA,EACF;AACA,QAAM,aAAY,aAAQ,WAAR,mBAAgB;AAClC,MAAI,aAAa,QAAQ,CAAC,QAAQ,cAAc;AAC9C,WAAO,GAAG;AACV,OAAG,YAAY;AAAA,EACjB;AACA,SAAO;AACT;AAEA,SAAS,sBACP,OAC0C;AAC1C,MAAI,OAAO,UAAU,UAAU;AAC7B,UAAMA,QAAO,YAAY,KAAK;AAC9B,WAAOA,QAAO,EAAE,MAAAA,MAAAA,IAAS;AAAA,EAC3B;AACA,QAAM,SAAS,YAAY,KAAK;AAChC,QAAM,OAAO,YAAY,OAAO,IAAI;AACpC,QAAM,SAAS,YAAY,OAAO,MAAM;AACxC,QAAM,eAAe,YAAY,OAAO,YAAY;AACpD,QAAM,SAAS,YAAY,OAAO,MAAM;AACxC,QAAM,WAAW,gBAAgB,OAAO,QAAQ;AAChD,QAAM,MAAM;AAAA,IACV,GAAI,OAAO,EAAE,KAAA,IAAS,CAAA;AAAA,IACtB,GAAI,SAAS,EAAE,OAAA,IAAW,CAAA;AAAA,IAC1B,GAAI,eAAe,EAAE,aAAA,IAAiB,CAAA;AAAA,IACtC,GAAI,SAAS,EAAE,OAAA,IAAW,CAAA;AAAA,IAC1B,GAAI,WAAW,EAAE,aAAa,CAAA;AAAA,EAAC;AAEjC,SAAO,QAAQ,GAAG,IAAI,MAAM;AAC9B;AAEA,SAAS,WAAW,IAA8C;AAChE,QAAM,gBAAgB,YAAY,GAAG,aAAa;AAClD,QAAM,WAAW,YAAY,GAAG,QAAQ;AACxC,SAAO;AAAA,IACL,GAAI,iBAAiB,OAAO,EAAE,cAAA,IAAkB,CAAA;AAAA,IAChD,GAAI,WAAW,EAAE,aAAa,CAAA;AAAA,EAAC;AAEnC;AAEA,SAAS,gBAAgB,QAAkD;AACzE,SAAO;AAAA,IACL,GAAI,YAAY,OAAO,aAAa,KAAK,OACrC,EAAE,eAAe,YAAY,OAAO,aAAa,EAAA,IACjD,CAAA;AAAA,IACJ,GAAI,YAAY,OAAO,QAAQ,IAAI,EAAE,UAAU,YAAY,OAAO,QAAQ,MAAM,CAAA;AAAA,EAAC;AAErF;AAEA,SAAS,oBAAoB,OAAuC;AAClE,MAAI,CAAC,SAAS,KAAK,UAAU,CAAA;AAC7B,QAAM,UAAiC,CAAA;AACvC,aAAW,CAAC,MAAM,QAAQ,KAAK,OAAO,QAAQ,KAAK,GAAG;AACpD,UAAM,MAAM,KAAK,KAAA;AACjB,QAAI,CAAC,OAAO,OAAO,aAAa,SAAU;AAC1C,YAAQ,KAAK,EAAE,MAAM,KAAK,OAAO,UAAU;AAAA,EAC7C;AACA,SAAO;AACT;AAEA,SAAS,oBACP,OACyB;AACzB,QAAM,MAA+B,CAAA;AACrC,aAAW,QAAQ,SAAS,IAAI;AAC9B,UAAM,OAAO,YAAY,KAAK,IAAI;AAClC,QAAI,CAAC,KAAM;AACX,UAAM,UAAU,OAAO,KAAK,UAAU,WAAW,KAAK,QAAQ;AAC9D,UAAM,YACJ,OAAO,KAAK,cAAc,WAAW,KAAK,YAAY;AACxD,QAAI,WAAW,KAAM,KAAI,IAAI,IAAI;AAAA,aACxB,UAAW,KAAI,IAAI,IAAI;AAAA,EAClC;AACA,SAAO;AACT;AAEA,SAAS,4BACP,aACA,MACQ;AACR,MAAI,CAAC,QAAQ,WAAW,EAAG,QAAO;AAClC,QAAM,OAAO,UAAU,aAAa;AAAA,IAClC,WAAW;AAAA,IACX,iBAAiB;AAAA,EAAA,CAClB;AACD,QAAM,iBAAiB,KAAK,SAAS,IAAI,IAAI,OAAO,GAAG,IAAI;AAAA;AAC3D,SAAO;AAAA,EAAQ,cAAc;AAAA,EAAQ,IAAI;AAC3C;AAEA,SAAS,yBAAyB,UAEuC;AACvE,QAAM,QAAQ,sBAAsB,QAAQ;AAC5C,MAAI,gBAAgB,MAAM,CAAC,KAAK,EAAE,MAAM,MAAO,QAAO,EAAE,gBAAgB,MAAA;AAExE,WAAS,QAAQ,GAAG,QAAQ,MAAM,QAAQ,SAAS,GAAG;AACpD,UAAM,OAAO,gBAAgB,MAAM,KAAK,KAAK,EAAE;AAC/C,QAAI,SAAS,SAAS,SAAS,OAAO;AACpC,aAAO;AAAA,QACL,gBAAgB;AAAA,QAChB,QAAQ;AAAA,QACR,KAAK,MAAM,MAAM,GAAG,KAAK,EAAE,KAAK,EAAE;AAAA,QAClC,MAAM,MAAM,MAAM,QAAQ,CAAC,EAAE,KAAK,EAAE;AAAA,MAAA;AAAA,IAExC;AAAA,EACF;AAEA,SAAO;AAAA,IACL,gBAAgB;AAAA,IAChB,QAAQ;AAAA,IACR,KAAK,MAAM,MAAM,CAAC,EAAE,KAAK,EAAE;AAAA,IAC3B,MAAM;AAAA,EAAA;AAEV;AAEA,SAAS,sBAAsB,MAAwB;AACrD,MAAI,SAAS,GAAI,QAAO,CAAA;AACxB,QAAM,QAAQ,KAAK,MAAM,iBAAiB,KAAK,CAAA;AAC/C,MAAI,MAAM,GAAG,EAAE,MAAM,UAAU,IAAA;AAC/B,SAAO;AACT;AAEA,SAAS,gBAAgB,MAAsB;AAC7C,SAAO,KAAK,QAAQ,UAAU,EAAE,EAAE,KAAA;AACpC;AAEA,SAAS,gBACP,MAC6E;AAC7E,MAAI,KAAK,KAAA,MAAW,GAAI,QAAO,EAAE,IAAI,MAAM,OAAO,GAAC;AACnD,QAAM,MAAM,cAAc,MAAM,EAAE,cAAc,OAAO;AACvD,QAAM,aAAa,IAAI,OAAO,CAAC;AAC/B,MAAI,WAAY,QAAO,EAAE,IAAI,OAAO,OAAO,WAAW,QAAA;AACtD,QAAM,QAAQ,IAAI,OAAA;AAClB,MAAI,SAAS,KAAM,QAAO,EAAE,IAAI,MAAM,OAAO,GAAC;AAC9C,MAAI,CAAC,SAAS,KAAK,UAAU,EAAE,IAAI,OAAO,OAAO,qCAAA;AACjD,SAAO,EAAE,IAAI,MAAM,MAAA;AACrB;AAEA,SAAS,qBAAqB,IAAsD;AAClF,QAAM,8BAAc,IAAI,CAAC,GAAG,iBAAiB,GAAG,eAAe,WAAW,CAAC;AAC3E,SAAO,SAAS,IAAI,CAAC,GAAG,OAAO,CAAC;AAClC;AAEA,SAAS,SACP,OACA,MACyB;AACzB,QAAM,UAAU,IAAI,IAAI,IAAI;AAC5B,SAAO,OAAO;AAAA,IACZ,OAAO,QAAQ,KAAK,EAAE,OAAO,CAAC,CAAC,GAAG,MAAM,CAAC,QAAQ,IAAI,GAAG,CAAC;AAAA,EAAA;AAE7D;AAEA,SAAS,YAAY,OAAyC;AAC5D,SAAO,SAAS,KAAK,IAAI,QAAQ,CAAA;AACnC;AAEA,SAAS,gBAAgB,OAAoD;AAC3E,MAAI,CAAC,SAAS,KAAK,EAAG,QAAO;AAC7B,QAAM,MAA8B,CAAA;AACpC,aAAW,CAAC,QAAQ,QAAQ,KAAK,OAAO,QAAQ,KAAK,GAAG;AACtD,UAAM,MAAM,OAAO,KAAA;AACnB,QAAI,CAAC,OAAO,OAAO,aAAa,SAAU;AAC1C,QAAI,GAAG,IAAI;AAAA,EACb;AACA,SAAO,QAAQ,GAAG,IAAI,MAAM;AAC9B;AAEA,SAAS,YAAY,OAAoC;AACvD,SAAO,OAAO,UAAU,YAAY,MAAM,SAAS,MAAM,SAAS;AACpE;AAEA,SAAS,YAAY,OAAoC;AACvD,SAAO,OAAO,UAAU,YAAY,OAAO,SAAS,KAAK,IAAI,QAAQ;AACvE;AAEA,SAAS,QAAQ,OAAyC;AACxD,SAAO,OAAO,KAAK,KAAK,EAAE,SAAS;AACrC;AAEA,SAAS,SAAS,OAAkD;AAClE,SAAO,OAAO,UAAU,YAAY,SAAS,QAAQ,CAAC,MAAM,QAAQ,KAAK;AAC3E;"}
|
|
1
|
+
{"version":3,"file":"fixture-frontmatter.js","sources":["../../../src/data/FixtureEditor/fixture-frontmatter.ts"],"sourcesContent":["import { parseDocument, stringify } from \"yaml\";\nimport {\n compactAISpecRuntime,\n type AISpecRuntimeEnvVar,\n type AISpecRuntimeValue,\n} from \"../ai/SpecRuntimeEditor.model\";\n\nexport type FixtureAIExtras = {\n maxConcurrent?: number;\n cacheTTL?: string;\n};\n\nexport type FixtureFrontmatterState = {\n runtime: AISpecRuntimeValue;\n aiExtras: FixtureAIExtras;\n};\n\nexport type FixtureFrontmatterApplyOptions = {\n /** Omit model/runtime knobs so a verification fixture inherits its parent runtime. */\n inheritModel?: boolean | undefined;\n};\n\nexport type FixtureFrontmatterParseResult =\n | {\n ok: true;\n hasFrontmatter: boolean;\n frontmatter: Record<string, unknown>;\n raw: string;\n body: string;\n }\n | {\n ok: false;\n hasFrontmatter: true;\n error: string;\n raw: string;\n body: string;\n };\n\nconst AI_RUNTIME_KEYS = new Set([\n \"backend\",\n \"budget\",\n \"effort\",\n \"id\",\n \"model\",\n \"mode\",\n \"noCache\",\n \"prompt\",\n \"temperature\",\n]);\n\nconst AI_MODEL_KEYS = new Set([\n \"backend\",\n \"budget\",\n \"effort\",\n \"id\",\n \"model\",\n \"mode\",\n \"noCache\",\n \"temperature\",\n]);\n\nconst AI_EXTRA_KEYS = new Set([\"maxConcurrent\", \"cacheTTL\"]);\n\nexport function parseFixtureFrontmatter(\n markdown: string,\n): FixtureFrontmatterParseResult {\n const split = splitMarkdownFrontmatter(markdown);\n if (!split.hasFrontmatter) {\n return {\n ok: true,\n hasFrontmatter: false,\n frontmatter: {},\n raw: \"\",\n body: markdown,\n };\n }\n if (!split.closed) {\n return {\n ok: false,\n hasFrontmatter: true,\n error: \"Frontmatter closing delimiter not found\",\n raw: split.raw,\n body: split.body,\n };\n }\n\n const parsed = parseYamlRecord(split.raw);\n if (!parsed.ok) {\n return {\n ok: false,\n hasFrontmatter: true,\n error: parsed.error,\n raw: split.raw,\n body: split.body,\n };\n }\n\n return {\n ok: true,\n hasFrontmatter: true,\n frontmatter: parsed.value,\n raw: split.raw,\n body: split.body,\n };\n}\n\nexport function fixtureFrontmatterState(\n frontmatter: Record<string, unknown>,\n): FixtureFrontmatterState {\n const ai = recordValue(frontmatter.ai);\n const runtime = aiToRuntime(ai);\n const envVars = envToRuntimeEnvVars(frontmatter.env);\n if (envVars.length > 0) {\n runtime.setup = { ...runtime.setup, envVars };\n }\n const aiExtras = aiToExtras(ai);\n return { runtime, aiExtras };\n}\n\nexport function applyFixtureFrontmatterState(\n markdown: string,\n state: FixtureFrontmatterState,\n options: FixtureFrontmatterApplyOptions = {},\n): string {\n const parsed = parseFixtureFrontmatter(markdown);\n const body = parsed.body;\n const existing = parsed.ok ? parsed.frontmatter : {};\n const frontmatter = frontmatterFromState(existing, state, options);\n return serializeFixtureFrontmatter(frontmatter, body);\n}\n\nexport function applyFixtureFrontmatterRaw(\n markdown: string,\n raw: string,\n): string {\n const split = splitMarkdownFrontmatter(markdown);\n const body = split.hasFrontmatter ? split.body : markdown;\n if (raw.trim() === \"\") return body;\n const normalizedRaw = raw.endsWith(\"\\n\") ? raw : `${raw}\\n`;\n return `---\\n${normalizedRaw}---\\n${body}`;\n}\n\nexport function frontmatterFromState(\n existing: Record<string, unknown>,\n state: FixtureFrontmatterState,\n options: FixtureFrontmatterApplyOptions = {},\n): Record<string, unknown> {\n const next = omitKeys(existing, [\"ai\", \"env\"]);\n const currentAI = recordValue(existing.ai);\n const ai = {\n ...omitControlledAIKeys(currentAI),\n ...runtimeToAI(state.runtime, options),\n ...compactAIExtras(state.aiExtras),\n };\n const env = runtimeEnvVarsToEnv(state.runtime.setup?.envVars);\n\n if (hasKeys(ai)) next.ai = ai;\n if (hasKeys(env)) next.env = env;\n return next;\n}\n\nfunction aiToRuntime(ai: Record<string, unknown>): AISpecRuntimeValue {\n const runtime: AISpecRuntimeValue = {};\n const model = stringValue(ai.model);\n if (model) runtime.model = model;\n const backend = stringValue(ai.backend);\n if (backend) runtime.backend = backend;\n const mode = stringValue(ai.mode);\n if (mode) runtime.mode = mode;\n const id = stringValue(ai.id);\n if (id) runtime.id = id;\n const effort = stringValue(ai.effort);\n if (effort) runtime.effort = effort;\n const temperature = numberValue(ai.temperature);\n if (temperature != null) runtime.temperature = temperature;\n if (ai.noCache === true) runtime.noCache = true;\n\n const budget = recordValue(ai.budget);\n const maxTokens = numberValue(ai.maxTokens) ?? numberValue(budget.maxTokens);\n const cost = numberValue(budget.cost);\n const maxTurns = numberValue(budget.maxTurns);\n const timeout = stringValue(budget.timeout);\n if (maxTokens != null || cost != null || maxTurns != null || timeout) {\n runtime.budget = {\n ...(cost != null ? { cost } : {}),\n ...(maxTokens != null ? { maxTokens } : {}),\n ...(maxTurns != null ? { maxTurns } : {}),\n ...(timeout ? { timeout } : {}),\n };\n }\n\n const prompt = promptToRuntimePrompt(ai.prompt);\n if (prompt) runtime.prompt = prompt;\n\n return runtime;\n}\n\nfunction runtimeToAI(\n runtime: AISpecRuntimeValue,\n options: FixtureFrontmatterApplyOptions = {},\n): Record<string, unknown> {\n const compact = compactAISpecRuntime(runtime);\n const ai: Record<string, unknown> = {};\n for (const key of AI_RUNTIME_KEYS) {\n if (options.inheritModel && AI_MODEL_KEYS.has(key)) continue;\n const value = (compact as Record<string, unknown>)[key];\n if (value != null && (key !== \"budget\" || hasKeys(recordValue(value)))) {\n ai[key] = value;\n }\n }\n const maxTokens = compact.budget?.maxTokens;\n if (maxTokens != null && !options.inheritModel) {\n delete ai.budget;\n ai.maxTokens = maxTokens;\n }\n return ai;\n}\n\nfunction promptToRuntimePrompt(\n value: unknown,\n): AISpecRuntimeValue[\"prompt\"] | undefined {\n if (typeof value === \"string\") {\n const user = stringValue(value);\n return user ? { user } : undefined;\n }\n const prompt = recordValue(value);\n const user = stringValue(prompt.user);\n const system = stringValue(prompt.system);\n const appendSystem = stringValue(prompt.appendSystem);\n const source = stringValue(prompt.source);\n const metadata = recordStringMap(prompt.metadata);\n const out = {\n ...(user ? { user } : {}),\n ...(system ? { system } : {}),\n ...(appendSystem ? { appendSystem } : {}),\n ...(source ? { source } : {}),\n ...(metadata ? { metadata } : {}),\n };\n return hasKeys(out) ? out : undefined;\n}\n\nfunction aiToExtras(ai: Record<string, unknown>): FixtureAIExtras {\n const maxConcurrent = numberValue(ai.maxConcurrent);\n const cacheTTL = stringValue(ai.cacheTTL);\n return {\n ...(maxConcurrent != null ? { maxConcurrent } : {}),\n ...(cacheTTL ? { cacheTTL } : {}),\n };\n}\n\nfunction compactAIExtras(extras: FixtureAIExtras): Record<string, unknown> {\n return {\n ...(numberValue(extras.maxConcurrent) != null\n ? { maxConcurrent: numberValue(extras.maxConcurrent) }\n : {}),\n ...(stringValue(extras.cacheTTL) ? { cacheTTL: stringValue(extras.cacheTTL) } : {}),\n };\n}\n\nfunction envToRuntimeEnvVars(value: unknown): AISpecRuntimeEnvVar[] {\n if (!isRecord(value)) return [];\n const envVars: AISpecRuntimeEnvVar[] = [];\n for (const [name, envValue] of Object.entries(value)) {\n const key = name.trim();\n if (!key || typeof envValue !== \"string\") continue;\n envVars.push({ name: key, value: envValue });\n }\n return envVars;\n}\n\nfunction runtimeEnvVarsToEnv(\n value: AISpecRuntimeEnvVar[] | undefined,\n): Record<string, unknown> {\n const env: Record<string, unknown> = {};\n for (const item of value ?? []) {\n const name = stringValue(item.name);\n if (!name) continue;\n const literal = typeof item.value === \"string\" ? item.value : undefined;\n const valueFrom =\n typeof item.valueFrom === \"string\" ? item.valueFrom : undefined;\n if (literal != null) env[name] = literal;\n else if (valueFrom) env[name] = valueFrom;\n }\n return env;\n}\n\nfunction serializeFixtureFrontmatter(\n frontmatter: Record<string, unknown>,\n body: string,\n): string {\n if (!hasKeys(frontmatter)) return body;\n const yaml = stringify(frontmatter, {\n lineWidth: 0,\n collectionStyle: \"block\",\n });\n const normalizedYaml = yaml.endsWith(\"\\n\") ? yaml : `${yaml}\\n`;\n return `---\\n${normalizedYaml}---\\n${body}`;\n}\n\nfunction splitMarkdownFrontmatter(markdown: string):\n | { hasFrontmatter: false }\n | { hasFrontmatter: true; closed: boolean; raw: string; body: string } {\n const lines = splitLinesWithEndings(markdown);\n if (stripLineEnding(lines[0] ?? \"\") !== \"---\") return { hasFrontmatter: false };\n\n for (let index = 1; index < lines.length; index += 1) {\n const line = stripLineEnding(lines[index] ?? \"\");\n if (line === \"---\" || line === \"...\") {\n return {\n hasFrontmatter: true,\n closed: true,\n raw: lines.slice(1, index).join(\"\"),\n body: lines.slice(index + 1).join(\"\"),\n };\n }\n }\n\n return {\n hasFrontmatter: true,\n closed: false,\n raw: lines.slice(1).join(\"\"),\n body: \"\",\n };\n}\n\nfunction splitLinesWithEndings(text: string): string[] {\n if (text === \"\") return [];\n const lines = text.match(/[^\\n]*(?:\\n|$)/g) ?? [];\n if (lines.at(-1) === \"\") lines.pop();\n return lines;\n}\n\nfunction stripLineEnding(line: string): string {\n return line.replace(/\\r?\\n$/, \"\").trim();\n}\n\nfunction parseYamlRecord(\n yaml: string,\n): { ok: true; value: Record<string, unknown> } | { ok: false; error: string } {\n if (yaml.trim() === \"\") return { ok: true, value: {} };\n const doc = parseDocument(yaml, { prettyErrors: false });\n const firstError = doc.errors[0];\n if (firstError) return { ok: false, error: firstError.message };\n const value = doc.toJSON();\n if (value == null) return { ok: true, value: {} };\n if (!isRecord(value)) return { ok: false, error: \"Frontmatter root must be an object\" };\n return { ok: true, value };\n}\n\nfunction omitControlledAIKeys(ai: Record<string, unknown>): Record<string, unknown> {\n const omitted = new Set([...AI_RUNTIME_KEYS, ...AI_EXTRA_KEYS, \"maxTokens\"]);\n return omitKeys(ai, [...omitted]);\n}\n\nfunction omitKeys(\n value: Record<string, unknown>,\n keys: readonly string[],\n): Record<string, unknown> {\n const omitted = new Set(keys);\n return Object.fromEntries(\n Object.entries(value).filter(([key]) => !omitted.has(key)),\n );\n}\n\nfunction recordValue(value: unknown): Record<string, unknown> {\n return isRecord(value) ? value : {};\n}\n\nfunction recordStringMap(value: unknown): Record<string, string> | undefined {\n if (!isRecord(value)) return undefined;\n const out: Record<string, string> = {};\n for (const [rawKey, rawValue] of Object.entries(value)) {\n const key = rawKey.trim();\n if (!key || typeof rawValue !== \"string\") continue;\n out[key] = rawValue;\n }\n return hasKeys(out) ? out : undefined;\n}\n\nfunction stringValue(value: unknown): string | undefined {\n return typeof value === \"string\" && value.trim() ? value.trim() : undefined;\n}\n\nfunction numberValue(value: unknown): number | undefined {\n return typeof value === \"number\" && Number.isFinite(value) ? value : undefined;\n}\n\nfunction hasKeys(value: Record<string, unknown>): boolean {\n return Object.keys(value).length > 0;\n}\n\nfunction isRecord(value: unknown): value is Record<string, unknown> {\n return typeof value === \"object\" && value != null && !Array.isArray(value);\n}\n"],"names":["user"],"mappings":"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"}
|
|
@@ -11,12 +11,16 @@ function formatExecDuration(nanoseconds) {
|
|
|
11
11
|
const minutes = Math.floor(seconds / 60);
|
|
12
12
|
return `${minutes}m ${Number((seconds % 60).toFixed(1))}s`;
|
|
13
13
|
}
|
|
14
|
+
function TaskCommandLine({ command, args }) {
|
|
15
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
16
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "text-[11px] font-semibold uppercase tracking-wide text-muted-foreground", children: "Command and arguments" }),
|
|
17
|
+
/* @__PURE__ */ jsxRuntime.jsx("code", { className: "block overflow-x-auto whitespace-pre rounded border bg-background p-2 text-xs", children: JSON.stringify([command, ...args ?? []]) })
|
|
18
|
+
] });
|
|
19
|
+
}
|
|
14
20
|
function TaskExecDetailsView({ details }) {
|
|
15
|
-
const argv = [details.command, ...details.args ?? []];
|
|
16
21
|
const extra = Object.fromEntries(Object.entries(details).filter(([key]) => !EXEC_KEYS.has(key)));
|
|
17
22
|
return /* @__PURE__ */ jsxRuntime.jsxs("section", { "aria-label": "Execution details", className: "mb-3 space-y-2 rounded-md border bg-muted/20 p-3", children: [
|
|
18
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
19
|
-
/* @__PURE__ */ jsxRuntime.jsx("code", { className: "block overflow-x-auto whitespace-pre rounded border bg-background p-2 text-xs", children: JSON.stringify(argv) }),
|
|
23
|
+
/* @__PURE__ */ jsxRuntime.jsx(TaskCommandLine, { command: details.command, ...details.args ? { args: details.args } : {} }),
|
|
20
24
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-wrap items-center gap-x-4 gap-y-1 text-xs text-muted-foreground", children: [
|
|
21
25
|
/* @__PURE__ */ jsxRuntime.jsx("span", { children: details.status }),
|
|
22
26
|
details.pid !== void 0 && /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "font-mono text-foreground", children: [
|
|
@@ -36,5 +40,6 @@ function TaskExecDetailsView({ details }) {
|
|
|
36
40
|
Object.keys(extra).length > 0 && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "rounded border bg-background p-2", children: /* @__PURE__ */ jsxRuntime.jsx(JsonView.JsonView, { data: extra, defaultOpenDepth: 3 }) })
|
|
37
41
|
] });
|
|
38
42
|
}
|
|
43
|
+
exports.TaskCommandLine = TaskCommandLine;
|
|
39
44
|
exports.TaskExecDetailsView = TaskExecDetailsView;
|
|
40
45
|
//# sourceMappingURL=TaskExecDetails.cjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TaskExecDetails.cjs","sources":["../../src/data/TaskExecDetails.tsx"],"sourcesContent":["import { JsonView } from \"./JsonView\";\nimport type { TaskExecDetails } from \"./TaskSnapshot\";\n\nconst EXEC_KEYS = new Set([\"command\", \"args\", \"pid\", \"status\", \"exitCode\", \"started\", \"duration\"]);\n\nfunction formatExecDuration(nanoseconds: number): string {\n const milliseconds = nanoseconds / 1_000_000;\n if (milliseconds < 1000) return `${Number(milliseconds.toFixed(1))}ms`;\n const seconds = milliseconds / 1000;\n if (seconds < 60) return `${Number(seconds.toFixed(1))}s`;\n const minutes = Math.floor(seconds / 60);\n return `${minutes}m ${Number((seconds % 60).toFixed(1))}s`;\n}\n\nexport function
|
|
1
|
+
{"version":3,"file":"TaskExecDetails.cjs","sources":["../../src/data/TaskExecDetails.tsx"],"sourcesContent":["import { JsonView } from \"./JsonView\";\nimport type { TaskExecDetails } from \"./TaskSnapshot\";\n\nconst EXEC_KEYS = new Set([\"command\", \"args\", \"pid\", \"status\", \"exitCode\", \"started\", \"duration\"]);\n\nfunction formatExecDuration(nanoseconds: number): string {\n const milliseconds = nanoseconds / 1_000_000;\n if (milliseconds < 1000) return `${Number(milliseconds.toFixed(1))}ms`;\n const seconds = milliseconds / 1000;\n if (seconds < 60) return `${Number(seconds.toFixed(1))}s`;\n const minutes = Math.floor(seconds / 60);\n return `${minutes}m ${Number((seconds % 60).toFixed(1))}s`;\n}\n\nexport function TaskCommandLine({ command, args }: { command: string; args?: string[] }) {\n return (\n <>\n <div className=\"text-[11px] font-semibold uppercase tracking-wide text-muted-foreground\">\n Command and arguments\n </div>\n <code className=\"block overflow-x-auto whitespace-pre rounded border bg-background p-2 text-xs\">\n {JSON.stringify([command, ...(args ?? [])])}\n </code>\n </>\n );\n}\n\nexport function TaskExecDetailsView({ details }: { details: TaskExecDetails }) {\n const extra = Object.fromEntries(Object.entries(details).filter(([key]) => !EXEC_KEYS.has(key)));\n\n return (\n <section aria-label=\"Execution details\" className=\"mb-3 space-y-2 rounded-md border bg-muted/20 p-3\">\n <TaskCommandLine command={details.command} {...(details.args ? { args: details.args } : {})} />\n <div className=\"flex flex-wrap items-center gap-x-4 gap-y-1 text-xs text-muted-foreground\">\n <span>{details.status}</span>\n {details.pid !== undefined && <span className=\"font-mono text-foreground\">pid {details.pid}</span>}\n <span className=\"font-mono text-foreground\">exit {details.exitCode}</span>\n {details.duration !== undefined && <span>{formatExecDuration(details.duration)}</span>}\n {details.started && <span>started {details.started}</span>}\n </div>\n {Object.keys(extra).length > 0 && (\n <div className=\"rounded border bg-background p-2\">\n <JsonView data={extra} defaultOpenDepth={3} />\n </div>\n )}\n </section>\n );\n}\n"],"names":["jsxs","Fragment","jsx","JsonView"],"mappings":";;;;AAGA,MAAM,YAAY,oBAAI,IAAI,CAAC,WAAW,QAAQ,OAAO,UAAU,YAAY,WAAW,UAAU,CAAC;AAEjG,SAAS,mBAAmB,aAA6B;AACvD,QAAM,eAAe,cAAc;AACnC,MAAI,eAAe,IAAM,QAAO,GAAG,OAAO,aAAa,QAAQ,CAAC,CAAC,CAAC;AAClE,QAAM,UAAU,eAAe;AAC/B,MAAI,UAAU,GAAI,QAAO,GAAG,OAAO,QAAQ,QAAQ,CAAC,CAAC,CAAC;AACtD,QAAM,UAAU,KAAK,MAAM,UAAU,EAAE;AACvC,SAAO,GAAG,OAAO,KAAK,QAAQ,UAAU,IAAI,QAAQ,CAAC,CAAC,CAAC;AACzD;AAEO,SAAS,gBAAgB,EAAE,SAAS,QAA8C;AACvF,SACEA,2BAAAA,KAAAC,qBAAA,EACE,UAAA;AAAA,IAAAC,2BAAAA,IAAC,OAAA,EAAI,WAAU,2EAA0E,UAAA,yBAEzF;AAAA,IACAA,2BAAAA,IAAC,QAAA,EAAK,WAAU,iFACb,UAAA,KAAK,UAAU,CAAC,SAAS,GAAI,QAAQ,CAAA,CAAG,CAAC,EAAA,CAC5C;AAAA,EAAA,GACF;AAEJ;AAEO,SAAS,oBAAoB,EAAE,WAAyC;AAC7E,QAAM,QAAQ,OAAO,YAAY,OAAO,QAAQ,OAAO,EAAE,OAAO,CAAC,CAAC,GAAG,MAAM,CAAC,UAAU,IAAI,GAAG,CAAC,CAAC;AAE/F,SACEF,2BAAAA,KAAC,WAAA,EAAQ,cAAW,qBAAoB,WAAU,oDAChD,UAAA;AAAA,IAAAE,2BAAAA,IAAC,iBAAA,EAAgB,SAAS,QAAQ,SAAU,GAAI,QAAQ,OAAO,EAAE,MAAM,QAAQ,KAAA,IAAS,CAAA,EAAC,CAAI;AAAA,IAC7FF,2BAAAA,KAAC,OAAA,EAAI,WAAU,6EACb,UAAA;AAAA,MAAAE,2BAAAA,IAAC,QAAA,EAAM,kBAAQ,OAAA,CAAO;AAAA,MACrB,QAAQ,QAAQ,UAAaF,2BAAAA,KAAC,QAAA,EAAK,WAAU,6BAA4B,UAAA;AAAA,QAAA;AAAA,QAAK,QAAQ;AAAA,MAAA,GAAI;AAAA,MAC3FA,2BAAAA,KAAC,QAAA,EAAK,WAAU,6BAA4B,UAAA;AAAA,QAAA;AAAA,QAAM,QAAQ;AAAA,MAAA,GAAS;AAAA,MAClE,QAAQ,aAAa,UAAaE,2BAAAA,IAAC,UAAM,UAAA,mBAAmB,QAAQ,QAAQ,GAAE;AAAA,MAC9E,QAAQ,WAAWF,2BAAAA,KAAC,QAAA,EAAK,UAAA;AAAA,QAAA;AAAA,QAAS,QAAQ;AAAA,MAAA,EAAA,CAAQ;AAAA,IAAA,GACrD;AAAA,IACC,OAAO,KAAK,KAAK,EAAE,SAAS,KAC3BE,2BAAAA,IAAC,OAAA,EAAI,WAAU,oCACb,yCAACC,SAAAA,UAAA,EAAS,MAAM,OAAO,kBAAkB,GAAG,EAAA,CAC9C;AAAA,EAAA,GAEJ;AAEJ;;;"}
|
|
@@ -1,4 +1,8 @@
|
|
|
1
1
|
import { TaskExecDetails } from './TaskSnapshot';
|
|
2
|
+
export declare function TaskCommandLine({ command, args }: {
|
|
3
|
+
command: string;
|
|
4
|
+
args?: string[];
|
|
5
|
+
}): import("react/jsx-runtime").JSX.Element;
|
|
2
6
|
export declare function TaskExecDetailsView({ details }: {
|
|
3
7
|
details: TaskExecDetails;
|
|
4
8
|
}): import("react/jsx-runtime").JSX.Element;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TaskExecDetails.d.ts","sourceRoot":"","sources":["../../src/data/TaskExecDetails.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC;AAatD,wBAAgB,mBAAmB,CAAC,EAAE,OAAO,EAAE,EAAE;IAAE,OAAO,EAAE,eAAe,CAAA;CAAE,
|
|
1
|
+
{"version":3,"file":"TaskExecDetails.d.ts","sourceRoot":"","sources":["../../src/data/TaskExecDetails.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC;AAatD,wBAAgB,eAAe,CAAC,EAAE,OAAO,EAAE,IAAI,EAAE,EAAE;IAAE,OAAO,EAAE,MAAM,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,EAAE,CAAA;CAAE,2CAWtF;AAED,wBAAgB,mBAAmB,CAAC,EAAE,OAAO,EAAE,EAAE;IAAE,OAAO,EAAE,eAAe,CAAA;CAAE,2CAoB5E"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { jsxs, jsx } from "react/jsx-runtime";
|
|
1
|
+
import { jsxs, jsx, Fragment } from "react/jsx-runtime";
|
|
2
2
|
import { JsonView } from "./JsonView.js";
|
|
3
3
|
const EXEC_KEYS = /* @__PURE__ */ new Set(["command", "args", "pid", "status", "exitCode", "started", "duration"]);
|
|
4
4
|
function formatExecDuration(nanoseconds) {
|
|
@@ -9,12 +9,16 @@ function formatExecDuration(nanoseconds) {
|
|
|
9
9
|
const minutes = Math.floor(seconds / 60);
|
|
10
10
|
return `${minutes}m ${Number((seconds % 60).toFixed(1))}s`;
|
|
11
11
|
}
|
|
12
|
+
function TaskCommandLine({ command, args }) {
|
|
13
|
+
return /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
14
|
+
/* @__PURE__ */ jsx("div", { className: "text-[11px] font-semibold uppercase tracking-wide text-muted-foreground", children: "Command and arguments" }),
|
|
15
|
+
/* @__PURE__ */ jsx("code", { className: "block overflow-x-auto whitespace-pre rounded border bg-background p-2 text-xs", children: JSON.stringify([command, ...args ?? []]) })
|
|
16
|
+
] });
|
|
17
|
+
}
|
|
12
18
|
function TaskExecDetailsView({ details }) {
|
|
13
|
-
const argv = [details.command, ...details.args ?? []];
|
|
14
19
|
const extra = Object.fromEntries(Object.entries(details).filter(([key]) => !EXEC_KEYS.has(key)));
|
|
15
20
|
return /* @__PURE__ */ jsxs("section", { "aria-label": "Execution details", className: "mb-3 space-y-2 rounded-md border bg-muted/20 p-3", children: [
|
|
16
|
-
/* @__PURE__ */ jsx(
|
|
17
|
-
/* @__PURE__ */ jsx("code", { className: "block overflow-x-auto whitespace-pre rounded border bg-background p-2 text-xs", children: JSON.stringify(argv) }),
|
|
21
|
+
/* @__PURE__ */ jsx(TaskCommandLine, { command: details.command, ...details.args ? { args: details.args } : {} }),
|
|
18
22
|
/* @__PURE__ */ jsxs("div", { className: "flex flex-wrap items-center gap-x-4 gap-y-1 text-xs text-muted-foreground", children: [
|
|
19
23
|
/* @__PURE__ */ jsx("span", { children: details.status }),
|
|
20
24
|
details.pid !== void 0 && /* @__PURE__ */ jsxs("span", { className: "font-mono text-foreground", children: [
|
|
@@ -35,6 +39,7 @@ function TaskExecDetailsView({ details }) {
|
|
|
35
39
|
] });
|
|
36
40
|
}
|
|
37
41
|
export {
|
|
42
|
+
TaskCommandLine,
|
|
38
43
|
TaskExecDetailsView
|
|
39
44
|
};
|
|
40
45
|
//# sourceMappingURL=TaskExecDetails.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TaskExecDetails.js","sources":["../../src/data/TaskExecDetails.tsx"],"sourcesContent":["import { JsonView } from \"./JsonView\";\nimport type { TaskExecDetails } from \"./TaskSnapshot\";\n\nconst EXEC_KEYS = new Set([\"command\", \"args\", \"pid\", \"status\", \"exitCode\", \"started\", \"duration\"]);\n\nfunction formatExecDuration(nanoseconds: number): string {\n const milliseconds = nanoseconds / 1_000_000;\n if (milliseconds < 1000) return `${Number(milliseconds.toFixed(1))}ms`;\n const seconds = milliseconds / 1000;\n if (seconds < 60) return `${Number(seconds.toFixed(1))}s`;\n const minutes = Math.floor(seconds / 60);\n return `${minutes}m ${Number((seconds % 60).toFixed(1))}s`;\n}\n\nexport function
|
|
1
|
+
{"version":3,"file":"TaskExecDetails.js","sources":["../../src/data/TaskExecDetails.tsx"],"sourcesContent":["import { JsonView } from \"./JsonView\";\nimport type { TaskExecDetails } from \"./TaskSnapshot\";\n\nconst EXEC_KEYS = new Set([\"command\", \"args\", \"pid\", \"status\", \"exitCode\", \"started\", \"duration\"]);\n\nfunction formatExecDuration(nanoseconds: number): string {\n const milliseconds = nanoseconds / 1_000_000;\n if (milliseconds < 1000) return `${Number(milliseconds.toFixed(1))}ms`;\n const seconds = milliseconds / 1000;\n if (seconds < 60) return `${Number(seconds.toFixed(1))}s`;\n const minutes = Math.floor(seconds / 60);\n return `${minutes}m ${Number((seconds % 60).toFixed(1))}s`;\n}\n\nexport function TaskCommandLine({ command, args }: { command: string; args?: string[] }) {\n return (\n <>\n <div className=\"text-[11px] font-semibold uppercase tracking-wide text-muted-foreground\">\n Command and arguments\n </div>\n <code className=\"block overflow-x-auto whitespace-pre rounded border bg-background p-2 text-xs\">\n {JSON.stringify([command, ...(args ?? [])])}\n </code>\n </>\n );\n}\n\nexport function TaskExecDetailsView({ details }: { details: TaskExecDetails }) {\n const extra = Object.fromEntries(Object.entries(details).filter(([key]) => !EXEC_KEYS.has(key)));\n\n return (\n <section aria-label=\"Execution details\" className=\"mb-3 space-y-2 rounded-md border bg-muted/20 p-3\">\n <TaskCommandLine command={details.command} {...(details.args ? { args: details.args } : {})} />\n <div className=\"flex flex-wrap items-center gap-x-4 gap-y-1 text-xs text-muted-foreground\">\n <span>{details.status}</span>\n {details.pid !== undefined && <span className=\"font-mono text-foreground\">pid {details.pid}</span>}\n <span className=\"font-mono text-foreground\">exit {details.exitCode}</span>\n {details.duration !== undefined && <span>{formatExecDuration(details.duration)}</span>}\n {details.started && <span>started {details.started}</span>}\n </div>\n {Object.keys(extra).length > 0 && (\n <div className=\"rounded border bg-background p-2\">\n <JsonView data={extra} defaultOpenDepth={3} />\n </div>\n )}\n </section>\n );\n}\n"],"names":[],"mappings":";;AAGA,MAAM,YAAY,oBAAI,IAAI,CAAC,WAAW,QAAQ,OAAO,UAAU,YAAY,WAAW,UAAU,CAAC;AAEjG,SAAS,mBAAmB,aAA6B;AACvD,QAAM,eAAe,cAAc;AACnC,MAAI,eAAe,IAAM,QAAO,GAAG,OAAO,aAAa,QAAQ,CAAC,CAAC,CAAC;AAClE,QAAM,UAAU,eAAe;AAC/B,MAAI,UAAU,GAAI,QAAO,GAAG,OAAO,QAAQ,QAAQ,CAAC,CAAC,CAAC;AACtD,QAAM,UAAU,KAAK,MAAM,UAAU,EAAE;AACvC,SAAO,GAAG,OAAO,KAAK,QAAQ,UAAU,IAAI,QAAQ,CAAC,CAAC,CAAC;AACzD;AAEO,SAAS,gBAAgB,EAAE,SAAS,QAA8C;AACvF,SACE,qBAAA,UAAA,EACE,UAAA;AAAA,IAAA,oBAAC,OAAA,EAAI,WAAU,2EAA0E,UAAA,yBAEzF;AAAA,IACA,oBAAC,QAAA,EAAK,WAAU,iFACb,UAAA,KAAK,UAAU,CAAC,SAAS,GAAI,QAAQ,CAAA,CAAG,CAAC,EAAA,CAC5C;AAAA,EAAA,GACF;AAEJ;AAEO,SAAS,oBAAoB,EAAE,WAAyC;AAC7E,QAAM,QAAQ,OAAO,YAAY,OAAO,QAAQ,OAAO,EAAE,OAAO,CAAC,CAAC,GAAG,MAAM,CAAC,UAAU,IAAI,GAAG,CAAC,CAAC;AAE/F,SACE,qBAAC,WAAA,EAAQ,cAAW,qBAAoB,WAAU,oDAChD,UAAA;AAAA,IAAA,oBAAC,iBAAA,EAAgB,SAAS,QAAQ,SAAU,GAAI,QAAQ,OAAO,EAAE,MAAM,QAAQ,KAAA,IAAS,CAAA,EAAC,CAAI;AAAA,IAC7F,qBAAC,OAAA,EAAI,WAAU,6EACb,UAAA;AAAA,MAAA,oBAAC,QAAA,EAAM,kBAAQ,OAAA,CAAO;AAAA,MACrB,QAAQ,QAAQ,UAAa,qBAAC,QAAA,EAAK,WAAU,6BAA4B,UAAA;AAAA,QAAA;AAAA,QAAK,QAAQ;AAAA,MAAA,GAAI;AAAA,MAC3F,qBAAC,QAAA,EAAK,WAAU,6BAA4B,UAAA;AAAA,QAAA;AAAA,QAAM,QAAQ;AAAA,MAAA,GAAS;AAAA,MAClE,QAAQ,aAAa,UAAa,oBAAC,UAAM,UAAA,mBAAmB,QAAQ,QAAQ,GAAE;AAAA,MAC9E,QAAQ,WAAW,qBAAC,QAAA,EAAK,UAAA;AAAA,QAAA;AAAA,QAAS,QAAQ;AAAA,MAAA,EAAA,CAAQ;AAAA,IAAA,GACrD;AAAA,IACC,OAAO,KAAK,KAAK,EAAE,SAAS,KAC3B,oBAAC,OAAA,EAAI,WAAU,oCACb,8BAAC,UAAA,EAAS,MAAM,OAAO,kBAAkB,GAAG,EAAA,CAC9C;AAAA,EAAA,GAEJ;AAEJ;"}
|
|
@@ -4,16 +4,84 @@ const jsxRuntime = require("react/jsx-runtime");
|
|
|
4
4
|
const button = require("../components/button.cjs");
|
|
5
5
|
const useTaskRun = require("../hooks/use-task-run.cjs");
|
|
6
6
|
const DropdownMenu = require("../overlay/DropdownMenu.cjs");
|
|
7
|
+
const format = require("../lib/format.cjs");
|
|
8
|
+
const TaskManager = require("./TaskManager.cjs");
|
|
9
|
+
const taskProcessDetails = require("./task-process-details.cjs");
|
|
7
10
|
const taskStatus = require("./task-status.cjs");
|
|
8
11
|
const UiListChecks = require("../icons/components/UiListChecks.cjs");
|
|
12
|
+
const UiActivity = require("../icons/components/UiActivity.cjs");
|
|
13
|
+
const UiMemoryStick = require("../icons/components/UiMemoryStick.cjs");
|
|
9
14
|
function TaskManagerButton({
|
|
10
15
|
basePath,
|
|
11
16
|
tasksHref = "/tasks",
|
|
12
17
|
latest = 5,
|
|
13
|
-
onNavigate
|
|
18
|
+
onNavigate,
|
|
19
|
+
panel,
|
|
20
|
+
kind,
|
|
21
|
+
labels,
|
|
22
|
+
selectedId,
|
|
23
|
+
onSelectRun
|
|
14
24
|
}) {
|
|
15
|
-
const { runs } = useTaskRun.useTaskRuns({ basePath });
|
|
25
|
+
const { runs } = useTaskRun.useTaskRuns({ basePath, kind, labels });
|
|
16
26
|
const active = runs.filter((run) => run.status === "running" || run.status === "pending").length;
|
|
27
|
+
const activeRun = runs.find((run) => run.status === "running") ?? runs.find((run) => run.status === "pending");
|
|
28
|
+
const { snapshots } = useTaskRun.useTaskRun({
|
|
29
|
+
...basePath ? { basePath } : {},
|
|
30
|
+
...activeRun ? { id: activeRun.id } : {},
|
|
31
|
+
enabled: Boolean(activeRun)
|
|
32
|
+
});
|
|
33
|
+
const resources = resourceSummary(snapshots);
|
|
34
|
+
const trigger = /* @__PURE__ */ jsxRuntime.jsx(TaskTrigger, { active, ...resources ? { resources } : {} });
|
|
35
|
+
return panel ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
36
|
+
TaskPanelDropdown,
|
|
37
|
+
{
|
|
38
|
+
...basePath ? { basePath } : {},
|
|
39
|
+
...kind ? { kind } : {},
|
|
40
|
+
...labels ? { labels } : {},
|
|
41
|
+
...onSelectRun ? { onSelectRun } : {},
|
|
42
|
+
...selectedId ? { selectedId } : {},
|
|
43
|
+
trigger
|
|
44
|
+
}
|
|
45
|
+
) : /* @__PURE__ */ jsxRuntime.jsx(
|
|
46
|
+
RecentTasksDropdown,
|
|
47
|
+
{
|
|
48
|
+
latest,
|
|
49
|
+
...onNavigate ? { onNavigate } : {},
|
|
50
|
+
runs,
|
|
51
|
+
tasksHref,
|
|
52
|
+
trigger
|
|
53
|
+
}
|
|
54
|
+
);
|
|
55
|
+
}
|
|
56
|
+
function TaskPanelDropdown({ basePath, kind, labels, onSelectRun, selectedId, trigger }) {
|
|
57
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
58
|
+
DropdownMenu.DropdownMenu,
|
|
59
|
+
{
|
|
60
|
+
align: "right",
|
|
61
|
+
header: /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs font-semibold", children: "Activity" }),
|
|
62
|
+
menuClassName: "w-[min(42rem,calc(100vw-1rem))] max-w-none p-0",
|
|
63
|
+
menuLabel: "Task activity",
|
|
64
|
+
trigger,
|
|
65
|
+
children: () => /* @__PURE__ */ jsxRuntime.jsx("div", { className: "max-h-[min(42rem,calc(100vh-5rem))] overflow-auto p-3", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
66
|
+
TaskManager.TaskManager,
|
|
67
|
+
{
|
|
68
|
+
...basePath ? { basePath } : {},
|
|
69
|
+
...kind ? { kind } : {},
|
|
70
|
+
...labels ? { labels } : {},
|
|
71
|
+
...onSelectRun ? { onSelectRun } : {},
|
|
72
|
+
...selectedId ? { selectedId } : {}
|
|
73
|
+
}
|
|
74
|
+
) })
|
|
75
|
+
}
|
|
76
|
+
);
|
|
77
|
+
}
|
|
78
|
+
function RecentTasksDropdown({
|
|
79
|
+
latest,
|
|
80
|
+
onNavigate,
|
|
81
|
+
runs,
|
|
82
|
+
tasksHref,
|
|
83
|
+
trigger
|
|
84
|
+
}) {
|
|
17
85
|
const navigate = (href) => {
|
|
18
86
|
if (onNavigate) onNavigate(href);
|
|
19
87
|
else window.location.assign(href);
|
|
@@ -30,20 +98,46 @@ function TaskManagerButton({
|
|
|
30
98
|
items.push({ label: "No tasks yet", disabled: true, onSelect: () => {
|
|
31
99
|
} });
|
|
32
100
|
}
|
|
33
|
-
const label = `Tasks (${active} active)`;
|
|
34
101
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
35
102
|
DropdownMenu.DropdownMenu,
|
|
36
103
|
{
|
|
37
104
|
items,
|
|
38
105
|
align: "right",
|
|
39
106
|
menuLabel: "Recent tasks",
|
|
40
|
-
trigger
|
|
41
|
-
/* @__PURE__ */ jsxRuntime.jsx(UiListChecks.UiListChecks, {}),
|
|
42
|
-
active > 0 && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "absolute -right-0.5 -top-0.5 min-w-4 rounded-full bg-primary px-1 text-[9px] leading-4 text-primary-foreground", children: active })
|
|
43
|
-
] }),
|
|
107
|
+
trigger,
|
|
44
108
|
footer: /* @__PURE__ */ jsxRuntime.jsx(button.Button, { type: "button", variant: "ghost", size: "sm", className: "w-full justify-start", onClick: () => navigate(tasksHref), children: "View all tasks" })
|
|
45
109
|
}
|
|
46
110
|
);
|
|
47
111
|
}
|
|
112
|
+
function TaskTrigger({ active, resources }) {
|
|
113
|
+
const label = `Tasks (${active} active)`;
|
|
114
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(button.Button, { type: "button", variant: "ghost", size: resources ? "sm" : "icon", "aria-label": label, title: label, className: "relative gap-1.5", children: [
|
|
115
|
+
/* @__PURE__ */ jsxRuntime.jsx(UiListChecks.UiListChecks, { className: active > 0 ? "animate-pulse" : void 0 }),
|
|
116
|
+
resources ? /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
117
|
+
/* @__PURE__ */ jsxRuntime.jsx(ResourceGauge, { icon: /* @__PURE__ */ jsxRuntime.jsx(UiActivity.UiActivity, {}), label: "CPU", percent: resources.cpu, value: `${resources.cpu.toFixed(1)}%` }),
|
|
118
|
+
/* @__PURE__ */ jsxRuntime.jsx(ResourceGauge, { icon: /* @__PURE__ */ jsxRuntime.jsx(UiMemoryStick.UiMemoryStick, {}), label: "Memory", percent: resources.peakRss ? resources.rss / resources.peakRss * 100 : 0, value: format.formatBytes(resources.rss) })
|
|
119
|
+
] }) : active > 0 ? /* @__PURE__ */ jsxRuntime.jsx("span", { className: "absolute -right-0.5 -top-0.5 min-w-4 rounded-full bg-primary px-1 text-[9px] leading-4 text-primary-foreground", children: active }) : null
|
|
120
|
+
] });
|
|
121
|
+
}
|
|
122
|
+
function ResourceGauge({ icon, label, percent, value }) {
|
|
123
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("span", { "aria-label": `${label} ${value}`, className: "flex items-center gap-1 rounded bg-muted px-1.5 py-0.5 text-[10px] font-medium", title: `${label} ${value}`, children: [
|
|
124
|
+
icon,
|
|
125
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { "aria-hidden": true, className: "h-1 w-5 overflow-hidden rounded bg-border", children: /* @__PURE__ */ jsxRuntime.jsx("span", { className: "block h-full rounded bg-primary", style: { width: `${Math.max(0, Math.min(100, percent))}%` } }) }),
|
|
126
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: value })
|
|
127
|
+
] });
|
|
128
|
+
}
|
|
129
|
+
function resourceSummary(snapshots) {
|
|
130
|
+
const tasks = snapshots.filter((snapshot) => snapshot.type === "task" && taskProcessDetails.isTaskProcessDetails(snapshot.details));
|
|
131
|
+
const processes = tasks.length ? tasks : snapshots.filter((snapshot) => taskProcessDetails.isTaskProcessDetails(snapshot.details));
|
|
132
|
+
if (!processes.length) return void 0;
|
|
133
|
+
return processes.reduce((total, snapshot) => {
|
|
134
|
+
if (!taskProcessDetails.isTaskProcessDetails(snapshot.details)) return total;
|
|
135
|
+
return {
|
|
136
|
+
cpu: total.cpu + snapshot.details.latest.cpuPercent,
|
|
137
|
+
rss: total.rss + snapshot.details.latest.rssBytes,
|
|
138
|
+
peakRss: total.peakRss + snapshot.details.peak.rssBytes
|
|
139
|
+
};
|
|
140
|
+
}, { cpu: 0, rss: 0, peakRss: 0 });
|
|
141
|
+
}
|
|
48
142
|
exports.TaskManagerButton = TaskManagerButton;
|
|
49
143
|
//# sourceMappingURL=TaskManagerButton.cjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TaskManagerButton.cjs","sources":["../../src/data/TaskManagerButton.tsx"],"sourcesContent":["import { Button } from \"../components/button\";\nimport { UiListChecks } from \"../icons\";\nimport { useTaskRuns } from \"../hooks/use-task-run\";\nimport { DropdownMenu, type DropdownMenuItem } from \"../overlay/DropdownMenu\";\nimport { taskStatusIcon } from \"./task-status\";\n\nexport interface TaskManagerButtonProps {\n basePath?: string;\n tasksHref?: string;\n latest?: number;\n onNavigate?: (href: string) => void;\n}\n\nexport function TaskManagerButton({\n basePath,\n tasksHref = \"/tasks\",\n latest = 5,\n onNavigate,\n}: TaskManagerButtonProps) {\n const { runs } = useTaskRuns({ basePath });\n const active = runs.filter((run) => run.status === \"running\" || run.status === \"pending\").length;\n const navigate = (href: string) => {\n if (onNavigate) onNavigate(href);\n else window.location.assign(href);\n };\n const items: DropdownMenuItem[] = runs.slice(0, latest).map((run) => ({\n label: (\n <span className=\"flex min-w-0 items-center justify-between gap-3\">\n <span className=\"truncate\">{run.name}</span>\n <span className=\"shrink-0 text-[10px] text-muted-foreground\">{run.status}</span>\n </span>\n ),\n icon: taskStatusIcon(run.status),\n onSelect: () => navigate(run.href ?? `${tasksHref}/${encodeURIComponent(run.id)}`),\n }));\n if (items.length === 0) {\n items.push({ label: \"No tasks yet\", disabled: true, onSelect: () => {} });\n }\n const label = `Tasks (${active} active)`;\n\n return (\n <DropdownMenu\n items={items}\n align=\"right\"\n menuLabel=\"Recent tasks\"\n trigger={(\n <Button type=\"button\" variant=\"ghost\" size=\"icon\" aria-label={label} title={label} className=\"relative\">\n <UiListChecks />\n {active > 0 && (\n <span className=\"absolute -right-0.5 -top-0.5 min-w-4 rounded-full bg-primary px-1 text-[9px] leading-4 text-primary-foreground\">\n {active}\n </span>\n )}\n </Button>\n )}\n footer={(\n <Button type=\"button\" variant=\"ghost\" size=\"sm\" className=\"w-full justify-start\" onClick={() => navigate(tasksHref)}>\n View all tasks\n </Button>\n )}\n />\n );\n}\n"],"names":["useTaskRuns","jsxs","jsx","taskStatusIcon","DropdownMenu","Button","UiListChecks"],"mappings":";;;;;;;;AAaO,SAAS,kBAAkB;AAAA,EAChC;AAAA,EACA,YAAY;AAAA,EACZ,SAAS;AAAA,EACT;AACF,GAA2B;AACzB,QAAM,EAAE,KAAA,IAASA,uBAAY,EAAE,UAAU;AACzC,QAAM,SAAS,KAAK,OAAO,CAAC,QAAQ,IAAI,WAAW,aAAa,IAAI,WAAW,SAAS,EAAE;AAC1F,QAAM,WAAW,CAAC,SAAiB;AACjC,QAAI,uBAAuB,IAAI;AAAA,QAC1B,QAAO,SAAS,OAAO,IAAI;AAAA,EAClC;AACA,QAAM,QAA4B,KAAK,MAAM,GAAG,MAAM,EAAE,IAAI,CAAC,SAAS;AAAA,IACpE,OACEC,2BAAAA,KAAC,QAAA,EAAK,WAAU,mDACd,UAAA;AAAA,MAAAC,2BAAAA,IAAC,QAAA,EAAK,WAAU,YAAY,UAAA,IAAI,MAAK;AAAA,MACrCA,2BAAAA,IAAC,QAAA,EAAK,WAAU,8CAA8C,cAAI,OAAA,CAAO;AAAA,IAAA,GAC3E;AAAA,IAEF,MAAMC,WAAAA,eAAe,IAAI,MAAM;AAAA,IAC/B,UAAU,MAAM,SAAS,IAAI,QAAQ,GAAG,SAAS,IAAI,mBAAmB,IAAI,EAAE,CAAC,EAAE;AAAA,EAAA,EACjF;AACF,MAAI,MAAM,WAAW,GAAG;AACtB,UAAM,KAAK,EAAE,OAAO,gBAAgB,UAAU,MAAM,UAAU,MAAM;AAAA,IAAC,GAAG;AAAA,EAC1E;AACA,QAAM,QAAQ,UAAU,MAAM;AAE9B,SACED,2BAAAA;AAAAA,IAACE,aAAAA;AAAAA,IAAA;AAAA,MACC;AAAA,MACA,OAAM;AAAA,MACN,WAAU;AAAA,MACV,SACEH,2BAAAA,KAACI,eAAA,EAAO,MAAK,UAAS,SAAQ,SAAQ,MAAK,QAAO,cAAY,OAAO,OAAO,OAAO,WAAU,YAC3F,UAAA;AAAA,QAAAH,2BAAAA,IAACI,aAAAA,cAAA,EAAa;AAAA,QACb,SAAS,KACRJ,2BAAAA,IAAC,QAAA,EAAK,WAAU,kHACb,UAAA,OAAA,CACH;AAAA,MAAA,GAEJ;AAAA,MAEF,QACEA,2BAAAA,IAACG,eAAA,EAAO,MAAK,UAAS,SAAQ,SAAQ,MAAK,MAAK,WAAU,wBAAuB,SAAS,MAAM,SAAS,SAAS,GAAG,UAAA,iBAAA,CAErH;AAAA,IAAA;AAAA,EAAA;AAIR;;"}
|
|
1
|
+
{"version":3,"file":"TaskManagerButton.cjs","sources":["../../src/data/TaskManagerButton.tsx"],"sourcesContent":["import { Button } from \"../components/button\";\nimport { UiActivity, UiListChecks, UiMemoryStick } from \"../icons\";\nimport { useTaskRun, useTaskRuns } from \"../hooks/use-task-run\";\nimport { DropdownMenu, type DropdownMenuItem } from \"../overlay/DropdownMenu\";\nimport { formatBytes } from \"../lib/format\";\nimport { TaskManager } from \"./TaskManager\";\nimport { isTaskProcessDetails } from \"./task-process-details\";\nimport type { TaskSnapshot } from \"./TaskSnapshot\";\nimport { taskStatusIcon } from \"./task-status\";\n\nexport interface TaskManagerButtonProps {\n basePath?: string;\n tasksHref?: string;\n latest?: number;\n onNavigate?: (href: string) => void;\n panel?: boolean;\n kind?: string;\n labels?: Record<string, string>;\n selectedId?: string;\n onSelectRun?: (id: string | null) => void;\n}\n\nexport function TaskManagerButton({\n basePath,\n tasksHref = \"/tasks\",\n latest = 5,\n onNavigate,\n panel,\n kind,\n labels,\n selectedId,\n onSelectRun,\n}: TaskManagerButtonProps) {\n const { runs } = useTaskRuns({ basePath, kind, labels });\n const active = runs.filter((run) => run.status === \"running\" || run.status === \"pending\").length;\n const activeRun = runs.find((run) => run.status === \"running\") ?? runs.find((run) => run.status === \"pending\");\n const { snapshots } = useTaskRun({\n ...(basePath ? { basePath } : {}),\n ...(activeRun ? { id: activeRun.id } : {}),\n enabled: Boolean(activeRun),\n });\n const resources = resourceSummary(snapshots);\n const trigger = <TaskTrigger active={active} {...(resources ? { resources } : {})} />;\n\n return panel ? (\n <TaskPanelDropdown\n {...(basePath ? { basePath } : {})}\n {...(kind ? { kind } : {})}\n {...(labels ? { labels } : {})}\n {...(onSelectRun ? { onSelectRun } : {})}\n {...(selectedId ? { selectedId } : {})}\n trigger={trigger}\n />\n ) : (\n <RecentTasksDropdown\n latest={latest}\n {...(onNavigate ? { onNavigate } : {})}\n runs={runs}\n tasksHref={tasksHref}\n trigger={trigger}\n />\n );\n}\n\nfunction TaskPanelDropdown({ basePath, kind, labels, onSelectRun, selectedId, trigger }: TaskManagerButtonProps & { trigger: React.ReactNode }) {\n return (\n <DropdownMenu\n align=\"right\"\n header={<span className=\"text-xs font-semibold\">Activity</span>}\n menuClassName=\"w-[min(42rem,calc(100vw-1rem))] max-w-none p-0\"\n menuLabel=\"Task activity\"\n trigger={trigger}\n >\n {() => (\n <div className=\"max-h-[min(42rem,calc(100vh-5rem))] overflow-auto p-3\">\n <TaskManager\n {...(basePath ? { basePath } : {})}\n {...(kind ? { kind } : {})}\n {...(labels ? { labels } : {})}\n {...(onSelectRun ? { onSelectRun } : {})}\n {...(selectedId ? { selectedId } : {})}\n />\n </div>\n )}\n </DropdownMenu>\n );\n}\n\ntype TaskRuns = ReturnType<typeof useTaskRuns>[\"runs\"];\n\nfunction RecentTasksDropdown({\n latest,\n onNavigate,\n runs,\n tasksHref,\n trigger,\n}: {\n latest: number;\n onNavigate?: (href: string) => void;\n runs: TaskRuns;\n tasksHref: string;\n trigger: React.ReactNode;\n}) {\n const navigate = (href: string) => {\n if (onNavigate) onNavigate(href);\n else window.location.assign(href);\n };\n const items: DropdownMenuItem[] = runs.slice(0, latest).map((run) => ({\n label: (\n <span className=\"flex min-w-0 items-center justify-between gap-3\">\n <span className=\"truncate\">{run.name}</span>\n <span className=\"shrink-0 text-[10px] text-muted-foreground\">{run.status}</span>\n </span>\n ),\n icon: taskStatusIcon(run.status),\n onSelect: () => navigate(run.href ?? `${tasksHref}/${encodeURIComponent(run.id)}`),\n }));\n if (items.length === 0) {\n items.push({ label: \"No tasks yet\", disabled: true, onSelect: () => {} });\n }\n\n return (\n <DropdownMenu\n items={items}\n align=\"right\"\n menuLabel=\"Recent tasks\"\n trigger={trigger}\n footer={(\n <Button type=\"button\" variant=\"ghost\" size=\"sm\" className=\"w-full justify-start\" onClick={() => navigate(tasksHref)}>\n View all tasks\n </Button>\n )}\n />\n );\n}\n\ntype ResourceSummary = { cpu: number; rss: number; peakRss: number };\n\nfunction TaskTrigger({ active, resources }: { active: number; resources?: ResourceSummary }) {\n const label = `Tasks (${active} active)`;\n return (\n <Button type=\"button\" variant=\"ghost\" size={resources ? \"sm\" : \"icon\"} aria-label={label} title={label} className=\"relative gap-1.5\">\n <UiListChecks className={active > 0 ? \"animate-pulse\" : undefined} />\n {resources ? (\n <>\n <ResourceGauge icon={<UiActivity />} label=\"CPU\" percent={resources.cpu} value={`${resources.cpu.toFixed(1)}%`} />\n <ResourceGauge icon={<UiMemoryStick />} label=\"Memory\" percent={resources.peakRss ? resources.rss / resources.peakRss * 100 : 0} value={formatBytes(resources.rss)} />\n </>\n ) : active > 0 ? (\n <span className=\"absolute -right-0.5 -top-0.5 min-w-4 rounded-full bg-primary px-1 text-[9px] leading-4 text-primary-foreground\">{active}</span>\n ) : null}\n </Button>\n );\n}\n\nfunction ResourceGauge({ icon, label, percent, value }: { icon: React.ReactNode; label: string; percent: number; value: string }) {\n return (\n <span aria-label={`${label} ${value}`} className=\"flex items-center gap-1 rounded bg-muted px-1.5 py-0.5 text-[10px] font-medium\" title={`${label} ${value}`}>\n {icon}\n <span aria-hidden className=\"h-1 w-5 overflow-hidden rounded bg-border\">\n <span className=\"block h-full rounded bg-primary\" style={{ width: `${Math.max(0, Math.min(100, percent))}%` }} />\n </span>\n <span>{value}</span>\n </span>\n );\n}\n\nfunction resourceSummary(snapshots: TaskSnapshot[]): ResourceSummary | undefined {\n const tasks = snapshots.filter((snapshot) => snapshot.type === \"task\" && isTaskProcessDetails(snapshot.details));\n const processes = tasks.length ? tasks : snapshots.filter((snapshot) => isTaskProcessDetails(snapshot.details));\n if (!processes.length) return undefined;\n return processes.reduce<ResourceSummary>((total, snapshot) => {\n if (!isTaskProcessDetails(snapshot.details)) return total;\n return {\n cpu: total.cpu + snapshot.details.latest.cpuPercent,\n rss: total.rss + snapshot.details.latest.rssBytes,\n peakRss: total.peakRss + snapshot.details.peak.rssBytes,\n };\n }, { cpu: 0, rss: 0, peakRss: 0 });\n}\n"],"names":["useTaskRuns","useTaskRun","jsx","DropdownMenu","TaskManager","jsxs","taskStatusIcon","Button","UiListChecks","Fragment","UiActivity","UiMemoryStick","formatBytes","isTaskProcessDetails"],"mappings":"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"}
|
|
@@ -3,6 +3,11 @@ export interface TaskManagerButtonProps {
|
|
|
3
3
|
tasksHref?: string;
|
|
4
4
|
latest?: number;
|
|
5
5
|
onNavigate?: (href: string) => void;
|
|
6
|
+
panel?: boolean;
|
|
7
|
+
kind?: string;
|
|
8
|
+
labels?: Record<string, string>;
|
|
9
|
+
selectedId?: string;
|
|
10
|
+
onSelectRun?: (id: string | null) => void;
|
|
6
11
|
}
|
|
7
|
-
export declare function TaskManagerButton({ basePath, tasksHref, latest, onNavigate, }: TaskManagerButtonProps): import("react/jsx-runtime").JSX.Element;
|
|
12
|
+
export declare function TaskManagerButton({ basePath, tasksHref, latest, onNavigate, panel, kind, labels, selectedId, onSelectRun, }: TaskManagerButtonProps): import("react/jsx-runtime").JSX.Element;
|
|
8
13
|
//# sourceMappingURL=TaskManagerButton.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TaskManagerButton.d.ts","sourceRoot":"","sources":["../../src/data/TaskManagerButton.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"TaskManagerButton.d.ts","sourceRoot":"","sources":["../../src/data/TaskManagerButton.tsx"],"names":[],"mappings":"AAUA,MAAM,WAAW,sBAAsB;IACrC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IACpC,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAChC,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,WAAW,CAAC,EAAE,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI,KAAK,IAAI,CAAC;CAC3C;AAED,wBAAgB,iBAAiB,CAAC,EAChC,QAAQ,EACR,SAAoB,EACpB,MAAU,EACV,UAAU,EACV,KAAK,EACL,IAAI,EACJ,MAAM,EACN,UAAU,EACV,WAAW,GACZ,EAAE,sBAAsB,2CA8BxB"}
|