@contractspec/bundle.workspace 1.44.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 +79 -0
- package/dist/_virtual/rolldown_runtime.js +36 -0
- package/dist/adapters/ai.d.ts +12 -0
- package/dist/adapters/ai.d.ts.map +1 -0
- package/dist/adapters/ai.js +83 -0
- package/dist/adapters/ai.js.map +1 -0
- package/dist/adapters/factory.d.ts +29 -0
- package/dist/adapters/factory.d.ts.map +1 -0
- package/dist/adapters/factory.js +37 -0
- package/dist/adapters/factory.js.map +1 -0
- package/dist/adapters/fs.d.ts +11 -0
- package/dist/adapters/fs.d.ts.map +1 -0
- package/dist/adapters/fs.js +131 -0
- package/dist/adapters/fs.js.map +1 -0
- package/dist/adapters/git.d.ts +11 -0
- package/dist/adapters/git.d.ts.map +1 -0
- package/dist/adapters/git.js +55 -0
- package/dist/adapters/git.js.map +1 -0
- package/dist/adapters/index.d.ts +7 -0
- package/dist/adapters/index.js +7 -0
- package/dist/adapters/logger.d.ts +18 -0
- package/dist/adapters/logger.d.ts.map +1 -0
- package/dist/adapters/logger.js +81 -0
- package/dist/adapters/logger.js.map +1 -0
- package/dist/adapters/watcher.d.ts +11 -0
- package/dist/adapters/watcher.d.ts.map +1 -0
- package/dist/adapters/watcher.js +74 -0
- package/dist/adapters/watcher.js.map +1 -0
- package/dist/adapters/workspace.d.ts +148 -0
- package/dist/adapters/workspace.d.ts.map +1 -0
- package/dist/adapters/workspace.js +275 -0
- package/dist/adapters/workspace.js.map +1 -0
- package/dist/ai/agents/claude-code-agent.d.ts +22 -0
- package/dist/ai/agents/claude-code-agent.d.ts.map +1 -0
- package/dist/ai/agents/claude-code-agent.js +182 -0
- package/dist/ai/agents/claude-code-agent.js.map +1 -0
- package/dist/ai/agents/cursor-agent.d.ts +68 -0
- package/dist/ai/agents/cursor-agent.d.ts.map +1 -0
- package/dist/ai/agents/cursor-agent.js +436 -0
- package/dist/ai/agents/cursor-agent.js.map +1 -0
- package/dist/ai/agents/index.js +5 -0
- package/dist/ai/agents/openai-codex-agent.d.ts +22 -0
- package/dist/ai/agents/openai-codex-agent.d.ts.map +1 -0
- package/dist/ai/agents/openai-codex-agent.js +167 -0
- package/dist/ai/agents/openai-codex-agent.js.map +1 -0
- package/dist/ai/agents/orchestrator.d.ts +50 -0
- package/dist/ai/agents/orchestrator.d.ts.map +1 -0
- package/dist/ai/agents/orchestrator.js +143 -0
- package/dist/ai/agents/orchestrator.js.map +1 -0
- package/dist/ai/agents/simple-agent.d.ts +17 -0
- package/dist/ai/agents/simple-agent.d.ts.map +1 -0
- package/dist/ai/agents/simple-agent.js +92 -0
- package/dist/ai/agents/simple-agent.js.map +1 -0
- package/dist/ai/agents/types.d.ts +36 -0
- package/dist/ai/agents/types.d.ts.map +1 -0
- package/dist/ai/client.d.ts +83 -0
- package/dist/ai/client.d.ts.map +1 -0
- package/dist/ai/client.js +163 -0
- package/dist/ai/client.js.map +1 -0
- package/dist/ai/index.d.ts +17 -0
- package/dist/ai/index.d.ts.map +1 -0
- package/dist/ai/index.js +28 -0
- package/dist/ai/index.js.map +1 -0
- package/dist/ai/prompts/code-generation.d.ts +26 -0
- package/dist/ai/prompts/code-generation.d.ts.map +1 -0
- package/dist/ai/prompts/code-generation.js +143 -0
- package/dist/ai/prompts/code-generation.js.map +1 -0
- package/dist/ai/prompts/index.d.ts +10 -0
- package/dist/ai/prompts/index.d.ts.map +1 -0
- package/dist/ai/prompts/index.js +13 -0
- package/dist/ai/prompts/index.js.map +1 -0
- package/dist/ai/prompts/spec-creation.d.ts +29 -0
- package/dist/ai/prompts/spec-creation.d.ts.map +1 -0
- package/dist/ai/prompts/spec-creation.js +111 -0
- package/dist/ai/prompts/spec-creation.js.map +1 -0
- package/dist/ai/providers.d.ts +29 -0
- package/dist/ai/providers.d.ts.map +1 -0
- package/dist/ai/providers.js +39 -0
- package/dist/ai/providers.js.map +1 -0
- package/dist/formatters/index.d.ts +11 -0
- package/dist/formatters/index.d.ts.map +1 -0
- package/dist/formatters/index.js +19 -0
- package/dist/formatters/index.js.map +1 -0
- package/dist/formatters/json.d.ts +89 -0
- package/dist/formatters/json.d.ts.map +1 -0
- package/dist/formatters/json.js +72 -0
- package/dist/formatters/json.js.map +1 -0
- package/dist/formatters/sarif.d.ts +101 -0
- package/dist/formatters/sarif.d.ts.map +1 -0
- package/dist/formatters/sarif.js +163 -0
- package/dist/formatters/sarif.js.map +1 -0
- package/dist/formatters/text.d.ts +35 -0
- package/dist/formatters/text.d.ts.map +1 -0
- package/dist/formatters/text.js +209 -0
- package/dist/formatters/text.js.map +1 -0
- package/dist/index.d.ts +82 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +204 -0
- package/dist/index.js.map +1 -0
- package/dist/ports/ai.d.ts +59 -0
- package/dist/ports/ai.d.ts.map +1 -0
- package/dist/ports/fs.d.ts +81 -0
- package/dist/ports/fs.d.ts.map +1 -0
- package/dist/ports/git.d.ts +33 -0
- package/dist/ports/git.d.ts.map +1 -0
- package/dist/ports/index.d.ts +5 -0
- package/dist/ports/logger.d.ts +88 -0
- package/dist/ports/logger.d.ts.map +1 -0
- package/dist/ports/watcher.d.ts +52 -0
- package/dist/ports/watcher.d.ts.map +1 -0
- package/dist/services/agent-guide/adapters/claude-code.d.ts +35 -0
- package/dist/services/agent-guide/adapters/claude-code.d.ts.map +1 -0
- package/dist/services/agent-guide/adapters/claude-code.js +144 -0
- package/dist/services/agent-guide/adapters/claude-code.js.map +1 -0
- package/dist/services/agent-guide/adapters/cursor-cli.d.ts +39 -0
- package/dist/services/agent-guide/adapters/cursor-cli.d.ts.map +1 -0
- package/dist/services/agent-guide/adapters/cursor-cli.js +135 -0
- package/dist/services/agent-guide/adapters/cursor-cli.js.map +1 -0
- package/dist/services/agent-guide/adapters/generic-mcp.d.ts +53 -0
- package/dist/services/agent-guide/adapters/generic-mcp.d.ts.map +1 -0
- package/dist/services/agent-guide/adapters/generic-mcp.js +159 -0
- package/dist/services/agent-guide/adapters/generic-mcp.js.map +1 -0
- package/dist/services/agent-guide/adapters/index.d.ts +23 -0
- package/dist/services/agent-guide/adapters/index.d.ts.map +1 -0
- package/dist/services/agent-guide/adapters/index.js +31 -0
- package/dist/services/agent-guide/adapters/index.js.map +1 -0
- package/dist/services/agent-guide/agent-guide-service.d.ts +56 -0
- package/dist/services/agent-guide/agent-guide-service.d.ts.map +1 -0
- package/dist/services/agent-guide/agent-guide-service.js +147 -0
- package/dist/services/agent-guide/agent-guide-service.js.map +1 -0
- package/dist/services/agent-guide/index.d.ts +6 -0
- package/dist/services/agent-guide/index.js +5 -0
- package/dist/services/agent-guide/types.d.ts +58 -0
- package/dist/services/agent-guide/types.d.ts.map +1 -0
- package/dist/services/build.d.ts +59 -0
- package/dist/services/build.d.ts.map +1 -0
- package/dist/services/build.js +140 -0
- package/dist/services/build.js.map +1 -0
- package/dist/services/ci-check/ci-check-service.d.ts +16 -0
- package/dist/services/ci-check/ci-check-service.d.ts.map +1 -0
- package/dist/services/ci-check/ci-check-service.js +392 -0
- package/dist/services/ci-check/ci-check-service.js.map +1 -0
- package/dist/services/ci-check/index.d.ts +2 -0
- package/dist/services/ci-check/index.js +2 -0
- package/dist/services/ci-check/types.d.ts +143 -0
- package/dist/services/ci-check/types.d.ts.map +1 -0
- package/dist/services/ci-check/types.js +29 -0
- package/dist/services/ci-check/types.js.map +1 -0
- package/dist/services/clean.d.ts +41 -0
- package/dist/services/clean.d.ts.map +1 -0
- package/dist/services/clean.js +72 -0
- package/dist/services/clean.js.map +1 -0
- package/dist/services/config.d.ts +26 -0
- package/dist/services/config.d.ts.map +1 -0
- package/dist/services/config.js +77 -0
- package/dist/services/config.js.map +1 -0
- package/dist/services/deps.d.ts +53 -0
- package/dist/services/deps.d.ts.map +1 -0
- package/dist/services/deps.js +62 -0
- package/dist/services/deps.js.map +1 -0
- package/dist/services/diff.d.ts +34 -0
- package/dist/services/diff.d.ts.map +1 -0
- package/dist/services/diff.js +34 -0
- package/dist/services/diff.js.map +1 -0
- package/dist/services/doctor/checks/ai.js +119 -0
- package/dist/services/doctor/checks/ai.js.map +1 -0
- package/dist/services/doctor/checks/cli.js +147 -0
- package/dist/services/doctor/checks/cli.js.map +1 -0
- package/dist/services/doctor/checks/config.js +171 -0
- package/dist/services/doctor/checks/config.js.map +1 -0
- package/dist/services/doctor/checks/deps.js +247 -0
- package/dist/services/doctor/checks/deps.js.map +1 -0
- package/dist/services/doctor/checks/index.js +6 -0
- package/dist/services/doctor/checks/mcp.js +145 -0
- package/dist/services/doctor/checks/mcp.js.map +1 -0
- package/dist/services/doctor/checks/workspace.js +244 -0
- package/dist/services/doctor/checks/workspace.js.map +1 -0
- package/dist/services/doctor/doctor-service.d.ts +24 -0
- package/dist/services/doctor/doctor-service.d.ts.map +1 -0
- package/dist/services/doctor/doctor-service.js +116 -0
- package/dist/services/doctor/doctor-service.js.map +1 -0
- package/dist/services/doctor/index.d.ts +2 -0
- package/dist/services/doctor/index.js +2 -0
- package/dist/services/doctor/types.d.ts +118 -0
- package/dist/services/doctor/types.d.ts.map +1 -0
- package/dist/services/doctor/types.js +27 -0
- package/dist/services/doctor/types.js.map +1 -0
- package/dist/services/impact/formatters.d.ts +27 -0
- package/dist/services/impact/formatters.d.ts.map +1 -0
- package/dist/services/impact/formatters.js +111 -0
- package/dist/services/impact/formatters.js.map +1 -0
- package/dist/services/impact/impact-detection-service.d.ts +22 -0
- package/dist/services/impact/impact-detection-service.d.ts.map +1 -0
- package/dist/services/impact/impact-detection-service.js +96 -0
- package/dist/services/impact/impact-detection-service.js.map +1 -0
- package/dist/services/impact/index.d.ts +11 -0
- package/dist/services/impact/index.d.ts.map +1 -0
- package/dist/services/impact/index.js +16 -0
- package/dist/services/impact/index.js.map +1 -0
- package/dist/services/impact/types.d.ts +58 -0
- package/dist/services/impact/types.d.ts.map +1 -0
- package/dist/services/implementation/discovery.d.ts +30 -0
- package/dist/services/implementation/discovery.d.ts.map +1 -0
- package/dist/services/implementation/discovery.js +144 -0
- package/dist/services/implementation/discovery.js.map +1 -0
- package/dist/services/implementation/index.d.ts +3 -0
- package/dist/services/implementation/index.js +2 -0
- package/dist/services/implementation/resolver.d.ts +44 -0
- package/dist/services/implementation/resolver.d.ts.map +1 -0
- package/dist/services/implementation/resolver.js +224 -0
- package/dist/services/implementation/resolver.js.map +1 -0
- package/dist/services/implementation/types.d.ts +79 -0
- package/dist/services/implementation/types.d.ts.map +1 -0
- package/dist/services/index.d.ts +60 -0
- package/dist/services/index.js +57 -0
- package/dist/services/integrity-diagram.d.ts +36 -0
- package/dist/services/integrity-diagram.d.ts.map +1 -0
- package/dist/services/integrity-diagram.js +275 -0
- package/dist/services/integrity-diagram.js.map +1 -0
- package/dist/services/integrity.d.ts +134 -0
- package/dist/services/integrity.d.ts.map +1 -0
- package/dist/services/integrity.js +272 -0
- package/dist/services/integrity.js.map +1 -0
- package/dist/services/list.d.ts +31 -0
- package/dist/services/list.d.ts.map +1 -0
- package/dist/services/list.js +36 -0
- package/dist/services/list.js.map +1 -0
- package/dist/services/openapi/export-service.d.ts +53 -0
- package/dist/services/openapi/export-service.d.ts.map +1 -0
- package/dist/services/openapi/export-service.js +50 -0
- package/dist/services/openapi/export-service.js.map +1 -0
- package/dist/services/openapi/import-service.d.ts +17 -0
- package/dist/services/openapi/import-service.d.ts.map +1 -0
- package/dist/services/openapi/import-service.js +74 -0
- package/dist/services/openapi/import-service.js.map +1 -0
- package/dist/services/openapi/index.d.ts +5 -0
- package/dist/services/openapi/index.js +4 -0
- package/dist/services/openapi/sync-service.d.ts +17 -0
- package/dist/services/openapi/sync-service.d.ts.map +1 -0
- package/dist/services/openapi/sync-service.js +120 -0
- package/dist/services/openapi/sync-service.js.map +1 -0
- package/dist/services/openapi/types.d.ts +162 -0
- package/dist/services/openapi/types.d.ts.map +1 -0
- package/dist/services/openapi/validate-service.d.ts +16 -0
- package/dist/services/openapi/validate-service.d.ts.map +1 -0
- package/dist/services/openapi/validate-service.js +130 -0
- package/dist/services/openapi/validate-service.js.map +1 -0
- package/dist/services/quickstart/dependencies.d.ts +31 -0
- package/dist/services/quickstart/dependencies.d.ts.map +1 -0
- package/dist/services/quickstart/dependencies.js +57 -0
- package/dist/services/quickstart/dependencies.js.map +1 -0
- package/dist/services/quickstart/index.js +2 -0
- package/dist/services/quickstart/quickstart-service.d.ts +20 -0
- package/dist/services/quickstart/quickstart-service.d.ts.map +1 -0
- package/dist/services/quickstart/quickstart-service.js +196 -0
- package/dist/services/quickstart/quickstart-service.js.map +1 -0
- package/dist/services/quickstart/types.d.ts +81 -0
- package/dist/services/quickstart/types.d.ts.map +1 -0
- package/dist/services/regenerator.d.ts +18 -0
- package/dist/services/regenerator.d.ts.map +1 -0
- package/dist/services/regenerator.js +23 -0
- package/dist/services/regenerator.js.map +1 -0
- package/dist/services/registry.d.ts +53 -0
- package/dist/services/registry.d.ts.map +1 -0
- package/dist/services/registry.js +74 -0
- package/dist/services/registry.js.map +1 -0
- package/dist/services/setup/config-generators.d.ts +42 -0
- package/dist/services/setup/config-generators.d.ts.map +1 -0
- package/dist/services/setup/config-generators.js +238 -0
- package/dist/services/setup/config-generators.js.map +1 -0
- package/dist/services/setup/file-merger.d.ts +27 -0
- package/dist/services/setup/file-merger.d.ts.map +1 -0
- package/dist/services/setup/file-merger.js +61 -0
- package/dist/services/setup/file-merger.js.map +1 -0
- package/dist/services/setup/index.js +4 -0
- package/dist/services/setup/setup-service.d.ts +12 -0
- package/dist/services/setup/setup-service.d.ts.map +1 -0
- package/dist/services/setup/setup-service.js +96 -0
- package/dist/services/setup/setup-service.js.map +1 -0
- package/dist/services/setup/targets/agents-md.js +47 -0
- package/dist/services/setup/targets/agents-md.js.map +1 -0
- package/dist/services/setup/targets/cli-config.js +60 -0
- package/dist/services/setup/targets/cli-config.js.map +1 -0
- package/dist/services/setup/targets/cursor-rules.js +48 -0
- package/dist/services/setup/targets/cursor-rules.js.map +1 -0
- package/dist/services/setup/targets/mcp-claude.js +60 -0
- package/dist/services/setup/targets/mcp-claude.js.map +1 -0
- package/dist/services/setup/targets/mcp-cursor.js +59 -0
- package/dist/services/setup/targets/mcp-cursor.js.map +1 -0
- package/dist/services/setup/targets/vscode-settings.js +63 -0
- package/dist/services/setup/targets/vscode-settings.js.map +1 -0
- package/dist/services/setup/types.d.ts +85 -0
- package/dist/services/setup/types.d.ts.map +1 -0
- package/dist/services/setup/types.js +27 -0
- package/dist/services/setup/types.js.map +1 -0
- package/dist/services/sync.d.ts +41 -0
- package/dist/services/sync.d.ts.map +1 -0
- package/dist/services/sync.js +63 -0
- package/dist/services/sync.js.map +1 -0
- package/dist/services/test.d.ts +15 -0
- package/dist/services/test.d.ts.map +1 -0
- package/dist/services/test.js +30 -0
- package/dist/services/test.js.map +1 -0
- package/dist/services/validate-implementation.d.ts +32 -0
- package/dist/services/validate-implementation.d.ts.map +1 -0
- package/dist/services/validate-implementation.js +64 -0
- package/dist/services/validate-implementation.js.map +1 -0
- package/dist/services/validate.d.ts +41 -0
- package/dist/services/validate.d.ts.map +1 -0
- package/dist/services/validate.js +48 -0
- package/dist/services/validate.js.map +1 -0
- package/dist/services/verification-cache/adapters/filesystem.d.ts +46 -0
- package/dist/services/verification-cache/adapters/filesystem.d.ts.map +1 -0
- package/dist/services/verification-cache/adapters/filesystem.js +120 -0
- package/dist/services/verification-cache/adapters/filesystem.js.map +1 -0
- package/dist/services/verification-cache/adapters/in-memory.d.ts +27 -0
- package/dist/services/verification-cache/adapters/in-memory.d.ts.map +1 -0
- package/dist/services/verification-cache/adapters/in-memory.js +46 -0
- package/dist/services/verification-cache/adapters/in-memory.js.map +1 -0
- package/dist/services/verification-cache/adapters/index.d.ts +3 -0
- package/dist/services/verification-cache/adapters/index.js +3 -0
- package/dist/services/verification-cache/adapters/workspace-state.d.ts +49 -0
- package/dist/services/verification-cache/adapters/workspace-state.d.ts.map +1 -0
- package/dist/services/verification-cache/adapters/workspace-state.js +91 -0
- package/dist/services/verification-cache/adapters/workspace-state.js.map +1 -0
- package/dist/services/verification-cache/cache-service.d.ts +70 -0
- package/dist/services/verification-cache/cache-service.d.ts.map +1 -0
- package/dist/services/verification-cache/cache-service.js +256 -0
- package/dist/services/verification-cache/cache-service.js.map +1 -0
- package/dist/services/verification-cache/index.d.ts +6 -0
- package/dist/services/verification-cache/index.js +6 -0
- package/dist/services/verification-cache/types.d.ts +124 -0
- package/dist/services/verification-cache/types.d.ts.map +1 -0
- package/dist/services/verification-cache/types.js +16 -0
- package/dist/services/verification-cache/types.js.map +1 -0
- package/dist/services/verify/ai-verifier.d.ts +25 -0
- package/dist/services/verify/ai-verifier.d.ts.map +1 -0
- package/dist/services/verify/ai-verifier.js +403 -0
- package/dist/services/verify/ai-verifier.js.map +1 -0
- package/dist/services/verify/behavior-verifier.d.ts +12 -0
- package/dist/services/verify/behavior-verifier.d.ts.map +1 -0
- package/dist/services/verify/behavior-verifier.js +186 -0
- package/dist/services/verify/behavior-verifier.js.map +1 -0
- package/dist/services/verify/index.d.ts +5 -0
- package/dist/services/verify/index.js +4 -0
- package/dist/services/verify/structure-verifier.d.ts +12 -0
- package/dist/services/verify/structure-verifier.d.ts.map +1 -0
- package/dist/services/verify/structure-verifier.js +196 -0
- package/dist/services/verify/structure-verifier.js.map +1 -0
- package/dist/services/verify/types.d.ts +137 -0
- package/dist/services/verify/types.d.ts.map +1 -0
- package/dist/services/verify/verify-service.d.ts +60 -0
- package/dist/services/verify/verify-service.d.ts.map +1 -0
- package/dist/services/verify/verify-service.js +204 -0
- package/dist/services/verify/verify-service.js.map +1 -0
- package/dist/services/watch.d.ts +25 -0
- package/dist/services/watch.d.ts.map +1 -0
- package/dist/services/watch.js +32 -0
- package/dist/services/watch.js.map +1 -0
- package/dist/services/workspace-info.d.ts +62 -0
- package/dist/services/workspace-info.d.ts.map +1 -0
- package/dist/services/workspace-info.js +103 -0
- package/dist/services/workspace-info.js.map +1 -0
- package/dist/templates/app-config.template.d.ts +7 -0
- package/dist/templates/app-config.template.d.ts.map +1 -0
- package/dist/templates/app-config.template.js +107 -0
- package/dist/templates/app-config.template.js.map +1 -0
- package/dist/templates/data-view.template.d.ts +7 -0
- package/dist/templates/data-view.template.d.ts.map +1 -0
- package/dist/templates/data-view.template.js +70 -0
- package/dist/templates/data-view.template.js.map +1 -0
- package/dist/templates/event.template.d.ts +11 -0
- package/dist/templates/event.template.d.ts.map +1 -0
- package/dist/templates/event.template.js +40 -0
- package/dist/templates/event.template.js.map +1 -0
- package/dist/templates/experiment.template.d.ts +7 -0
- package/dist/templates/experiment.template.d.ts.map +1 -0
- package/dist/templates/experiment.template.js +89 -0
- package/dist/templates/experiment.template.js.map +1 -0
- package/dist/templates/handler.template.d.ts +16 -0
- package/dist/templates/handler.template.d.ts.map +1 -0
- package/dist/templates/handler.template.js +100 -0
- package/dist/templates/handler.template.js.map +1 -0
- package/dist/templates/index.d.ts +21 -0
- package/dist/templates/index.d.ts.map +1 -0
- package/dist/templates/index.js +37 -0
- package/dist/templates/index.js.map +1 -0
- package/dist/templates/integration.template.d.ts +7 -0
- package/dist/templates/integration.template.d.ts.map +1 -0
- package/dist/templates/integration.template.js +160 -0
- package/dist/templates/integration.template.js.map +1 -0
- package/dist/templates/knowledge.template.d.ts +7 -0
- package/dist/templates/knowledge.template.d.ts.map +1 -0
- package/dist/templates/knowledge.template.js +75 -0
- package/dist/templates/knowledge.template.js.map +1 -0
- package/dist/templates/migration.template.d.ts +7 -0
- package/dist/templates/migration.template.d.ts.map +1 -0
- package/dist/templates/migration.template.js +62 -0
- package/dist/templates/migration.template.js.map +1 -0
- package/dist/templates/operation.template.d.ts +11 -0
- package/dist/templates/operation.template.d.ts.map +1 -0
- package/dist/templates/operation.template.js +105 -0
- package/dist/templates/operation.template.js.map +1 -0
- package/dist/templates/presentation.template.d.ts +11 -0
- package/dist/templates/presentation.template.d.ts.map +1 -0
- package/dist/templates/presentation.template.js +80 -0
- package/dist/templates/presentation.template.js.map +1 -0
- package/dist/templates/telemetry.template.d.ts +7 -0
- package/dist/templates/telemetry.template.d.ts.map +1 -0
- package/dist/templates/telemetry.template.js +91 -0
- package/dist/templates/telemetry.template.js.map +1 -0
- package/dist/templates/workflow-runner.template.d.ts +16 -0
- package/dist/templates/workflow-runner.template.d.ts.map +1 -0
- package/dist/templates/workflow-runner.template.js +50 -0
- package/dist/templates/workflow-runner.template.js.map +1 -0
- package/dist/templates/workflow.template.d.ts +7 -0
- package/dist/templates/workflow.template.d.ts.map +1 -0
- package/dist/templates/workflow.template.js +69 -0
- package/dist/templates/workflow.template.js.map +1 -0
- package/dist/types/config.d.ts +34 -0
- package/dist/types/config.d.ts.map +1 -0
- package/dist/types.d.ts +324 -0
- package/dist/types.d.ts.map +1 -0
- package/package.json +68 -0
|
@@ -0,0 +1,238 @@
|
|
|
1
|
+
//#region src/services/setup/config-generators.ts
|
|
2
|
+
/**
|
|
3
|
+
* Generate .contractsrc.json content.
|
|
4
|
+
*
|
|
5
|
+
* Adapts defaults based on monorepo scope.
|
|
6
|
+
*/
|
|
7
|
+
function generateContractsrcConfig(options) {
|
|
8
|
+
const isPackageLevel = options.isMonorepo && options.scope === "package";
|
|
9
|
+
return {
|
|
10
|
+
$schema: "https://api.contractspec.io/schemas/contractsrc.json",
|
|
11
|
+
aiProvider: "claude",
|
|
12
|
+
aiModel: "claude-sonnet-4-20250514",
|
|
13
|
+
agentMode: "claude-code",
|
|
14
|
+
outputDir: "./src",
|
|
15
|
+
conventions: {
|
|
16
|
+
operations: "contracts/operations",
|
|
17
|
+
events: "contracts/events",
|
|
18
|
+
presentations: "contracts/presentations",
|
|
19
|
+
forms: "contracts/forms",
|
|
20
|
+
features: "contracts/features"
|
|
21
|
+
},
|
|
22
|
+
defaultOwners: options.defaultOwners ?? ["@team"],
|
|
23
|
+
defaultTags: [],
|
|
24
|
+
...isPackageLevel && options.packageName ? { package: options.packageName } : {}
|
|
25
|
+
};
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* Generate .vscode/settings.json ContractSpec settings.
|
|
29
|
+
*/
|
|
30
|
+
function generateVscodeSettings() {
|
|
31
|
+
return {
|
|
32
|
+
"contractspec.validation.enabled": true,
|
|
33
|
+
"contractspec.validation.validateOnSave": true,
|
|
34
|
+
"contractspec.validation.validateOnOpen": true,
|
|
35
|
+
"contractspec.codeLens.enabled": true,
|
|
36
|
+
"contractspec.diagnostics.showWarnings": true,
|
|
37
|
+
"contractspec.diagnostics.showHints": true,
|
|
38
|
+
"contractspec.integrity.enabled": true,
|
|
39
|
+
"contractspec.integrity.checkOnSave": true
|
|
40
|
+
};
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Generate .cursor/mcp.json content.
|
|
44
|
+
*/
|
|
45
|
+
function generateCursorMcpConfig() {
|
|
46
|
+
return { mcpServers: { "contractspec-local": {
|
|
47
|
+
command: "bunx",
|
|
48
|
+
args: ["contractspec-mcp"]
|
|
49
|
+
} } };
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Generate Claude Desktop MCP config.
|
|
53
|
+
* Returns the mcpServers section to merge into claude_desktop_config.json.
|
|
54
|
+
*/
|
|
55
|
+
function generateClaudeMcpConfig() {
|
|
56
|
+
return { mcpServers: { "contractspec-local": {
|
|
57
|
+
command: "bunx",
|
|
58
|
+
args: ["contractspec-mcp"]
|
|
59
|
+
} } };
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Generate .cursor/rules/contractspec.mdc content.
|
|
63
|
+
*
|
|
64
|
+
* Adapts paths based on monorepo scope.
|
|
65
|
+
*/
|
|
66
|
+
function generateCursorRules(options) {
|
|
67
|
+
const projectName = options.projectName ?? "this project";
|
|
68
|
+
const basePath = options.isMonorepo && options.scope === "package" && options.packageRoot ? `${options.packageRoot.split("/").slice(-2).join("/")}/src/contracts` : "src/contracts";
|
|
69
|
+
return `# ContractSpec Development Rules
|
|
70
|
+
|
|
71
|
+
This project uses ContractSpec for spec-first development. Follow these guidelines when working with AI agents.
|
|
72
|
+
|
|
73
|
+
## Spec-First Principle
|
|
74
|
+
|
|
75
|
+
- **Always update contracts first** before changing implementation code.
|
|
76
|
+
- Contracts are the source of truth for operations, events, and presentations.
|
|
77
|
+
- Implementation code should be generated or derived from contracts.
|
|
78
|
+
${options.isMonorepo ? `\n## Monorepo Structure\n\nThis is a monorepo. Contracts may exist at:\n- Package level: \`packages/*/src/contracts/\`\n- Workspace level: \`src/contracts/\`\n\nCheck the appropriate level based on the feature scope.\n` : ""}
|
|
79
|
+
## Contract Locations
|
|
80
|
+
|
|
81
|
+
Contracts are located in:
|
|
82
|
+
- \`${basePath}/operations/\` - Command and query specs
|
|
83
|
+
- \`${basePath}/events/\` - Event specs
|
|
84
|
+
- \`${basePath}/presentations/\` - UI presentation specs
|
|
85
|
+
- \`${basePath}/features/\` - Feature module specs
|
|
86
|
+
|
|
87
|
+
## When Making Changes
|
|
88
|
+
|
|
89
|
+
1. **Before coding**: Check if a contract exists for the feature.
|
|
90
|
+
2. **If contract exists**: Update the contract first, then regenerate code.
|
|
91
|
+
3. **If no contract**: Create a new contract using \`contractspec create\`.
|
|
92
|
+
4. **After changes**: Validate with \`contractspec validate\`.
|
|
93
|
+
|
|
94
|
+
## Key Commands
|
|
95
|
+
|
|
96
|
+
- \`contractspec create\` - Scaffold new specs
|
|
97
|
+
- \`contractspec validate\` - Validate specs
|
|
98
|
+
- \`contractspec build\` - Generate implementation code
|
|
99
|
+
- \`contractspec integrity\` - Check contract health
|
|
100
|
+
|
|
101
|
+
## Contract Structure
|
|
102
|
+
|
|
103
|
+
Operations follow this pattern:
|
|
104
|
+
\`\`\`typescript
|
|
105
|
+
defineCommand({
|
|
106
|
+
meta: { name: 'service.action', version: 1, ... },
|
|
107
|
+
io: { input: InputSchema, output: OutputSchema },
|
|
108
|
+
policy: { auth: 'user', ... },
|
|
109
|
+
handler: async (args, ctx) => { ... }
|
|
110
|
+
});
|
|
111
|
+
\`\`\`
|
|
112
|
+
|
|
113
|
+
## Rules for ${projectName}
|
|
114
|
+
|
|
115
|
+
- All API endpoints must have a corresponding operation contract.
|
|
116
|
+
- Events must be declared in contracts before being emitted.
|
|
117
|
+
- UI components should reference presentation contracts.
|
|
118
|
+
- Feature flags should be defined in feature modules.
|
|
119
|
+
`;
|
|
120
|
+
}
|
|
121
|
+
/**
|
|
122
|
+
* Generate AGENTS.md content.
|
|
123
|
+
*
|
|
124
|
+
* Adapts paths and instructions based on monorepo scope.
|
|
125
|
+
*/
|
|
126
|
+
function generateAgentsMd(options) {
|
|
127
|
+
const projectName = options.projectName ?? "This Project";
|
|
128
|
+
const isPackageLevel = options.isMonorepo && options.scope === "package";
|
|
129
|
+
const contractPath = "src/contracts/";
|
|
130
|
+
return `# AI Agent Guide
|
|
131
|
+
|
|
132
|
+
This repository uses **ContractSpec** for spec-first development. AI agents should follow these guidelines.
|
|
133
|
+
|
|
134
|
+
## Project: ${projectName}
|
|
135
|
+
|
|
136
|
+
## ContractSpec Overview
|
|
137
|
+
|
|
138
|
+
ContractSpec is a deterministic, spec-first compiler that keeps AI-written software coherent, safe, and regenerable.
|
|
139
|
+
|
|
140
|
+
### Key Principles
|
|
141
|
+
|
|
142
|
+
1. **Contracts are the source of truth** - Always check/update contracts before modifying implementation.
|
|
143
|
+
2. **Safe regeneration** - Code can be regenerated from specs without breaking invariants.
|
|
144
|
+
3. **Multi-surface consistency** - API, events, and UI stay in sync via shared contracts.
|
|
145
|
+
${options.isMonorepo ? `
|
|
146
|
+
## Monorepo Structure
|
|
147
|
+
|
|
148
|
+
This is a monorepo. Contracts can exist at multiple levels:
|
|
149
|
+
|
|
150
|
+
| Level | Location | Use Case |
|
|
151
|
+
|-------|----------|----------|
|
|
152
|
+
| Package | \`packages/*/src/contracts/\` | Package-specific contracts |
|
|
153
|
+
| Workspace | \`src/contracts/\` | Shared cross-package contracts |
|
|
154
|
+
|
|
155
|
+
When adding a contract, consider:
|
|
156
|
+
- Is this specific to one package? → Add at package level
|
|
157
|
+
- Is this shared across packages? → Add at workspace level
|
|
158
|
+
|
|
159
|
+
### Current Scope
|
|
160
|
+
|
|
161
|
+
${isPackageLevel ? `You are working at the **package level**: \`${options.packageName ?? options.packageRoot}\`` : "You are working at the **workspace level**."}
|
|
162
|
+
` : ""}
|
|
163
|
+
## Working in This Repository
|
|
164
|
+
|
|
165
|
+
### Before Making Changes
|
|
166
|
+
|
|
167
|
+
1. Check for existing contracts in \`${contractPath}\`
|
|
168
|
+
2. If a contract exists, update it first
|
|
169
|
+
3. Regenerate implementation with \`contractspec build\`
|
|
170
|
+
4. Validate with \`contractspec validate\`
|
|
171
|
+
|
|
172
|
+
### Creating New Features
|
|
173
|
+
|
|
174
|
+
1. Create a feature spec: \`contractspec create --type=feature\`
|
|
175
|
+
2. Add operations: \`contractspec create --type=operation\`
|
|
176
|
+
3. Add events if needed: \`contractspec create --type=event\`
|
|
177
|
+
4. Build implementation: \`contractspec build\`
|
|
178
|
+
|
|
179
|
+
### Contract Locations
|
|
180
|
+
|
|
181
|
+
| Type | Location |
|
|
182
|
+
|------|----------|
|
|
183
|
+
| Operations | \`${contractPath}operations/\` |
|
|
184
|
+
| Events | \`${contractPath}events/\` |
|
|
185
|
+
| Presentations | \`${contractPath}presentations/\` |
|
|
186
|
+
| Features | \`${contractPath}features/\` |
|
|
187
|
+
|
|
188
|
+
## MCP Tools Available
|
|
189
|
+
|
|
190
|
+
The ContractSpec MCP server provides these tools:
|
|
191
|
+
|
|
192
|
+
- \`integrity.analyze\` - Check contract health
|
|
193
|
+
- \`specs.list\` - List all specs
|
|
194
|
+
- \`specs.validate\` - Validate a spec file
|
|
195
|
+
- \`specs.create\` - Create new specs
|
|
196
|
+
- \`deps.analyze\` - Analyze dependencies
|
|
197
|
+
|
|
198
|
+
## Common Tasks
|
|
199
|
+
|
|
200
|
+
### Add a new API endpoint
|
|
201
|
+
|
|
202
|
+
\`\`\`bash
|
|
203
|
+
contractspec create --type=operation --name=myService.newAction
|
|
204
|
+
\`\`\`
|
|
205
|
+
|
|
206
|
+
### Add a new event
|
|
207
|
+
|
|
208
|
+
\`\`\`bash
|
|
209
|
+
contractspec create --type=event --name=entity.changed
|
|
210
|
+
\`\`\`
|
|
211
|
+
|
|
212
|
+
### Check contract integrity
|
|
213
|
+
|
|
214
|
+
\`\`\`bash
|
|
215
|
+
contractspec integrity
|
|
216
|
+
\`\`\`
|
|
217
|
+
|
|
218
|
+
## Nested AGENTS.md
|
|
219
|
+
|
|
220
|
+
More specific instructions may exist in subdirectories. Check for \`AGENTS.md\` files in the relevant package or module.
|
|
221
|
+
`;
|
|
222
|
+
}
|
|
223
|
+
/**
|
|
224
|
+
* Get the file path for Claude Desktop config based on platform.
|
|
225
|
+
*/
|
|
226
|
+
function getClaudeDesktopConfigPath() {
|
|
227
|
+
const platform = process.platform;
|
|
228
|
+
const homeDir = process.env["HOME"] ?? process.env["USERPROFILE"] ?? "";
|
|
229
|
+
switch (platform) {
|
|
230
|
+
case "darwin": return `${homeDir}/Library/Application Support/Claude/claude_desktop_config.json`;
|
|
231
|
+
case "win32": return `${process.env["APPDATA"] ?? homeDir}/Claude/claude_desktop_config.json`;
|
|
232
|
+
default: return `${homeDir}/.config/claude/claude_desktop_config.json`;
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
//#endregion
|
|
237
|
+
export { generateAgentsMd, generateClaudeMcpConfig, generateContractsrcConfig, generateCursorMcpConfig, generateCursorRules, generateVscodeSettings, getClaudeDesktopConfigPath };
|
|
238
|
+
//# sourceMappingURL=config-generators.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config-generators.js","names":[],"sources":["../../../src/services/setup/config-generators.ts"],"sourcesContent":["/**\n * Config generators for setup targets.\n *\n * Each generator returns the default configuration for a target.\n */\n\nimport type { SetupOptions } from './types';\n\n/**\n * Generate .contractsrc.json content.\n *\n * Adapts defaults based on monorepo scope.\n */\nexport function generateContractsrcConfig(options: SetupOptions): object {\n // For package-level config in monorepo, use simpler relative paths\n const isPackageLevel = options.isMonorepo && options.scope === 'package';\n\n return {\n $schema: 'https://api.contractspec.io/schemas/contractsrc.json',\n aiProvider: 'claude',\n aiModel: 'claude-sonnet-4-20250514',\n agentMode: 'claude-code',\n // outputDir is relative to the config file location\n outputDir: './src',\n conventions: {\n operations: 'contracts/operations',\n events: 'contracts/events',\n presentations: 'contracts/presentations',\n forms: 'contracts/forms',\n features: 'contracts/features',\n },\n defaultOwners: options.defaultOwners ?? ['@team'],\n defaultTags: [],\n // Add monorepo hint if at package level\n ...(isPackageLevel && options.packageName\n ? { package: options.packageName }\n : {}),\n };\n}\n\n/**\n * Generate .vscode/settings.json ContractSpec settings.\n */\nexport function generateVscodeSettings(): object {\n return {\n 'contractspec.validation.enabled': true,\n 'contractspec.validation.validateOnSave': true,\n 'contractspec.validation.validateOnOpen': true,\n 'contractspec.codeLens.enabled': true,\n 'contractspec.diagnostics.showWarnings': true,\n 'contractspec.diagnostics.showHints': true,\n 'contractspec.integrity.enabled': true,\n 'contractspec.integrity.checkOnSave': true,\n };\n}\n\n/**\n * Generate .cursor/mcp.json content.\n */\nexport function generateCursorMcpConfig(): object {\n return {\n mcpServers: {\n 'contractspec-local': {\n command: 'bunx',\n args: ['contractspec-mcp'],\n },\n },\n };\n}\n\n/**\n * Generate Claude Desktop MCP config.\n * Returns the mcpServers section to merge into claude_desktop_config.json.\n */\nexport function generateClaudeMcpConfig(): object {\n return {\n mcpServers: {\n 'contractspec-local': {\n command: 'bunx',\n args: ['contractspec-mcp'],\n },\n },\n };\n}\n\n/**\n * Generate .cursor/rules/contractspec.mdc content.\n *\n * Adapts paths based on monorepo scope.\n */\nexport function generateCursorRules(options: SetupOptions): string {\n const projectName = options.projectName ?? 'this project';\n const isPackageLevel = options.isMonorepo && options.scope === 'package';\n\n // Base contract path depends on scope\n const basePath =\n isPackageLevel && options.packageRoot\n ? `${options.packageRoot.split('/').slice(-2).join('/')}/src/contracts`\n : 'src/contracts';\n\n const monorepoNote = options.isMonorepo\n ? `\\n## Monorepo Structure\\n\\nThis is a monorepo. Contracts may exist at:\\n- Package level: \\`packages/*/src/contracts/\\`\\n- Workspace level: \\`src/contracts/\\`\\n\\nCheck the appropriate level based on the feature scope.\\n`\n : '';\n\n return `# ContractSpec Development Rules\n\nThis project uses ContractSpec for spec-first development. Follow these guidelines when working with AI agents.\n\n## Spec-First Principle\n\n- **Always update contracts first** before changing implementation code.\n- Contracts are the source of truth for operations, events, and presentations.\n- Implementation code should be generated or derived from contracts.\n${monorepoNote}\n## Contract Locations\n\nContracts are located in:\n- \\`${basePath}/operations/\\` - Command and query specs\n- \\`${basePath}/events/\\` - Event specs\n- \\`${basePath}/presentations/\\` - UI presentation specs\n- \\`${basePath}/features/\\` - Feature module specs\n\n## When Making Changes\n\n1. **Before coding**: Check if a contract exists for the feature.\n2. **If contract exists**: Update the contract first, then regenerate code.\n3. **If no contract**: Create a new contract using \\`contractspec create\\`.\n4. **After changes**: Validate with \\`contractspec validate\\`.\n\n## Key Commands\n\n- \\`contractspec create\\` - Scaffold new specs\n- \\`contractspec validate\\` - Validate specs\n- \\`contractspec build\\` - Generate implementation code\n- \\`contractspec integrity\\` - Check contract health\n\n## Contract Structure\n\nOperations follow this pattern:\n\\`\\`\\`typescript\ndefineCommand({\n meta: { name: 'service.action', version: 1, ... },\n io: { input: InputSchema, output: OutputSchema },\n policy: { auth: 'user', ... },\n handler: async (args, ctx) => { ... }\n});\n\\`\\`\\`\n\n## Rules for ${projectName}\n\n- All API endpoints must have a corresponding operation contract.\n- Events must be declared in contracts before being emitted.\n- UI components should reference presentation contracts.\n- Feature flags should be defined in feature modules.\n`;\n}\n\n/**\n * Generate AGENTS.md content.\n *\n * Adapts paths and instructions based on monorepo scope.\n */\nexport function generateAgentsMd(options: SetupOptions): string {\n const projectName = options.projectName ?? 'This Project';\n const isPackageLevel = options.isMonorepo && options.scope === 'package';\n\n // Contract path depends on scope\n const contractPath = 'src/contracts/';\n\n const monorepoSection = options.isMonorepo\n ? `\n## Monorepo Structure\n\nThis is a monorepo. Contracts can exist at multiple levels:\n\n| Level | Location | Use Case |\n|-------|----------|----------|\n| Package | \\`packages/*/src/contracts/\\` | Package-specific contracts |\n| Workspace | \\`src/contracts/\\` | Shared cross-package contracts |\n\nWhen adding a contract, consider:\n- Is this specific to one package? → Add at package level\n- Is this shared across packages? → Add at workspace level\n\n### Current Scope\n\n${isPackageLevel ? `You are working at the **package level**: \\`${options.packageName ?? options.packageRoot}\\`` : 'You are working at the **workspace level**.'}\n`\n : '';\n\n return `# AI Agent Guide\n\nThis repository uses **ContractSpec** for spec-first development. AI agents should follow these guidelines.\n\n## Project: ${projectName}\n\n## ContractSpec Overview\n\nContractSpec is a deterministic, spec-first compiler that keeps AI-written software coherent, safe, and regenerable.\n\n### Key Principles\n\n1. **Contracts are the source of truth** - Always check/update contracts before modifying implementation.\n2. **Safe regeneration** - Code can be regenerated from specs without breaking invariants.\n3. **Multi-surface consistency** - API, events, and UI stay in sync via shared contracts.\n${monorepoSection}\n## Working in This Repository\n\n### Before Making Changes\n\n1. Check for existing contracts in \\`${contractPath}\\`\n2. If a contract exists, update it first\n3. Regenerate implementation with \\`contractspec build\\`\n4. Validate with \\`contractspec validate\\`\n\n### Creating New Features\n\n1. Create a feature spec: \\`contractspec create --type=feature\\`\n2. Add operations: \\`contractspec create --type=operation\\`\n3. Add events if needed: \\`contractspec create --type=event\\`\n4. Build implementation: \\`contractspec build\\`\n\n### Contract Locations\n\n| Type | Location |\n|------|----------|\n| Operations | \\`${contractPath}operations/\\` |\n| Events | \\`${contractPath}events/\\` |\n| Presentations | \\`${contractPath}presentations/\\` |\n| Features | \\`${contractPath}features/\\` |\n\n## MCP Tools Available\n\nThe ContractSpec MCP server provides these tools:\n\n- \\`integrity.analyze\\` - Check contract health\n- \\`specs.list\\` - List all specs\n- \\`specs.validate\\` - Validate a spec file\n- \\`specs.create\\` - Create new specs\n- \\`deps.analyze\\` - Analyze dependencies\n\n## Common Tasks\n\n### Add a new API endpoint\n\n\\`\\`\\`bash\ncontractspec create --type=operation --name=myService.newAction\n\\`\\`\\`\n\n### Add a new event\n\n\\`\\`\\`bash\ncontractspec create --type=event --name=entity.changed\n\\`\\`\\`\n\n### Check contract integrity\n\n\\`\\`\\`bash\ncontractspec integrity\n\\`\\`\\`\n\n## Nested AGENTS.md\n\nMore specific instructions may exist in subdirectories. Check for \\`AGENTS.md\\` files in the relevant package or module.\n`;\n}\n\n/**\n * Get the file path for Claude Desktop config based on platform.\n */\nexport function getClaudeDesktopConfigPath(): string {\n const platform = process.platform;\n const homeDir = process.env['HOME'] ?? process.env['USERPROFILE'] ?? '';\n\n switch (platform) {\n case 'darwin':\n return `${homeDir}/Library/Application Support/Claude/claude_desktop_config.json`;\n case 'win32':\n return `${process.env['APPDATA'] ?? homeDir}/Claude/claude_desktop_config.json`;\n default:\n // Linux and others\n return `${homeDir}/.config/claude/claude_desktop_config.json`;\n }\n}\n"],"mappings":";;;;;;AAaA,SAAgB,0BAA0B,SAA+B;CAEvE,MAAM,iBAAiB,QAAQ,cAAc,QAAQ,UAAU;AAE/D,QAAO;EACL,SAAS;EACT,YAAY;EACZ,SAAS;EACT,WAAW;EAEX,WAAW;EACX,aAAa;GACX,YAAY;GACZ,QAAQ;GACR,eAAe;GACf,OAAO;GACP,UAAU;GACX;EACD,eAAe,QAAQ,iBAAiB,CAAC,QAAQ;EACjD,aAAa,EAAE;EAEf,GAAI,kBAAkB,QAAQ,cAC1B,EAAE,SAAS,QAAQ,aAAa,GAChC,EAAE;EACP;;;;;AAMH,SAAgB,yBAAiC;AAC/C,QAAO;EACL,mCAAmC;EACnC,0CAA0C;EAC1C,0CAA0C;EAC1C,iCAAiC;EACjC,yCAAyC;EACzC,sCAAsC;EACtC,kCAAkC;EAClC,sCAAsC;EACvC;;;;;AAMH,SAAgB,0BAAkC;AAChD,QAAO,EACL,YAAY,EACV,sBAAsB;EACpB,SAAS;EACT,MAAM,CAAC,mBAAmB;EAC3B,EACF,EACF;;;;;;AAOH,SAAgB,0BAAkC;AAChD,QAAO,EACL,YAAY,EACV,sBAAsB;EACpB,SAAS;EACT,MAAM,CAAC,mBAAmB;EAC3B,EACF,EACF;;;;;;;AAQH,SAAgB,oBAAoB,SAA+B;CACjE,MAAM,cAAc,QAAQ,eAAe;CAI3C,MAAM,WAHiB,QAAQ,cAAc,QAAQ,UAAU,aAI3C,QAAQ,cACtB,GAAG,QAAQ,YAAY,MAAM,IAAI,CAAC,MAAM,GAAG,CAAC,KAAK,IAAI,CAAC,kBACtD;AAMN,QAAO;;;;;;;;;EAJc,QAAQ,aACzB,+NACA,GAWS;;;;MAIT,SAAS;MACT,SAAS;MACT,SAAS;MACT,SAAS;;;;;;;;;;;;;;;;;;;;;;;;;;;;eA4BA,YAAY;;;;;;;;;;;;;AAc3B,SAAgB,iBAAiB,SAA+B;CAC9D,MAAM,cAAc,QAAQ,eAAe;CAC3C,MAAM,iBAAiB,QAAQ,cAAc,QAAQ,UAAU;CAG/D,MAAM,eAAe;AAuBrB,QAAO;;;;cAIK,YAAY;;;;;;;;;;;EAzBA,QAAQ,aAC5B;;;;;;;;;;;;;;;;EAgBJ,iBAAiB,+CAA+C,QAAQ,eAAe,QAAQ,YAAY,MAAM,8CAA8C;IAE3J,GAiBY;;;;;uCAKqB,aAAa;;;;;;;;;;;;;;;;mBAgBjC,aAAa;eACjB,aAAa;sBACN,aAAa;iBAClB,aAAa;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAyC9B,SAAgB,6BAAqC;CACnD,MAAM,WAAW,QAAQ;CACzB,MAAM,UAAU,QAAQ,IAAI,WAAW,QAAQ,IAAI,kBAAkB;AAErE,SAAQ,UAAR;EACE,KAAK,SACH,QAAO,GAAG,QAAQ;EACpB,KAAK,QACH,QAAO,GAAG,QAAQ,IAAI,cAAc,QAAQ;EAC9C,QAEE,QAAO,GAAG,QAAQ"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
//#region src/services/setup/file-merger.d.ts
|
|
2
|
+
/**
|
|
3
|
+
* File merger utilities.
|
|
4
|
+
*
|
|
5
|
+
* Deep-merges JSON files without losing user settings.
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Deep merge two objects, preserving existing user values.
|
|
9
|
+
* New keys are added, but existing keys are NOT overwritten.
|
|
10
|
+
*/
|
|
11
|
+
declare function deepMergePreserve<T extends Record<string, unknown>>(existing: T, defaults: T): T;
|
|
12
|
+
/**
|
|
13
|
+
* Deep merge two objects, with new values taking precedence.
|
|
14
|
+
* Used when we want to update existing configs.
|
|
15
|
+
*/
|
|
16
|
+
declare function deepMergeOverwrite<T extends Record<string, unknown>>(existing: T, updates: Partial<T>): T;
|
|
17
|
+
/**
|
|
18
|
+
* Parse JSON safely, returning null on failure.
|
|
19
|
+
*/
|
|
20
|
+
declare function safeParseJson<T>(content: string): T | null;
|
|
21
|
+
/**
|
|
22
|
+
* Format JSON with consistent indentation.
|
|
23
|
+
*/
|
|
24
|
+
declare function formatJson(obj: unknown): string;
|
|
25
|
+
//#endregion
|
|
26
|
+
export { deepMergeOverwrite, deepMergePreserve, formatJson, safeParseJson };
|
|
27
|
+
//# sourceMappingURL=file-merger.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"file-merger.d.ts","names":[],"sources":["../../../src/services/setup/file-merger.ts"],"sourcesContent":[],"mappings":";;AAUA;;;;;;AA8BA;;AACY,iBA/BI,iBA+BJ,CAAA,UA/BgC,MA+BhC,CAAA,MAAA,EAAA,OAAA,CAAA,CAAA,CAAA,QAAA,EA9BA,CA8BA,EAAA,QAAA,EA7BA,CA6BA,CAAA,EA5BT,CA4BS;;;;;AAyCI,iBA1CA,kBA0CoC,CAAA,UA1CP,MA0CO,CAAA,MAAA,EAAA,OAAA,CAAA,CAAA,CAAA,QAAA,EAzCxC,CAyCwC,EAAA,OAAA,EAxCzC,OAwCyC,CAxCjC,CAwCiC,CAAA,CAAA,EAvCjD,CAuCiD;AAWpD;;;iBAXgB,mCAAmC;;;;iBAWnC,UAAA"}
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
//#region src/services/setup/file-merger.ts
|
|
2
|
+
/**
|
|
3
|
+
* File merger utilities.
|
|
4
|
+
*
|
|
5
|
+
* Deep-merges JSON files without losing user settings.
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Deep merge two objects, preserving existing user values.
|
|
9
|
+
* New keys are added, but existing keys are NOT overwritten.
|
|
10
|
+
*/
|
|
11
|
+
function deepMergePreserve(existing, defaults) {
|
|
12
|
+
const result = { ...existing };
|
|
13
|
+
for (const key of Object.keys(defaults)) {
|
|
14
|
+
const existingValue = existing[key];
|
|
15
|
+
const defaultValue = defaults[key];
|
|
16
|
+
if (existingValue === void 0) result[key] = defaultValue;
|
|
17
|
+
else if (isPlainObject(existingValue) && isPlainObject(defaultValue)) result[key] = deepMergePreserve(existingValue, defaultValue);
|
|
18
|
+
}
|
|
19
|
+
return result;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Deep merge two objects, with new values taking precedence.
|
|
23
|
+
* Used when we want to update existing configs.
|
|
24
|
+
*/
|
|
25
|
+
function deepMergeOverwrite(existing, updates) {
|
|
26
|
+
const result = { ...existing };
|
|
27
|
+
for (const key of Object.keys(updates)) {
|
|
28
|
+
const existingValue = existing[key];
|
|
29
|
+
const updateValue = updates[key];
|
|
30
|
+
if (updateValue === void 0) continue;
|
|
31
|
+
if (isPlainObject(existingValue) && isPlainObject(updateValue)) result[key] = deepMergeOverwrite(existingValue, updateValue);
|
|
32
|
+
else result[key] = updateValue;
|
|
33
|
+
}
|
|
34
|
+
return result;
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Check if a value is a plain object (not array, null, or other).
|
|
38
|
+
*/
|
|
39
|
+
function isPlainObject(value) {
|
|
40
|
+
return typeof value === "object" && value !== null && !Array.isArray(value) && Object.getPrototypeOf(value) === Object.prototype;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Parse JSON safely, returning null on failure.
|
|
44
|
+
*/
|
|
45
|
+
function safeParseJson(content) {
|
|
46
|
+
try {
|
|
47
|
+
return JSON.parse(content);
|
|
48
|
+
} catch {
|
|
49
|
+
return null;
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Format JSON with consistent indentation.
|
|
54
|
+
*/
|
|
55
|
+
function formatJson(obj) {
|
|
56
|
+
return JSON.stringify(obj, null, 2) + "\n";
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
//#endregion
|
|
60
|
+
export { deepMergeOverwrite, deepMergePreserve, formatJson, safeParseJson };
|
|
61
|
+
//# sourceMappingURL=file-merger.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"file-merger.js","names":[],"sources":["../../../src/services/setup/file-merger.ts"],"sourcesContent":["/**\n * File merger utilities.\n *\n * Deep-merges JSON files without losing user settings.\n */\n\n/**\n * Deep merge two objects, preserving existing user values.\n * New keys are added, but existing keys are NOT overwritten.\n */\nexport function deepMergePreserve<T extends Record<string, unknown>>(\n existing: T,\n defaults: T\n): T {\n const result = { ...existing };\n\n for (const key of Object.keys(defaults)) {\n const existingValue = existing[key];\n const defaultValue = defaults[key];\n\n if (existingValue === undefined) {\n // Key doesn't exist in user config, add it\n (result as Record<string, unknown>)[key] = defaultValue;\n } else if (isPlainObject(existingValue) && isPlainObject(defaultValue)) {\n // Both are objects, recurse\n (result as Record<string, unknown>)[key] = deepMergePreserve(\n existingValue as Record<string, unknown>,\n defaultValue as Record<string, unknown>\n );\n }\n // If key exists and is not an object, keep user's value\n }\n\n return result;\n}\n\n/**\n * Deep merge two objects, with new values taking precedence.\n * Used when we want to update existing configs.\n */\nexport function deepMergeOverwrite<T extends Record<string, unknown>>(\n existing: T,\n updates: Partial<T>\n): T {\n const result = { ...existing };\n\n for (const key of Object.keys(updates)) {\n const existingValue = existing[key];\n const updateValue = updates[key];\n\n if (updateValue === undefined) {\n continue;\n }\n\n if (isPlainObject(existingValue) && isPlainObject(updateValue)) {\n (result as Record<string, unknown>)[key] = deepMergeOverwrite(\n existingValue as Record<string, unknown>,\n updateValue as Record<string, unknown>\n );\n } else {\n (result as Record<string, unknown>)[key] = updateValue;\n }\n }\n\n return result;\n}\n\n/**\n * Check if a value is a plain object (not array, null, or other).\n */\nfunction isPlainObject(value: unknown): value is Record<string, unknown> {\n return (\n typeof value === 'object' &&\n value !== null &&\n !Array.isArray(value) &&\n Object.getPrototypeOf(value) === Object.prototype\n );\n}\n\n/**\n * Parse JSON safely, returning null on failure.\n */\nexport function safeParseJson<T>(content: string): T | null {\n try {\n return JSON.parse(content) as T;\n } catch {\n return null;\n }\n}\n\n/**\n * Format JSON with consistent indentation.\n */\nexport function formatJson(obj: unknown): string {\n return JSON.stringify(obj, null, 2) + '\\n';\n}\n"],"mappings":";;;;;;;;;;AAUA,SAAgB,kBACd,UACA,UACG;CACH,MAAM,SAAS,EAAE,GAAG,UAAU;AAE9B,MAAK,MAAM,OAAO,OAAO,KAAK,SAAS,EAAE;EACvC,MAAM,gBAAgB,SAAS;EAC/B,MAAM,eAAe,SAAS;AAE9B,MAAI,kBAAkB,OAEpB,CAAC,OAAmC,OAAO;WAClC,cAAc,cAAc,IAAI,cAAc,aAAa,CAEpE,CAAC,OAAmC,OAAO,kBACzC,eACA,aACD;;AAKL,QAAO;;;;;;AAOT,SAAgB,mBACd,UACA,SACG;CACH,MAAM,SAAS,EAAE,GAAG,UAAU;AAE9B,MAAK,MAAM,OAAO,OAAO,KAAK,QAAQ,EAAE;EACtC,MAAM,gBAAgB,SAAS;EAC/B,MAAM,cAAc,QAAQ;AAE5B,MAAI,gBAAgB,OAClB;AAGF,MAAI,cAAc,cAAc,IAAI,cAAc,YAAY,CAC5D,CAAC,OAAmC,OAAO,mBACzC,eACA,YACD;MAED,CAAC,OAAmC,OAAO;;AAI/C,QAAO;;;;;AAMT,SAAS,cAAc,OAAkD;AACvE,QACE,OAAO,UAAU,YACjB,UAAU,QACV,CAAC,MAAM,QAAQ,MAAM,IACrB,OAAO,eAAe,MAAM,KAAK,OAAO;;;;;AAO5C,SAAgB,cAAiB,SAA2B;AAC1D,KAAI;AACF,SAAO,KAAK,MAAM,QAAQ;SACpB;AACN,SAAO;;;;;;AAOX,SAAgB,WAAW,KAAsB;AAC/C,QAAO,KAAK,UAAU,KAAK,MAAM,EAAE,GAAG"}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import { ALL_SETUP_TARGETS, SETUP_TARGET_LABELS } from "./types.js";
|
|
2
|
+
import { generateAgentsMd, generateClaudeMcpConfig, generateContractsrcConfig, generateCursorMcpConfig, generateCursorRules, generateVscodeSettings, getClaudeDesktopConfigPath } from "./config-generators.js";
|
|
3
|
+
import { deepMergeOverwrite, deepMergePreserve, formatJson, safeParseJson } from "./file-merger.js";
|
|
4
|
+
import { runSetup } from "./setup-service.js";
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { FsAdapter } from "../../ports/fs.js";
|
|
2
|
+
import { SetupOptions, SetupPromptCallbacks, SetupResult } from "./types.js";
|
|
3
|
+
|
|
4
|
+
//#region src/services/setup/setup-service.d.ts
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* Run the ContractSpec setup.
|
|
8
|
+
*/
|
|
9
|
+
declare function runSetup(fs: FsAdapter, options: SetupOptions, prompts?: SetupPromptCallbacks): Promise<SetupResult>;
|
|
10
|
+
//#endregion
|
|
11
|
+
export { runSetup };
|
|
12
|
+
//# sourceMappingURL=setup-service.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"setup-service.d.ts","names":[],"sources":["../../../src/services/setup/setup-service.ts"],"sourcesContent":[],"mappings":";;;;;;;;iBA6CsB,QAAA,KAChB,oBACK,wBACA,uBACR,QAAQ"}
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
import { findPackageRoot, findWorkspaceRoot, getPackageName, isMonorepo } from "../../adapters/workspace.js";
|
|
2
|
+
import { ALL_SETUP_TARGETS, SETUP_TARGET_LABELS } from "./types.js";
|
|
3
|
+
import { setupCliConfig } from "./targets/cli-config.js";
|
|
4
|
+
import { setupVscodeSettings } from "./targets/vscode-settings.js";
|
|
5
|
+
import { setupMcpCursor } from "./targets/mcp-cursor.js";
|
|
6
|
+
import { setupMcpClaude } from "./targets/mcp-claude.js";
|
|
7
|
+
import { setupCursorRules } from "./targets/cursor-rules.js";
|
|
8
|
+
import { setupAgentsMd } from "./targets/agents-md.js";
|
|
9
|
+
|
|
10
|
+
//#region src/services/setup/setup-service.ts
|
|
11
|
+
/**
|
|
12
|
+
* Default prompt callbacks that always accept defaults.
|
|
13
|
+
*/
|
|
14
|
+
const defaultPrompts = {
|
|
15
|
+
confirm: async () => true,
|
|
16
|
+
multiSelect: async (_msg, options) => options.filter((o) => o.selected !== false).map((o) => o.value),
|
|
17
|
+
input: async (_msg, defaultValue) => defaultValue ?? ""
|
|
18
|
+
};
|
|
19
|
+
/**
|
|
20
|
+
* Run the ContractSpec setup.
|
|
21
|
+
*/
|
|
22
|
+
async function runSetup(fs, options, prompts = defaultPrompts) {
|
|
23
|
+
const results = [];
|
|
24
|
+
const targets = options.targets.length > 0 ? options.targets : ALL_SETUP_TARGETS;
|
|
25
|
+
const workspaceRoot = options.workspaceRoot;
|
|
26
|
+
const detectedWorkspaceRoot = findWorkspaceRoot(workspaceRoot);
|
|
27
|
+
const packageRoot = options.packageRoot ?? findPackageRoot(workspaceRoot);
|
|
28
|
+
const monorepo = options.isMonorepo ?? isMonorepo(detectedWorkspaceRoot);
|
|
29
|
+
const packageName = options.packageName ?? (monorepo ? getPackageName(packageRoot) : void 0);
|
|
30
|
+
let scope = options.scope ?? "workspace";
|
|
31
|
+
const isDifferentRoots = packageRoot !== detectedWorkspaceRoot;
|
|
32
|
+
if (monorepo && options.interactive && isDifferentRoots) scope = (await prompts.multiSelect(`Monorepo detected. Configure at which level?`, [{
|
|
33
|
+
value: "package",
|
|
34
|
+
label: `Package level (${packageName ?? packageRoot})`,
|
|
35
|
+
selected: true
|
|
36
|
+
}, {
|
|
37
|
+
value: "workspace",
|
|
38
|
+
label: `Workspace level (${detectedWorkspaceRoot})`
|
|
39
|
+
}]))[0] ?? "package";
|
|
40
|
+
let selectedTargets = targets;
|
|
41
|
+
if (options.interactive) selectedTargets = await prompts.multiSelect("Select components to configure:", ALL_SETUP_TARGETS.map((t) => ({
|
|
42
|
+
value: t,
|
|
43
|
+
label: SETUP_TARGET_LABELS[t],
|
|
44
|
+
selected: targets.includes(t)
|
|
45
|
+
})));
|
|
46
|
+
let projectName = options.projectName;
|
|
47
|
+
if (options.interactive && !projectName) {
|
|
48
|
+
const defaultName = scope === "package" && packageName ? packageName : workspaceRoot.split("/").pop() ?? "my-project";
|
|
49
|
+
projectName = await prompts.input("Project name:", defaultName);
|
|
50
|
+
}
|
|
51
|
+
const setupOptions = {
|
|
52
|
+
...options,
|
|
53
|
+
workspaceRoot: detectedWorkspaceRoot,
|
|
54
|
+
packageRoot,
|
|
55
|
+
isMonorepo: monorepo,
|
|
56
|
+
scope,
|
|
57
|
+
packageName,
|
|
58
|
+
projectName,
|
|
59
|
+
targets: selectedTargets
|
|
60
|
+
};
|
|
61
|
+
for (const target of selectedTargets) {
|
|
62
|
+
const result = await setupTarget(fs, target, setupOptions, prompts);
|
|
63
|
+
results.push(result);
|
|
64
|
+
}
|
|
65
|
+
const succeeded = results.filter((r) => r.action !== "error").length;
|
|
66
|
+
const failed = results.filter((r) => r.action === "error").length;
|
|
67
|
+
const scopeInfo = monorepo ? ` (${scope} level)` : "";
|
|
68
|
+
return {
|
|
69
|
+
success: failed === 0,
|
|
70
|
+
files: results,
|
|
71
|
+
summary: `Setup complete${scopeInfo}: ${succeeded} configured, ${failed} failed.`
|
|
72
|
+
};
|
|
73
|
+
}
|
|
74
|
+
/**
|
|
75
|
+
* Setup a single target.
|
|
76
|
+
*/
|
|
77
|
+
async function setupTarget(fs, target, options, prompts) {
|
|
78
|
+
switch (target) {
|
|
79
|
+
case "cli-config": return setupCliConfig(fs, options, prompts);
|
|
80
|
+
case "vscode-settings": return setupVscodeSettings(fs, options, prompts);
|
|
81
|
+
case "mcp-cursor": return setupMcpCursor(fs, options, prompts);
|
|
82
|
+
case "mcp-claude": return setupMcpClaude(fs, options, prompts);
|
|
83
|
+
case "cursor-rules": return setupCursorRules(fs, options, prompts);
|
|
84
|
+
case "agents-md": return setupAgentsMd(fs, options, prompts);
|
|
85
|
+
default: return {
|
|
86
|
+
target,
|
|
87
|
+
filePath: "",
|
|
88
|
+
action: "error",
|
|
89
|
+
message: `Unknown target: ${target}`
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
//#endregion
|
|
95
|
+
export { runSetup };
|
|
96
|
+
//# sourceMappingURL=setup-service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"setup-service.js","names":["defaultPrompts: SetupPromptCallbacks","results: SetupFileResult[]","scope: SetupScope","setupOptions: SetupOptions"],"sources":["../../../src/services/setup/setup-service.ts"],"sourcesContent":["/**\n * Setup service.\n *\n * Orchestrates the full ContractSpec setup flow.\n * Supports both single projects and monorepos.\n */\n\nimport type { FsAdapter } from '../../ports/fs';\nimport type {\n SetupOptions,\n SetupResult,\n SetupFileResult,\n SetupTarget,\n SetupPromptCallbacks,\n SetupScope,\n} from './types';\nimport { ALL_SETUP_TARGETS, SETUP_TARGET_LABELS } from './types';\nimport {\n setupCliConfig,\n setupVscodeSettings,\n setupMcpCursor,\n setupMcpClaude,\n setupCursorRules,\n setupAgentsMd,\n} from './targets/index';\nimport {\n findPackageRoot,\n findWorkspaceRoot,\n isMonorepo,\n getPackageName,\n} from '../../adapters/workspace';\n\n/**\n * Default prompt callbacks that always accept defaults.\n */\nconst defaultPrompts: SetupPromptCallbacks = {\n confirm: async () => true,\n multiSelect: async (_msg, options) =>\n options.filter((o) => o.selected !== false).map((o) => o.value),\n input: async (_msg, defaultValue) => defaultValue ?? '',\n};\n\n/**\n * Run the ContractSpec setup.\n */\nexport async function runSetup(\n fs: FsAdapter,\n options: SetupOptions,\n prompts: SetupPromptCallbacks = defaultPrompts\n): Promise<SetupResult> {\n const results: SetupFileResult[] = [];\n const targets =\n options.targets.length > 0 ? options.targets : ALL_SETUP_TARGETS;\n\n // Detect monorepo context if not already provided\n const workspaceRoot = options.workspaceRoot;\n const detectedWorkspaceRoot = findWorkspaceRoot(workspaceRoot);\n const packageRoot = options.packageRoot ?? findPackageRoot(workspaceRoot);\n const monorepo = options.isMonorepo ?? isMonorepo(detectedWorkspaceRoot);\n const packageName =\n options.packageName ?? (monorepo ? getPackageName(packageRoot) : undefined);\n\n // Determine scope\n let scope: SetupScope = options.scope ?? 'workspace';\n const isDifferentRoots = packageRoot !== detectedWorkspaceRoot;\n\n // If in a monorepo and interactive, prompt for scope\n if (monorepo && options.interactive && isDifferentRoots) {\n const scopeChoice = await prompts.multiSelect<SetupScope>(\n `Monorepo detected. Configure at which level?`,\n [\n {\n value: 'package',\n label: `Package level (${packageName ?? packageRoot})`,\n selected: true,\n },\n {\n value: 'workspace',\n label: `Workspace level (${detectedWorkspaceRoot})`,\n },\n ]\n );\n scope = scopeChoice[0] ?? 'package';\n }\n\n // If interactive, prompt for target selection\n let selectedTargets = targets;\n if (options.interactive) {\n selectedTargets = await prompts.multiSelect(\n 'Select components to configure:',\n ALL_SETUP_TARGETS.map((t) => ({\n value: t,\n label: SETUP_TARGET_LABELS[t],\n selected: targets.includes(t),\n }))\n );\n }\n\n // Get project name if interactive\n let projectName = options.projectName;\n if (options.interactive && !projectName) {\n const defaultName =\n scope === 'package' && packageName\n ? packageName\n : (workspaceRoot.split('/').pop() ?? 'my-project');\n projectName = await prompts.input('Project name:', defaultName);\n }\n\n const setupOptions: SetupOptions = {\n ...options,\n workspaceRoot: detectedWorkspaceRoot,\n packageRoot,\n isMonorepo: monorepo,\n scope,\n packageName,\n projectName,\n targets: selectedTargets,\n };\n\n // Run each target setup\n for (const target of selectedTargets) {\n const result = await setupTarget(fs, target, setupOptions, prompts);\n results.push(result);\n }\n\n const succeeded = results.filter((r) => r.action !== 'error').length;\n const failed = results.filter((r) => r.action === 'error').length;\n\n const scopeInfo = monorepo ? ` (${scope} level)` : '';\n return {\n success: failed === 0,\n files: results,\n summary: `Setup complete${scopeInfo}: ${succeeded} configured, ${failed} failed.`,\n };\n}\n\n/**\n * Setup a single target.\n */\nasync function setupTarget(\n fs: FsAdapter,\n target: SetupTarget,\n options: SetupOptions,\n prompts: SetupPromptCallbacks\n): Promise<SetupFileResult> {\n switch (target) {\n case 'cli-config':\n return setupCliConfig(fs, options, prompts);\n case 'vscode-settings':\n return setupVscodeSettings(fs, options, prompts);\n case 'mcp-cursor':\n return setupMcpCursor(fs, options, prompts);\n case 'mcp-claude':\n return setupMcpClaude(fs, options, prompts);\n case 'cursor-rules':\n return setupCursorRules(fs, options, prompts);\n case 'agents-md':\n return setupAgentsMd(fs, options, prompts);\n default:\n return {\n target,\n filePath: '',\n action: 'error',\n message: `Unknown target: ${target}`,\n };\n }\n}\n"],"mappings":";;;;;;;;;;;;;AAmCA,MAAMA,iBAAuC;CAC3C,SAAS,YAAY;CACrB,aAAa,OAAO,MAAM,YACxB,QAAQ,QAAQ,MAAM,EAAE,aAAa,MAAM,CAAC,KAAK,MAAM,EAAE,MAAM;CACjE,OAAO,OAAO,MAAM,iBAAiB,gBAAgB;CACtD;;;;AAKD,eAAsB,SACpB,IACA,SACA,UAAgC,gBACV;CACtB,MAAMC,UAA6B,EAAE;CACrC,MAAM,UACJ,QAAQ,QAAQ,SAAS,IAAI,QAAQ,UAAU;CAGjD,MAAM,gBAAgB,QAAQ;CAC9B,MAAM,wBAAwB,kBAAkB,cAAc;CAC9D,MAAM,cAAc,QAAQ,eAAe,gBAAgB,cAAc;CACzE,MAAM,WAAW,QAAQ,cAAc,WAAW,sBAAsB;CACxE,MAAM,cACJ,QAAQ,gBAAgB,WAAW,eAAe,YAAY,GAAG;CAGnE,IAAIC,QAAoB,QAAQ,SAAS;CACzC,MAAM,mBAAmB,gBAAgB;AAGzC,KAAI,YAAY,QAAQ,eAAe,iBAerC,UAdoB,MAAM,QAAQ,YAChC,gDACA,CACE;EACE,OAAO;EACP,OAAO,kBAAkB,eAAe,YAAY;EACpD,UAAU;EACX,EACD;EACE,OAAO;EACP,OAAO,oBAAoB,sBAAsB;EAClD,CACF,CACF,EACmB,MAAM;CAI5B,IAAI,kBAAkB;AACtB,KAAI,QAAQ,YACV,mBAAkB,MAAM,QAAQ,YAC9B,mCACA,kBAAkB,KAAK,OAAO;EAC5B,OAAO;EACP,OAAO,oBAAoB;EAC3B,UAAU,QAAQ,SAAS,EAAE;EAC9B,EAAE,CACJ;CAIH,IAAI,cAAc,QAAQ;AAC1B,KAAI,QAAQ,eAAe,CAAC,aAAa;EACvC,MAAM,cACJ,UAAU,aAAa,cACnB,cACC,cAAc,MAAM,IAAI,CAAC,KAAK,IAAI;AACzC,gBAAc,MAAM,QAAQ,MAAM,iBAAiB,YAAY;;CAGjE,MAAMC,eAA6B;EACjC,GAAG;EACH,eAAe;EACf;EACA,YAAY;EACZ;EACA;EACA;EACA,SAAS;EACV;AAGD,MAAK,MAAM,UAAU,iBAAiB;EACpC,MAAM,SAAS,MAAM,YAAY,IAAI,QAAQ,cAAc,QAAQ;AACnE,UAAQ,KAAK,OAAO;;CAGtB,MAAM,YAAY,QAAQ,QAAQ,MAAM,EAAE,WAAW,QAAQ,CAAC;CAC9D,MAAM,SAAS,QAAQ,QAAQ,MAAM,EAAE,WAAW,QAAQ,CAAC;CAE3D,MAAM,YAAY,WAAW,KAAK,MAAM,WAAW;AACnD,QAAO;EACL,SAAS,WAAW;EACpB,OAAO;EACP,SAAS,iBAAiB,UAAU,IAAI,UAAU,eAAe,OAAO;EACzE;;;;;AAMH,eAAe,YACb,IACA,QACA,SACA,SAC0B;AAC1B,SAAQ,QAAR;EACE,KAAK,aACH,QAAO,eAAe,IAAI,SAAS,QAAQ;EAC7C,KAAK,kBACH,QAAO,oBAAoB,IAAI,SAAS,QAAQ;EAClD,KAAK,aACH,QAAO,eAAe,IAAI,SAAS,QAAQ;EAC7C,KAAK,aACH,QAAO,eAAe,IAAI,SAAS,QAAQ;EAC7C,KAAK,eACH,QAAO,iBAAiB,IAAI,SAAS,QAAQ;EAC/C,KAAK,YACH,QAAO,cAAc,IAAI,SAAS,QAAQ;EAC5C,QACE,QAAO;GACL;GACA,UAAU;GACV,QAAQ;GACR,SAAS,mBAAmB;GAC7B"}
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import { generateAgentsMd } from "../config-generators.js";
|
|
2
|
+
|
|
3
|
+
//#region src/services/setup/targets/agents-md.ts
|
|
4
|
+
/**
|
|
5
|
+
* Setup AGENTS.md
|
|
6
|
+
*
|
|
7
|
+
* In monorepo with package scope, creates AGENTS.md at package root.
|
|
8
|
+
*/
|
|
9
|
+
async function setupAgentsMd(fs, options, prompts) {
|
|
10
|
+
const targetRoot = options.isMonorepo && options.scope === "package" ? options.packageRoot ?? options.workspaceRoot : options.workspaceRoot;
|
|
11
|
+
const filePath = fs.join(targetRoot, "AGENTS.md");
|
|
12
|
+
try {
|
|
13
|
+
const exists = await fs.exists(filePath);
|
|
14
|
+
const content = generateAgentsMd(options);
|
|
15
|
+
if (exists) if (options.interactive) {
|
|
16
|
+
if (!await prompts.confirm(`${filePath} exists. Overwrite?`)) return {
|
|
17
|
+
target: "agents-md",
|
|
18
|
+
filePath,
|
|
19
|
+
action: "skipped",
|
|
20
|
+
message: "User kept existing AGENTS.md"
|
|
21
|
+
};
|
|
22
|
+
} else return {
|
|
23
|
+
target: "agents-md",
|
|
24
|
+
filePath,
|
|
25
|
+
action: "skipped",
|
|
26
|
+
message: "File already exists"
|
|
27
|
+
};
|
|
28
|
+
await fs.writeFile(filePath, content);
|
|
29
|
+
return {
|
|
30
|
+
target: "agents-md",
|
|
31
|
+
filePath,
|
|
32
|
+
action: exists ? "merged" : "created",
|
|
33
|
+
message: exists ? "Updated AGENTS.md" : "Created AGENTS.md"
|
|
34
|
+
};
|
|
35
|
+
} catch (error) {
|
|
36
|
+
return {
|
|
37
|
+
target: "agents-md",
|
|
38
|
+
filePath,
|
|
39
|
+
action: "error",
|
|
40
|
+
message: error instanceof Error ? error.message : "Unknown error"
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
//#endregion
|
|
46
|
+
export { setupAgentsMd };
|
|
47
|
+
//# sourceMappingURL=agents-md.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"agents-md.js","names":[],"sources":["../../../../src/services/setup/targets/agents-md.ts"],"sourcesContent":["/**\n * AGENTS.md setup target.\n */\n\nimport type { FsAdapter } from '../../../ports/fs';\nimport type {\n SetupOptions,\n SetupFileResult,\n SetupPromptCallbacks,\n} from '../types';\nimport { generateAgentsMd } from '../config-generators';\n\n/**\n * Setup AGENTS.md\n *\n * In monorepo with package scope, creates AGENTS.md at package root.\n */\nexport async function setupAgentsMd(\n fs: FsAdapter,\n options: SetupOptions,\n prompts: SetupPromptCallbacks\n): Promise<SetupFileResult> {\n // Determine target root based on scope\n const targetRoot =\n options.isMonorepo && options.scope === 'package'\n ? (options.packageRoot ?? options.workspaceRoot)\n : options.workspaceRoot;\n\n const filePath = fs.join(targetRoot, 'AGENTS.md');\n\n try {\n const exists = await fs.exists(filePath);\n const content = generateAgentsMd(options);\n\n if (exists) {\n if (options.interactive) {\n const proceed = await prompts.confirm(`${filePath} exists. Overwrite?`);\n if (!proceed) {\n return {\n target: 'agents-md',\n filePath,\n action: 'skipped',\n message: 'User kept existing AGENTS.md',\n };\n }\n } else {\n // Non-interactive: skip existing file\n return {\n target: 'agents-md',\n filePath,\n action: 'skipped',\n message: 'File already exists',\n };\n }\n }\n\n await fs.writeFile(filePath, content);\n return {\n target: 'agents-md',\n filePath,\n action: exists ? 'merged' : 'created',\n message: exists ? 'Updated AGENTS.md' : 'Created AGENTS.md',\n };\n } catch (error) {\n return {\n target: 'agents-md',\n filePath,\n action: 'error',\n message: error instanceof Error ? error.message : 'Unknown error',\n };\n }\n}\n"],"mappings":";;;;;;;;AAiBA,eAAsB,cACpB,IACA,SACA,SAC0B;CAE1B,MAAM,aACJ,QAAQ,cAAc,QAAQ,UAAU,YACnC,QAAQ,eAAe,QAAQ,gBAChC,QAAQ;CAEd,MAAM,WAAW,GAAG,KAAK,YAAY,YAAY;AAEjD,KAAI;EACF,MAAM,SAAS,MAAM,GAAG,OAAO,SAAS;EACxC,MAAM,UAAU,iBAAiB,QAAQ;AAEzC,MAAI,OACF,KAAI,QAAQ,aAEV;OAAI,CADY,MAAM,QAAQ,QAAQ,GAAG,SAAS,qBAAqB,CAErE,QAAO;IACL,QAAQ;IACR;IACA,QAAQ;IACR,SAAS;IACV;QAIH,QAAO;GACL,QAAQ;GACR;GACA,QAAQ;GACR,SAAS;GACV;AAIL,QAAM,GAAG,UAAU,UAAU,QAAQ;AACrC,SAAO;GACL,QAAQ;GACR;GACA,QAAQ,SAAS,WAAW;GAC5B,SAAS,SAAS,sBAAsB;GACzC;UACM,OAAO;AACd,SAAO;GACL,QAAQ;GACR;GACA,QAAQ;GACR,SAAS,iBAAiB,QAAQ,MAAM,UAAU;GACnD"}
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
import { generateContractsrcConfig } from "../config-generators.js";
|
|
2
|
+
import { deepMergePreserve, formatJson, safeParseJson } from "../file-merger.js";
|
|
3
|
+
|
|
4
|
+
//#region src/services/setup/targets/cli-config.ts
|
|
5
|
+
/**
|
|
6
|
+
* Setup .contractsrc.json
|
|
7
|
+
*
|
|
8
|
+
* In monorepo with package scope, creates config at package root.
|
|
9
|
+
*/
|
|
10
|
+
async function setupCliConfig(fs, options, prompts) {
|
|
11
|
+
const targetRoot = options.isMonorepo && options.scope === "package" ? options.packageRoot ?? options.workspaceRoot : options.workspaceRoot;
|
|
12
|
+
const filePath = fs.join(targetRoot, ".contractsrc.json");
|
|
13
|
+
try {
|
|
14
|
+
const exists = await fs.exists(filePath);
|
|
15
|
+
const defaults = generateContractsrcConfig(options);
|
|
16
|
+
if (exists) {
|
|
17
|
+
const existing = safeParseJson(await fs.readFile(filePath));
|
|
18
|
+
if (!existing) return {
|
|
19
|
+
target: "cli-config",
|
|
20
|
+
filePath,
|
|
21
|
+
action: "error",
|
|
22
|
+
message: "Existing file is not valid JSON"
|
|
23
|
+
};
|
|
24
|
+
if (options.interactive) {
|
|
25
|
+
if (!await prompts.confirm(`${filePath} exists. Merge ContractSpec defaults?`)) return {
|
|
26
|
+
target: "cli-config",
|
|
27
|
+
filePath,
|
|
28
|
+
action: "skipped",
|
|
29
|
+
message: "User skipped merge"
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
const merged = deepMergePreserve(existing, defaults);
|
|
33
|
+
await fs.writeFile(filePath, formatJson(merged));
|
|
34
|
+
return {
|
|
35
|
+
target: "cli-config",
|
|
36
|
+
filePath,
|
|
37
|
+
action: "merged",
|
|
38
|
+
message: "Merged with existing configuration"
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
await fs.writeFile(filePath, formatJson(defaults));
|
|
42
|
+
return {
|
|
43
|
+
target: "cli-config",
|
|
44
|
+
filePath,
|
|
45
|
+
action: "created",
|
|
46
|
+
message: "Created CLI configuration"
|
|
47
|
+
};
|
|
48
|
+
} catch (error) {
|
|
49
|
+
return {
|
|
50
|
+
target: "cli-config",
|
|
51
|
+
filePath,
|
|
52
|
+
action: "error",
|
|
53
|
+
message: error instanceof Error ? error.message : "Unknown error"
|
|
54
|
+
};
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
//#endregion
|
|
59
|
+
export { setupCliConfig };
|
|
60
|
+
//# sourceMappingURL=cli-config.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cli-config.js","names":[],"sources":["../../../../src/services/setup/targets/cli-config.ts"],"sourcesContent":["/**\n * CLI config setup target.\n */\n\nimport type { FsAdapter } from '../../../ports/fs';\nimport type {\n SetupOptions,\n SetupFileResult,\n SetupPromptCallbacks,\n} from '../types';\nimport { generateContractsrcConfig } from '../config-generators';\nimport { deepMergePreserve, safeParseJson, formatJson } from '../file-merger';\n\n/**\n * Setup .contractsrc.json\n *\n * In monorepo with package scope, creates config at package root.\n */\nexport async function setupCliConfig(\n fs: FsAdapter,\n options: SetupOptions,\n prompts: SetupPromptCallbacks\n): Promise<SetupFileResult> {\n // Determine target root based on scope\n const targetRoot =\n options.isMonorepo && options.scope === 'package'\n ? (options.packageRoot ?? options.workspaceRoot)\n : options.workspaceRoot;\n\n const filePath = fs.join(targetRoot, '.contractsrc.json');\n\n try {\n const exists = await fs.exists(filePath);\n const defaults = generateContractsrcConfig(options);\n\n if (exists) {\n const content = await fs.readFile(filePath);\n const existing = safeParseJson<Record<string, unknown>>(content);\n\n if (!existing) {\n return {\n target: 'cli-config',\n filePath,\n action: 'error',\n message: 'Existing file is not valid JSON',\n };\n }\n\n if (options.interactive) {\n const proceed = await prompts.confirm(\n `${filePath} exists. Merge ContractSpec defaults?`\n );\n if (!proceed) {\n return {\n target: 'cli-config',\n filePath,\n action: 'skipped',\n message: 'User skipped merge',\n };\n }\n }\n\n const merged = deepMergePreserve(\n existing,\n defaults as Record<string, unknown>\n );\n await fs.writeFile(filePath, formatJson(merged));\n\n return {\n target: 'cli-config',\n filePath,\n action: 'merged',\n message: 'Merged with existing configuration',\n };\n }\n\n await fs.writeFile(filePath, formatJson(defaults));\n return {\n target: 'cli-config',\n filePath,\n action: 'created',\n message: 'Created CLI configuration',\n };\n } catch (error) {\n return {\n target: 'cli-config',\n filePath,\n action: 'error',\n message: error instanceof Error ? error.message : 'Unknown error',\n };\n }\n}\n"],"mappings":";;;;;;;;;AAkBA,eAAsB,eACpB,IACA,SACA,SAC0B;CAE1B,MAAM,aACJ,QAAQ,cAAc,QAAQ,UAAU,YACnC,QAAQ,eAAe,QAAQ,gBAChC,QAAQ;CAEd,MAAM,WAAW,GAAG,KAAK,YAAY,oBAAoB;AAEzD,KAAI;EACF,MAAM,SAAS,MAAM,GAAG,OAAO,SAAS;EACxC,MAAM,WAAW,0BAA0B,QAAQ;AAEnD,MAAI,QAAQ;GAEV,MAAM,WAAW,cADD,MAAM,GAAG,SAAS,SAAS,CACqB;AAEhE,OAAI,CAAC,SACH,QAAO;IACL,QAAQ;IACR;IACA,QAAQ;IACR,SAAS;IACV;AAGH,OAAI,QAAQ,aAIV;QAAI,CAHY,MAAM,QAAQ,QAC5B,GAAG,SAAS,uCACb,CAEC,QAAO;KACL,QAAQ;KACR;KACA,QAAQ;KACR,SAAS;KACV;;GAIL,MAAM,SAAS,kBACb,UACA,SACD;AACD,SAAM,GAAG,UAAU,UAAU,WAAW,OAAO,CAAC;AAEhD,UAAO;IACL,QAAQ;IACR;IACA,QAAQ;IACR,SAAS;IACV;;AAGH,QAAM,GAAG,UAAU,UAAU,WAAW,SAAS,CAAC;AAClD,SAAO;GACL,QAAQ;GACR;GACA,QAAQ;GACR,SAAS;GACV;UACM,OAAO;AACd,SAAO;GACL,QAAQ;GACR;GACA,QAAQ;GACR,SAAS,iBAAiB,QAAQ,MAAM,UAAU;GACnD"}
|