@justscale/core 0.1.0
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/LICENSE +21 -0
- package/README.md +261 -0
- package/bin/just.js +34 -0
- package/dist/app.d.ts +56 -0
- package/dist/app.d.ts.map +1 -0
- package/dist/app.js +182 -0
- package/dist/app.js.map +1 -0
- package/dist/builder/build-context.d.ts +8 -0
- package/dist/builder/build-context.d.ts.map +1 -0
- package/dist/builder/build-context.js +4 -0
- package/dist/builder/build-context.js.map +1 -0
- package/dist/builder/builder.d.ts +60 -0
- package/dist/builder/builder.d.ts.map +1 -0
- package/dist/builder/builder.js +72 -0
- package/dist/builder/builder.js.map +1 -0
- package/dist/builder/create-builder.d.ts +36 -0
- package/dist/builder/create-builder.d.ts.map +1 -0
- package/dist/builder/create-builder.js +66 -0
- package/dist/builder/create-builder.js.map +1 -0
- package/dist/builder/execute.d.ts +37 -0
- package/dist/builder/execute.d.ts.map +1 -0
- package/dist/builder/execute.js +62 -0
- package/dist/builder/execute.js.map +1 -0
- package/dist/builder/feature-builder.d.ts +147 -0
- package/dist/builder/feature-builder.d.ts.map +1 -0
- package/dist/builder/feature-builder.js +138 -0
- package/dist/builder/feature-builder.js.map +1 -0
- package/dist/builder/index.d.ts +35 -0
- package/dist/builder/index.d.ts.map +1 -0
- package/dist/builder/index.js +37 -0
- package/dist/builder/index.js.map +1 -0
- package/dist/builder/plugin.d.ts +90 -0
- package/dist/builder/plugin.d.ts.map +1 -0
- package/dist/builder/plugin.js +101 -0
- package/dist/builder/plugin.js.map +1 -0
- package/dist/builder/plugins/query.d.ts +31 -0
- package/dist/builder/plugins/query.d.ts.map +1 -0
- package/dist/builder/plugins/query.js +42 -0
- package/dist/builder/plugins/query.js.map +1 -0
- package/dist/builder/plugins/validation.d.ts +12 -0
- package/dist/builder/plugins/validation.d.ts.map +1 -0
- package/dist/builder/plugins/validation.js +12 -0
- package/dist/builder/plugins/validation.js.map +1 -0
- package/dist/builder/sort.d.ts +27 -0
- package/dist/builder/sort.d.ts.map +1 -0
- package/dist/builder/sort.js +210 -0
- package/dist/builder/sort.js.map +1 -0
- package/dist/builder/stop.d.ts +24 -0
- package/dist/builder/stop.d.ts.map +1 -0
- package/dist/builder/stop.js +27 -0
- package/dist/builder/stop.js.map +1 -0
- package/dist/builder/test/permits-type-spike.d.ts +8 -0
- package/dist/builder/test/permits-type-spike.d.ts.map +1 -0
- package/dist/builder/test/permits-type-spike.js +117 -0
- package/dist/builder/test/permits-type-spike.js.map +1 -0
- package/dist/builder/types.d.ts +678 -0
- package/dist/builder/types.d.ts.map +1 -0
- package/dist/builder/types.js +98 -0
- package/dist/builder/types.js.map +1 -0
- package/dist/builder/validation.d.ts +101 -0
- package/dist/builder/validation.d.ts.map +1 -0
- package/dist/builder/validation.js +335 -0
- package/dist/builder/validation.js.map +1 -0
- package/dist/cli/adapter.d.ts +23 -0
- package/dist/cli/adapter.d.ts.map +1 -0
- package/dist/cli/adapter.js +26 -0
- package/dist/cli/adapter.js.map +1 -0
- package/dist/cli/args.d.ts +150 -0
- package/dist/cli/args.d.ts.map +1 -0
- package/dist/cli/args.js +172 -0
- package/dist/cli/args.js.map +1 -0
- package/dist/cli/assemble.d.ts +20 -0
- package/dist/cli/assemble.d.ts.map +1 -0
- package/dist/cli/assemble.js +55 -0
- package/dist/cli/assemble.js.map +1 -0
- package/dist/cli/bin/main.d.ts +26 -0
- package/dist/cli/bin/main.d.ts.map +1 -0
- package/dist/cli/bin/main.js +475 -0
- package/dist/cli/bin/main.js.map +1 -0
- package/dist/cli/build/migrations-plugin.d.ts +21 -0
- package/dist/cli/build/migrations-plugin.d.ts.map +1 -0
- package/dist/cli/build/migrations-plugin.js +41 -0
- package/dist/cli/build/migrations-plugin.js.map +1 -0
- package/dist/cli/build/process-plugin.d.ts +29 -0
- package/dist/cli/build/process-plugin.d.ts.map +1 -0
- package/dist/cli/build/process-plugin.js +66 -0
- package/dist/cli/build/process-plugin.js.map +1 -0
- package/dist/cli/builder/create-cli-builder.d.ts +42 -0
- package/dist/cli/builder/create-cli-builder.d.ts.map +1 -0
- package/dist/cli/builder/create-cli-builder.js +104 -0
- package/dist/cli/builder/create-cli-builder.js.map +1 -0
- package/dist/cli/builder/index.d.ts +8 -0
- package/dist/cli/builder/index.d.ts.map +1 -0
- package/dist/cli/builder/index.js +7 -0
- package/dist/cli/builder/index.js.map +1 -0
- package/dist/cli/builder/types.d.ts +113 -0
- package/dist/cli/builder/types.d.ts.map +1 -0
- package/dist/cli/builder/types.js +7 -0
- package/dist/cli/builder/types.js.map +1 -0
- package/dist/cli/cluster.d.ts +8 -0
- package/dist/cli/cluster.d.ts.map +1 -0
- package/dist/cli/cluster.js +145 -0
- package/dist/cli/cluster.js.map +1 -0
- package/dist/cli/current-app.d.ts +36 -0
- package/dist/cli/current-app.d.ts.map +1 -0
- package/dist/cli/current-app.js +21 -0
- package/dist/cli/current-app.js.map +1 -0
- package/dist/cli/define-app.d.ts +35 -0
- package/dist/cli/define-app.d.ts.map +1 -0
- package/dist/cli/define-app.js +79 -0
- package/dist/cli/define-app.js.map +1 -0
- package/dist/cli/define-main.d.ts +33 -0
- package/dist/cli/define-main.d.ts.map +1 -0
- package/dist/cli/define-main.js +67 -0
- package/dist/cli/define-main.js.map +1 -0
- package/dist/cli/define-project.d.ts +93 -0
- package/dist/cli/define-project.d.ts.map +1 -0
- package/dist/cli/define-project.js +85 -0
- package/dist/cli/define-project.js.map +1 -0
- package/dist/cli/dev-server.d.ts +20 -0
- package/dist/cli/dev-server.d.ts.map +1 -0
- package/dist/cli/dev-server.js +131 -0
- package/dist/cli/dev-server.js.map +1 -0
- package/dist/cli/discovery.d.ts +29 -0
- package/dist/cli/discovery.d.ts.map +1 -0
- package/dist/cli/discovery.js +142 -0
- package/dist/cli/discovery.js.map +1 -0
- package/dist/cli/factory.d.ts +43 -0
- package/dist/cli/factory.d.ts.map +1 -0
- package/dist/cli/factory.js +52 -0
- package/dist/cli/factory.js.map +1 -0
- package/dist/cli/generators/ai.d.ts +3 -0
- package/dist/cli/generators/ai.d.ts.map +1 -0
- package/dist/cli/generators/ai.js +65 -0
- package/dist/cli/generators/ai.js.map +1 -0
- package/dist/cli/generators/ci.d.ts +5 -0
- package/dist/cli/generators/ci.d.ts.map +1 -0
- package/dist/cli/generators/ci.js +102 -0
- package/dist/cli/generators/ci.js.map +1 -0
- package/dist/cli/generators/detect.d.ts +15 -0
- package/dist/cli/generators/detect.d.ts.map +1 -0
- package/dist/cli/generators/detect.js +75 -0
- package/dist/cli/generators/detect.js.map +1 -0
- package/dist/cli/generators/ide.d.ts +3 -0
- package/dist/cli/generators/ide.d.ts.map +1 -0
- package/dist/cli/generators/ide.js +179 -0
- package/dist/cli/generators/ide.js.map +1 -0
- package/dist/cli/generators/index.d.ts +5 -0
- package/dist/cli/generators/index.d.ts.map +1 -0
- package/dist/cli/generators/index.js +5 -0
- package/dist/cli/generators/index.js.map +1 -0
- package/dist/cli/index.d.ts +81 -0
- package/dist/cli/index.d.ts.map +1 -0
- package/dist/cli/index.js +88 -0
- package/dist/cli/index.js.map +1 -0
- package/dist/cli/io.d.ts +131 -0
- package/dist/cli/io.d.ts.map +1 -0
- package/dist/cli/io.js +373 -0
- package/dist/cli/io.js.map +1 -0
- package/dist/cli/mcp/server.d.ts +23 -0
- package/dist/cli/mcp/server.d.ts.map +1 -0
- package/dist/cli/mcp/server.js +148 -0
- package/dist/cli/mcp/server.js.map +1 -0
- package/dist/cli/parser.d.ts +106 -0
- package/dist/cli/parser.d.ts.map +1 -0
- package/dist/cli/parser.js +520 -0
- package/dist/cli/parser.js.map +1 -0
- package/dist/cli/runner.d.ts +75 -0
- package/dist/cli/runner.d.ts.map +1 -0
- package/dist/cli/runner.js +422 -0
- package/dist/cli/runner.js.map +1 -0
- package/dist/cli/service.d.ts +61 -0
- package/dist/cli/service.d.ts.map +1 -0
- package/dist/cli/service.js +95 -0
- package/dist/cli/service.js.map +1 -0
- package/dist/cli/types.d.ts +47 -0
- package/dist/cli/types.d.ts.map +1 -0
- package/dist/cli/types.js +20 -0
- package/dist/cli/types.js.map +1 -0
- package/dist/cli/wizard.d.ts +11 -0
- package/dist/cli/wizard.d.ts.map +1 -0
- package/dist/cli/wizard.js +2 -0
- package/dist/cli/wizard.js.map +1 -0
- package/dist/cli/workspace-controller.d.ts +36 -0
- package/dist/cli/workspace-controller.d.ts.map +1 -0
- package/dist/cli/workspace-controller.js +896 -0
- package/dist/cli/workspace-controller.js.map +1 -0
- package/dist/cluster/client.d.ts +101 -0
- package/dist/cluster/client.d.ts.map +1 -0
- package/dist/cluster/client.js +256 -0
- package/dist/cluster/client.js.map +1 -0
- package/dist/cluster/cluster.d.ts +82 -0
- package/dist/cluster/cluster.d.ts.map +1 -0
- package/dist/cluster/cluster.js +27 -0
- package/dist/cluster/cluster.js.map +1 -0
- package/dist/cluster/coordinator/cluster-node.model.d.ts +14 -0
- package/dist/cluster/coordinator/cluster-node.model.d.ts.map +1 -0
- package/dist/cluster/coordinator/cluster-node.model.js +15 -0
- package/dist/cluster/coordinator/cluster-node.model.js.map +1 -0
- package/dist/cluster/coordinator/cluster-signals.d.ts +45 -0
- package/dist/cluster/coordinator/cluster-signals.d.ts.map +1 -0
- package/dist/cluster/coordinator/cluster-signals.js +24 -0
- package/dist/cluster/coordinator/cluster-signals.js.map +1 -0
- package/dist/cluster/coordinator/coordinator.process.d.ts +21 -0
- package/dist/cluster/coordinator/coordinator.process.d.ts.map +1 -0
- package/dist/cluster/coordinator/coordinator.process.js +221 -0
- package/dist/cluster/coordinator/coordinator.process.js.map +1 -0
- package/dist/cluster/coordinator/index.d.ts +13 -0
- package/dist/cluster/coordinator/index.d.ts.map +1 -0
- package/dist/cluster/coordinator/index.js +13 -0
- package/dist/cluster/coordinator/index.js.map +1 -0
- package/dist/cluster/coordinator/node-lifecycle.d.ts +31 -0
- package/dist/cluster/coordinator/node-lifecycle.d.ts.map +1 -0
- package/dist/cluster/coordinator/node-lifecycle.js +178 -0
- package/dist/cluster/coordinator/node-lifecycle.js.map +1 -0
- package/dist/cluster/index.d.ts +45 -0
- package/dist/cluster/index.d.ts.map +1 -0
- package/dist/cluster/index.js +57 -0
- package/dist/cluster/index.js.map +1 -0
- package/dist/cluster/protocol.d.ts +204 -0
- package/dist/cluster/protocol.d.ts.map +1 -0
- package/dist/cluster/protocol.js +274 -0
- package/dist/cluster/protocol.js.map +1 -0
- package/dist/cluster/scheduled-task/builder.d.ts +24 -0
- package/dist/cluster/scheduled-task/builder.d.ts.map +1 -0
- package/dist/cluster/scheduled-task/builder.js +63 -0
- package/dist/cluster/scheduled-task/builder.js.map +1 -0
- package/dist/cluster/scheduled-task/factory.d.ts +76 -0
- package/dist/cluster/scheduled-task/factory.d.ts.map +1 -0
- package/dist/cluster/scheduled-task/factory.js +64 -0
- package/dist/cluster/scheduled-task/factory.js.map +1 -0
- package/dist/cluster/scheduled-task/index.d.ts +43 -0
- package/dist/cluster/scheduled-task/index.d.ts.map +1 -0
- package/dist/cluster/scheduled-task/index.js +45 -0
- package/dist/cluster/scheduled-task/index.js.map +1 -0
- package/dist/cluster/scheduled-task/transport.d.ts +12 -0
- package/dist/cluster/scheduled-task/transport.d.ts.map +1 -0
- package/dist/cluster/scheduled-task/transport.js +146 -0
- package/dist/cluster/scheduled-task/transport.js.map +1 -0
- package/dist/cluster/scheduled-task/types.d.ts +89 -0
- package/dist/cluster/scheduled-task/types.d.ts.map +1 -0
- package/dist/cluster/scheduled-task/types.js +7 -0
- package/dist/cluster/scheduled-task/types.js.map +1 -0
- package/dist/cluster/server.d.ts +87 -0
- package/dist/cluster/server.d.ts.map +1 -0
- package/dist/cluster/server.js +290 -0
- package/dist/cluster/server.js.map +1 -0
- package/dist/cluster/transport.d.ts +86 -0
- package/dist/cluster/transport.d.ts.map +1 -0
- package/dist/cluster/transport.js +138 -0
- package/dist/cluster/transport.js.map +1 -0
- package/dist/core/container-hooks.d.ts +22 -0
- package/dist/core/container-hooks.d.ts.map +1 -0
- package/dist/core/container-hooks.js +29 -0
- package/dist/core/container-hooks.js.map +1 -0
- package/dist/core/container-reflection.d.ts +71 -0
- package/dist/core/container-reflection.d.ts.map +1 -0
- package/dist/core/container-reflection.js +60 -0
- package/dist/core/container-reflection.js.map +1 -0
- package/dist/core/context.d.ts +146 -0
- package/dist/core/context.d.ts.map +1 -0
- package/dist/core/context.js +155 -0
- package/dist/core/context.js.map +1 -0
- package/dist/core/contribution.d.ts +152 -0
- package/dist/core/contribution.d.ts.map +1 -0
- package/dist/core/contribution.js +213 -0
- package/dist/core/contribution.js.map +1 -0
- package/dist/core/controller.contextual.d.ts +193 -0
- package/dist/core/controller.contextual.d.ts.map +1 -0
- package/dist/core/controller.contextual.js +459 -0
- package/dist/core/controller.contextual.js.map +1 -0
- package/dist/core/controller.d.ts +510 -0
- package/dist/core/controller.d.ts.map +1 -0
- package/dist/core/controller.js +411 -0
- package/dist/core/controller.js.map +1 -0
- package/dist/core/controller.procedure.d.ts +147 -0
- package/dist/core/controller.procedure.d.ts.map +1 -0
- package/dist/core/controller.procedure.js +115 -0
- package/dist/core/controller.procedure.js.map +1 -0
- package/dist/core/disposable.d.ts +126 -0
- package/dist/core/disposable.d.ts.map +1 -0
- package/dist/core/disposable.js +179 -0
- package/dist/core/disposable.js.map +1 -0
- package/dist/core/hmr.d.ts +83 -0
- package/dist/core/hmr.d.ts.map +1 -0
- package/dist/core/hmr.js +211 -0
- package/dist/core/hmr.js.map +1 -0
- package/dist/core/index.d.ts +17 -0
- package/dist/core/index.d.ts.map +1 -0
- package/dist/core/index.js +25 -0
- package/dist/core/index.js.map +1 -0
- package/dist/core/internal/routes.d.ts +26 -0
- package/dist/core/internal/routes.d.ts.map +1 -0
- package/dist/core/internal/routes.js +48 -0
- package/dist/core/internal/routes.js.map +1 -0
- package/dist/core/lifecycle-impl.d.ts +45 -0
- package/dist/core/lifecycle-impl.d.ts.map +1 -0
- package/dist/core/lifecycle-impl.js +102 -0
- package/dist/core/lifecycle-impl.js.map +1 -0
- package/dist/core/lifecycle.d.ts +86 -0
- package/dist/core/lifecycle.d.ts.map +1 -0
- package/dist/core/lifecycle.js +38 -0
- package/dist/core/lifecycle.js.map +1 -0
- package/dist/core/logger.d.ts +282 -0
- package/dist/core/logger.d.ts.map +1 -0
- package/dist/core/logger.js +368 -0
- package/dist/core/logger.js.map +1 -0
- package/dist/core/middleware.d.ts +108 -0
- package/dist/core/middleware.d.ts.map +1 -0
- package/dist/core/middleware.js +60 -0
- package/dist/core/middleware.js.map +1 -0
- package/dist/core/openapi-methods.d.ts +61 -0
- package/dist/core/openapi-methods.d.ts.map +1 -0
- package/dist/core/openapi-methods.js +53 -0
- package/dist/core/openapi-methods.js.map +1 -0
- package/dist/core/plugin.d.ts +209 -0
- package/dist/core/plugin.d.ts.map +1 -0
- package/dist/core/plugin.js +36 -0
- package/dist/core/plugin.js.map +1 -0
- package/dist/core/scope-bridge.d.ts +19 -0
- package/dist/core/scope-bridge.d.ts.map +1 -0
- package/dist/core/scope-bridge.js +34 -0
- package/dist/core/scope-bridge.js.map +1 -0
- package/dist/core/service.d.ts +429 -0
- package/dist/core/service.d.ts.map +1 -0
- package/dist/core/service.js +875 -0
- package/dist/core/service.js.map +1 -0
- package/dist/features/channel/backend.d.ts +98 -0
- package/dist/features/channel/backend.d.ts.map +1 -0
- package/dist/features/channel/backend.js +75 -0
- package/dist/features/channel/backend.js.map +1 -0
- package/dist/features/channel/channel.d.ts +18 -0
- package/dist/features/channel/channel.d.ts.map +1 -0
- package/dist/features/channel/channel.js +219 -0
- package/dist/features/channel/channel.js.map +1 -0
- package/dist/features/channel/channels.d.ts +87 -0
- package/dist/features/channel/channels.d.ts.map +1 -0
- package/dist/features/channel/channels.js +252 -0
- package/dist/features/channel/channels.js.map +1 -0
- package/dist/features/channel/feature.d.ts +40 -0
- package/dist/features/channel/feature.d.ts.map +1 -0
- package/dist/features/channel/feature.js +44 -0
- package/dist/features/channel/feature.js.map +1 -0
- package/dist/features/channel/index.d.ts +41 -0
- package/dist/features/channel/index.d.ts.map +1 -0
- package/dist/features/channel/index.js +41 -0
- package/dist/features/channel/index.js.map +1 -0
- package/dist/features/channel/types.d.ts +165 -0
- package/dist/features/channel/types.d.ts.map +1 -0
- package/dist/features/channel/types.js +10 -0
- package/dist/features/channel/types.js.map +1 -0
- package/dist/features/config/cli/config-controller.d.ts +77 -0
- package/dist/features/config/cli/config-controller.d.ts.map +1 -0
- package/dist/features/config/cli/config-controller.js +209 -0
- package/dist/features/config/cli/config-controller.js.map +1 -0
- package/dist/features/config/cli/index.d.ts +9 -0
- package/dist/features/config/cli/index.d.ts.map +1 -0
- package/dist/features/config/cli/index.js +9 -0
- package/dist/features/config/cli/index.js.map +1 -0
- package/dist/features/config/cli/profile-controller.d.ts +87 -0
- package/dist/features/config/cli/profile-controller.d.ts.map +1 -0
- package/dist/features/config/cli/profile-controller.js +223 -0
- package/dist/features/config/cli/profile-controller.js.map +1 -0
- package/dist/features/config/cli/utils.d.ts +14 -0
- package/dist/features/config/cli/utils.d.ts.map +1 -0
- package/dist/features/config/cli/utils.js +29 -0
- package/dist/features/config/cli/utils.js.map +1 -0
- package/dist/features/config/config-of.d.ts +36 -0
- package/dist/features/config/config-of.d.ts.map +1 -0
- package/dist/features/config/config-of.js +36 -0
- package/dist/features/config/config-of.js.map +1 -0
- package/dist/features/config/config-service.d.ts +54 -0
- package/dist/features/config/config-service.d.ts.map +1 -0
- package/dist/features/config/config-service.js +184 -0
- package/dist/features/config/config-service.js.map +1 -0
- package/dist/features/config/create-config.d.ts +21 -0
- package/dist/features/config/create-config.d.ts.map +1 -0
- package/dist/features/config/create-config.js +16 -0
- package/dist/features/config/create-config.js.map +1 -0
- package/dist/features/config/define-config-partial.d.ts +13 -0
- package/dist/features/config/define-config-partial.d.ts.map +1 -0
- package/dist/features/config/define-config-partial.js +19 -0
- package/dist/features/config/define-config-partial.js.map +1 -0
- package/dist/features/config/env-service.d.ts +54 -0
- package/dist/features/config/env-service.d.ts.map +1 -0
- package/dist/features/config/env-service.js +115 -0
- package/dist/features/config/env-service.js.map +1 -0
- package/dist/features/config/file-watcher.d.ts +13 -0
- package/dist/features/config/file-watcher.d.ts.map +1 -0
- package/dist/features/config/file-watcher.js +98 -0
- package/dist/features/config/file-watcher.js.map +1 -0
- package/dist/features/config/index.d.ts +21 -0
- package/dist/features/config/index.d.ts.map +1 -0
- package/dist/features/config/index.js +24 -0
- package/dist/features/config/index.js.map +1 -0
- package/dist/features/config/profile-service.d.ts +59 -0
- package/dist/features/config/profile-service.d.ts.map +1 -0
- package/dist/features/config/profile-service.js +114 -0
- package/dist/features/config/profile-service.js.map +1 -0
- package/dist/features/config/types.d.ts +38 -0
- package/dist/features/config/types.d.ts.map +1 -0
- package/dist/features/config/types.js +17 -0
- package/dist/features/config/types.js.map +1 -0
- package/dist/features/contract/contract.d.ts +264 -0
- package/dist/features/contract/contract.d.ts.map +1 -0
- package/dist/features/contract/contract.js +183 -0
- package/dist/features/contract/contract.js.map +1 -0
- package/dist/features/contract/index.d.ts +2 -0
- package/dist/features/contract/index.d.ts.map +1 -0
- package/dist/features/contract/index.js +2 -0
- package/dist/features/contract/index.js.map +1 -0
- package/dist/features/env/contribute.d.ts +70 -0
- package/dist/features/env/contribute.d.ts.map +1 -0
- package/dist/features/env/contribute.js +195 -0
- package/dist/features/env/contribute.js.map +1 -0
- package/dist/features/environment/create-environment.d.ts +58 -0
- package/dist/features/environment/create-environment.d.ts.map +1 -0
- package/dist/features/environment/create-environment.js +22 -0
- package/dist/features/environment/create-environment.js.map +1 -0
- package/dist/features/environment/index.d.ts +12 -0
- package/dist/features/environment/index.d.ts.map +1 -0
- package/dist/features/environment/index.js +10 -0
- package/dist/features/environment/index.js.map +1 -0
- package/dist/features/environment/load.d.ts +59 -0
- package/dist/features/environment/load.d.ts.map +1 -0
- package/dist/features/environment/load.js +117 -0
- package/dist/features/environment/load.js.map +1 -0
- package/dist/features/environment/types.d.ts +165 -0
- package/dist/features/environment/types.d.ts.map +1 -0
- package/dist/features/environment/types.js +18 -0
- package/dist/features/environment/types.js.map +1 -0
- package/dist/features/feature-flags/create-feature-flag-provider.d.ts +21 -0
- package/dist/features/feature-flags/create-feature-flag-provider.d.ts.map +1 -0
- package/dist/features/feature-flags/create-feature-flag-provider.js +16 -0
- package/dist/features/feature-flags/create-feature-flag-provider.js.map +1 -0
- package/dist/features/feature-flags/define-feature-flag-partial.d.ts +20 -0
- package/dist/features/feature-flags/define-feature-flag-partial.d.ts.map +1 -0
- package/dist/features/feature-flags/define-feature-flag-partial.js +26 -0
- package/dist/features/feature-flags/define-feature-flag-partial.js.map +1 -0
- package/dist/features/feature-flags/feature-flag-of.d.ts +16 -0
- package/dist/features/feature-flags/feature-flag-of.d.ts.map +1 -0
- package/dist/features/feature-flags/feature-flag-of.js +16 -0
- package/dist/features/feature-flags/feature-flag-of.js.map +1 -0
- package/dist/features/feature-flags/feature-flag-service.d.ts +22 -0
- package/dist/features/feature-flags/feature-flag-service.d.ts.map +1 -0
- package/dist/features/feature-flags/feature-flag-service.js +112 -0
- package/dist/features/feature-flags/feature-flag-service.js.map +1 -0
- package/dist/features/feature-flags/index.d.ts +15 -0
- package/dist/features/feature-flags/index.d.ts.map +1 -0
- package/dist/features/feature-flags/index.js +12 -0
- package/dist/features/feature-flags/index.js.map +1 -0
- package/dist/features/feature-flags/types.d.ts +30 -0
- package/dist/features/feature-flags/types.d.ts.map +1 -0
- package/dist/features/feature-flags/types.js +8 -0
- package/dist/features/feature-flags/types.js.map +1 -0
- package/dist/features/index.d.ts +6 -0
- package/dist/features/index.d.ts.map +1 -0
- package/dist/features/index.js +7 -0
- package/dist/features/index.js.map +1 -0
- package/dist/features/lock/index.d.ts +4 -0
- package/dist/features/lock/index.d.ts.map +1 -0
- package/dist/features/lock/index.js +4 -0
- package/dist/features/lock/index.js.map +1 -0
- package/dist/features/lock/lock-service.d.ts +74 -0
- package/dist/features/lock/lock-service.d.ts.map +1 -0
- package/dist/features/lock/lock-service.js +210 -0
- package/dist/features/lock/lock-service.js.map +1 -0
- package/dist/features/lock/memory.d.ts +60 -0
- package/dist/features/lock/memory.d.ts.map +1 -0
- package/dist/features/lock/memory.js +194 -0
- package/dist/features/lock/memory.js.map +1 -0
- package/dist/features/lock/types.d.ts +151 -0
- package/dist/features/lock/types.d.ts.map +1 -0
- package/dist/features/lock/types.js +17 -0
- package/dist/features/lock/types.js.map +1 -0
- package/dist/features/memory/index.d.ts +18 -0
- package/dist/features/memory/index.d.ts.map +1 -0
- package/dist/features/memory/index.js +18 -0
- package/dist/features/memory/index.js.map +1 -0
- package/dist/features/memory/lock-feature.d.ts +21 -0
- package/dist/features/memory/lock-feature.d.ts.map +1 -0
- package/dist/features/memory/lock-feature.js +24 -0
- package/dist/features/memory/lock-feature.js.map +1 -0
- package/dist/features/secrets/create-secret-provider.d.ts +31 -0
- package/dist/features/secrets/create-secret-provider.d.ts.map +1 -0
- package/dist/features/secrets/create-secret-provider.js +26 -0
- package/dist/features/secrets/create-secret-provider.js.map +1 -0
- package/dist/features/secrets/define-secret-partial.d.ts +16 -0
- package/dist/features/secrets/define-secret-partial.d.ts.map +1 -0
- package/dist/features/secrets/define-secret-partial.js +26 -0
- package/dist/features/secrets/define-secret-partial.js.map +1 -0
- package/dist/features/secrets/index.d.ts +17 -0
- package/dist/features/secrets/index.d.ts.map +1 -0
- package/dist/features/secrets/index.js +14 -0
- package/dist/features/secrets/index.js.map +1 -0
- package/dist/features/secrets/secret-of.d.ts +19 -0
- package/dist/features/secrets/secret-of.d.ts.map +1 -0
- package/dist/features/secrets/secret-of.js +21 -0
- package/dist/features/secrets/secret-of.js.map +1 -0
- package/dist/features/secrets/secret-service.d.ts +21 -0
- package/dist/features/secrets/secret-service.d.ts.map +1 -0
- package/dist/features/secrets/secret-service.js +28 -0
- package/dist/features/secrets/secret-service.js.map +1 -0
- package/dist/features/secrets/types.d.ts +30 -0
- package/dist/features/secrets/types.d.ts.map +1 -0
- package/dist/features/secrets/types.js +8 -0
- package/dist/features/secrets/types.js.map +1 -0
- package/dist/features/vault/env-var-vault.d.ts +24 -0
- package/dist/features/vault/env-var-vault.d.ts.map +1 -0
- package/dist/features/vault/env-var-vault.js +43 -0
- package/dist/features/vault/env-var-vault.js.map +1 -0
- package/dist/features/vault/hardcoded-vault.d.ts +34 -0
- package/dist/features/vault/hardcoded-vault.d.ts.map +1 -0
- package/dist/features/vault/hardcoded-vault.js +46 -0
- package/dist/features/vault/hardcoded-vault.js.map +1 -0
- package/dist/features/vault/hashicorp-vault.d.ts +32 -0
- package/dist/features/vault/hashicorp-vault.d.ts.map +1 -0
- package/dist/features/vault/hashicorp-vault.js +69 -0
- package/dist/features/vault/hashicorp-vault.js.map +1 -0
- package/dist/features/vault/index.d.ts +13 -0
- package/dist/features/vault/index.d.ts.map +1 -0
- package/dist/features/vault/index.js +12 -0
- package/dist/features/vault/index.js.map +1 -0
- package/dist/features/vault/kubernetes-vault.d.ts +27 -0
- package/dist/features/vault/kubernetes-vault.d.ts.map +1 -0
- package/dist/features/vault/kubernetes-vault.js +51 -0
- package/dist/features/vault/kubernetes-vault.js.map +1 -0
- package/dist/features/vault/types.d.ts +41 -0
- package/dist/features/vault/types.d.ts.map +1 -0
- package/dist/features/vault/types.js +21 -0
- package/dist/features/vault/types.js.map +1 -0
- package/dist/index.d.ts +78 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +48 -0
- package/dist/index.js.map +1 -0
- package/dist/justscale.d.ts +63 -0
- package/dist/justscale.d.ts.map +1 -0
- package/dist/justscale.js +501 -0
- package/dist/justscale.js.map +1 -0
- package/dist/kernel/adapter.d.ts +9 -0
- package/dist/kernel/adapter.d.ts.map +1 -0
- package/dist/kernel/adapter.js +2 -0
- package/dist/kernel/adapter.js.map +1 -0
- package/dist/kernel/kernel.d.ts +15 -0
- package/dist/kernel/kernel.d.ts.map +1 -0
- package/dist/kernel/kernel.js +134 -0
- package/dist/kernel/kernel.js.map +1 -0
- package/dist/models/access.d.ts +26 -0
- package/dist/models/access.d.ts.map +1 -0
- package/dist/models/access.js +126 -0
- package/dist/models/access.js.map +1 -0
- package/dist/models/apply-types-config.d.ts +52 -0
- package/dist/models/apply-types-config.d.ts.map +1 -0
- package/dist/models/apply-types-config.js +47 -0
- package/dist/models/apply-types-config.js.map +1 -0
- package/dist/models/define-model.d.ts +249 -0
- package/dist/models/define-model.d.ts.map +1 -0
- package/dist/models/define-model.js +388 -0
- package/dist/models/define-model.js.map +1 -0
- package/dist/models/field.d.ts +309 -0
- package/dist/models/field.d.ts.map +1 -0
- package/dist/models/field.js +312 -0
- package/dist/models/field.js.map +1 -0
- package/dist/models/in-memory/condition-evaluator.d.ts +53 -0
- package/dist/models/in-memory/condition-evaluator.d.ts.map +1 -0
- package/dist/models/in-memory/condition-evaluator.js +593 -0
- package/dist/models/in-memory/condition-evaluator.js.map +1 -0
- package/dist/models/in-memory/in-memory-model.d.ts +89 -0
- package/dist/models/in-memory/in-memory-model.d.ts.map +1 -0
- package/dist/models/in-memory/in-memory-model.js +101 -0
- package/dist/models/in-memory/in-memory-model.js.map +1 -0
- package/dist/models/in-memory/in-memory-repository.d.ts +208 -0
- package/dist/models/in-memory/in-memory-repository.d.ts.map +1 -0
- package/dist/models/in-memory/in-memory-repository.js +618 -0
- package/dist/models/in-memory/in-memory-repository.js.map +1 -0
- package/dist/models/in-memory/in-memory-scheduled-task.repository.d.ts +92 -0
- package/dist/models/in-memory/in-memory-scheduled-task.repository.d.ts.map +1 -0
- package/dist/models/in-memory/in-memory-scheduled-task.repository.js +395 -0
- package/dist/models/in-memory/in-memory-scheduled-task.repository.js.map +1 -0
- package/dist/models/in-memory/index.d.ts +35 -0
- package/dist/models/in-memory/index.d.ts.map +1 -0
- package/dist/models/in-memory/index.js +36 -0
- package/dist/models/in-memory/index.js.map +1 -0
- package/dist/models/index.d.ts +52 -0
- package/dist/models/index.d.ts.map +1 -0
- package/dist/models/index.js +86 -0
- package/dist/models/index.js.map +1 -0
- package/dist/models/model-name-registry.d.ts +16 -0
- package/dist/models/model-name-registry.d.ts.map +1 -0
- package/dist/models/model-name-registry.js +19 -0
- package/dist/models/model-name-registry.js.map +1 -0
- package/dist/models/model.d.ts +15 -0
- package/dist/models/model.d.ts.map +1 -0
- package/dist/models/model.js +114 -0
- package/dist/models/model.js.map +1 -0
- package/dist/models/model.repository.d.ts +318 -0
- package/dist/models/model.repository.d.ts.map +1 -0
- package/dist/models/model.repository.js +146 -0
- package/dist/models/model.repository.js.map +1 -0
- package/dist/models/observable.d.ts +15 -0
- package/dist/models/observable.d.ts.map +1 -0
- package/dist/models/observable.js +64 -0
- package/dist/models/observable.js.map +1 -0
- package/dist/models/proxy.d.ts +5 -0
- package/dist/models/proxy.d.ts.map +1 -0
- package/dist/models/proxy.js +407 -0
- package/dist/models/proxy.js.map +1 -0
- package/dist/models/query.d.ts +574 -0
- package/dist/models/query.d.ts.map +1 -0
- package/dist/models/query.js +701 -0
- package/dist/models/query.js.map +1 -0
- package/dist/models/reference/reference.d.ts +229 -0
- package/dist/models/reference/reference.d.ts.map +1 -0
- package/dist/models/reference/reference.js +331 -0
- package/dist/models/reference/reference.js.map +1 -0
- package/dist/models/reference/transient-ref.d.ts +123 -0
- package/dist/models/reference/transient-ref.d.ts.map +1 -0
- package/dist/models/reference/transient-ref.js +152 -0
- package/dist/models/reference/transient-ref.js.map +1 -0
- package/dist/models/repository.d.ts +53 -0
- package/dist/models/repository.d.ts.map +1 -0
- package/dist/models/repository.js +37 -0
- package/dist/models/repository.js.map +1 -0
- package/dist/models/scheduled-task/index.d.ts +13 -0
- package/dist/models/scheduled-task/index.d.ts.map +1 -0
- package/dist/models/scheduled-task/index.js +12 -0
- package/dist/models/scheduled-task/index.js.map +1 -0
- package/dist/models/scheduled-task/scheduled-task.d.ts +73 -0
- package/dist/models/scheduled-task/scheduled-task.d.ts.map +1 -0
- package/dist/models/scheduled-task/scheduled-task.js +95 -0
- package/dist/models/scheduled-task/scheduled-task.js.map +1 -0
- package/dist/models/scheduled-task/scheduled-task.repository.d.ts +150 -0
- package/dist/models/scheduled-task/scheduled-task.repository.d.ts.map +1 -0
- package/dist/models/scheduled-task/scheduled-task.repository.js +40 -0
- package/dist/models/scheduled-task/scheduled-task.repository.js.map +1 -0
- package/dist/models/stream.d.ts +139 -0
- package/dist/models/stream.d.ts.map +1 -0
- package/dist/models/stream.js +153 -0
- package/dist/models/stream.js.map +1 -0
- package/dist/models/symbols.d.ts +73 -0
- package/dist/models/symbols.d.ts.map +1 -0
- package/dist/models/symbols.js +97 -0
- package/dist/models/symbols.js.map +1 -0
- package/dist/models/types.d.ts +291 -0
- package/dist/models/types.d.ts.map +1 -0
- package/dist/models/types.js +50 -0
- package/dist/models/types.js.map +1 -0
- package/dist/models/watch.d.ts +27 -0
- package/dist/models/watch.d.ts.map +1 -0
- package/dist/models/watch.js +124 -0
- package/dist/models/watch.js.map +1 -0
- package/dist/models/zod-ref.d.ts +46 -0
- package/dist/models/zod-ref.d.ts.map +1 -0
- package/dist/models/zod-ref.js +31 -0
- package/dist/models/zod-ref.js.map +1 -0
- package/dist/process/builtin-serializers.d.ts +19 -0
- package/dist/process/builtin-serializers.d.ts.map +1 -0
- package/dist/process/builtin-serializers.js +213 -0
- package/dist/process/builtin-serializers.js.map +1 -0
- package/dist/process/cluster-plugin.d.ts +129 -0
- package/dist/process/cluster-plugin.d.ts.map +1 -0
- package/dist/process/cluster-plugin.js +175 -0
- package/dist/process/cluster-plugin.js.map +1 -0
- package/dist/process/createProcess.d.ts +67 -0
- package/dist/process/createProcess.d.ts.map +1 -0
- package/dist/process/createProcess.js +111 -0
- package/dist/process/createProcess.js.map +1 -0
- package/dist/process/define-signals.d.ts +113 -0
- package/dist/process/define-signals.d.ts.map +1 -0
- package/dist/process/define-signals.js +222 -0
- package/dist/process/define-signals.js.map +1 -0
- package/dist/process/delay-controller.d.ts +35 -0
- package/dist/process/delay-controller.d.ts.map +1 -0
- package/dist/process/delay-controller.js +55 -0
- package/dist/process/delay-controller.js.map +1 -0
- package/dist/process/index.d.ts +38 -0
- package/dist/process/index.d.ts.map +1 -0
- package/dist/process/index.js +47 -0
- package/dist/process/index.js.map +1 -0
- package/dist/process/primitives.d.ts +393 -0
- package/dist/process/primitives.d.ts.map +1 -0
- package/dist/process/primitives.js +325 -0
- package/dist/process/primitives.js.map +1 -0
- package/dist/process/serialization.d.ts +58 -0
- package/dist/process/serialization.d.ts.map +1 -0
- package/dist/process/serialization.js +220 -0
- package/dist/process/serialization.js.map +1 -0
- package/dist/process/stream-utils.d.ts +123 -0
- package/dist/process/stream-utils.d.ts.map +1 -0
- package/dist/process/stream-utils.js +247 -0
- package/dist/process/stream-utils.js.map +1 -0
- package/dist/process/testing/clock.d.ts +115 -0
- package/dist/process/testing/clock.d.ts.map +1 -0
- package/dist/process/testing/clock.js +166 -0
- package/dist/process/testing/clock.js.map +1 -0
- package/dist/process/testing/index.d.ts +9 -0
- package/dist/process/testing/index.d.ts.map +1 -0
- package/dist/process/testing/index.js +9 -0
- package/dist/process/testing/index.js.map +1 -0
- package/dist/process/testing.d.ts +50 -0
- package/dist/process/testing.d.ts.map +1 -0
- package/dist/process/testing.js +59 -0
- package/dist/process/testing.js.map +1 -0
- package/dist/process/types.d.ts +540 -0
- package/dist/process/types.d.ts.map +1 -0
- package/dist/process/types.js +21 -0
- package/dist/process/types.js.map +1 -0
- package/dist/queue/index.d.ts +2 -0
- package/dist/queue/index.d.ts.map +1 -0
- package/dist/queue/index.js +2 -0
- package/dist/queue/index.js.map +1 -0
- package/dist/queue/queue.d.ts +34 -0
- package/dist/queue/queue.d.ts.map +1 -0
- package/dist/queue/queue.js +108 -0
- package/dist/queue/queue.js.map +1 -0
- package/dist/runtime/process/compiled.d.ts +56 -0
- package/dist/runtime/process/compiled.d.ts.map +1 -0
- package/dist/runtime/process/compiled.js +221 -0
- package/dist/runtime/process/compiled.js.map +1 -0
- package/dist/runtime/process/executor.d.ts +279 -0
- package/dist/runtime/process/executor.d.ts.map +1 -0
- package/dist/runtime/process/executor.js +1941 -0
- package/dist/runtime/process/executor.js.map +1 -0
- package/dist/runtime/process/factory.d.ts +72 -0
- package/dist/runtime/process/factory.d.ts.map +1 -0
- package/dist/runtime/process/factory.js +78 -0
- package/dist/runtime/process/factory.js.map +1 -0
- package/dist/runtime/process/freeze.d.ts +5 -0
- package/dist/runtime/process/freeze.d.ts.map +1 -0
- package/dist/runtime/process/freeze.js +94 -0
- package/dist/runtime/process/freeze.js.map +1 -0
- package/dist/runtime/process/scheduled-task-timer.d.ts +52 -0
- package/dist/runtime/process/scheduled-task-timer.d.ts.map +1 -0
- package/dist/runtime/process/scheduled-task-timer.js +104 -0
- package/dist/runtime/process/scheduled-task-timer.js.map +1 -0
- package/dist/runtime/process/signal-bus.d.ts +186 -0
- package/dist/runtime/process/signal-bus.d.ts.map +1 -0
- package/dist/runtime/process/signal-bus.js +256 -0
- package/dist/runtime/process/signal-bus.js.map +1 -0
- package/dist/runtime/process/state-serializer.d.ts +30 -0
- package/dist/runtime/process/state-serializer.d.ts.map +1 -0
- package/dist/runtime/process/state-serializer.js +244 -0
- package/dist/runtime/process/state-serializer.js.map +1 -0
- package/dist/runtime/process/storage.d.ts +96 -0
- package/dist/runtime/process/storage.d.ts.map +1 -0
- package/dist/runtime/process/storage.js +165 -0
- package/dist/runtime/process/storage.js.map +1 -0
- package/dist/runtime/process/timer-scheduler.d.ts +115 -0
- package/dist/runtime/process/timer-scheduler.d.ts.map +1 -0
- package/dist/runtime/process/timer-scheduler.js +192 -0
- package/dist/runtime/process/timer-scheduler.js.map +1 -0
- package/dist/runtime/process/trace.d.ts +17 -0
- package/dist/runtime/process/trace.d.ts.map +1 -0
- package/dist/runtime/process/trace.js +26 -0
- package/dist/runtime/process/trace.js.map +1 -0
- package/dist/runtime/protobuf/encoding/index.d.ts +26 -0
- package/dist/runtime/protobuf/encoding/index.d.ts.map +1 -0
- package/dist/runtime/protobuf/encoding/index.js +30 -0
- package/dist/runtime/protobuf/encoding/index.js.map +1 -0
- package/dist/runtime/protobuf/encoding/reader.d.ts +182 -0
- package/dist/runtime/protobuf/encoding/reader.d.ts.map +1 -0
- package/dist/runtime/protobuf/encoding/reader.js +353 -0
- package/dist/runtime/protobuf/encoding/reader.js.map +1 -0
- package/dist/runtime/protobuf/encoding/varint.d.ts +67 -0
- package/dist/runtime/protobuf/encoding/varint.d.ts.map +1 -0
- package/dist/runtime/protobuf/encoding/varint.js +117 -0
- package/dist/runtime/protobuf/encoding/varint.js.map +1 -0
- package/dist/runtime/protobuf/encoding/wire-types.d.ts +62 -0
- package/dist/runtime/protobuf/encoding/wire-types.d.ts.map +1 -0
- package/dist/runtime/protobuf/encoding/wire-types.js +103 -0
- package/dist/runtime/protobuf/encoding/wire-types.js.map +1 -0
- package/dist/runtime/protobuf/encoding/writer.d.ts +147 -0
- package/dist/runtime/protobuf/encoding/writer.d.ts.map +1 -0
- package/dist/runtime/protobuf/encoding/writer.js +214 -0
- package/dist/runtime/protobuf/encoding/writer.js.map +1 -0
- package/dist/runtime/protobuf/index.d.ts +3 -0
- package/dist/runtime/protobuf/index.d.ts.map +1 -0
- package/dist/runtime/protobuf/index.js +3 -0
- package/dist/runtime/protobuf/index.js.map +1 -0
- package/dist/runtime/protobuf/serialized.d.ts +48 -0
- package/dist/runtime/protobuf/serialized.d.ts.map +1 -0
- package/dist/runtime/protobuf/serialized.js +517 -0
- package/dist/runtime/protobuf/serialized.js.map +1 -0
- package/package.json +209 -0
|
@@ -0,0 +1,896 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Workspace CLI Controller
|
|
3
|
+
*
|
|
4
|
+
* Provides built-in commands for workspace operations:
|
|
5
|
+
* - build: Build using TypeScript and Turbo
|
|
6
|
+
* - run: Run a package, script, or file
|
|
7
|
+
* - test: Run tests
|
|
8
|
+
* - init: Set up project config, IDE, and AI tooling
|
|
9
|
+
* - install: Install a JustScale plugin with optional wizard
|
|
10
|
+
*/
|
|
11
|
+
import { execSync, spawn } from 'node:child_process';
|
|
12
|
+
import { appendFileSync, existsSync, mkdirSync, readFileSync, writeFileSync } from 'node:fs';
|
|
13
|
+
import { copyFile, glob, readFile } from 'node:fs/promises';
|
|
14
|
+
import { createRequire } from 'node:module';
|
|
15
|
+
import { cpus, homedir } from 'node:os';
|
|
16
|
+
import { basename, dirname, join, relative, resolve as resolvePath } from 'node:path';
|
|
17
|
+
import { fileURLToPath, pathToFileURL } from 'node:url';
|
|
18
|
+
import { z } from 'zod';
|
|
19
|
+
import { createController } from '../core/index.js';
|
|
20
|
+
import { Cli } from './builder/index.js';
|
|
21
|
+
import { detectSystem, generateJetBrainsConfig, generateVSCodeConfig, generateClaudeConfig, generateCursorConfig, generateGitHubActions, generateGitLabCI, } from './generators/index.js';
|
|
22
|
+
// ============================================================================
|
|
23
|
+
// Utilities
|
|
24
|
+
// ============================================================================
|
|
25
|
+
/**
|
|
26
|
+
* Find the workspace root by looking for pnpm-workspace.yaml.
|
|
27
|
+
*/
|
|
28
|
+
export function findWorkspaceRoot(startDir) {
|
|
29
|
+
let dir = startDir ?? process.cwd();
|
|
30
|
+
while (dir !== '/') {
|
|
31
|
+
if (existsSync(join(dir, 'pnpm-workspace.yaml'))) {
|
|
32
|
+
return dir;
|
|
33
|
+
}
|
|
34
|
+
const parent = dirname(dir);
|
|
35
|
+
if (parent === dir)
|
|
36
|
+
break;
|
|
37
|
+
dir = parent;
|
|
38
|
+
}
|
|
39
|
+
return process.cwd();
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* Execute a command and stream output.
|
|
43
|
+
*
|
|
44
|
+
* Prepends local `node_modules/.bin` to PATH so commands like `tsx`,
|
|
45
|
+
* `ptsc`, and `turbo` resolve even when the spawned process doesn't
|
|
46
|
+
* inherit the interactive shell's PATH munging. Without this, a plain
|
|
47
|
+
* `spawn('tsx', ...)` hits ENOENT because Node uses execvp with the
|
|
48
|
+
* child's PATH (which excludes the project's .bin).
|
|
49
|
+
*/
|
|
50
|
+
function exec(command, args, options = {}) {
|
|
51
|
+
return new Promise((resolve) => {
|
|
52
|
+
const baseEnv = options.env ?? process.env;
|
|
53
|
+
const cwd = options.cwd ?? process.cwd();
|
|
54
|
+
const binDirs = [
|
|
55
|
+
join(cwd, 'node_modules', '.bin'),
|
|
56
|
+
join(findWorkspaceRoot(cwd), 'node_modules', '.bin'),
|
|
57
|
+
];
|
|
58
|
+
const sep = process.platform === 'win32' ? ';' : ':';
|
|
59
|
+
const env = {
|
|
60
|
+
...baseEnv,
|
|
61
|
+
PATH: [...binDirs, baseEnv.PATH ?? ''].filter(Boolean).join(sep),
|
|
62
|
+
};
|
|
63
|
+
const proc = spawn(command, args, {
|
|
64
|
+
cwd: options.cwd,
|
|
65
|
+
stdio: 'inherit',
|
|
66
|
+
env,
|
|
67
|
+
});
|
|
68
|
+
proc.on('close', (code) => {
|
|
69
|
+
resolve(code ?? 0);
|
|
70
|
+
});
|
|
71
|
+
proc.on('error', () => {
|
|
72
|
+
resolve(1);
|
|
73
|
+
});
|
|
74
|
+
});
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Build a child process env with JUSTSCALE_ENV set (if requested).
|
|
78
|
+
* Other env vars are inherited from the parent.
|
|
79
|
+
*/
|
|
80
|
+
function envWithJustscaleEnv(envName) {
|
|
81
|
+
if (!envName)
|
|
82
|
+
return process.env;
|
|
83
|
+
return { ...process.env, JUSTSCALE_ENV: envName };
|
|
84
|
+
}
|
|
85
|
+
/** Marker line used to detect a previously-installed completion entry. */
|
|
86
|
+
const COMPLETION_MARKER = '# justscale:tab-completion';
|
|
87
|
+
function detectShell() {
|
|
88
|
+
const shell = process.env.SHELL ?? '';
|
|
89
|
+
if (/\/(bash)(\.exe)?$/.test(shell))
|
|
90
|
+
return 'bash';
|
|
91
|
+
if (/\/(zsh)(\.exe)?$/.test(shell))
|
|
92
|
+
return 'zsh';
|
|
93
|
+
if (/\/(fish)$/.test(shell))
|
|
94
|
+
return 'fish';
|
|
95
|
+
return undefined;
|
|
96
|
+
}
|
|
97
|
+
/**
|
|
98
|
+
* Where the snippet should live for the given shell. For bash/zsh that's
|
|
99
|
+
* the user's rc file (we'll create it if missing). For fish it's a file
|
|
100
|
+
* inside `~/.config/fish/completions/` which fish auto-discovers — so the
|
|
101
|
+
* install is "drop the full script" rather than "source from rc".
|
|
102
|
+
*/
|
|
103
|
+
function completionTargetFor(shell) {
|
|
104
|
+
const home = homedir();
|
|
105
|
+
if (shell === 'zsh')
|
|
106
|
+
return join(home, '.zshrc');
|
|
107
|
+
if (shell === 'fish')
|
|
108
|
+
return join(home, '.config', 'fish', 'completions', 'just.fish');
|
|
109
|
+
const bashrc = join(home, '.bashrc');
|
|
110
|
+
const bashProfile = join(home, '.bash_profile');
|
|
111
|
+
return existsSync(bashrc) || !existsSync(bashProfile) ? bashrc : bashProfile;
|
|
112
|
+
}
|
|
113
|
+
function isAlreadyInstalled(target) {
|
|
114
|
+
if (!existsSync(target))
|
|
115
|
+
return false;
|
|
116
|
+
try {
|
|
117
|
+
return readFileSync(target, 'utf8').includes(COMPLETION_MARKER);
|
|
118
|
+
}
|
|
119
|
+
catch {
|
|
120
|
+
return false;
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
/**
|
|
124
|
+
* Heuristic: is this invocation running in a developer's interactive
|
|
125
|
+
* workflow (as opposed to CI, prod, or a scripted test run)?
|
|
126
|
+
*
|
|
127
|
+
* - `CI=true` or `CI=1` — universal CI signal, skip.
|
|
128
|
+
* - `NODE_ENV` or `JUSTSCALE_ENV` explicitly set to anything other than
|
|
129
|
+
* `development`/`dev` — respect it; we're not dev-mode.
|
|
130
|
+
* - Otherwise: assume dev.
|
|
131
|
+
*
|
|
132
|
+
* Keeps prod servers, migration jobs, and CI pipelines from silently
|
|
133
|
+
* mutating the operator's shell rc.
|
|
134
|
+
*/
|
|
135
|
+
function isDevInvocation() {
|
|
136
|
+
if (process.env.CI && process.env.CI !== '0' && process.env.CI !== 'false')
|
|
137
|
+
return false;
|
|
138
|
+
const nodeEnv = (process.env.NODE_ENV ?? '').toLowerCase();
|
|
139
|
+
const justEnv = (process.env.JUSTSCALE_ENV ?? '').toLowerCase();
|
|
140
|
+
for (const v of [nodeEnv, justEnv]) {
|
|
141
|
+
if (!v)
|
|
142
|
+
continue;
|
|
143
|
+
if (v === 'development' || v === 'dev')
|
|
144
|
+
continue;
|
|
145
|
+
return false;
|
|
146
|
+
}
|
|
147
|
+
return true;
|
|
148
|
+
}
|
|
149
|
+
/**
|
|
150
|
+
* Idempotently install tab-completion for the current shell. Returns a
|
|
151
|
+
* short status string when a change was made (to show the user), or
|
|
152
|
+
* `null` when there was nothing to do (already installed, unsupported
|
|
153
|
+
* shell, non-dev environment, or completion intentionally opted out).
|
|
154
|
+
*
|
|
155
|
+
* `force: true` bypasses the dev-mode gate and the opt-out env var —
|
|
156
|
+
* used by the explicit `just completion install` command.
|
|
157
|
+
*/
|
|
158
|
+
export function installShellCompletion(opts = {}) {
|
|
159
|
+
if (!opts.force) {
|
|
160
|
+
// Opt-out hatch — CI, sandboxed environments, or users who've set
|
|
161
|
+
// up completion via a package manager shouldn't be surprised by
|
|
162
|
+
// writes to their shell rc on every `just ...` call.
|
|
163
|
+
if (process.env.JUSTSCALE_NO_COMPLETION_INSTALL === '1')
|
|
164
|
+
return null;
|
|
165
|
+
// Dev-only gate — never mutate rc files on prod/CI/test runs.
|
|
166
|
+
if (!isDevInvocation())
|
|
167
|
+
return null;
|
|
168
|
+
}
|
|
169
|
+
const shell = detectShell();
|
|
170
|
+
if (!shell)
|
|
171
|
+
return null;
|
|
172
|
+
const target = completionTargetFor(shell);
|
|
173
|
+
if (isAlreadyInstalled(target) && !opts.force)
|
|
174
|
+
return null;
|
|
175
|
+
if (shell === 'fish') {
|
|
176
|
+
// Fish auto-loads files under completions/; drop the whole script.
|
|
177
|
+
mkdirSync(dirname(target), { recursive: true });
|
|
178
|
+
const body = `${COMPLETION_MARKER}\n${renderCompletionScript('fish')}\n`;
|
|
179
|
+
writeFileSync(target, body, 'utf8');
|
|
180
|
+
return `[just] wrote tab-completion to ${displayPath(target)} — open a new shell to activate`;
|
|
181
|
+
}
|
|
182
|
+
// bash / zsh → append the full completion function inline. No
|
|
183
|
+
// `source <(just ...)` at shell-startup time — the snippet is
|
|
184
|
+
// self-contained so shells start cleanly even if the `just` binary
|
|
185
|
+
// isn't on PATH when they open.
|
|
186
|
+
const block = `\n${COMPLETION_MARKER}\n${renderCompletionScript(shell)}\n`;
|
|
187
|
+
appendFileSync(target, block, 'utf8');
|
|
188
|
+
return `[just] enabled tab-completion in ${displayPath(target)} — open a new shell to activate`;
|
|
189
|
+
}
|
|
190
|
+
function displayPath(p) {
|
|
191
|
+
const home = homedir();
|
|
192
|
+
return p.startsWith(home) ? `~${p.slice(home.length)}` : p;
|
|
193
|
+
}
|
|
194
|
+
/**
|
|
195
|
+
* Resolve `--import` args for child test workers spawned by `node:test`'s
|
|
196
|
+
* `run()`. We always try to pre-load the process compiler (so `.process.ts`
|
|
197
|
+
* and anything importing `@justscale/core/process` compiles correctly) and
|
|
198
|
+
* tsx (for plain `.ts` under Node's loader). Missing packages are skipped —
|
|
199
|
+
* Node 24+ type-stripping covers simple cases.
|
|
200
|
+
*/
|
|
201
|
+
function buildTestExecArgv(cwd) {
|
|
202
|
+
const execArgv = [];
|
|
203
|
+
const req = createRequire(`${cwd}/`);
|
|
204
|
+
for (const spec of ['@justscale/typescript/register', 'tsx']) {
|
|
205
|
+
try {
|
|
206
|
+
req.resolve(spec);
|
|
207
|
+
execArgv.push('--import', spec);
|
|
208
|
+
}
|
|
209
|
+
catch {
|
|
210
|
+
// package not installed in the user's project — skip
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
return execArgv;
|
|
214
|
+
}
|
|
215
|
+
/**
|
|
216
|
+
* Discover workspace packages that have a `test` script. Uses turbo's dep
|
|
217
|
+
* graph so `--changed` respects package-level change detection, matching
|
|
218
|
+
* `pnpm test:changed`. Filter is a substring on the package directory path.
|
|
219
|
+
*/
|
|
220
|
+
function getWorkspaceTestDirs(opts) {
|
|
221
|
+
const { root, filter, changed } = opts;
|
|
222
|
+
const filterArg = changed ? '--filter=...[origin/main]' : '';
|
|
223
|
+
try {
|
|
224
|
+
const output = execSync(`pnpm turbo run test ${filterArg} --dry-run=json`, {
|
|
225
|
+
encoding: 'utf-8',
|
|
226
|
+
cwd: root,
|
|
227
|
+
stdio: ['ignore', 'pipe', 'ignore'],
|
|
228
|
+
});
|
|
229
|
+
const data = JSON.parse(output);
|
|
230
|
+
return data.tasks
|
|
231
|
+
.filter((t) => t.task === 'test')
|
|
232
|
+
.map((t) => join(root, t.directory))
|
|
233
|
+
.filter((dir) => !filter || dir.includes(filter));
|
|
234
|
+
}
|
|
235
|
+
catch {
|
|
236
|
+
return [];
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
/**
|
|
240
|
+
* Extract file globs from a package's `test` script. Falls back to sane
|
|
241
|
+
* defaults when the script doesn't include explicit patterns. Mirrors the
|
|
242
|
+
* repo's `test/run.ts` heuristic so behavior stays consistent whether you
|
|
243
|
+
* invoke tests via `pnpm test` or `just test`.
|
|
244
|
+
*/
|
|
245
|
+
function extractTestGlobs(pkgDir) {
|
|
246
|
+
const pkgJsonPath = join(pkgDir, 'package.json');
|
|
247
|
+
if (!existsSync(pkgJsonPath))
|
|
248
|
+
return [];
|
|
249
|
+
let testScript;
|
|
250
|
+
try {
|
|
251
|
+
const pkg = JSON.parse(readFileSync(pkgJsonPath, 'utf-8'));
|
|
252
|
+
testScript = pkg.scripts?.test ?? '';
|
|
253
|
+
}
|
|
254
|
+
catch {
|
|
255
|
+
return [];
|
|
256
|
+
}
|
|
257
|
+
const matches = testScript.match(/['"]?[^\s'"]*\*[^\s'"]*\.test\.ts['"]?/g);
|
|
258
|
+
if (matches && matches.length > 0) {
|
|
259
|
+
return matches.map((m) => m.replace(/['"]/g, ''));
|
|
260
|
+
}
|
|
261
|
+
return ['test/**/*.test.ts', 'src/**/*.test.ts'];
|
|
262
|
+
}
|
|
263
|
+
async function expandGlobs(globs, cwd) {
|
|
264
|
+
const files = [];
|
|
265
|
+
for (const pattern of globs) {
|
|
266
|
+
for await (const file of glob(pattern, { cwd })) {
|
|
267
|
+
files.push(join(cwd, file));
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
return files;
|
|
271
|
+
}
|
|
272
|
+
async function resolveTestFiles(opts) {
|
|
273
|
+
const { cwd, root, isAtRoot, pattern, filter, changed } = opts;
|
|
274
|
+
if (pattern && pattern.length > 0) {
|
|
275
|
+
return (await expandGlobs(pattern, cwd)).sort();
|
|
276
|
+
}
|
|
277
|
+
if (!isAtRoot) {
|
|
278
|
+
return (await expandGlobs(['test/**/*.test.ts', 'src/**/*.test.ts'], cwd)).sort();
|
|
279
|
+
}
|
|
280
|
+
const dirs = getWorkspaceTestDirs({ root, filter, changed });
|
|
281
|
+
const all = [];
|
|
282
|
+
for (const dir of dirs) {
|
|
283
|
+
const globs = extractTestGlobs(dir);
|
|
284
|
+
all.push(...(await expandGlobs(globs, dir)));
|
|
285
|
+
}
|
|
286
|
+
return all.sort();
|
|
287
|
+
}
|
|
288
|
+
async function buildApp(opts) {
|
|
289
|
+
const { cwd, envName, verbose, log, error } = opts;
|
|
290
|
+
const { discover } = await import('./discovery.js');
|
|
291
|
+
const result = await discover();
|
|
292
|
+
if (!result) {
|
|
293
|
+
error('App-mode build requires a justscale.config.ts in the current directory.');
|
|
294
|
+
return 1;
|
|
295
|
+
}
|
|
296
|
+
if (!result.config.app) {
|
|
297
|
+
error('justscale.config.ts has no `app` entry. Define one via defineProject({ app: ... }).');
|
|
298
|
+
return 1;
|
|
299
|
+
}
|
|
300
|
+
const { loadEnvironment } = await import('../features/environment/load.js');
|
|
301
|
+
let env;
|
|
302
|
+
try {
|
|
303
|
+
env = await loadEnvironment({
|
|
304
|
+
name: envName,
|
|
305
|
+
from: { url: result.configFileUrl },
|
|
306
|
+
});
|
|
307
|
+
}
|
|
308
|
+
catch (err) {
|
|
309
|
+
error(`Failed to load environment '${envName}': ${err.message}`);
|
|
310
|
+
return 1;
|
|
311
|
+
}
|
|
312
|
+
const { resolveAppEntry } = await import('./define-project.js');
|
|
313
|
+
const entry = resolveAppEntry(result.configFileUrl, result.config.app, env.type);
|
|
314
|
+
if (!entry) {
|
|
315
|
+
error(`Could not resolve app entry for env '${envName}' (type='${env.type}'). ` +
|
|
316
|
+
'Ensure config.app is a `() => import(\'./path.js\')` form and the file exists.');
|
|
317
|
+
return 1;
|
|
318
|
+
}
|
|
319
|
+
// esbuild is an optional peer dep — apps that never run app-mode build
|
|
320
|
+
// shouldn't carry the bundler. Dynamic-import with a helpful error.
|
|
321
|
+
let esbuild;
|
|
322
|
+
try {
|
|
323
|
+
esbuild = await import('esbuild');
|
|
324
|
+
}
|
|
325
|
+
catch (err) {
|
|
326
|
+
error('App-mode build requires esbuild. Install it as a dev dep: pnpm add -D esbuild\n' +
|
|
327
|
+
`Underlying error: ${err.message}`);
|
|
328
|
+
return 1;
|
|
329
|
+
}
|
|
330
|
+
const { justscaleProcessPlugin } = await import('./build/process-plugin.js');
|
|
331
|
+
const { justscaleMigrationsPlugin } = await import('./build/migrations-plugin.js');
|
|
332
|
+
const configDir = dirname(fileURLToPath(result.configFileUrl));
|
|
333
|
+
const outDir = result.config.build?.outDir
|
|
334
|
+
? resolvePath(configDir, result.config.build.outDir)
|
|
335
|
+
: join(configDir, 'dist');
|
|
336
|
+
mkdirSync(outDir, { recursive: true });
|
|
337
|
+
const entryBase = basename(entry).replace(/\.(m|c)?(ts|js)$/, '');
|
|
338
|
+
const outFile = join(outDir, `${entryBase}-${envName}.js`);
|
|
339
|
+
const metaFile = join(outDir, `${entryBase}-${envName}.meta.json`);
|
|
340
|
+
// Locate the env file now (not during bundling) so we can fail fast with
|
|
341
|
+
// a clear message when it's missing, and so we can inline its absolute
|
|
342
|
+
// path into the virtual entry's import statement.
|
|
343
|
+
const envFileCandidates = [
|
|
344
|
+
join(configDir, 'env', `${envName}.ts`),
|
|
345
|
+
join(configDir, 'env', `${envName}.js`),
|
|
346
|
+
join(configDir, 'env', `${envName}.mjs`),
|
|
347
|
+
];
|
|
348
|
+
const envFile = envFileCandidates.find((p) => existsSync(p));
|
|
349
|
+
if (!envFile) {
|
|
350
|
+
error(`Could not find env file for '${envName}'. Looked in:\n ` +
|
|
351
|
+
envFileCandidates.map((p) => relative(cwd, p)).join('\n '));
|
|
352
|
+
return 1;
|
|
353
|
+
}
|
|
354
|
+
// Env registration has to happen BEFORE the user's app module evaluates,
|
|
355
|
+
// because `defineApp` autoruns `loadEnvironment({ from: meta })` during
|
|
356
|
+
// module eval (via an async IIFE) when invoked from the entrypoint.
|
|
357
|
+
// ESM evaluates a module's dependencies in declaration order before the
|
|
358
|
+
// module body runs, so the first import in the virtual entry is a
|
|
359
|
+
// synthetic side-effect module that performs the registration. It
|
|
360
|
+
// evaluates first, env is in the registry, then `src/app.ts` evaluates
|
|
361
|
+
// and its autorun path finds the static env.
|
|
362
|
+
const REGISTER_SPECIFIER = 'justscale:static-env-register';
|
|
363
|
+
const virtualEntrySource = `import ${JSON.stringify(REGISTER_SPECIFIER)};\n` +
|
|
364
|
+
`import __appDefault from ${JSON.stringify(entry)};\n` +
|
|
365
|
+
'export default __appDefault;\n';
|
|
366
|
+
const envRegisterPlugin = {
|
|
367
|
+
name: 'justscale-static-env-register',
|
|
368
|
+
setup(build) {
|
|
369
|
+
build.onResolve({ filter: new RegExp(`^${REGISTER_SPECIFIER}$`) }, () => ({
|
|
370
|
+
path: REGISTER_SPECIFIER,
|
|
371
|
+
namespace: 'justscale-static-env',
|
|
372
|
+
}));
|
|
373
|
+
build.onLoad({ filter: /.*/, namespace: 'justscale-static-env' }, () => ({
|
|
374
|
+
resolveDir: configDir,
|
|
375
|
+
loader: 'ts',
|
|
376
|
+
contents: `import __envModule from ${JSON.stringify(envFile)};\n` +
|
|
377
|
+
'import { __registerStaticEnvironment } from \'@justscale/core\';\n' +
|
|
378
|
+
`__registerStaticEnvironment(${JSON.stringify(envName)}, __envModule);\n`,
|
|
379
|
+
}));
|
|
380
|
+
},
|
|
381
|
+
};
|
|
382
|
+
log(`Bundling ${relative(cwd, entry)} → ${relative(cwd, outFile)} (env=${envName}, type=${env.type})`);
|
|
383
|
+
const started = Date.now();
|
|
384
|
+
try {
|
|
385
|
+
await esbuild.build({
|
|
386
|
+
stdin: {
|
|
387
|
+
contents: virtualEntrySource,
|
|
388
|
+
resolveDir: configDir,
|
|
389
|
+
sourcefile: `${entryBase}-${envName}.entry.ts`,
|
|
390
|
+
loader: 'ts',
|
|
391
|
+
},
|
|
392
|
+
outfile: outFile,
|
|
393
|
+
bundle: true,
|
|
394
|
+
platform: 'node',
|
|
395
|
+
format: 'esm',
|
|
396
|
+
target: result.config.build?.target ?? 'node24',
|
|
397
|
+
// Bundle everything into a single file so the deploy artifact needs
|
|
398
|
+
// nothing from node_modules at runtime except the packages explicitly
|
|
399
|
+
// kept external (native modules, things listed in config.build.external).
|
|
400
|
+
// `platform: 'node'` auto-externalizes `node:*` builtins.
|
|
401
|
+
external: result.config.build?.external ?? [],
|
|
402
|
+
sourcemap: true,
|
|
403
|
+
treeShaking: true,
|
|
404
|
+
// Collapse whitespace only — keep names readable so stack traces
|
|
405
|
+
// map cleanly without a sourcemap. Real identifier minification is
|
|
406
|
+
// opt-in later (users that want it can set it via config).
|
|
407
|
+
minifyWhitespace: true,
|
|
408
|
+
logLevel: verbose ? 'info' : 'warning',
|
|
409
|
+
define: {
|
|
410
|
+
'process.env.JUSTSCALE_ENV': JSON.stringify(envName),
|
|
411
|
+
'process.env.NODE_ENV': env.type === 'production' ? '"production"' : JSON.stringify(env.type),
|
|
412
|
+
},
|
|
413
|
+
plugins: [
|
|
414
|
+
envRegisterPlugin,
|
|
415
|
+
justscaleProcessPlugin({ rootDir: configDir, sourceMap: true, verbose }),
|
|
416
|
+
justscaleMigrationsPlugin({ rootDir: configDir }),
|
|
417
|
+
],
|
|
418
|
+
banner: {
|
|
419
|
+
// Re-enable dynamic require() for ESM output so bundled CJS deps
|
|
420
|
+
// (which occasionally call `require` internally via shims) and any
|
|
421
|
+
// externalized CJS packages still resolve after the bundle runs.
|
|
422
|
+
js: "import { createRequire as __jsCreateRequire } from 'node:module';"
|
|
423
|
+
+ 'const require = __jsCreateRequire(import.meta.url);',
|
|
424
|
+
},
|
|
425
|
+
});
|
|
426
|
+
}
|
|
427
|
+
catch (err) {
|
|
428
|
+
error(`esbuild failed: ${err.message}`);
|
|
429
|
+
return 1;
|
|
430
|
+
}
|
|
431
|
+
// Copy include patterns (e.g. migrations) into the output directory so
|
|
432
|
+
// the deploy artifact is self-contained. Relative paths are preserved:
|
|
433
|
+
// `migrations/001.sql` → `dist/migrations/001.sql`. `withFileTypes: true`
|
|
434
|
+
// lets us skip directory entries — `copyFile` only handles files, and
|
|
435
|
+
// globs like `migrations/**` also match the containing directory.
|
|
436
|
+
const includePatterns = result.config.build?.include ?? [];
|
|
437
|
+
const copiedFiles = [];
|
|
438
|
+
for (const pattern of includePatterns) {
|
|
439
|
+
for await (const entry of glob(pattern, { cwd: configDir, withFileTypes: true })) {
|
|
440
|
+
if (!entry.isFile())
|
|
441
|
+
continue;
|
|
442
|
+
const rel = relative(configDir, join(entry.parentPath, entry.name));
|
|
443
|
+
const src = join(configDir, rel);
|
|
444
|
+
const dst = join(outDir, rel);
|
|
445
|
+
mkdirSync(dirname(dst), { recursive: true });
|
|
446
|
+
await copyFile(src, dst);
|
|
447
|
+
copiedFiles.push(rel);
|
|
448
|
+
}
|
|
449
|
+
}
|
|
450
|
+
const meta = {
|
|
451
|
+
env: envName,
|
|
452
|
+
envType: env.type,
|
|
453
|
+
entry: relative(configDir, entry),
|
|
454
|
+
bundle: relative(configDir, outFile),
|
|
455
|
+
builtAt: new Date().toISOString(),
|
|
456
|
+
durationMs: Date.now() - started,
|
|
457
|
+
include: copiedFiles,
|
|
458
|
+
};
|
|
459
|
+
writeFileSync(metaFile, JSON.stringify(meta, null, 2) + '\n');
|
|
460
|
+
log(` ✓ bundle: ${relative(cwd, outFile)}`);
|
|
461
|
+
log(` ✓ meta: ${relative(cwd, metaFile)}`);
|
|
462
|
+
if (copiedFiles.length > 0) {
|
|
463
|
+
log(` ✓ include: ${copiedFiles.length} file${copiedFiles.length === 1 ? '' : 's'}`);
|
|
464
|
+
}
|
|
465
|
+
log(` Built in ${meta.durationMs}ms`);
|
|
466
|
+
return 0;
|
|
467
|
+
}
|
|
468
|
+
// ============================================================================
|
|
469
|
+
// Input Schemas
|
|
470
|
+
// ============================================================================
|
|
471
|
+
const BuildInput = z.object({
|
|
472
|
+
filter: z.string().optional().describe('Build specific package(s)'),
|
|
473
|
+
watch: z.boolean().default(false).describe('Watch mode for incremental builds'),
|
|
474
|
+
verbose: z.boolean().default(false).describe('Verbose output'),
|
|
475
|
+
env: z.string().optional().describe('Environment name (sets JUSTSCALE_ENV)'),
|
|
476
|
+
});
|
|
477
|
+
const RunInput = z.object({
|
|
478
|
+
// Explicit position: 0 via CLI metadata keeps this positional even when
|
|
479
|
+
// .optional() would otherwise flip it to a flag. Convention-only parsing
|
|
480
|
+
// treats any optional/defaulted field as a flag; explicit metadata wins.
|
|
481
|
+
target: z.string().optional().meta({
|
|
482
|
+
cli: {
|
|
483
|
+
position: 0,
|
|
484
|
+
description: 'File path, package name, or script name. Omit to run the current package\'s app entry (src/app.ts).',
|
|
485
|
+
},
|
|
486
|
+
}),
|
|
487
|
+
verbose: z.boolean().default(false).describe('Verbose output'),
|
|
488
|
+
env: z.string().optional().describe('Environment name (sets JUSTSCALE_ENV)'),
|
|
489
|
+
});
|
|
490
|
+
const TestInput = z.object({
|
|
491
|
+
filter: z.string().optional().describe('Run tests only for packages matching this name (workspace mode)'),
|
|
492
|
+
pattern: z.array(z.string()).optional().describe('Test file glob(s). Repeat for multiple. Default: test/**/*.test.ts, src/**/*.test.ts'),
|
|
493
|
+
grep: z.string().optional().describe('Run only tests whose name matches this regex'),
|
|
494
|
+
watch: z.boolean().default(false).describe('Watch files and re-run on change'),
|
|
495
|
+
bail: z.boolean().default(false).describe('Stop at the first failure'),
|
|
496
|
+
only: z.boolean().default(false).describe('Run only tests marked with .only'),
|
|
497
|
+
timeout: z.number().default(10_000).describe('Per-test timeout in ms'),
|
|
498
|
+
concurrency: z.number().optional().describe('Max concurrent test files (default: cpus-1)'),
|
|
499
|
+
reporter: z.enum(['spec', 'tap', 'dot']).default('spec').describe('Output reporter'),
|
|
500
|
+
changed: z.boolean().default(false).describe('Only run tests in packages changed vs origin/main (workspace mode)'),
|
|
501
|
+
verbose: z.boolean().default(false).describe('Verbose output'),
|
|
502
|
+
skipTypecheck: z.boolean().default(false).describe('Skip typecheck before running tests'),
|
|
503
|
+
env: z.string().optional().describe('Environment name (sets JUSTSCALE_ENV, default: test)'),
|
|
504
|
+
});
|
|
505
|
+
// ============================================================================
|
|
506
|
+
// Controller
|
|
507
|
+
// ============================================================================
|
|
508
|
+
export const WorkspaceController = createController({
|
|
509
|
+
// No command prefix - these are root-level commands
|
|
510
|
+
inject: {},
|
|
511
|
+
routes: () => ({
|
|
512
|
+
build: Cli('build')
|
|
513
|
+
.input(BuildInput)
|
|
514
|
+
.handle(async (ctx) => {
|
|
515
|
+
const { filter, watch, verbose } = ctx.args;
|
|
516
|
+
// `--env` is consumed as a global flag by `main.ts`; it lands
|
|
517
|
+
// in `process.env.JUSTSCALE_ENV`. Fall through to ctx.args.env
|
|
518
|
+
// for the rare call-site that set it directly.
|
|
519
|
+
const env = ctx.args.env ?? process.env.JUSTSCALE_ENV ?? undefined;
|
|
520
|
+
const cwd = process.cwd();
|
|
521
|
+
const workspaceRoot = findWorkspaceRoot();
|
|
522
|
+
const isWorkspace = existsSync(join(workspaceRoot, 'pnpm-workspace.yaml')) ||
|
|
523
|
+
existsSync(join(workspaceRoot, 'turbo.json'));
|
|
524
|
+
const childEnv = envWithJustscaleEnv(env);
|
|
525
|
+
// App mode: `--env <name>` + a justscale.config.ts in cwd means
|
|
526
|
+
// "build a deployable artifact for this env", not "compile TS for
|
|
527
|
+
// publishing". Bundler path, output lands at dist/<entry>-<env>.js.
|
|
528
|
+
// Watch and workspace filter don't apply here — this is a one-shot
|
|
529
|
+
// artifact build.
|
|
530
|
+
const hasProjectConfig = existsSync(join(cwd, 'justscale.config.ts')) ||
|
|
531
|
+
existsSync(join(cwd, 'justscale.config.js'));
|
|
532
|
+
if (env && hasProjectConfig && !watch) {
|
|
533
|
+
const code = await buildApp({
|
|
534
|
+
cwd,
|
|
535
|
+
envName: env,
|
|
536
|
+
verbose,
|
|
537
|
+
log: (m) => ctx.io.log(m),
|
|
538
|
+
error: (m) => ctx.io.error(m),
|
|
539
|
+
});
|
|
540
|
+
process.exit(code);
|
|
541
|
+
}
|
|
542
|
+
if (env)
|
|
543
|
+
ctx.io.log(`Using environment: ${env}`);
|
|
544
|
+
if (watch) {
|
|
545
|
+
ctx.io.log('Starting watch mode...');
|
|
546
|
+
const args = ['--build', '--watch'];
|
|
547
|
+
if (verbose)
|
|
548
|
+
args.push('--verbose');
|
|
549
|
+
const code = await exec('ptsc', args, { cwd, verbose, env: childEnv });
|
|
550
|
+
process.exit(code);
|
|
551
|
+
}
|
|
552
|
+
if (isWorkspace) {
|
|
553
|
+
// Monorepo — use turbo for orchestrated builds
|
|
554
|
+
const args = ['run', 'build'];
|
|
555
|
+
if (filter)
|
|
556
|
+
args.push('--filter', filter);
|
|
557
|
+
if (verbose)
|
|
558
|
+
args.push('--verbose');
|
|
559
|
+
ctx.io.log(`Building${filter ? ` ${filter}` : ' all packages'}...`);
|
|
560
|
+
const code = await exec('turbo', args, { cwd: workspaceRoot, verbose, env: childEnv });
|
|
561
|
+
process.exit(code);
|
|
562
|
+
}
|
|
563
|
+
// Single project — use ptsc directly from cwd
|
|
564
|
+
ctx.io.log('Building...');
|
|
565
|
+
const tsconfigBuild = join(cwd, 'tsconfig.build.json');
|
|
566
|
+
const args = existsSync(tsconfigBuild)
|
|
567
|
+
? ['-b', 'tsconfig.build.json']
|
|
568
|
+
: ['--outDir', 'dist'];
|
|
569
|
+
if (verbose)
|
|
570
|
+
args.push('--verbose');
|
|
571
|
+
const code = await exec('ptsc', args, { cwd, verbose, env: childEnv });
|
|
572
|
+
process.exit(code);
|
|
573
|
+
}),
|
|
574
|
+
run: Cli('run')
|
|
575
|
+
.input(RunInput)
|
|
576
|
+
.handle(async (ctx) => {
|
|
577
|
+
const { target, verbose, env } = ctx.args;
|
|
578
|
+
const root = findWorkspaceRoot();
|
|
579
|
+
const childEnv = envWithJustscaleEnv(env);
|
|
580
|
+
if (env && verbose)
|
|
581
|
+
ctx.io.log(`Using environment: ${env}`);
|
|
582
|
+
// No target → run the user's app entry (defineApp default export
|
|
583
|
+
// at src/app.ts). Same shape as `just dev` minus the watcher.
|
|
584
|
+
if (!target) {
|
|
585
|
+
const cwd = process.cwd();
|
|
586
|
+
const candidates = ['src/app.ts', 'src/main.ts', 'src/server.ts', 'src/serve.ts'];
|
|
587
|
+
const entry = candidates.map((c) => join(cwd, c)).find((p) => existsSync(p));
|
|
588
|
+
if (!entry) {
|
|
589
|
+
ctx.io.error('Error: No app entry found and no target specified.');
|
|
590
|
+
ctx.io.log('Usage: just run <target> | run from a package with src/app.ts');
|
|
591
|
+
process.exit(1);
|
|
592
|
+
}
|
|
593
|
+
if (verbose)
|
|
594
|
+
ctx.io.log(`Running ${entry}...`);
|
|
595
|
+
const code = await exec('tsx', [entry], { cwd, verbose, env: childEnv });
|
|
596
|
+
process.exit(code);
|
|
597
|
+
}
|
|
598
|
+
// Check if it's a file path
|
|
599
|
+
if (target.endsWith('.ts') || target.endsWith('.js')) {
|
|
600
|
+
const filePath = target.startsWith('/') ? target : join(root, target);
|
|
601
|
+
if (!existsSync(filePath)) {
|
|
602
|
+
ctx.io.error(`Error: File not found: ${filePath}`);
|
|
603
|
+
process.exit(1);
|
|
604
|
+
}
|
|
605
|
+
if (verbose)
|
|
606
|
+
ctx.io.log(`Running ${filePath}...`);
|
|
607
|
+
const code = await exec('tsx', [filePath], { cwd: root, verbose, env: childEnv });
|
|
608
|
+
process.exit(code);
|
|
609
|
+
}
|
|
610
|
+
// Check if it's a root package.json script
|
|
611
|
+
const pkgPath = join(root, 'package.json');
|
|
612
|
+
if (existsSync(pkgPath)) {
|
|
613
|
+
const pkg = JSON.parse(await readFile(pkgPath, 'utf-8'));
|
|
614
|
+
if (pkg.scripts?.[target]) {
|
|
615
|
+
if (verbose)
|
|
616
|
+
ctx.io.log(`Running script: ${target}`);
|
|
617
|
+
const code = await exec('pnpm', ['run', target], { cwd: root, verbose, env: childEnv });
|
|
618
|
+
process.exit(code);
|
|
619
|
+
}
|
|
620
|
+
}
|
|
621
|
+
// Try running as package
|
|
622
|
+
if (verbose)
|
|
623
|
+
ctx.io.log(`Running package: ${target}`);
|
|
624
|
+
const code = await exec('pnpm', ['--filter', target, 'start'], { cwd: root, verbose, env: childEnv });
|
|
625
|
+
process.exit(code);
|
|
626
|
+
}),
|
|
627
|
+
test: Cli('test')
|
|
628
|
+
.input(TestInput)
|
|
629
|
+
.handle(async (ctx) => {
|
|
630
|
+
const { filter, pattern, grep, watch, bail, only, timeout, concurrency, reporter, changed, verbose, skipTypecheck, } = ctx.args;
|
|
631
|
+
// `--env` is a global flag on the `just` binary; it lands in
|
|
632
|
+
// process.env.JUSTSCALE_ENV. Fall through to ctx.args.env for
|
|
633
|
+
// the rare direct call site that set it programmatically.
|
|
634
|
+
const env = ctx.args.env ?? process.env.JUSTSCALE_ENV;
|
|
635
|
+
const cwd = process.cwd();
|
|
636
|
+
const root = findWorkspaceRoot(cwd);
|
|
637
|
+
const isAtRoot = cwd === root && existsSync(join(root, 'pnpm-workspace.yaml'));
|
|
638
|
+
// Default to the 'test' env so configs/adapters with environment-
|
|
639
|
+
// gated behavior (pglite, in-memory channels, …) pick the test
|
|
640
|
+
// variant without the user having to type `--env test` every run.
|
|
641
|
+
process.env.JUSTSCALE_ENV = env ?? 'test';
|
|
642
|
+
if (env && verbose)
|
|
643
|
+
ctx.io.log(`Using environment: ${env}`);
|
|
644
|
+
// Typecheck: scope to cwd in single-package mode so running tests
|
|
645
|
+
// inside e.g. examples/simple-app doesn't drag in the whole
|
|
646
|
+
// monorepo's typecheck cost.
|
|
647
|
+
if (!skipTypecheck) {
|
|
648
|
+
ctx.io.log('Running typecheck...');
|
|
649
|
+
const typecheckCwd = isAtRoot ? root : cwd;
|
|
650
|
+
const code = await exec('pnpm', ['typecheck'], { cwd: typecheckCwd, verbose });
|
|
651
|
+
if (code !== 0) {
|
|
652
|
+
ctx.io.error('Typecheck failed');
|
|
653
|
+
process.exit(code);
|
|
654
|
+
}
|
|
655
|
+
}
|
|
656
|
+
const files = await resolveTestFiles({ cwd, root, isAtRoot, pattern, filter, changed });
|
|
657
|
+
if (files.length === 0) {
|
|
658
|
+
ctx.io.log('No test files found.');
|
|
659
|
+
if (filter)
|
|
660
|
+
ctx.io.log(` (no packages matched --filter=${filter})`);
|
|
661
|
+
else if (changed)
|
|
662
|
+
ctx.io.log(' (no changes detected vs origin/main)');
|
|
663
|
+
process.exit(0);
|
|
664
|
+
}
|
|
665
|
+
if (verbose) {
|
|
666
|
+
for (const f of files)
|
|
667
|
+
ctx.io.log(` ${relative(cwd, f)}`);
|
|
668
|
+
}
|
|
669
|
+
ctx.io.log(`Running ${files.length} test file${files.length === 1 ? '' : 's'}` +
|
|
670
|
+
`${filter ? ` (filter: ${filter})` : ''}${changed ? ' (changed)' : ''}...`);
|
|
671
|
+
const { run } = await import('node:test');
|
|
672
|
+
const { spec, tap, dot } = await import('node:test/reporters');
|
|
673
|
+
const reporterFactory = { spec, tap, dot }[reporter];
|
|
674
|
+
const controller = new AbortController();
|
|
675
|
+
const runOptions = {
|
|
676
|
+
files,
|
|
677
|
+
timeout,
|
|
678
|
+
concurrency: concurrency ?? Math.max(1, cpus().length - 1),
|
|
679
|
+
forceExit: !watch,
|
|
680
|
+
watch,
|
|
681
|
+
only,
|
|
682
|
+
execArgv: buildTestExecArgv(cwd),
|
|
683
|
+
signal: controller.signal,
|
|
684
|
+
};
|
|
685
|
+
if (grep)
|
|
686
|
+
runOptions.testNamePatterns = [grep];
|
|
687
|
+
const stream = run(runOptions);
|
|
688
|
+
let failed = 0;
|
|
689
|
+
stream.on('test:fail', (ev) => {
|
|
690
|
+
// Node reports test suites with failing children as 'test:fail'
|
|
691
|
+
// too; those carry a `subtest` flag. Count only leaf failures so
|
|
692
|
+
// bail semantics match what the user sees in the spec output.
|
|
693
|
+
const details = ev.details;
|
|
694
|
+
if (details?.type === 'suite')
|
|
695
|
+
return;
|
|
696
|
+
failed++;
|
|
697
|
+
if (bail)
|
|
698
|
+
controller.abort();
|
|
699
|
+
});
|
|
700
|
+
const output = stream.compose(reporterFactory);
|
|
701
|
+
output.pipe(process.stdout);
|
|
702
|
+
await new Promise((resolve, reject) => {
|
|
703
|
+
output.once('end', resolve);
|
|
704
|
+
output.once('error', reject);
|
|
705
|
+
});
|
|
706
|
+
if (watch)
|
|
707
|
+
return; // watch never finishes naturally
|
|
708
|
+
process.exit(failed > 0 ? 1 : 0);
|
|
709
|
+
}),
|
|
710
|
+
init: Cli('init')
|
|
711
|
+
.handle(async (ctx) => {
|
|
712
|
+
const root = process.cwd();
|
|
713
|
+
const system = detectSystem(root);
|
|
714
|
+
ctx.io.log('JustScale — Project Setup\n');
|
|
715
|
+
ctx.io.log(` OS: ${system.os} (${system.arch})`);
|
|
716
|
+
ctx.io.log(` Node: ${system.nodeVersion}`);
|
|
717
|
+
ctx.io.log(` Package manager: ${system.packageManager}`);
|
|
718
|
+
ctx.io.log(` IDEs: ${system.ides.length ? system.ides.join(', ') : 'none detected'}`);
|
|
719
|
+
ctx.io.log(` AI tools: ${system.aiTools.length ? system.aiTools.join(', ') : 'none detected'}`);
|
|
720
|
+
ctx.io.log(` Git hosting: ${system.gitHosting ?? 'not detected'}`);
|
|
721
|
+
ctx.io.log('');
|
|
722
|
+
const generated = [];
|
|
723
|
+
// IDE config
|
|
724
|
+
if (system.ides.includes('jetbrains')) {
|
|
725
|
+
generated.push(...generateJetBrainsConfig(root));
|
|
726
|
+
}
|
|
727
|
+
if (system.ides.includes('vscode') || system.ides.includes('cursor')) {
|
|
728
|
+
generated.push(...generateVSCodeConfig(root));
|
|
729
|
+
}
|
|
730
|
+
// AI config
|
|
731
|
+
if (system.aiTools.includes('claude')) {
|
|
732
|
+
generated.push(...generateClaudeConfig(root));
|
|
733
|
+
}
|
|
734
|
+
if (system.aiTools.includes('cursor')) {
|
|
735
|
+
generated.push(...generateCursorConfig(root));
|
|
736
|
+
}
|
|
737
|
+
// CI/CD
|
|
738
|
+
if (system.gitHosting === 'github') {
|
|
739
|
+
generated.push(...generateGitHubActions(root));
|
|
740
|
+
}
|
|
741
|
+
else if (system.gitHosting === 'gitlab') {
|
|
742
|
+
generated.push(...generateGitLabCI(root));
|
|
743
|
+
}
|
|
744
|
+
if (generated.length > 0) {
|
|
745
|
+
ctx.io.log('Generated:');
|
|
746
|
+
for (const file of generated) {
|
|
747
|
+
ctx.io.log(` ✓ ${file}`);
|
|
748
|
+
}
|
|
749
|
+
}
|
|
750
|
+
else {
|
|
751
|
+
ctx.io.log('Everything is already configured.');
|
|
752
|
+
}
|
|
753
|
+
}),
|
|
754
|
+
install: Cli('install')
|
|
755
|
+
.input(z.object({
|
|
756
|
+
package: z.string().describe('Package name to install'),
|
|
757
|
+
}))
|
|
758
|
+
.handle(async (ctx) => {
|
|
759
|
+
const root = findWorkspaceRoot();
|
|
760
|
+
const pkgName = ctx.args.package;
|
|
761
|
+
ctx.io.log(`Installing ${pkgName}...`);
|
|
762
|
+
// Install via detected package manager
|
|
763
|
+
const pm = detectSystem(root).packageManager;
|
|
764
|
+
const pmCmd = pm === 'pnpm' ? 'pnpm' : pm === 'yarn' ? 'yarn' : 'npm';
|
|
765
|
+
const pmArgs = pm === 'npm' ? ['install', pkgName] : ['add', pkgName];
|
|
766
|
+
const installCode = await exec(pmCmd, pmArgs, { cwd: root });
|
|
767
|
+
if (installCode !== 0) {
|
|
768
|
+
ctx.io.error(`Failed to install ${pkgName}`);
|
|
769
|
+
process.exit(installCode);
|
|
770
|
+
}
|
|
771
|
+
ctx.io.log(' ✓ Package installed');
|
|
772
|
+
// Check for justscale wizard
|
|
773
|
+
const depPkgPath = join(root, 'node_modules', pkgName, 'package.json');
|
|
774
|
+
if (!existsSync(depPkgPath))
|
|
775
|
+
return;
|
|
776
|
+
let depPkg;
|
|
777
|
+
try {
|
|
778
|
+
depPkg = JSON.parse(readFileSync(depPkgPath, 'utf-8'));
|
|
779
|
+
}
|
|
780
|
+
catch {
|
|
781
|
+
return;
|
|
782
|
+
}
|
|
783
|
+
const justscaleField = depPkg.justscale;
|
|
784
|
+
if (!justscaleField?.wizard)
|
|
785
|
+
return;
|
|
786
|
+
// Resolve wizard module
|
|
787
|
+
const depDir = join(depPkgPath, '..');
|
|
788
|
+
const wizardConfig = justscaleField.wizard;
|
|
789
|
+
let wizardPath = null;
|
|
790
|
+
// Prefer import (built JS) over source (TS) — same as discovery.ts
|
|
791
|
+
if (wizardConfig.import) {
|
|
792
|
+
const candidate = join(depDir, wizardConfig.import);
|
|
793
|
+
if (existsSync(candidate))
|
|
794
|
+
wizardPath = candidate;
|
|
795
|
+
}
|
|
796
|
+
if (!wizardPath && wizardConfig.source) {
|
|
797
|
+
const candidate = join(depDir, wizardConfig.source);
|
|
798
|
+
if (existsSync(candidate))
|
|
799
|
+
wizardPath = candidate;
|
|
800
|
+
}
|
|
801
|
+
if (!wizardPath)
|
|
802
|
+
return;
|
|
803
|
+
ctx.io.log(' Running setup wizard...\n');
|
|
804
|
+
try {
|
|
805
|
+
const wizardModule = await import(pathToFileURL(wizardPath).href);
|
|
806
|
+
const wizardFn = wizardModule.default ?? wizardModule.wizard;
|
|
807
|
+
if (typeof wizardFn !== 'function')
|
|
808
|
+
return;
|
|
809
|
+
const projectPkg = JSON.parse(readFileSync(join(root, 'package.json'), 'utf-8'));
|
|
810
|
+
const wizardCtx = {
|
|
811
|
+
io: ctx.io,
|
|
812
|
+
project: {
|
|
813
|
+
root,
|
|
814
|
+
packageJson: projectPkg,
|
|
815
|
+
hasDependency: (name) => !!(projectPkg.dependencies?.[name] || projectPkg.devDependencies?.[name]),
|
|
816
|
+
},
|
|
817
|
+
};
|
|
818
|
+
await wizardFn(wizardCtx);
|
|
819
|
+
}
|
|
820
|
+
catch (err) {
|
|
821
|
+
ctx.io.error(`Wizard failed: ${err.message}`);
|
|
822
|
+
}
|
|
823
|
+
}),
|
|
824
|
+
dev: Cli('dev')
|
|
825
|
+
.handle(async (ctx) => {
|
|
826
|
+
// Use the invoking cwd so `cd examples/simple-app && just dev` picks
|
|
827
|
+
// up that package's `src/app.ts`, not the monorepo root.
|
|
828
|
+
const root = process.cwd();
|
|
829
|
+
ctx.io.log('JustScale Dev Server\n');
|
|
830
|
+
const { startDevServer } = await import('./dev-server.js');
|
|
831
|
+
await startDevServer({
|
|
832
|
+
root,
|
|
833
|
+
log: (msg) => ctx.io.log(msg),
|
|
834
|
+
});
|
|
835
|
+
}),
|
|
836
|
+
mcpServe: Cli('mcp serve')
|
|
837
|
+
.handle(async (_ctx) => {
|
|
838
|
+
// MCP stdio mode — launched by Claude Code / Cursor. Uses the same
|
|
839
|
+
// assembly path as the `just` binary so discovered package commands
|
|
840
|
+
// resolve against the user's real DI container.
|
|
841
|
+
try {
|
|
842
|
+
const { startMcpStdio } = await import('./mcp/server.js');
|
|
843
|
+
const { assembleCliApp } = await import('./assemble.js');
|
|
844
|
+
const app = await assembleCliApp();
|
|
845
|
+
await startMcpStdio(app);
|
|
846
|
+
}
|
|
847
|
+
catch (err) {
|
|
848
|
+
process.stderr.write(`MCP server failed: ${err.message}\n`);
|
|
849
|
+
process.exit(1);
|
|
850
|
+
}
|
|
851
|
+
}),
|
|
852
|
+
}),
|
|
853
|
+
});
|
|
854
|
+
/**
|
|
855
|
+
* The inlined shell completion function for each supported shell.
|
|
856
|
+
* Self-contained — each snippet calls `just __complete` only at tab
|
|
857
|
+
* time, not at shell-startup time, so shells open cleanly even if
|
|
858
|
+
* `just` isn't on PATH when they launch.
|
|
859
|
+
*/
|
|
860
|
+
function renderCompletionScript(shell) {
|
|
861
|
+
if (shell === 'bash') {
|
|
862
|
+
return [
|
|
863
|
+
'_just_complete() {',
|
|
864
|
+
' local IFS=$\'\\n\'',
|
|
865
|
+
' local cursor=$((COMP_CWORD - 1))',
|
|
866
|
+
' local -a words=("${COMP_WORDS[@]:1}")',
|
|
867
|
+
' COMPREPLY=($(just __complete "$cursor" "${words[@]}" 2>/dev/null))',
|
|
868
|
+
' return 0',
|
|
869
|
+
'}',
|
|
870
|
+
'complete -o default -F _just_complete just',
|
|
871
|
+
].join('\n');
|
|
872
|
+
}
|
|
873
|
+
if (shell === 'zsh') {
|
|
874
|
+
return [
|
|
875
|
+
'#compdef just',
|
|
876
|
+
'_just() {',
|
|
877
|
+
' local -a completions',
|
|
878
|
+
' local cursor=$((CURRENT - 2))',
|
|
879
|
+
' completions=(${(f)"$(just __complete "$cursor" "${words[@]:1}" 2>/dev/null)"})',
|
|
880
|
+
' if (( ${#completions} )); then',
|
|
881
|
+
' compadd -a completions',
|
|
882
|
+
' fi',
|
|
883
|
+
'}',
|
|
884
|
+
'compdef _just just',
|
|
885
|
+
].join('\n');
|
|
886
|
+
}
|
|
887
|
+
return [
|
|
888
|
+
'function __just_complete',
|
|
889
|
+
' set -l tokens (commandline -opc) (commandline -ct)',
|
|
890
|
+
' set -l cursor (math (count $tokens) - 2)',
|
|
891
|
+
' just __complete $cursor $tokens[2..-1] 2>/dev/null',
|
|
892
|
+
'end',
|
|
893
|
+
'complete -c just -f -a "(__just_complete)"',
|
|
894
|
+
].join('\n');
|
|
895
|
+
}
|
|
896
|
+
//# sourceMappingURL=workspace-controller.js.map
|