@amodalai/amodal 0.1.2
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/CHANGELOG.md +21 -0
- package/LICENSE +21 -0
- package/README.md +42 -0
- package/dist/src/auth/index.d.ts +13 -0
- package/dist/src/auth/index.d.ts.map +1 -0
- package/dist/src/auth/index.js +10 -0
- package/dist/src/auth/index.js.map +1 -0
- package/dist/src/auth/oauth2.d.ts +51 -0
- package/dist/src/auth/oauth2.d.ts.map +1 -0
- package/dist/src/auth/oauth2.js +196 -0
- package/dist/src/auth/oauth2.js.map +1 -0
- package/dist/src/auth/prompt.d.ts +21 -0
- package/dist/src/auth/prompt.d.ts.map +1 -0
- package/dist/src/auth/prompt.js +81 -0
- package/dist/src/auth/prompt.js.map +1 -0
- package/dist/src/auth/test-connection.d.ts +27 -0
- package/dist/src/auth/test-connection.d.ts.map +1 -0
- package/dist/src/auth/test-connection.js +153 -0
- package/dist/src/auth/test-connection.js.map +1 -0
- package/dist/src/auth/types.d.ts +32 -0
- package/dist/src/auth/types.d.ts.map +1 -0
- package/dist/src/auth/types.js +7 -0
- package/dist/src/auth/types.js.map +1 -0
- package/dist/src/commands/audit.d.ts +18 -0
- package/dist/src/commands/audit.d.ts.map +1 -0
- package/dist/src/commands/audit.js +86 -0
- package/dist/src/commands/audit.js.map +1 -0
- package/dist/src/commands/automations.d.ts +28 -0
- package/dist/src/commands/automations.d.ts.map +1 -0
- package/dist/src/commands/automations.js +179 -0
- package/dist/src/commands/automations.js.map +1 -0
- package/dist/src/commands/build-manifest-types.d.ts +33 -0
- package/dist/src/commands/build-manifest-types.d.ts.map +1 -0
- package/dist/src/commands/build-manifest-types.js +30 -0
- package/dist/src/commands/build-manifest-types.js.map +1 -0
- package/dist/src/commands/build-tools.d.ts +33 -0
- package/dist/src/commands/build-tools.d.ts.map +1 -0
- package/dist/src/commands/build-tools.js +237 -0
- package/dist/src/commands/build-tools.js.map +1 -0
- package/dist/src/commands/build.d.ts +23 -0
- package/dist/src/commands/build.d.ts.map +1 -0
- package/dist/src/commands/build.js +120 -0
- package/dist/src/commands/build.js.map +1 -0
- package/dist/src/commands/chat.d.ts +26 -0
- package/dist/src/commands/chat.d.ts.map +1 -0
- package/dist/src/commands/chat.js +123 -0
- package/dist/src/commands/chat.js.map +1 -0
- package/dist/src/commands/connect.d.ts +18 -0
- package/dist/src/commands/connect.d.ts.map +1 -0
- package/dist/src/commands/connect.js +198 -0
- package/dist/src/commands/connect.js.map +1 -0
- package/dist/src/commands/deploy.d.ts +20 -0
- package/dist/src/commands/deploy.d.ts.map +1 -0
- package/dist/src/commands/deploy.js +137 -0
- package/dist/src/commands/deploy.js.map +1 -0
- package/dist/src/commands/deployments.d.ts +17 -0
- package/dist/src/commands/deployments.d.ts.map +1 -0
- package/dist/src/commands/deployments.js +77 -0
- package/dist/src/commands/deployments.js.map +1 -0
- package/dist/src/commands/dev.d.ts +17 -0
- package/dist/src/commands/dev.d.ts.map +1 -0
- package/dist/src/commands/dev.js +109 -0
- package/dist/src/commands/dev.js.map +1 -0
- package/dist/src/commands/diff.d.ts +19 -0
- package/dist/src/commands/diff.d.ts.map +1 -0
- package/dist/src/commands/diff.js +120 -0
- package/dist/src/commands/diff.js.map +1 -0
- package/dist/src/commands/docker.d.ts +21 -0
- package/dist/src/commands/docker.d.ts.map +1 -0
- package/dist/src/commands/docker.js +215 -0
- package/dist/src/commands/docker.js.map +1 -0
- package/dist/src/commands/eval.d.ts +20 -0
- package/dist/src/commands/eval.d.ts.map +1 -0
- package/dist/src/commands/eval.js +236 -0
- package/dist/src/commands/eval.js.map +1 -0
- package/dist/src/commands/experiment.d.ts +21 -0
- package/dist/src/commands/experiment.d.ts.map +1 -0
- package/dist/src/commands/experiment.js +133 -0
- package/dist/src/commands/experiment.js.map +1 -0
- package/dist/src/commands/index.d.ts +10 -0
- package/dist/src/commands/index.d.ts.map +1 -0
- package/dist/src/commands/index.js +75 -0
- package/dist/src/commands/index.js.map +1 -0
- package/dist/src/commands/init.d.ts +17 -0
- package/dist/src/commands/init.d.ts.map +1 -0
- package/dist/src/commands/init.js +73 -0
- package/dist/src/commands/init.js.map +1 -0
- package/dist/src/commands/inspect.d.ts +22 -0
- package/dist/src/commands/inspect.d.ts.map +1 -0
- package/dist/src/commands/inspect.js +131 -0
- package/dist/src/commands/inspect.js.map +1 -0
- package/dist/src/commands/install-pkg.d.ts +29 -0
- package/dist/src/commands/install-pkg.d.ts.map +1 -0
- package/dist/src/commands/install-pkg.js +202 -0
- package/dist/src/commands/install-pkg.js.map +1 -0
- package/dist/src/commands/link.d.ts +32 -0
- package/dist/src/commands/link.d.ts.map +1 -0
- package/dist/src/commands/link.js +227 -0
- package/dist/src/commands/link.js.map +1 -0
- package/dist/src/commands/list.d.ts +19 -0
- package/dist/src/commands/list.d.ts.map +1 -0
- package/dist/src/commands/list.js +78 -0
- package/dist/src/commands/list.js.map +1 -0
- package/dist/src/commands/login.d.ts +31 -0
- package/dist/src/commands/login.d.ts.map +1 -0
- package/dist/src/commands/login.js +205 -0
- package/dist/src/commands/login.js.map +1 -0
- package/dist/src/commands/promote.d.ts +16 -0
- package/dist/src/commands/promote.d.ts.map +1 -0
- package/dist/src/commands/promote.js +55 -0
- package/dist/src/commands/promote.js.map +1 -0
- package/dist/src/commands/publish.d.ts +18 -0
- package/dist/src/commands/publish.d.ts.map +1 -0
- package/dist/src/commands/publish.js +122 -0
- package/dist/src/commands/publish.js.map +1 -0
- package/dist/src/commands/rollback.d.ts +17 -0
- package/dist/src/commands/rollback.d.ts.map +1 -0
- package/dist/src/commands/rollback.js +62 -0
- package/dist/src/commands/rollback.js.map +1 -0
- package/dist/src/commands/search.d.ts +20 -0
- package/dist/src/commands/search.d.ts.map +1 -0
- package/dist/src/commands/search.js +133 -0
- package/dist/src/commands/search.js.map +1 -0
- package/dist/src/commands/secrets.d.ts +20 -0
- package/dist/src/commands/secrets.d.ts.map +1 -0
- package/dist/src/commands/secrets.js +137 -0
- package/dist/src/commands/secrets.js.map +1 -0
- package/dist/src/commands/serve.d.ts +23 -0
- package/dist/src/commands/serve.d.ts.map +1 -0
- package/dist/src/commands/serve.js +144 -0
- package/dist/src/commands/serve.js.map +1 -0
- package/dist/src/commands/status.d.ts +16 -0
- package/dist/src/commands/status.d.ts.map +1 -0
- package/dist/src/commands/status.js +83 -0
- package/dist/src/commands/status.js.map +1 -0
- package/dist/src/commands/sync.d.ts +21 -0
- package/dist/src/commands/sync.d.ts.map +1 -0
- package/dist/src/commands/sync.js +94 -0
- package/dist/src/commands/sync.js.map +1 -0
- package/dist/src/commands/test-query.d.ts +19 -0
- package/dist/src/commands/test-query.d.ts.map +1 -0
- package/dist/src/commands/test-query.js +116 -0
- package/dist/src/commands/test-query.js.map +1 -0
- package/dist/src/commands/uninstall.d.ts +19 -0
- package/dist/src/commands/uninstall.d.ts.map +1 -0
- package/dist/src/commands/uninstall.js +84 -0
- package/dist/src/commands/uninstall.js.map +1 -0
- package/dist/src/commands/update.d.ts +21 -0
- package/dist/src/commands/update.d.ts.map +1 -0
- package/dist/src/commands/update.js +145 -0
- package/dist/src/commands/update.js.map +1 -0
- package/dist/src/commands/validate.d.ts +19 -0
- package/dist/src/commands/validate.d.ts.map +1 -0
- package/dist/src/commands/validate.js +114 -0
- package/dist/src/commands/validate.js.map +1 -0
- package/dist/src/fixtures/incident-response.d.ts +91 -0
- package/dist/src/fixtures/incident-response.d.ts.map +1 -0
- package/dist/src/fixtures/incident-response.js +208 -0
- package/dist/src/fixtures/incident-response.js.map +1 -0
- package/dist/src/main.d.ts +8 -0
- package/dist/src/main.d.ts.map +1 -0
- package/dist/src/main.js +30 -0
- package/dist/src/main.js.map +1 -0
- package/dist/src/shared/platform-client.d.ts +92 -0
- package/dist/src/shared/platform-client.d.ts.map +1 -0
- package/dist/src/shared/platform-client.js +155 -0
- package/dist/src/shared/platform-client.js.map +1 -0
- package/dist/src/shared/repo-discovery.d.ts +11 -0
- package/dist/src/shared/repo-discovery.d.ts.map +1 -0
- package/dist/src/shared/repo-discovery.js +33 -0
- package/dist/src/shared/repo-discovery.js.map +1 -0
- package/dist/src/templates/compose-template.d.ts +10 -0
- package/dist/src/templates/compose-template.d.ts.map +1 -0
- package/dist/src/templates/compose-template.js +30 -0
- package/dist/src/templates/compose-template.js.map +1 -0
- package/dist/src/templates/config-template.d.ts +14 -0
- package/dist/src/templates/config-template.d.ts.map +1 -0
- package/dist/src/templates/config-template.js +35 -0
- package/dist/src/templates/config-template.js.map +1 -0
- package/dist/src/templates/dockerfile-template.d.ts +10 -0
- package/dist/src/templates/dockerfile-template.d.ts.map +1 -0
- package/dist/src/templates/dockerfile-template.js +30 -0
- package/dist/src/templates/dockerfile-template.js.map +1 -0
- package/dist/src/templates/env-template.d.ts +12 -0
- package/dist/src/templates/env-template.d.ts.map +1 -0
- package/dist/src/templates/env-template.js +24 -0
- package/dist/src/templates/env-template.js.map +1 -0
- package/dist/src/templates/knowledge-template.d.ts +10 -0
- package/dist/src/templates/knowledge-template.d.ts.map +1 -0
- package/dist/src/templates/knowledge-template.js +24 -0
- package/dist/src/templates/knowledge-template.js.map +1 -0
- package/dist/src/templates/skill-template.d.ts +10 -0
- package/dist/src/templates/skill-template.d.ts.map +1 -0
- package/dist/src/templates/skill-template.js +27 -0
- package/dist/src/templates/skill-template.js.map +1 -0
- package/dist/src/ui/AskUserPrompt.d.ts +14 -0
- package/dist/src/ui/AskUserPrompt.d.ts.map +1 -0
- package/dist/src/ui/AskUserPrompt.js +17 -0
- package/dist/src/ui/AskUserPrompt.js.map +1 -0
- package/dist/src/ui/AssistantMessage.d.ts +14 -0
- package/dist/src/ui/AssistantMessage.d.ts.map +1 -0
- package/dist/src/ui/AssistantMessage.js +8 -0
- package/dist/src/ui/AssistantMessage.js.map +1 -0
- package/dist/src/ui/ChatApp.d.ts +15 -0
- package/dist/src/ui/ChatApp.d.ts.map +1 -0
- package/dist/src/ui/ChatApp.js +144 -0
- package/dist/src/ui/ChatApp.js.map +1 -0
- package/dist/src/ui/ConfirmationPrompt.d.ts +17 -0
- package/dist/src/ui/ConfirmationPrompt.d.ts.map +1 -0
- package/dist/src/ui/ConfirmationPrompt.js +21 -0
- package/dist/src/ui/ConfirmationPrompt.js.map +1 -0
- package/dist/src/ui/DiffRenderer.d.ts +32 -0
- package/dist/src/ui/DiffRenderer.d.ts.map +1 -0
- package/dist/src/ui/DiffRenderer.js +118 -0
- package/dist/src/ui/DiffRenderer.js.map +1 -0
- package/dist/src/ui/ExpandableContent.d.ts +15 -0
- package/dist/src/ui/ExpandableContent.d.ts.map +1 -0
- package/dist/src/ui/ExpandableContent.js +22 -0
- package/dist/src/ui/ExpandableContent.js.map +1 -0
- package/dist/src/ui/ExploreIndicator.d.ts +13 -0
- package/dist/src/ui/ExploreIndicator.d.ts.map +1 -0
- package/dist/src/ui/ExploreIndicator.js +14 -0
- package/dist/src/ui/ExploreIndicator.js.map +1 -0
- package/dist/src/ui/Footer.d.ts +19 -0
- package/dist/src/ui/Footer.d.ts.map +1 -0
- package/dist/src/ui/Footer.js +57 -0
- package/dist/src/ui/Footer.js.map +1 -0
- package/dist/src/ui/FullScreenLayout.d.ts +18 -0
- package/dist/src/ui/FullScreenLayout.d.ts.map +1 -0
- package/dist/src/ui/FullScreenLayout.js +14 -0
- package/dist/src/ui/FullScreenLayout.js.map +1 -0
- package/dist/src/ui/Header.d.ts +14 -0
- package/dist/src/ui/Header.d.ts.map +1 -0
- package/dist/src/ui/Header.js +11 -0
- package/dist/src/ui/Header.js.map +1 -0
- package/dist/src/ui/InputBar.d.ts +17 -0
- package/dist/src/ui/InputBar.d.ts.map +1 -0
- package/dist/src/ui/InputBar.js +49 -0
- package/dist/src/ui/InputBar.js.map +1 -0
- package/dist/src/ui/MessageList.d.ts +18 -0
- package/dist/src/ui/MessageList.d.ts.map +1 -0
- package/dist/src/ui/MessageList.js +9 -0
- package/dist/src/ui/MessageList.js.map +1 -0
- package/dist/src/ui/NotificationBar.d.ts +14 -0
- package/dist/src/ui/NotificationBar.d.ts.map +1 -0
- package/dist/src/ui/NotificationBar.js +38 -0
- package/dist/src/ui/NotificationBar.js.map +1 -0
- package/dist/src/ui/ScrollableMessageList.d.ts +27 -0
- package/dist/src/ui/ScrollableMessageList.d.ts.map +1 -0
- package/dist/src/ui/ScrollableMessageList.js +16 -0
- package/dist/src/ui/ScrollableMessageList.js.map +1 -0
- package/dist/src/ui/SessionBrowser.d.ts +20 -0
- package/dist/src/ui/SessionBrowser.d.ts.map +1 -0
- package/dist/src/ui/SessionBrowser.js +93 -0
- package/dist/src/ui/SessionBrowser.js.map +1 -0
- package/dist/src/ui/StatusMessage.d.ts +13 -0
- package/dist/src/ui/StatusMessage.d.ts.map +1 -0
- package/dist/src/ui/StatusMessage.js +17 -0
- package/dist/src/ui/StatusMessage.js.map +1 -0
- package/dist/src/ui/StreamingView.d.ts +19 -0
- package/dist/src/ui/StreamingView.d.ts.map +1 -0
- package/dist/src/ui/StreamingView.js +18 -0
- package/dist/src/ui/StreamingView.js.map +1 -0
- package/dist/src/ui/SubagentDisplay.d.ts +13 -0
- package/dist/src/ui/SubagentDisplay.d.ts.map +1 -0
- package/dist/src/ui/SubagentDisplay.js +22 -0
- package/dist/src/ui/SubagentDisplay.js.map +1 -0
- package/dist/src/ui/ThinkingDisplay.d.ts +13 -0
- package/dist/src/ui/ThinkingDisplay.d.ts.map +1 -0
- package/dist/src/ui/ThinkingDisplay.js +15 -0
- package/dist/src/ui/ThinkingDisplay.js.map +1 -0
- package/dist/src/ui/ToolCallDisplay.d.ts +16 -0
- package/dist/src/ui/ToolCallDisplay.d.ts.map +1 -0
- package/dist/src/ui/ToolCallDisplay.js +136 -0
- package/dist/src/ui/ToolCallDisplay.js.map +1 -0
- package/dist/src/ui/UserMessage.d.ts +12 -0
- package/dist/src/ui/UserMessage.d.ts.map +1 -0
- package/dist/src/ui/UserMessage.js +5 -0
- package/dist/src/ui/UserMessage.js.map +1 -0
- package/dist/src/ui/commands/clear.d.ts +7 -0
- package/dist/src/ui/commands/clear.d.ts.map +1 -0
- package/dist/src/ui/commands/clear.js +13 -0
- package/dist/src/ui/commands/clear.js.map +1 -0
- package/dist/src/ui/commands/help.d.ts +7 -0
- package/dist/src/ui/commands/help.d.ts.map +1 -0
- package/dist/src/ui/commands/help.js +26 -0
- package/dist/src/ui/commands/help.js.map +1 -0
- package/dist/src/ui/commands/index.d.ts +14 -0
- package/dist/src/ui/commands/index.d.ts.map +1 -0
- package/dist/src/ui/commands/index.js +15 -0
- package/dist/src/ui/commands/index.js.map +1 -0
- package/dist/src/ui/commands/model.d.ts +7 -0
- package/dist/src/ui/commands/model.d.ts.map +1 -0
- package/dist/src/ui/commands/model.js +16 -0
- package/dist/src/ui/commands/model.js.map +1 -0
- package/dist/src/ui/commands/registry.d.ts +30 -0
- package/dist/src/ui/commands/registry.d.ts.map +1 -0
- package/dist/src/ui/commands/registry.js +45 -0
- package/dist/src/ui/commands/registry.js.map +1 -0
- package/dist/src/ui/commands/sessions.d.ts +7 -0
- package/dist/src/ui/commands/sessions.d.ts.map +1 -0
- package/dist/src/ui/commands/sessions.js +13 -0
- package/dist/src/ui/commands/sessions.js.map +1 -0
- package/dist/src/ui/commands/stats.d.ts +7 -0
- package/dist/src/ui/commands/stats.d.ts.map +1 -0
- package/dist/src/ui/commands/stats.js +33 -0
- package/dist/src/ui/commands/stats.js.map +1 -0
- package/dist/src/ui/commands/theme.d.ts +7 -0
- package/dist/src/ui/commands/theme.d.ts.map +1 -0
- package/dist/src/ui/commands/theme.js +35 -0
- package/dist/src/ui/commands/theme.js.map +1 -0
- package/dist/src/ui/markdown/CodeBlock.d.ts +14 -0
- package/dist/src/ui/markdown/CodeBlock.d.ts.map +1 -0
- package/dist/src/ui/markdown/CodeBlock.js +55 -0
- package/dist/src/ui/markdown/CodeBlock.js.map +1 -0
- package/dist/src/ui/markdown/InlineRenderer.d.ts +12 -0
- package/dist/src/ui/markdown/InlineRenderer.d.ts.map +1 -0
- package/dist/src/ui/markdown/InlineRenderer.js +70 -0
- package/dist/src/ui/markdown/InlineRenderer.js.map +1 -0
- package/dist/src/ui/markdown/MarkdownDisplay.d.ts +17 -0
- package/dist/src/ui/markdown/MarkdownDisplay.d.ts.map +1 -0
- package/dist/src/ui/markdown/MarkdownDisplay.js +142 -0
- package/dist/src/ui/markdown/MarkdownDisplay.js.map +1 -0
- package/dist/src/ui/markdown/Table.d.ts +14 -0
- package/dist/src/ui/markdown/Table.d.ts.map +1 -0
- package/dist/src/ui/markdown/Table.js +31 -0
- package/dist/src/ui/markdown/Table.js.map +1 -0
- package/dist/src/ui/theme.d.ts +39 -0
- package/dist/src/ui/theme.d.ts.map +1 -0
- package/dist/src/ui/theme.js +39 -0
- package/dist/src/ui/theme.js.map +1 -0
- package/dist/src/ui/themes/index.d.ts +45 -0
- package/dist/src/ui/themes/index.d.ts.map +1 -0
- package/dist/src/ui/themes/index.js +73 -0
- package/dist/src/ui/themes/index.js.map +1 -0
- package/dist/src/ui/themes/light.d.ts +8 -0
- package/dist/src/ui/themes/light.d.ts.map +1 -0
- package/dist/src/ui/themes/light.js +37 -0
- package/dist/src/ui/themes/light.js.map +1 -0
- package/dist/src/ui/themes/monochrome.d.ts +8 -0
- package/dist/src/ui/themes/monochrome.d.ts.map +1 -0
- package/dist/src/ui/themes/monochrome.js +37 -0
- package/dist/src/ui/themes/monochrome.js.map +1 -0
- package/dist/src/ui/types.d.ts +191 -0
- package/dist/src/ui/types.d.ts.map +1 -0
- package/dist/src/ui/types.js +7 -0
- package/dist/src/ui/types.js.map +1 -0
- package/dist/src/ui/useAlternateBuffer.d.ts +11 -0
- package/dist/src/ui/useAlternateBuffer.d.ts.map +1 -0
- package/dist/src/ui/useAlternateBuffer.js +25 -0
- package/dist/src/ui/useAlternateBuffer.js.map +1 -0
- package/dist/src/ui/useChat.d.ts +18 -0
- package/dist/src/ui/useChat.d.ts.map +1 -0
- package/dist/src/ui/useChat.js +599 -0
- package/dist/src/ui/useChat.js.map +1 -0
- package/dist/src/ui/useElapsedTime.d.ts +11 -0
- package/dist/src/ui/useElapsedTime.d.ts.map +1 -0
- package/dist/src/ui/useElapsedTime.js +39 -0
- package/dist/src/ui/useElapsedTime.js.map +1 -0
- package/dist/src/ui/useResponsiveLayout.d.ts +16 -0
- package/dist/src/ui/useResponsiveLayout.d.ts.map +1 -0
- package/dist/src/ui/useResponsiveLayout.js +24 -0
- package/dist/src/ui/useResponsiveLayout.js.map +1 -0
- package/dist/src/ui/useScroll.d.ts +20 -0
- package/dist/src/ui/useScroll.d.ts.map +1 -0
- package/dist/src/ui/useScroll.js +64 -0
- package/dist/src/ui/useScroll.js.map +1 -0
- package/dist/src/ui/useSessionResume.d.ts +20 -0
- package/dist/src/ui/useSessionResume.d.ts.map +1 -0
- package/dist/src/ui/useSessionResume.js +77 -0
- package/dist/src/ui/useSessionResume.js.map +1 -0
- package/dist/tsconfig.tsbuildinfo +1 -0
- package/package.json +60 -0
- package/src/auth/index.ts +13 -0
- package/src/auth/oauth2.test.ts +305 -0
- package/src/auth/oauth2.ts +269 -0
- package/src/auth/prompt.test.ts +205 -0
- package/src/auth/prompt.ts +111 -0
- package/src/auth/test-connection.test.ts +224 -0
- package/src/auth/test-connection.ts +196 -0
- package/src/auth/types.ts +34 -0
- package/src/commands/audit.test.ts +92 -0
- package/src/commands/audit.ts +113 -0
- package/src/commands/automations.test.ts +85 -0
- package/src/commands/automations.ts +205 -0
- package/src/commands/build-manifest-types.ts +35 -0
- package/src/commands/build-tools.ts +281 -0
- package/src/commands/build.test.ts +63 -0
- package/src/commands/build.ts +135 -0
- package/src/commands/chat.ts +147 -0
- package/src/commands/command-exports.test.ts +88 -0
- package/src/commands/connect.test.ts +343 -0
- package/src/commands/connect.ts +237 -0
- package/src/commands/deploy.test.ts +124 -0
- package/src/commands/deploy.ts +153 -0
- package/src/commands/deployments.ts +90 -0
- package/src/commands/dev.test.ts +63 -0
- package/src/commands/dev.ts +124 -0
- package/src/commands/diff.test.ts +183 -0
- package/src/commands/diff.ts +143 -0
- package/src/commands/docker.ts +232 -0
- package/src/commands/eval.test.ts +88 -0
- package/src/commands/eval.ts +268 -0
- package/src/commands/experiment.test.ts +125 -0
- package/src/commands/experiment.ts +153 -0
- package/src/commands/index.ts +76 -0
- package/src/commands/init.test.ts +109 -0
- package/src/commands/init.ts +98 -0
- package/src/commands/inspect.test.ts +234 -0
- package/src/commands/inspect.ts +157 -0
- package/src/commands/install-pkg.test.ts +265 -0
- package/src/commands/install-pkg.ts +234 -0
- package/src/commands/link.ts +270 -0
- package/src/commands/list.test.ts +152 -0
- package/src/commands/list.ts +95 -0
- package/src/commands/login.test.ts +195 -0
- package/src/commands/login.ts +258 -0
- package/src/commands/promote.ts +64 -0
- package/src/commands/publish.test.ts +203 -0
- package/src/commands/publish.ts +142 -0
- package/src/commands/rollback.ts +72 -0
- package/src/commands/search.test.ts +174 -0
- package/src/commands/search.ts +154 -0
- package/src/commands/secrets.test.ts +168 -0
- package/src/commands/secrets.ts +163 -0
- package/src/commands/serve.ts +166 -0
- package/src/commands/status.ts +94 -0
- package/src/commands/sync.test.ts +130 -0
- package/src/commands/sync.ts +119 -0
- package/src/commands/test-query.test.ts +42 -0
- package/src/commands/test-query.ts +129 -0
- package/src/commands/uninstall.test.ts +162 -0
- package/src/commands/uninstall.ts +107 -0
- package/src/commands/update.test.ts +281 -0
- package/src/commands/update.ts +180 -0
- package/src/commands/validate.test.ts +260 -0
- package/src/commands/validate.ts +139 -0
- package/src/e2e-automations.test.ts +305 -0
- package/src/e2e-commands.test.ts +587 -0
- package/src/e2e-incident-response.test.ts +345 -0
- package/src/e2e-plugin-connections.test.ts +415 -0
- package/src/e2e-plugins.test.ts +492 -0
- package/src/e2e.test.ts +602 -0
- package/src/fixtures/incident-response.ts +232 -0
- package/src/main.ts +35 -0
- package/src/shared/platform-client.test.ts +106 -0
- package/src/shared/platform-client.ts +193 -0
- package/src/shared/repo-discovery.test.ts +56 -0
- package/src/shared/repo-discovery.ts +40 -0
- package/src/templates/compose-template.ts +30 -0
- package/src/templates/config-template.ts +44 -0
- package/src/templates/deployment-templates.test.ts +99 -0
- package/src/templates/dockerfile-template.ts +30 -0
- package/src/templates/env-template.ts +27 -0
- package/src/templates/knowledge-template.ts +24 -0
- package/src/templates/skill-template.ts +27 -0
- package/src/ui/AskUserPrompt.tsx +58 -0
- package/src/ui/AssistantMessage.tsx +51 -0
- package/src/ui/ChatApp.tsx +283 -0
- package/src/ui/ConfirmationPrompt.tsx +75 -0
- package/src/ui/DiffRenderer.test.ts +104 -0
- package/src/ui/DiffRenderer.tsx +188 -0
- package/src/ui/ExpandableContent.tsx +68 -0
- package/src/ui/ExploreIndicator.tsx +44 -0
- package/src/ui/Footer.tsx +87 -0
- package/src/ui/FullScreenLayout.tsx +45 -0
- package/src/ui/Header.tsx +50 -0
- package/src/ui/InputBar.tsx +105 -0
- package/src/ui/MessageList.tsx +31 -0
- package/src/ui/NotificationBar.tsx +64 -0
- package/src/ui/ScrollableMessageList.tsx +82 -0
- package/src/ui/SessionBrowser.test.ts +49 -0
- package/src/ui/SessionBrowser.tsx +179 -0
- package/src/ui/StatusMessage.tsx +35 -0
- package/src/ui/StreamingView.tsx +87 -0
- package/src/ui/SubagentDisplay.tsx +57 -0
- package/src/ui/ThinkingDisplay.tsx +45 -0
- package/src/ui/ToolCallDisplay.tsx +268 -0
- package/src/ui/UserMessage.tsx +22 -0
- package/src/ui/chat-e2e.test.ts +581 -0
- package/src/ui/commands/clear.ts +15 -0
- package/src/ui/commands/help.ts +31 -0
- package/src/ui/commands/index.ts +22 -0
- package/src/ui/commands/model.ts +19 -0
- package/src/ui/commands/registry.test.ts +76 -0
- package/src/ui/commands/registry.ts +66 -0
- package/src/ui/commands/sessions.ts +16 -0
- package/src/ui/commands/stats.ts +35 -0
- package/src/ui/commands/theme.ts +41 -0
- package/src/ui/markdown/CodeBlock.tsx +118 -0
- package/src/ui/markdown/InlineRenderer.tsx +115 -0
- package/src/ui/markdown/MarkdownDisplay.tsx +223 -0
- package/src/ui/markdown/Table.tsx +75 -0
- package/src/ui/theme.ts +39 -0
- package/src/ui/themes/index.ts +113 -0
- package/src/ui/themes/light.ts +39 -0
- package/src/ui/themes/monochrome.ts +39 -0
- package/src/ui/types.ts +157 -0
- package/src/ui/useAlternateBuffer.ts +27 -0
- package/src/ui/useChat.test.ts +492 -0
- package/src/ui/useChat.ts +693 -0
- package/src/ui/useElapsedTime.test.ts +33 -0
- package/src/ui/useElapsedTime.ts +43 -0
- package/src/ui/useResponsiveLayout.test.ts +54 -0
- package/src/ui/useResponsiveLayout.ts +32 -0
- package/src/ui/useScroll.test.ts +99 -0
- package/src/ui/useScroll.ts +97 -0
- package/src/ui/useSessionResume.test.ts +80 -0
- package/src/ui/useSessionResume.ts +102 -0
- package/tsconfig.json +17 -0
- package/vitest.config.ts +20 -0
|
@@ -0,0 +1,265 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2025 Amodal Labs, Inc.
|
|
4
|
+
* SPDX-License-Identifier: MIT
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
import {describe, it, expect, vi, beforeEach} from 'vitest';
|
|
8
|
+
|
|
9
|
+
const mockFindRepoRoot = vi.fn(() => '/test/repo');
|
|
10
|
+
const mockEnsureNpmContext = vi.fn();
|
|
11
|
+
const mockNpmInstall = vi.fn();
|
|
12
|
+
const mockNpmInstallAll = vi.fn();
|
|
13
|
+
const mockAddLockEntry = vi.fn();
|
|
14
|
+
const mockReadLockFile = vi.fn();
|
|
15
|
+
const mockEnsureSymlink = vi.fn();
|
|
16
|
+
const mockEnsureAllSymlinks = vi.fn();
|
|
17
|
+
const mockMakePackageRef = vi.fn((type: string, name: string) => ({
|
|
18
|
+
type,
|
|
19
|
+
name,
|
|
20
|
+
key: `${type}/${name}`,
|
|
21
|
+
npmName: `@amodalai/${type}-${name}`,
|
|
22
|
+
}));
|
|
23
|
+
const mockParsePackageKey = vi.fn((key: string) => {
|
|
24
|
+
const [type, name] = key.split('/');
|
|
25
|
+
return {type, name};
|
|
26
|
+
});
|
|
27
|
+
const mockAddConfigDep = vi.fn();
|
|
28
|
+
const mockReadConfigDeps = vi.fn();
|
|
29
|
+
|
|
30
|
+
vi.mock('../shared/repo-discovery.js', () => ({
|
|
31
|
+
findRepoRoot: mockFindRepoRoot,
|
|
32
|
+
}));
|
|
33
|
+
|
|
34
|
+
vi.mock('@amodalai/core', () => ({
|
|
35
|
+
ensureNpmContext: mockEnsureNpmContext,
|
|
36
|
+
npmInstall: mockNpmInstall,
|
|
37
|
+
npmInstallAll: mockNpmInstallAll,
|
|
38
|
+
addLockEntry: mockAddLockEntry,
|
|
39
|
+
readLockFile: mockReadLockFile,
|
|
40
|
+
ensureSymlink: mockEnsureSymlink,
|
|
41
|
+
ensureAllSymlinks: mockEnsureAllSymlinks,
|
|
42
|
+
makePackageRef: mockMakePackageRef,
|
|
43
|
+
parsePackageKey: mockParsePackageKey,
|
|
44
|
+
addConfigDep: mockAddConfigDep,
|
|
45
|
+
readConfigDeps: mockReadConfigDeps,
|
|
46
|
+
}));
|
|
47
|
+
|
|
48
|
+
const mockPaths = {
|
|
49
|
+
root: '/test/repo/.amodal/packages',
|
|
50
|
+
npmDir: '/test/repo/.amodal/packages/.npm',
|
|
51
|
+
npmrc: '/test/repo/.amodal/packages/.npm/.npmrc',
|
|
52
|
+
packageJson: '/test/repo/.amodal/packages/.npm/package.json',
|
|
53
|
+
nodeModules: '/test/repo/.amodal/packages/.npm/node_modules',
|
|
54
|
+
};
|
|
55
|
+
|
|
56
|
+
describe('runInstallPkg', () => {
|
|
57
|
+
let stderrOutput: string;
|
|
58
|
+
|
|
59
|
+
beforeEach(() => {
|
|
60
|
+
vi.clearAllMocks();
|
|
61
|
+
mockFindRepoRoot.mockReturnValue('/test/repo');
|
|
62
|
+
mockEnsureNpmContext.mockResolvedValue(mockPaths);
|
|
63
|
+
mockNpmInstall.mockResolvedValue({version: '1.0.0', integrity: 'sha512-abc'});
|
|
64
|
+
mockAddLockEntry.mockResolvedValue({lockVersion: 1, packages: {}});
|
|
65
|
+
mockEnsureSymlink.mockResolvedValue('/test/repo/.amodal/packages/connection--test');
|
|
66
|
+
stderrOutput = '';
|
|
67
|
+
vi.spyOn(process.stderr, 'write').mockImplementation((chunk) => {
|
|
68
|
+
stderrOutput += String(chunk);
|
|
69
|
+
return true;
|
|
70
|
+
});
|
|
71
|
+
});
|
|
72
|
+
|
|
73
|
+
it('should restore from lock file on bare install', async () => {
|
|
74
|
+
mockReadLockFile.mockResolvedValue({
|
|
75
|
+
lockVersion: 1,
|
|
76
|
+
packages: {'connection/salesforce': {version: '2.0.0', npm: '@amodalai/connection-salesforce', integrity: 'sha512-x'}},
|
|
77
|
+
});
|
|
78
|
+
|
|
79
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
80
|
+
const result = await runInstallPkg();
|
|
81
|
+
expect(result).toBe(0);
|
|
82
|
+
expect(mockNpmInstall).toHaveBeenCalledWith(mockPaths, '@amodalai/connection-salesforce', '2.0.0');
|
|
83
|
+
expect(mockEnsureSymlink).toHaveBeenCalled();
|
|
84
|
+
expect(stderrOutput).toContain('Restoring 1 package');
|
|
85
|
+
});
|
|
86
|
+
|
|
87
|
+
it('should print nothing to install when no lock file and no deps on bare install', async () => {
|
|
88
|
+
mockReadLockFile.mockResolvedValue(null);
|
|
89
|
+
mockReadConfigDeps.mockResolvedValue({});
|
|
90
|
+
|
|
91
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
92
|
+
const result = await runInstallPkg();
|
|
93
|
+
expect(result).toBe(0);
|
|
94
|
+
expect(stderrOutput).toContain('Nothing to install');
|
|
95
|
+
});
|
|
96
|
+
|
|
97
|
+
it('should install a single package', async () => {
|
|
98
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
99
|
+
const result = await runInstallPkg({
|
|
100
|
+
packages: [{type: 'connection', name: 'stripe'}],
|
|
101
|
+
});
|
|
102
|
+
expect(result).toBe(0);
|
|
103
|
+
expect(mockNpmInstall).toHaveBeenCalledWith(mockPaths, '@amodalai/connection-stripe', undefined);
|
|
104
|
+
expect(mockAddLockEntry).toHaveBeenCalledWith('/test/repo', 'connection', 'stripe', {
|
|
105
|
+
version: '1.0.0',
|
|
106
|
+
npm: '@amodalai/connection-stripe',
|
|
107
|
+
integrity: 'sha512-abc',
|
|
108
|
+
});
|
|
109
|
+
expect(mockEnsureSymlink).toHaveBeenCalled();
|
|
110
|
+
});
|
|
111
|
+
|
|
112
|
+
it('should install a package with version', async () => {
|
|
113
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
114
|
+
const result = await runInstallPkg({
|
|
115
|
+
packages: [{type: 'skill', name: 'triage', version: '2.0.0'}],
|
|
116
|
+
});
|
|
117
|
+
expect(result).toBe(0);
|
|
118
|
+
expect(mockNpmInstall).toHaveBeenCalledWith(mockPaths, '@amodalai/skill-triage', '2.0.0');
|
|
119
|
+
});
|
|
120
|
+
|
|
121
|
+
it('should install multiple packages', async () => {
|
|
122
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
123
|
+
const result = await runInstallPkg({
|
|
124
|
+
packages: [
|
|
125
|
+
{type: 'connection', name: 'stripe'},
|
|
126
|
+
{type: 'skill', name: 'triage'},
|
|
127
|
+
],
|
|
128
|
+
});
|
|
129
|
+
expect(result).toBe(0);
|
|
130
|
+
expect(mockNpmInstall).toHaveBeenCalledTimes(2);
|
|
131
|
+
expect(stderrOutput).toContain('2 packages installed successfully');
|
|
132
|
+
});
|
|
133
|
+
|
|
134
|
+
it('should continue on error and report failure count', async () => {
|
|
135
|
+
mockNpmInstall
|
|
136
|
+
.mockRejectedValueOnce(new Error('Network error'))
|
|
137
|
+
.mockResolvedValueOnce({version: '1.0.0', integrity: 'sha512-ok'});
|
|
138
|
+
|
|
139
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
140
|
+
const result = await runInstallPkg({
|
|
141
|
+
packages: [
|
|
142
|
+
{type: 'connection', name: 'bad'},
|
|
143
|
+
{type: 'skill', name: 'good'},
|
|
144
|
+
],
|
|
145
|
+
});
|
|
146
|
+
expect(result).toBe(1);
|
|
147
|
+
expect(stderrOutput).toContain('Failed to install @amodalai/connection-bad');
|
|
148
|
+
expect(stderrOutput).toContain('1 of 2 packages failed');
|
|
149
|
+
});
|
|
150
|
+
|
|
151
|
+
it('should report all failures', async () => {
|
|
152
|
+
mockNpmInstall
|
|
153
|
+
.mockRejectedValueOnce(new Error('Fail 1'))
|
|
154
|
+
.mockRejectedValueOnce(new Error('Fail 2'));
|
|
155
|
+
|
|
156
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
157
|
+
const result = await runInstallPkg({
|
|
158
|
+
packages: [
|
|
159
|
+
{type: 'connection', name: 'bad1'},
|
|
160
|
+
{type: 'connection', name: 'bad2'},
|
|
161
|
+
],
|
|
162
|
+
});
|
|
163
|
+
expect(result).toBe(2);
|
|
164
|
+
expect(stderrOutput).toContain('2 of 2 packages failed');
|
|
165
|
+
});
|
|
166
|
+
|
|
167
|
+
it('should return 1 when repo not found', async () => {
|
|
168
|
+
mockFindRepoRoot.mockImplementation(() => {
|
|
169
|
+
throw new Error('Not found');
|
|
170
|
+
});
|
|
171
|
+
|
|
172
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
173
|
+
const result = await runInstallPkg();
|
|
174
|
+
expect(result).toBe(1);
|
|
175
|
+
expect(stderrOutput).toContain('Not found');
|
|
176
|
+
});
|
|
177
|
+
|
|
178
|
+
it('should handle bare install with empty lock file packages', async () => {
|
|
179
|
+
mockReadLockFile.mockResolvedValue({lockVersion: 1, packages: {}});
|
|
180
|
+
|
|
181
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
182
|
+
const result = await runInstallPkg();
|
|
183
|
+
expect(result).toBe(0);
|
|
184
|
+
expect(stderrOutput).toContain('Nothing to install');
|
|
185
|
+
expect(mockNpmInstallAll).not.toHaveBeenCalled();
|
|
186
|
+
});
|
|
187
|
+
|
|
188
|
+
it('should pass cwd to findRepoRoot', async () => {
|
|
189
|
+
mockReadLockFile.mockResolvedValue(null);
|
|
190
|
+
|
|
191
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
192
|
+
await runInstallPkg({cwd: '/custom/dir'});
|
|
193
|
+
expect(mockFindRepoRoot).toHaveBeenCalledWith('/custom/dir');
|
|
194
|
+
});
|
|
195
|
+
|
|
196
|
+
it('should use correct singular form for single package success', async () => {
|
|
197
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
198
|
+
const result = await runInstallPkg({
|
|
199
|
+
packages: [{type: 'connection', name: 'stripe'}],
|
|
200
|
+
});
|
|
201
|
+
expect(result).toBe(0);
|
|
202
|
+
expect(stderrOutput).toContain('1 package installed successfully');
|
|
203
|
+
expect(stderrOutput).not.toContain('1 packages');
|
|
204
|
+
});
|
|
205
|
+
|
|
206
|
+
it('should handle npm install failure for single package', async () => {
|
|
207
|
+
mockNpmInstall.mockRejectedValue(new Error('Registry unreachable'));
|
|
208
|
+
|
|
209
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
210
|
+
const result = await runInstallPkg({
|
|
211
|
+
packages: [{type: 'connection', name: 'fail'}],
|
|
212
|
+
});
|
|
213
|
+
expect(result).toBe(1);
|
|
214
|
+
expect(stderrOutput).toContain('Registry unreachable');
|
|
215
|
+
});
|
|
216
|
+
|
|
217
|
+
it('should handle empty packages array like bare install', async () => {
|
|
218
|
+
mockReadLockFile.mockResolvedValue(null);
|
|
219
|
+
|
|
220
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
221
|
+
const result = await runInstallPkg({packages: []});
|
|
222
|
+
expect(result).toBe(0);
|
|
223
|
+
expect(stderrOutput).toContain('Nothing to install');
|
|
224
|
+
});
|
|
225
|
+
|
|
226
|
+
it('should print version in install progress message', async () => {
|
|
227
|
+
const {runInstallPkg} = await import('./install-pkg.js');
|
|
228
|
+
await runInstallPkg({
|
|
229
|
+
packages: [{type: 'connection', name: 'stripe', version: '3.2.1'}],
|
|
230
|
+
});
|
|
231
|
+
expect(stderrOutput).toContain('@3.2.1');
|
|
232
|
+
});
|
|
233
|
+
});
|
|
234
|
+
|
|
235
|
+
describe('parseInstallArgs', () => {
|
|
236
|
+
it('parses single type/name pair', async () => {
|
|
237
|
+
const {parseInstallArgs} = await import('./install-pkg.js');
|
|
238
|
+
const result = parseInstallArgs(['connection', 'salesforce']);
|
|
239
|
+
expect(result).toEqual([{type: 'connection', name: 'salesforce'}]);
|
|
240
|
+
});
|
|
241
|
+
|
|
242
|
+
it('parses multiple type/name pairs', async () => {
|
|
243
|
+
const {parseInstallArgs} = await import('./install-pkg.js');
|
|
244
|
+
const result = parseInstallArgs(['connection', 'salesforce', 'skill', 'triage']);
|
|
245
|
+
expect(result).toEqual([
|
|
246
|
+
{type: 'connection', name: 'salesforce'},
|
|
247
|
+
{type: 'skill', name: 'triage'},
|
|
248
|
+
]);
|
|
249
|
+
});
|
|
250
|
+
|
|
251
|
+
it('throws on incomplete pair', async () => {
|
|
252
|
+
const {parseInstallArgs} = await import('./install-pkg.js');
|
|
253
|
+
expect(() => parseInstallArgs(['connection'])).toThrow('incomplete pair');
|
|
254
|
+
});
|
|
255
|
+
|
|
256
|
+
it('throws on invalid type', async () => {
|
|
257
|
+
const {parseInstallArgs} = await import('./install-pkg.js');
|
|
258
|
+
expect(() => parseInstallArgs(['invalid', 'test'])).toThrow('Invalid package type');
|
|
259
|
+
});
|
|
260
|
+
|
|
261
|
+
it('returns empty array for empty input', async () => {
|
|
262
|
+
const {parseInstallArgs} = await import('./install-pkg.js');
|
|
263
|
+
expect(parseInstallArgs([])).toEqual([]);
|
|
264
|
+
});
|
|
265
|
+
});
|
|
@@ -0,0 +1,234 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2025 Amodal Labs, Inc.
|
|
4
|
+
* SPDX-License-Identifier: MIT
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
import {readFile, writeFile} from 'node:fs/promises';
|
|
8
|
+
import * as path from 'node:path';
|
|
9
|
+
import type {CommandModule} from 'yargs';
|
|
10
|
+
import {
|
|
11
|
+
addConfigDep,
|
|
12
|
+
addLockEntry,
|
|
13
|
+
ensureNpmContext,
|
|
14
|
+
ensureSymlink,
|
|
15
|
+
makePackageRef,
|
|
16
|
+
npmInstall,
|
|
17
|
+
parsePackageKey,
|
|
18
|
+
readConfigDeps,
|
|
19
|
+
readLockFile,
|
|
20
|
+
readPackageManifest,
|
|
21
|
+
getPackageDir,
|
|
22
|
+
} from '@amodalai/core';
|
|
23
|
+
import type {PackageType} from '@amodalai/core';
|
|
24
|
+
import {findRepoRoot} from '../shared/repo-discovery.js';
|
|
25
|
+
|
|
26
|
+
const VALID_TYPES = new Set<string>(['connection', 'skill', 'automation', 'knowledge', 'mcp']);
|
|
27
|
+
|
|
28
|
+
/**
|
|
29
|
+
* Parse variadic install args: `connection salesforce skill triage` → [{type, name}]
|
|
30
|
+
*/
|
|
31
|
+
export function parseInstallArgs(args: string[]): Array<{type: PackageType; name: string}> {
|
|
32
|
+
const result: Array<{type: PackageType; name: string}> = [];
|
|
33
|
+
for (let i = 0; i < args.length; i += 2) {
|
|
34
|
+
const rawType = args[i];
|
|
35
|
+
const name = args[i + 1];
|
|
36
|
+
if (!rawType || !name) {
|
|
37
|
+
throw new Error(`Invalid install arguments: expected pairs of <type> <name>, got incomplete pair at position ${i}`);
|
|
38
|
+
}
|
|
39
|
+
if (!VALID_TYPES.has(rawType)) {
|
|
40
|
+
throw new Error(`Invalid package type "${rawType}". Valid types: ${[...VALID_TYPES].join(', ')}`);
|
|
41
|
+
}
|
|
42
|
+
// eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion
|
|
43
|
+
result.push({type: rawType as PackageType, name});
|
|
44
|
+
}
|
|
45
|
+
return result;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
export interface InstallPkgOptions {
|
|
49
|
+
cwd?: string;
|
|
50
|
+
packages?: Array<{type: PackageType; name: string; version?: string}>;
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
/**
|
|
54
|
+
* Install one or more packages, or restore all from lock file.
|
|
55
|
+
* Returns the number of failures (0 = success).
|
|
56
|
+
*/
|
|
57
|
+
export async function runInstallPkg(options: InstallPkgOptions = {}): Promise<number> {
|
|
58
|
+
let repoPath: string;
|
|
59
|
+
try {
|
|
60
|
+
repoPath = findRepoRoot(options.cwd);
|
|
61
|
+
} catch (err) {
|
|
62
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
63
|
+
process.stderr.write(`[install] ${msg}\n`);
|
|
64
|
+
return 1;
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
const paths = await ensureNpmContext(repoPath);
|
|
68
|
+
|
|
69
|
+
// Bare install: restore from lock file, or install from amodal.json dependencies
|
|
70
|
+
if (!options.packages || options.packages.length === 0) {
|
|
71
|
+
const lockFile = await readLockFile(repoPath);
|
|
72
|
+
|
|
73
|
+
if (lockFile && Object.keys(lockFile.packages).length > 0) {
|
|
74
|
+
// Lock file exists — install each package at its pinned version
|
|
75
|
+
const entryCount = Object.keys(lockFile.packages).length;
|
|
76
|
+
process.stderr.write(`[install] Restoring ${entryCount} package${entryCount === 1 ? '' : 's'} from lock file...\n`);
|
|
77
|
+
let failures = 0;
|
|
78
|
+
for (const [key, entry] of Object.entries(lockFile.packages)) {
|
|
79
|
+
const {type, name} = parsePackageKey(key);
|
|
80
|
+
const ref = makePackageRef(type, name);
|
|
81
|
+
try {
|
|
82
|
+
await npmInstall(paths, ref.npmName, entry.version);
|
|
83
|
+
await ensureSymlink(paths, ref);
|
|
84
|
+
} catch (err) {
|
|
85
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
86
|
+
process.stderr.write(`[install] Failed to restore ${ref.npmName}@${entry.version}: ${msg}\n`);
|
|
87
|
+
failures++;
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
if (failures > 0) {
|
|
91
|
+
process.stderr.write(`[install] ${failures} of ${entryCount} packages failed to restore.\n`);
|
|
92
|
+
return failures;
|
|
93
|
+
}
|
|
94
|
+
process.stderr.write(`[install] Restored ${entryCount} package${entryCount === 1 ? '' : 's'}.\n`);
|
|
95
|
+
return 0;
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
// No lock file — check amodal.json dependencies (fresh clone)
|
|
99
|
+
let deps: Record<string, string>;
|
|
100
|
+
try {
|
|
101
|
+
deps = await readConfigDeps(repoPath);
|
|
102
|
+
} catch {
|
|
103
|
+
deps = {};
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
if (Object.keys(deps).length === 0) {
|
|
107
|
+
process.stderr.write('[install] Nothing to install. No dependencies in amodal.json and no lock file found.\n');
|
|
108
|
+
return 0;
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
// Install each dependency from amodal.json
|
|
112
|
+
process.stderr.write(`[install] Installing ${Object.keys(deps).length} package${Object.keys(deps).length === 1 ? '' : 's'} from amodal.json...\n`);
|
|
113
|
+
let failures = 0;
|
|
114
|
+
for (const [key, versionRange] of Object.entries(deps)) {
|
|
115
|
+
const {type, name} = parsePackageKey(key);
|
|
116
|
+
const ref = makePackageRef(type, name);
|
|
117
|
+
process.stderr.write(`[install] Installing ${ref.npmName}@${versionRange}...\n`);
|
|
118
|
+
try {
|
|
119
|
+
const result = await npmInstall(paths, ref.npmName, versionRange);
|
|
120
|
+
await addLockEntry(repoPath, type, name, {
|
|
121
|
+
version: result.version,
|
|
122
|
+
npm: ref.npmName,
|
|
123
|
+
integrity: result.integrity,
|
|
124
|
+
});
|
|
125
|
+
await ensureSymlink(paths, ref);
|
|
126
|
+
process.stderr.write(`[install] Installed ${ref.npmName}@${result.version}\n`);
|
|
127
|
+
} catch (err) {
|
|
128
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
129
|
+
process.stderr.write(`[install] Failed to install ${ref.npmName}: ${msg}\n`);
|
|
130
|
+
failures++;
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
return failures;
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
// Install specific packages
|
|
137
|
+
let failures = 0;
|
|
138
|
+
|
|
139
|
+
for (const pkg of options.packages) {
|
|
140
|
+
const ref = makePackageRef(pkg.type, pkg.name);
|
|
141
|
+
const versionLabel = pkg.version ? `@${pkg.version}` : '';
|
|
142
|
+
process.stderr.write(`[install] Installing ${ref.npmName}${versionLabel}...\n`);
|
|
143
|
+
|
|
144
|
+
try {
|
|
145
|
+
const result = await npmInstall(paths, ref.npmName, pkg.version);
|
|
146
|
+
await addLockEntry(repoPath, pkg.type, pkg.name, {
|
|
147
|
+
version: result.version,
|
|
148
|
+
npm: ref.npmName,
|
|
149
|
+
integrity: result.integrity,
|
|
150
|
+
});
|
|
151
|
+
await ensureSymlink(paths, ref);
|
|
152
|
+
|
|
153
|
+
// Add to amodal.json dependencies
|
|
154
|
+
await addConfigDep(repoPath, pkg.type, pkg.name, result.version);
|
|
155
|
+
|
|
156
|
+
// MCP packages: merge server config into amodal.json
|
|
157
|
+
if (pkg.type === 'mcp') {
|
|
158
|
+
await mergeMcpConfig(repoPath, ref.key, pkg.name);
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
process.stderr.write(`[install] Installed ${ref.npmName}@${result.version}\n`);
|
|
162
|
+
} catch (err) {
|
|
163
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
164
|
+
process.stderr.write(`[install] Failed to install ${ref.npmName}: ${msg}\n`);
|
|
165
|
+
failures++;
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
if (failures > 0) {
|
|
170
|
+
process.stderr.write(`[install] ${failures} of ${options.packages.length} package${options.packages.length === 1 ? '' : 's'} failed.\n`);
|
|
171
|
+
} else {
|
|
172
|
+
process.stderr.write(`[install] ${options.packages.length} package${options.packages.length === 1 ? '' : 's'} installed successfully.\n`);
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
return failures;
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
/**
|
|
179
|
+
* After installing an MCP package, read its manifest and merge
|
|
180
|
+
* the server config into amodal.json's mcp.servers block.
|
|
181
|
+
*/
|
|
182
|
+
async function mergeMcpConfig(repoPath: string, packageKey: string, name: string): Promise<void> {
|
|
183
|
+
const ref = makePackageRef('mcp', name);
|
|
184
|
+
const pkgDir = await getPackageDir(repoPath, ref);
|
|
185
|
+
if (!pkgDir) return;
|
|
186
|
+
|
|
187
|
+
const manifest = await readPackageManifest(pkgDir);
|
|
188
|
+
if (manifest.type !== 'mcp') return;
|
|
189
|
+
|
|
190
|
+
// Read current amodal.json
|
|
191
|
+
const configPath = path.join(repoPath, 'amodal.json');
|
|
192
|
+
const raw = await readFile(configPath, 'utf-8');
|
|
193
|
+
// eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion -- config JSON
|
|
194
|
+
const config = JSON.parse(raw) as Record<string, unknown>;
|
|
195
|
+
|
|
196
|
+
// Ensure mcp.servers exists
|
|
197
|
+
if (!config['mcp'] || typeof config['mcp'] !== 'object') {
|
|
198
|
+
config['mcp'] = {};
|
|
199
|
+
}
|
|
200
|
+
// eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion -- config shape
|
|
201
|
+
const mcp = config['mcp'] as Record<string, unknown>;
|
|
202
|
+
if (!mcp['servers'] || typeof mcp['servers'] !== 'object') {
|
|
203
|
+
mcp['servers'] = {};
|
|
204
|
+
}
|
|
205
|
+
// eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion -- config shape
|
|
206
|
+
const servers = mcp['servers'] as Record<string, unknown>;
|
|
207
|
+
|
|
208
|
+
// Build server entry from manifest
|
|
209
|
+
const entry: Record<string, unknown> = {transport: manifest.transport};
|
|
210
|
+
if (manifest.url) entry['url'] = manifest.url;
|
|
211
|
+
if (manifest.command) entry['command'] = manifest.command;
|
|
212
|
+
if (manifest.args) entry['args'] = manifest.args;
|
|
213
|
+
if (manifest.env) entry['env'] = manifest.env;
|
|
214
|
+
if (manifest.trust) entry['trust'] = manifest.trust;
|
|
215
|
+
|
|
216
|
+
servers[name] = entry;
|
|
217
|
+
|
|
218
|
+
await writeFile(configPath, JSON.stringify(config, null, 2) + '\n', 'utf-8');
|
|
219
|
+
process.stderr.write(`[install] Added MCP server "${name}" to amodal.json\n`);
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
export const installPkgCommand: CommandModule = {
|
|
223
|
+
command: 'install [packages..]',
|
|
224
|
+
describe: 'Install packages (or restore all from lock file)',
|
|
225
|
+
builder: (yargs) =>
|
|
226
|
+
yargs.positional('packages', {type: 'string', array: true, describe: 'Pairs of <type> <name>'}),
|
|
227
|
+
handler: async (argv) => {
|
|
228
|
+
// eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion
|
|
229
|
+
const raw = (argv['packages'] as string[] | undefined) ?? [];
|
|
230
|
+
const packages = raw.length > 0 ? parseInstallArgs(raw) : undefined;
|
|
231
|
+
const code = await runInstallPkg({packages});
|
|
232
|
+
process.exit(code);
|
|
233
|
+
},
|
|
234
|
+
};
|