specweave 0.10.1 → 0.12.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/.claude-plugin/marketplace.json +3 -3
- package/CLAUDE.md +184 -288
- package/README.md +48 -21
- package/dist/cli/commands/init.d.ts.map +1 -1
- package/dist/cli/commands/init.js +75 -113
- package/dist/cli/commands/init.js.map +1 -1
- package/dist/cli/helpers/issue-tracker/index.d.ts.map +1 -1
- package/dist/cli/helpers/issue-tracker/index.js +39 -0
- package/dist/cli/helpers/issue-tracker/index.js.map +1 -1
- package/dist/cli/helpers/issue-tracker/jira.d.ts.map +1 -1
- package/dist/cli/helpers/issue-tracker/jira.js +2 -9
- package/dist/cli/helpers/issue-tracker/jira.js.map +1 -1
- package/dist/hooks/lib/git-diff-analyzer.d.ts +89 -0
- package/dist/hooks/lib/git-diff-analyzer.d.ts.map +1 -0
- package/dist/hooks/lib/git-diff-analyzer.js +226 -0
- package/dist/hooks/lib/git-diff-analyzer.js.map +1 -0
- package/dist/hooks/lib/prepare-reflection-context.d.ts +42 -0
- package/dist/hooks/lib/prepare-reflection-context.d.ts.map +1 -0
- package/dist/hooks/lib/prepare-reflection-context.js +123 -0
- package/dist/hooks/lib/prepare-reflection-context.js.map +1 -0
- package/dist/hooks/lib/reflection-config-loader.d.ts +45 -0
- package/dist/hooks/lib/reflection-config-loader.d.ts.map +1 -0
- package/dist/hooks/lib/reflection-config-loader.js +132 -0
- package/dist/hooks/lib/reflection-config-loader.js.map +1 -0
- package/dist/hooks/lib/reflection-parser.d.ts +33 -0
- package/dist/hooks/lib/reflection-parser.d.ts.map +1 -0
- package/dist/hooks/lib/reflection-parser.js +419 -0
- package/dist/hooks/lib/reflection-parser.js.map +1 -0
- package/dist/hooks/lib/reflection-prompt-builder.d.ts +56 -0
- package/dist/hooks/lib/reflection-prompt-builder.d.ts.map +1 -0
- package/dist/hooks/lib/reflection-prompt-builder.js +239 -0
- package/dist/hooks/lib/reflection-prompt-builder.js.map +1 -0
- package/dist/hooks/lib/reflection-storage.d.ts +64 -0
- package/dist/hooks/lib/reflection-storage.d.ts.map +1 -0
- package/dist/hooks/lib/reflection-storage.js +305 -0
- package/dist/hooks/lib/reflection-storage.js.map +1 -0
- package/dist/hooks/lib/run-self-reflection.d.ts +43 -0
- package/dist/hooks/lib/run-self-reflection.d.ts.map +1 -0
- package/dist/hooks/lib/run-self-reflection.js +203 -0
- package/dist/hooks/lib/run-self-reflection.js.map +1 -0
- package/dist/hooks/lib/types/reflection-types.d.ts +164 -0
- package/dist/hooks/lib/types/reflection-types.d.ts.map +1 -0
- package/dist/hooks/lib/types/reflection-types.js +73 -0
- package/dist/hooks/lib/types/reflection-types.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/git-diff-analyzer.d.ts +89 -0
- package/dist/plugins/specweave/lib/hooks/git-diff-analyzer.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/git-diff-analyzer.js +226 -0
- package/dist/plugins/specweave/lib/hooks/git-diff-analyzer.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/invoke-translator-skill.d.ts +60 -0
- package/dist/plugins/specweave/lib/hooks/invoke-translator-skill.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/invoke-translator-skill.js +201 -0
- package/dist/plugins/specweave/lib/hooks/invoke-translator-skill.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/prepare-reflection-context.d.ts +42 -0
- package/dist/plugins/specweave/lib/hooks/prepare-reflection-context.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/prepare-reflection-context.js +123 -0
- package/dist/plugins/specweave/lib/hooks/prepare-reflection-context.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/reflection-config-loader.d.ts +45 -0
- package/dist/plugins/specweave/lib/hooks/reflection-config-loader.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/reflection-config-loader.js +132 -0
- package/dist/plugins/specweave/lib/hooks/reflection-config-loader.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/reflection-parser.d.ts +33 -0
- package/dist/plugins/specweave/lib/hooks/reflection-parser.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/reflection-parser.js +419 -0
- package/dist/plugins/specweave/lib/hooks/reflection-parser.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/reflection-prompt-builder.d.ts +56 -0
- package/dist/plugins/specweave/lib/hooks/reflection-prompt-builder.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/reflection-prompt-builder.js +239 -0
- package/dist/plugins/specweave/lib/hooks/reflection-prompt-builder.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/reflection-storage.d.ts +64 -0
- package/dist/plugins/specweave/lib/hooks/reflection-storage.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/reflection-storage.js +305 -0
- package/dist/plugins/specweave/lib/hooks/reflection-storage.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/run-self-reflection.d.ts +43 -0
- package/dist/plugins/specweave/lib/hooks/run-self-reflection.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/run-self-reflection.js +203 -0
- package/dist/plugins/specweave/lib/hooks/run-self-reflection.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/sync-living-docs.d.ts +27 -0
- package/dist/plugins/specweave/lib/hooks/sync-living-docs.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/sync-living-docs.js +116 -0
- package/dist/plugins/specweave/lib/hooks/sync-living-docs.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/translate-file.d.ts +59 -0
- package/dist/plugins/specweave/lib/hooks/translate-file.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/translate-file.js +350 -0
- package/dist/plugins/specweave/lib/hooks/translate-file.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/translate-living-docs.d.ts +13 -0
- package/dist/plugins/specweave/lib/hooks/translate-living-docs.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/translate-living-docs.js +175 -0
- package/dist/plugins/specweave/lib/hooks/translate-living-docs.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/types/reflection-types.d.ts +164 -0
- package/dist/plugins/specweave/lib/hooks/types/reflection-types.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/types/reflection-types.js +73 -0
- package/dist/plugins/specweave/lib/hooks/types/reflection-types.js.map +1 -0
- package/dist/plugins/specweave/lib/hooks/update-tasks-md.d.ts +29 -0
- package/dist/plugins/specweave/lib/hooks/update-tasks-md.d.ts.map +1 -0
- package/dist/plugins/specweave/lib/hooks/update-tasks-md.js +203 -0
- package/dist/plugins/specweave/lib/hooks/update-tasks-md.js.map +1 -0
- package/dist/plugins/specweave-ado/lib/ado-board-resolver.d.ts +94 -0
- package/dist/plugins/specweave-ado/lib/ado-board-resolver.d.ts.map +1 -0
- package/dist/plugins/specweave-ado/lib/ado-board-resolver.js +219 -0
- package/dist/plugins/specweave-ado/lib/ado-board-resolver.js.map +1 -0
- package/dist/plugins/specweave-ado/lib/ado-client-v2.d.ts +124 -0
- package/dist/plugins/specweave-ado/lib/ado-client-v2.d.ts.map +1 -0
- package/dist/plugins/specweave-ado/lib/ado-client-v2.js +382 -0
- package/dist/plugins/specweave-ado/lib/ado-client-v2.js.map +1 -0
- package/dist/plugins/specweave-ado/lib/ado-client.d.ts +112 -0
- package/dist/plugins/specweave-ado/lib/ado-client.d.ts.map +1 -0
- package/dist/plugins/specweave-ado/lib/ado-client.js +257 -0
- package/dist/plugins/specweave-ado/lib/ado-client.js.map +1 -0
- package/dist/plugins/specweave-ado/lib/ado-hierarchical-sync.d.ts +40 -0
- package/dist/plugins/specweave-ado/lib/ado-hierarchical-sync.d.ts.map +1 -0
- package/dist/plugins/specweave-ado/lib/ado-hierarchical-sync.js +370 -0
- package/dist/plugins/specweave-ado/lib/ado-hierarchical-sync.js.map +1 -0
- package/dist/plugins/specweave-ado/lib/project-selector.d.ts +42 -0
- package/dist/plugins/specweave-ado/lib/project-selector.d.ts.map +1 -0
- package/dist/plugins/specweave-ado/lib/project-selector.js +211 -0
- package/dist/plugins/specweave-ado/lib/project-selector.js.map +1 -0
- package/dist/plugins/specweave-github/lib/github-board-resolver.d.ts +54 -0
- package/dist/plugins/specweave-github/lib/github-board-resolver.d.ts.map +1 -0
- package/dist/plugins/specweave-github/lib/github-board-resolver.js +122 -0
- package/dist/plugins/specweave-github/lib/github-board-resolver.js.map +1 -0
- package/dist/plugins/specweave-github/lib/github-client-v2.d.ts +104 -0
- package/dist/plugins/specweave-github/lib/github-client-v2.d.ts.map +1 -0
- package/dist/plugins/specweave-github/lib/github-client-v2.js +408 -0
- package/dist/plugins/specweave-github/lib/github-client-v2.js.map +1 -0
- package/dist/plugins/specweave-github/lib/github-client.d.ts +10 -0
- package/dist/plugins/specweave-github/lib/github-client.d.ts.map +1 -1
- package/dist/plugins/specweave-github/lib/github-client.js +24 -0
- package/dist/plugins/specweave-github/lib/github-client.js.map +1 -1
- package/dist/plugins/specweave-github/lib/github-hierarchical-sync.d.ts +29 -0
- package/dist/plugins/specweave-github/lib/github-hierarchical-sync.d.ts.map +1 -0
- package/dist/plugins/specweave-github/lib/github-hierarchical-sync.js +268 -0
- package/dist/plugins/specweave-github/lib/github-hierarchical-sync.js.map +1 -0
- package/dist/plugins/specweave-github/lib/index.d.ts.map +1 -1
- package/dist/plugins/specweave-github/lib/index.js.map +1 -1
- package/dist/plugins/specweave-github/lib/repo-selector.d.ts +49 -0
- package/dist/plugins/specweave-github/lib/repo-selector.d.ts.map +1 -0
- package/dist/plugins/specweave-github/lib/repo-selector.js +216 -0
- package/dist/plugins/specweave-github/lib/repo-selector.js.map +1 -0
- package/dist/plugins/specweave-github/lib/subtask-sync.d.ts.map +1 -1
- package/dist/plugins/specweave-github/lib/subtask-sync.js.map +1 -1
- package/dist/plugins/specweave-github/lib/task-parser.d.ts.map +1 -1
- package/dist/plugins/specweave-github/lib/task-parser.js.map +1 -1
- package/dist/plugins/specweave-github/lib/task-sync.d.ts.map +1 -1
- package/dist/plugins/specweave-github/lib/task-sync.js.map +1 -1
- package/dist/plugins/specweave-github/lib/types.d.ts.map +1 -1
- package/dist/plugins/specweave-github/lib/types.js.map +1 -1
- package/dist/plugins/specweave-jira/lib/jira-board-resolver.d.ts +50 -0
- package/dist/plugins/specweave-jira/lib/jira-board-resolver.d.ts.map +1 -0
- package/dist/plugins/specweave-jira/lib/jira-board-resolver.js +84 -0
- package/dist/plugins/specweave-jira/lib/jira-board-resolver.js.map +1 -0
- package/dist/plugins/specweave-jira/lib/jira-hierarchical-sync.d.ts +33 -0
- package/dist/plugins/specweave-jira/lib/jira-hierarchical-sync.d.ts.map +1 -0
- package/dist/plugins/specweave-jira/lib/jira-hierarchical-sync.js +206 -0
- package/dist/plugins/specweave-jira/lib/jira-hierarchical-sync.js.map +1 -0
- package/dist/plugins/specweave-jira/lib/project-selector.d.ts +42 -0
- package/dist/plugins/specweave-jira/lib/project-selector.d.ts.map +1 -0
- package/dist/plugins/specweave-jira/lib/project-selector.js +216 -0
- package/dist/plugins/specweave-jira/lib/project-selector.js.map +1 -0
- package/dist/plugins/specweave-jira/lib/reorganization-detector.d.ts +67 -0
- package/dist/plugins/specweave-jira/lib/reorganization-detector.d.ts.map +1 -0
- package/dist/plugins/specweave-jira/lib/reorganization-detector.js +252 -0
- package/dist/plugins/specweave-jira/lib/reorganization-detector.js.map +1 -0
- package/dist/plugins/specweave-jira/lib/setup-wizard.d.ts +29 -0
- package/dist/plugins/specweave-jira/lib/setup-wizard.d.ts.map +1 -0
- package/dist/plugins/specweave-jira/lib/setup-wizard.js +219 -0
- package/dist/plugins/specweave-jira/lib/setup-wizard.js.map +1 -0
- package/dist/src/adapters/adapter-base.d.ts +71 -0
- package/dist/src/adapters/adapter-base.d.ts.map +1 -0
- package/dist/src/adapters/adapter-base.js +139 -0
- package/dist/src/adapters/adapter-base.js.map +1 -0
- package/dist/src/adapters/adapter-interface.d.ts +149 -0
- package/dist/src/adapters/adapter-interface.d.ts.map +1 -0
- package/dist/src/adapters/adapter-interface.js +8 -0
- package/dist/src/adapters/adapter-interface.js.map +1 -0
- package/dist/src/adapters/adapter-loader.d.ts +91 -0
- package/dist/src/adapters/adapter-loader.d.ts.map +1 -0
- package/dist/src/adapters/adapter-loader.js +238 -0
- package/dist/src/adapters/adapter-loader.js.map +1 -0
- package/dist/src/adapters/agents-md-generator.d.ts +48 -0
- package/dist/src/adapters/agents-md-generator.d.ts.map +1 -0
- package/dist/src/adapters/agents-md-generator.js +193 -0
- package/dist/src/adapters/agents-md-generator.js.map +1 -0
- package/dist/src/adapters/claude/adapter.d.ts +128 -0
- package/dist/src/adapters/claude/adapter.d.ts.map +1 -0
- package/dist/src/adapters/claude/adapter.js +415 -0
- package/dist/src/adapters/claude/adapter.js.map +1 -0
- package/dist/src/adapters/claude-md-generator.d.ts +78 -0
- package/dist/src/adapters/claude-md-generator.d.ts.map +1 -0
- package/dist/src/adapters/claude-md-generator.js +307 -0
- package/dist/src/adapters/claude-md-generator.js.map +1 -0
- package/dist/src/adapters/codex/adapter.d.ts +50 -0
- package/dist/src/adapters/codex/adapter.d.ts.map +1 -0
- package/dist/src/adapters/codex/adapter.js +316 -0
- package/dist/src/adapters/codex/adapter.js.map +1 -0
- package/dist/src/adapters/cursor/adapter.d.ts +98 -0
- package/dist/src/adapters/cursor/adapter.d.ts.map +1 -0
- package/dist/src/adapters/cursor/adapter.js +406 -0
- package/dist/src/adapters/cursor/adapter.js.map +1 -0
- package/dist/src/adapters/doc-generator.d.ts +69 -0
- package/dist/src/adapters/doc-generator.d.ts.map +1 -0
- package/dist/src/adapters/doc-generator.js +247 -0
- package/dist/src/adapters/doc-generator.js.map +1 -0
- package/dist/src/adapters/gemini/adapter.d.ts +50 -0
- package/dist/src/adapters/gemini/adapter.d.ts.map +1 -0
- package/dist/src/adapters/gemini/adapter.js +281 -0
- package/dist/src/adapters/gemini/adapter.js.map +1 -0
- package/dist/src/adapters/generic/adapter.d.ts +86 -0
- package/dist/src/adapters/generic/adapter.d.ts.map +1 -0
- package/dist/src/adapters/generic/adapter.js +338 -0
- package/dist/src/adapters/generic/adapter.js.map +1 -0
- package/dist/src/cli/commands/abandon.d.ts +13 -0
- package/dist/src/cli/commands/abandon.d.ts.map +1 -0
- package/dist/src/cli/commands/abandon.js +15 -0
- package/dist/src/cli/commands/abandon.js.map +1 -0
- package/dist/src/cli/commands/import-docs.d.ts +21 -0
- package/dist/src/cli/commands/import-docs.d.ts.map +1 -0
- package/dist/src/cli/commands/import-docs.js +146 -0
- package/dist/src/cli/commands/import-docs.js.map +1 -0
- package/dist/src/cli/commands/init-multiproject.d.ts +11 -0
- package/dist/src/cli/commands/init-multiproject.d.ts.map +1 -0
- package/dist/src/cli/commands/init-multiproject.js +202 -0
- package/dist/src/cli/commands/init-multiproject.js.map +1 -0
- package/dist/src/cli/commands/init.d.ts +9 -0
- package/dist/src/cli/commands/init.d.ts.map +1 -0
- package/dist/src/cli/commands/init.js +1205 -0
- package/dist/src/cli/commands/init.js.map +1 -0
- package/dist/src/cli/commands/install.d.ts +9 -0
- package/dist/src/cli/commands/install.d.ts.map +1 -0
- package/dist/src/cli/commands/install.js +127 -0
- package/dist/src/cli/commands/install.js.map +1 -0
- package/dist/src/cli/commands/list.d.ts +8 -0
- package/dist/src/cli/commands/list.d.ts.map +1 -0
- package/dist/src/cli/commands/list.js +119 -0
- package/dist/src/cli/commands/list.js.map +1 -0
- package/dist/src/cli/commands/migrate-to-multiproject.d.ts +37 -0
- package/dist/src/cli/commands/migrate-to-multiproject.d.ts.map +1 -0
- package/dist/src/cli/commands/migrate-to-multiproject.js +189 -0
- package/dist/src/cli/commands/migrate-to-multiproject.js.map +1 -0
- package/dist/src/cli/commands/migrate-to-profiles.d.ts +25 -0
- package/dist/src/cli/commands/migrate-to-profiles.d.ts.map +1 -0
- package/dist/src/cli/commands/migrate-to-profiles.js +350 -0
- package/dist/src/cli/commands/migrate-to-profiles.js.map +1 -0
- package/dist/src/cli/commands/pause.d.ts +13 -0
- package/dist/src/cli/commands/pause.d.ts.map +1 -0
- package/dist/src/cli/commands/pause.js +15 -0
- package/dist/src/cli/commands/pause.js.map +1 -0
- package/dist/src/cli/commands/qa.d.ts +54 -0
- package/dist/src/cli/commands/qa.d.ts.map +1 -0
- package/dist/src/cli/commands/qa.js +98 -0
- package/dist/src/cli/commands/qa.js.map +1 -0
- package/dist/src/cli/commands/resume.d.ts +12 -0
- package/dist/src/cli/commands/resume.d.ts.map +1 -0
- package/dist/src/cli/commands/resume.js +14 -0
- package/dist/src/cli/commands/resume.js.map +1 -0
- package/dist/src/cli/commands/status.d.ts +12 -0
- package/dist/src/cli/commands/status.d.ts.map +1 -0
- package/dist/src/cli/commands/status.js +23 -0
- package/dist/src/cli/commands/status.js.map +1 -0
- package/dist/src/cli/commands/switch-project.d.ts +13 -0
- package/dist/src/cli/commands/switch-project.d.ts.map +1 -0
- package/dist/src/cli/commands/switch-project.js +91 -0
- package/dist/src/cli/commands/switch-project.js.map +1 -0
- package/dist/src/cli/commands/validate-jira.d.ts +35 -0
- package/dist/src/cli/commands/validate-jira.d.ts.map +1 -0
- package/dist/src/cli/commands/validate-jira.js +112 -0
- package/dist/src/cli/commands/validate-jira.js.map +1 -0
- package/dist/src/cli/commands/validate-plugins.d.ts +41 -0
- package/dist/src/cli/commands/validate-plugins.d.ts.map +1 -0
- package/dist/src/cli/commands/validate-plugins.js +171 -0
- package/dist/src/cli/commands/validate-plugins.js.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/ado.d.ts +57 -0
- package/dist/src/cli/helpers/issue-tracker/ado.d.ts.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/ado.js +243 -0
- package/dist/src/cli/helpers/issue-tracker/ado.js.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/github.d.ts +65 -0
- package/dist/src/cli/helpers/issue-tracker/github.d.ts.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/github.js +426 -0
- package/dist/src/cli/helpers/issue-tracker/github.js.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/index.d.ts +22 -0
- package/dist/src/cli/helpers/issue-tracker/index.d.ts.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/index.js +314 -0
- package/dist/src/cli/helpers/issue-tracker/index.js.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/jira.d.ts +61 -0
- package/dist/src/cli/helpers/issue-tracker/jira.d.ts.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/jira.js +404 -0
- package/dist/src/cli/helpers/issue-tracker/jira.js.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/types.d.ts +107 -0
- package/dist/src/cli/helpers/issue-tracker/types.d.ts.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/types.js +16 -0
- package/dist/src/cli/helpers/issue-tracker/types.js.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/utils.d.ts +112 -0
- package/dist/src/cli/helpers/issue-tracker/utils.d.ts.map +1 -0
- package/dist/src/cli/helpers/issue-tracker/utils.js +247 -0
- package/dist/src/cli/helpers/issue-tracker/utils.js.map +1 -0
- package/dist/src/core/agent-model-manager.d.ts +52 -0
- package/dist/src/core/agent-model-manager.d.ts.map +1 -0
- package/dist/src/core/agent-model-manager.js +120 -0
- package/dist/src/core/agent-model-manager.js.map +1 -0
- package/dist/src/core/brownfield/analyzer.d.ts +86 -0
- package/dist/src/core/brownfield/analyzer.d.ts.map +1 -0
- package/dist/src/core/brownfield/analyzer.js +365 -0
- package/dist/src/core/brownfield/analyzer.js.map +1 -0
- package/dist/src/core/brownfield/importer.d.ts +76 -0
- package/dist/src/core/brownfield/importer.d.ts.map +1 -0
- package/dist/src/core/brownfield/importer.js +287 -0
- package/dist/src/core/brownfield/importer.js.map +1 -0
- package/dist/src/core/config-manager.d.ts +47 -0
- package/dist/src/core/config-manager.d.ts.map +1 -0
- package/dist/src/core/config-manager.js +136 -0
- package/dist/src/core/config-manager.js.map +1 -0
- package/dist/src/core/cost-tracker.d.ts +108 -0
- package/dist/src/core/cost-tracker.d.ts.map +1 -0
- package/dist/src/core/cost-tracker.js +281 -0
- package/dist/src/core/cost-tracker.js.map +1 -0
- package/dist/src/core/credentials-manager.d.ts +107 -0
- package/dist/src/core/credentials-manager.d.ts.map +1 -0
- package/dist/src/core/credentials-manager.js +457 -0
- package/dist/src/core/credentials-manager.js.map +1 -0
- package/dist/src/core/i18n/language-detector.d.ts +29 -0
- package/dist/src/core/i18n/language-detector.d.ts.map +1 -0
- package/dist/src/core/i18n/language-detector.js +143 -0
- package/dist/src/core/i18n/language-detector.js.map +1 -0
- package/dist/src/core/i18n/language-manager.d.ts +101 -0
- package/dist/src/core/i18n/language-manager.d.ts.map +1 -0
- package/dist/src/core/i18n/language-manager.js +232 -0
- package/dist/src/core/i18n/language-manager.js.map +1 -0
- package/dist/src/core/i18n/language-registry.d.ts +44 -0
- package/dist/src/core/i18n/language-registry.d.ts.map +1 -0
- package/dist/src/core/i18n/language-registry.js +234 -0
- package/dist/src/core/i18n/language-registry.js.map +1 -0
- package/dist/src/core/i18n/locale-manager.d.ts +62 -0
- package/dist/src/core/i18n/locale-manager.d.ts.map +1 -0
- package/dist/src/core/i18n/locale-manager.js +137 -0
- package/dist/src/core/i18n/locale-manager.js.map +1 -0
- package/dist/src/core/i18n/system-prompt-injector.d.ts +33 -0
- package/dist/src/core/i18n/system-prompt-injector.d.ts.map +1 -0
- package/dist/src/core/i18n/system-prompt-injector.js +131 -0
- package/dist/src/core/i18n/system-prompt-injector.js.map +1 -0
- package/dist/src/core/i18n/types.d.ts +151 -0
- package/dist/src/core/i18n/types.d.ts.map +1 -0
- package/dist/src/core/i18n/types.js +11 -0
- package/dist/src/core/i18n/types.js.map +1 -0
- package/dist/src/core/increment/limits.d.ts +68 -0
- package/dist/src/core/increment/limits.d.ts.map +1 -0
- package/dist/src/core/increment/limits.js +224 -0
- package/dist/src/core/increment/limits.js.map +1 -0
- package/dist/src/core/increment/metadata-manager.d.ts +114 -0
- package/dist/src/core/increment/metadata-manager.d.ts.map +1 -0
- package/dist/src/core/increment/metadata-manager.js +320 -0
- package/dist/src/core/increment/metadata-manager.js.map +1 -0
- package/dist/src/core/increment/status-commands.d.ts +43 -0
- package/dist/src/core/increment/status-commands.d.ts.map +1 -0
- package/dist/src/core/increment/status-commands.js +277 -0
- package/dist/src/core/increment/status-commands.js.map +1 -0
- package/dist/src/core/increment-status.d.ts +72 -0
- package/dist/src/core/increment-status.d.ts.map +1 -0
- package/dist/src/core/increment-status.js +227 -0
- package/dist/src/core/increment-status.js.map +1 -0
- package/dist/src/core/model-selector.d.ts +57 -0
- package/dist/src/core/model-selector.d.ts.map +1 -0
- package/dist/src/core/model-selector.js +115 -0
- package/dist/src/core/model-selector.js.map +1 -0
- package/dist/src/core/phase-detector.d.ts +62 -0
- package/dist/src/core/phase-detector.d.ts.map +1 -0
- package/dist/src/core/phase-detector.js +229 -0
- package/dist/src/core/phase-detector.js.map +1 -0
- package/dist/src/core/plugin-loader.d.ts +131 -0
- package/dist/src/core/plugin-loader.d.ts.map +1 -0
- package/dist/src/core/plugin-loader.js +421 -0
- package/dist/src/core/plugin-loader.js.map +1 -0
- package/dist/src/core/project-manager.d.ts +127 -0
- package/dist/src/core/project-manager.d.ts.map +1 -0
- package/dist/src/core/project-manager.js +524 -0
- package/dist/src/core/project-manager.js.map +1 -0
- package/dist/src/core/project-structure-detector.d.ts +92 -0
- package/dist/src/core/project-structure-detector.d.ts.map +1 -0
- package/dist/src/core/project-structure-detector.js +289 -0
- package/dist/src/core/project-structure-detector.js.map +1 -0
- package/dist/src/core/qa/qa-runner.d.ts +16 -0
- package/dist/src/core/qa/qa-runner.d.ts.map +1 -0
- package/dist/src/core/qa/qa-runner.js +404 -0
- package/dist/src/core/qa/qa-runner.js.map +1 -0
- package/dist/src/core/qa/quality-gate-decider.d.ts +53 -0
- package/dist/src/core/qa/quality-gate-decider.d.ts.map +1 -0
- package/dist/src/core/qa/quality-gate-decider.js +268 -0
- package/dist/src/core/qa/quality-gate-decider.js.map +1 -0
- package/dist/src/core/qa/risk-calculator.d.ts +126 -0
- package/dist/src/core/qa/risk-calculator.d.ts.map +1 -0
- package/dist/src/core/qa/risk-calculator.js +247 -0
- package/dist/src/core/qa/risk-calculator.js.map +1 -0
- package/dist/src/core/qa/types.d.ts +315 -0
- package/dist/src/core/qa/types.d.ts.map +1 -0
- package/dist/src/core/qa/types.js +8 -0
- package/dist/src/core/qa/types.js.map +1 -0
- package/dist/src/core/rfc-generator-v2.d.ts +149 -0
- package/dist/src/core/rfc-generator-v2.d.ts.map +1 -0
- package/dist/src/core/rfc-generator-v2.js +399 -0
- package/dist/src/core/rfc-generator-v2.js.map +1 -0
- package/dist/src/core/sync/bidirectional-engine.d.ts +110 -0
- package/dist/src/core/sync/bidirectional-engine.d.ts.map +1 -0
- package/dist/src/core/sync/bidirectional-engine.js +356 -0
- package/dist/src/core/sync/bidirectional-engine.js.map +1 -0
- package/dist/src/core/sync/folder-mapper.d.ts +71 -0
- package/dist/src/core/sync/folder-mapper.d.ts.map +1 -0
- package/dist/src/core/sync/folder-mapper.js +168 -0
- package/dist/src/core/sync/folder-mapper.js.map +1 -0
- package/dist/src/core/sync/profile-manager.d.ts +72 -0
- package/dist/src/core/sync/profile-manager.d.ts.map +1 -0
- package/dist/src/core/sync/profile-manager.js +338 -0
- package/dist/src/core/sync/profile-manager.js.map +1 -0
- package/dist/src/core/sync/profile-selector.d.ts +52 -0
- package/dist/src/core/sync/profile-selector.d.ts.map +1 -0
- package/dist/src/core/sync/profile-selector.js +179 -0
- package/dist/src/core/sync/profile-selector.js.map +1 -0
- package/dist/src/core/sync/profile-validator.d.ts +52 -0
- package/dist/src/core/sync/profile-validator.d.ts.map +1 -0
- package/dist/src/core/sync/profile-validator.js +225 -0
- package/dist/src/core/sync/profile-validator.js.map +1 -0
- package/dist/src/core/sync/project-context.d.ts +81 -0
- package/dist/src/core/sync/project-context.d.ts.map +1 -0
- package/dist/src/core/sync/project-context.js +354 -0
- package/dist/src/core/sync/project-context.js.map +1 -0
- package/dist/src/core/sync/rate-limiter.d.ts +116 -0
- package/dist/src/core/sync/rate-limiter.d.ts.map +1 -0
- package/dist/src/core/sync/rate-limiter.js +308 -0
- package/dist/src/core/sync/rate-limiter.js.map +1 -0
- package/dist/src/core/sync/time-range-selector.d.ts +48 -0
- package/dist/src/core/sync/time-range-selector.d.ts.map +1 -0
- package/dist/src/core/sync/time-range-selector.js +224 -0
- package/dist/src/core/sync/time-range-selector.js.map +1 -0
- package/dist/src/core/types/config.d.ts +90 -0
- package/dist/src/core/types/config.d.ts.map +1 -0
- package/dist/src/core/types/config.js +37 -0
- package/dist/src/core/types/config.js.map +1 -0
- package/dist/src/core/types/increment-metadata.d.ts +120 -0
- package/dist/src/core/types/increment-metadata.d.ts.map +1 -0
- package/dist/src/core/types/increment-metadata.js +138 -0
- package/dist/src/core/types/increment-metadata.js.map +1 -0
- package/dist/src/core/types/plugin.d.ts +283 -0
- package/dist/src/core/types/plugin.d.ts.map +1 -0
- package/dist/src/core/types/plugin.js +49 -0
- package/dist/src/core/types/plugin.js.map +1 -0
- package/dist/src/core/types/sync-profile.d.ts +403 -0
- package/dist/src/core/types/sync-profile.d.ts.map +1 -0
- package/dist/src/core/types/sync-profile.js +55 -0
- package/dist/src/core/types/sync-profile.js.map +1 -0
- package/dist/src/hooks/lib/types/reflection-types.d.ts +125 -0
- package/dist/src/hooks/lib/types/reflection-types.d.ts.map +1 -0
- package/dist/src/hooks/lib/types/reflection-types.js +54 -0
- package/dist/src/hooks/lib/types/reflection-types.js.map +1 -0
- package/dist/src/integrations/ado/ado-client.d.ts +127 -0
- package/dist/src/integrations/ado/ado-client.d.ts.map +1 -0
- package/dist/src/integrations/ado/ado-client.js +416 -0
- package/dist/src/integrations/ado/ado-client.js.map +1 -0
- package/dist/src/integrations/jira/jira-client.d.ts +139 -0
- package/dist/src/integrations/jira/jira-client.d.ts.map +1 -0
- package/dist/src/integrations/jira/jira-client.js +386 -0
- package/dist/src/integrations/jira/jira-client.js.map +1 -0
- package/dist/src/integrations/jira/jira-incremental-mapper.d.ts +75 -0
- package/dist/src/integrations/jira/jira-incremental-mapper.d.ts.map +1 -0
- package/dist/src/integrations/jira/jira-incremental-mapper.js +474 -0
- package/dist/src/integrations/jira/jira-incremental-mapper.js.map +1 -0
- package/dist/src/integrations/jira/jira-mapper.d.ts +105 -0
- package/dist/src/integrations/jira/jira-mapper.d.ts.map +1 -0
- package/dist/src/integrations/jira/jira-mapper.js +494 -0
- package/dist/src/integrations/jira/jira-mapper.js.map +1 -0
- package/dist/src/metrics/calculators/change-failure-rate.d.ts +22 -0
- package/dist/src/metrics/calculators/change-failure-rate.d.ts.map +1 -0
- package/dist/src/metrics/calculators/change-failure-rate.js +70 -0
- package/dist/src/metrics/calculators/change-failure-rate.js.map +1 -0
- package/dist/src/metrics/calculators/deployment-frequency.d.ts +20 -0
- package/dist/src/metrics/calculators/deployment-frequency.d.ts.map +1 -0
- package/dist/src/metrics/calculators/deployment-frequency.js +61 -0
- package/dist/src/metrics/calculators/deployment-frequency.js.map +1 -0
- package/dist/src/metrics/calculators/lead-time.d.ts +22 -0
- package/dist/src/metrics/calculators/lead-time.d.ts.map +1 -0
- package/dist/src/metrics/calculators/lead-time.js +82 -0
- package/dist/src/metrics/calculators/lead-time.js.map +1 -0
- package/dist/src/metrics/calculators/mttr.d.ts +21 -0
- package/dist/src/metrics/calculators/mttr.d.ts.map +1 -0
- package/dist/src/metrics/calculators/mttr.js +60 -0
- package/dist/src/metrics/calculators/mttr.js.map +1 -0
- package/dist/src/metrics/dora-calculator.d.ts +28 -0
- package/dist/src/metrics/dora-calculator.d.ts.map +1 -0
- package/dist/src/metrics/dora-calculator.js +117 -0
- package/dist/src/metrics/dora-calculator.js.map +1 -0
- package/dist/src/metrics/github-client.d.ts +51 -0
- package/dist/src/metrics/github-client.d.ts.map +1 -0
- package/dist/src/metrics/github-client.js +133 -0
- package/dist/src/metrics/github-client.js.map +1 -0
- package/dist/src/metrics/report-generator.d.ts +17 -0
- package/dist/src/metrics/report-generator.d.ts.map +1 -0
- package/dist/src/metrics/report-generator.js +403 -0
- package/dist/src/metrics/report-generator.js.map +1 -0
- package/dist/src/metrics/types.d.ts +112 -0
- package/dist/src/metrics/types.d.ts.map +1 -0
- package/dist/src/metrics/types.js +10 -0
- package/dist/src/metrics/types.js.map +1 -0
- package/dist/src/metrics/utils/percentile.d.ts +25 -0
- package/dist/src/metrics/utils/percentile.d.ts.map +1 -0
- package/dist/src/metrics/utils/percentile.js +46 -0
- package/dist/src/metrics/utils/percentile.js.map +1 -0
- package/dist/src/metrics/utils/tier-classifier.d.ts +61 -0
- package/dist/src/metrics/utils/tier-classifier.d.ts.map +1 -0
- package/dist/src/metrics/utils/tier-classifier.js +100 -0
- package/dist/src/metrics/utils/tier-classifier.js.map +1 -0
- package/dist/src/testing/test-generator.d.ts +117 -0
- package/dist/src/testing/test-generator.d.ts.map +1 -0
- package/dist/src/testing/test-generator.js +370 -0
- package/dist/src/testing/test-generator.js.map +1 -0
- package/dist/src/types/cost-tracking.d.ts +43 -0
- package/dist/src/types/cost-tracking.d.ts.map +1 -0
- package/dist/src/types/cost-tracking.js +8 -0
- package/dist/src/types/cost-tracking.js.map +1 -0
- package/dist/src/types/model-selection.d.ts +53 -0
- package/dist/src/types/model-selection.d.ts.map +1 -0
- package/dist/src/types/model-selection.js +12 -0
- package/dist/src/types/model-selection.js.map +1 -0
- package/dist/src/utils/agents-md-compiler.d.ts +68 -0
- package/dist/src/utils/agents-md-compiler.d.ts.map +1 -0
- package/dist/src/utils/agents-md-compiler.js +420 -0
- package/dist/src/utils/agents-md-compiler.js.map +1 -0
- package/dist/src/utils/auth-helpers.d.ts +58 -0
- package/dist/src/utils/auth-helpers.d.ts.map +1 -0
- package/dist/src/utils/auth-helpers.js +108 -0
- package/dist/src/utils/auth-helpers.js.map +1 -0
- package/dist/src/utils/auto-install.d.ts +47 -0
- package/dist/src/utils/auto-install.d.ts.map +1 -0
- package/dist/src/utils/auto-install.js +211 -0
- package/dist/src/utils/auto-install.js.map +1 -0
- package/dist/src/utils/claude-cli-detector.d.ts +75 -0
- package/dist/src/utils/claude-cli-detector.d.ts.map +1 -0
- package/dist/src/utils/claude-cli-detector.js +285 -0
- package/dist/src/utils/claude-cli-detector.js.map +1 -0
- package/dist/src/utils/cost-reporter.d.ts +58 -0
- package/dist/src/utils/cost-reporter.d.ts.map +1 -0
- package/dist/src/utils/cost-reporter.js +224 -0
- package/dist/src/utils/cost-reporter.js.map +1 -0
- package/dist/src/utils/docs-preview/config-generator.d.ts +46 -0
- package/dist/src/utils/docs-preview/config-generator.d.ts.map +1 -0
- package/dist/src/utils/docs-preview/config-generator.js +377 -0
- package/dist/src/utils/docs-preview/config-generator.js.map +1 -0
- package/dist/src/utils/docs-preview/docusaurus-setup.d.ts +38 -0
- package/dist/src/utils/docs-preview/docusaurus-setup.d.ts.map +1 -0
- package/dist/src/utils/docs-preview/docusaurus-setup.js +177 -0
- package/dist/src/utils/docs-preview/docusaurus-setup.js.map +1 -0
- package/dist/src/utils/docs-preview/index.d.ts +7 -0
- package/dist/src/utils/docs-preview/index.d.ts.map +1 -0
- package/dist/src/utils/docs-preview/index.js +7 -0
- package/dist/src/utils/docs-preview/index.js.map +1 -0
- package/dist/src/utils/docs-preview/package-installer.d.ts +42 -0
- package/dist/src/utils/docs-preview/package-installer.d.ts.map +1 -0
- package/dist/src/utils/docs-preview/package-installer.js +182 -0
- package/dist/src/utils/docs-preview/package-installer.js.map +1 -0
- package/dist/src/utils/docs-preview/server-manager.d.ts +30 -0
- package/dist/src/utils/docs-preview/server-manager.d.ts.map +1 -0
- package/dist/src/utils/docs-preview/server-manager.js +212 -0
- package/dist/src/utils/docs-preview/server-manager.js.map +1 -0
- package/dist/src/utils/docs-preview/sidebar-builder.d.ts +32 -0
- package/dist/src/utils/docs-preview/sidebar-builder.d.ts.map +1 -0
- package/dist/src/utils/docs-preview/sidebar-builder.js +202 -0
- package/dist/src/utils/docs-preview/sidebar-builder.js.map +1 -0
- package/dist/src/utils/docs-preview/types.d.ts +57 -0
- package/dist/src/utils/docs-preview/types.d.ts.map +1 -0
- package/dist/src/utils/docs-preview/types.js +2 -0
- package/dist/src/utils/docs-preview/types.js.map +1 -0
- package/dist/src/utils/env-file.d.ts +88 -0
- package/dist/src/utils/env-file.d.ts.map +1 -0
- package/dist/src/utils/env-file.js +180 -0
- package/dist/src/utils/env-file.js.map +1 -0
- package/dist/src/utils/env-multi-project-parser.d.ts +220 -0
- package/dist/src/utils/env-multi-project-parser.d.ts.map +1 -0
- package/dist/src/utils/env-multi-project-parser.js +403 -0
- package/dist/src/utils/env-multi-project-parser.js.map +1 -0
- package/dist/src/utils/esm-helpers.d.ts +50 -0
- package/dist/src/utils/esm-helpers.d.ts.map +1 -0
- package/dist/src/utils/esm-helpers.js +57 -0
- package/dist/src/utils/esm-helpers.js.map +1 -0
- package/dist/src/utils/execFileNoThrow.d.ts +99 -0
- package/dist/src/utils/execFileNoThrow.d.ts.map +1 -0
- package/dist/src/utils/execFileNoThrow.js +137 -0
- package/dist/src/utils/execFileNoThrow.js.map +1 -0
- package/dist/src/utils/external-resource-validator.d.ts +102 -0
- package/dist/src/utils/external-resource-validator.d.ts.map +1 -0
- package/dist/src/utils/external-resource-validator.js +400 -0
- package/dist/src/utils/external-resource-validator.js.map +1 -0
- package/dist/src/utils/generate-skills-index.d.ts +24 -0
- package/dist/src/utils/generate-skills-index.d.ts.map +1 -0
- package/dist/src/utils/generate-skills-index.js +410 -0
- package/dist/src/utils/generate-skills-index.js.map +1 -0
- package/dist/src/utils/model-selection.d.ts +75 -0
- package/dist/src/utils/model-selection.d.ts.map +1 -0
- package/dist/src/utils/model-selection.js +204 -0
- package/dist/src/utils/model-selection.js.map +1 -0
- package/dist/src/utils/plugin-validator.d.ts +161 -0
- package/dist/src/utils/plugin-validator.d.ts.map +1 -0
- package/dist/src/utils/plugin-validator.js +558 -0
- package/dist/src/utils/plugin-validator.js.map +1 -0
- package/dist/src/utils/pricing-constants.d.ts +70 -0
- package/dist/src/utils/pricing-constants.d.ts.map +1 -0
- package/dist/src/utils/pricing-constants.js +71 -0
- package/dist/src/utils/pricing-constants.js.map +1 -0
- package/dist/src/utils/project-detection.d.ts +141 -0
- package/dist/src/utils/project-detection.d.ts.map +1 -0
- package/dist/src/utils/project-detection.js +321 -0
- package/dist/src/utils/project-detection.js.map +1 -0
- package/dist/src/utils/string-utils.d.ts +40 -0
- package/dist/src/utils/string-utils.d.ts.map +1 -0
- package/dist/src/utils/string-utils.js +58 -0
- package/dist/src/utils/string-utils.js.map +1 -0
- package/dist/src/utils/translation.d.ts +187 -0
- package/dist/src/utils/translation.d.ts.map +1 -0
- package/dist/src/utils/translation.js +414 -0
- package/dist/src/utils/translation.js.map +1 -0
- package/dist/utils/plugin-validator.d.ts.map +1 -1
- package/dist/utils/plugin-validator.js +0 -7
- package/dist/utils/plugin-validator.js.map +1 -1
- package/package.json +3 -2
- package/plugins/specweave/agents/reflective-reviewer/AGENT.md +535 -0
- package/plugins/specweave/hooks/post-first-increment.sh +10 -28
- package/plugins/specweave/hooks/post-increment-planning.sh +261 -1
- package/plugins/specweave/hooks/post-task-completion.sh +26 -0
- package/plugins/specweave/lib/hooks/git-diff-analyzer.ts +269 -0
- package/plugins/specweave/lib/hooks/invoke-translator-skill.ts +264 -0
- package/plugins/specweave/lib/hooks/prepare-reflection-context.ts +178 -0
- package/plugins/specweave/lib/hooks/reflection-config-loader.ts +156 -0
- package/plugins/specweave/lib/hooks/reflection-parser.ts +484 -0
- package/plugins/specweave/lib/hooks/reflection-prompt-builder.ts +306 -0
- package/plugins/specweave/lib/hooks/reflection-storage.ts +369 -0
- package/plugins/specweave/lib/hooks/run-self-reflection.ts +258 -0
- package/plugins/specweave/lib/hooks/sync-living-docs.ts +147 -0
- package/plugins/specweave/lib/hooks/translate-file.ts +428 -0
- package/plugins/specweave/lib/hooks/translate-living-docs.ts +224 -0
- package/plugins/specweave/lib/hooks/types/reflection-types.ts +193 -0
- package/plugins/specweave/lib/hooks/update-tasks-md.ts +256 -0
- package/plugins/specweave/skills/SKILLS-INDEX.md +2 -2
- package/plugins/specweave/skills/increment-planner/SKILL.md +21 -92
- package/plugins/specweave/skills/plugin-expert/SKILL.md +0 -4
- package/plugins/specweave/skills/plugin-installer/SKILL.md +41 -28
- package/plugins/specweave/skills/plugin-validator/SKILL.md +0 -1
- package/plugins/specweave/skills/project-kickstarter/SKILL.md +3 -3
- package/plugins/specweave/skills/spec-generator/SKILL.md +3 -3
- package/plugins/specweave-ado/agents/ado-manager/AGENT.md +2 -0
- package/plugins/specweave-ado/commands/specweave-ado-sync.md +102 -9
- package/plugins/specweave-ado/skills/ado-sync/SKILL.md +7 -3
- package/plugins/specweave-docs-preview/.claude-plugin/plugin.json +21 -0
- package/plugins/specweave-docs-preview/commands/build.md +489 -0
- package/plugins/specweave-docs-preview/commands/preview.md +330 -0
- package/plugins/specweave-docs-preview/skills/docs-preview/SKILL.md +386 -0
- package/plugins/specweave-github/agents/github-manager/AGENT.md +14 -4
- package/plugins/specweave-github/commands/specweave-github-sync.md +60 -11
- package/plugins/specweave-github/skills/github-sync/SKILL.md +3 -1
- package/plugins/specweave-jira/agents/jira-manager/AGENT.md +18 -8
- package/plugins/specweave-jira/commands/specweave-jira-sync.md +62 -19
- package/plugins/specweave-jira/skills/jira-sync/SKILL.md +5 -3
- package/plugins/specweave/skills/translator/SKILL.md.bak +0 -172
|
@@ -0,0 +1,1205 @@
|
|
|
1
|
+
import fs from 'fs-extra';
|
|
2
|
+
import * as path from 'path';
|
|
3
|
+
import chalk from 'chalk';
|
|
4
|
+
import ora from 'ora';
|
|
5
|
+
import inquirer from 'inquirer';
|
|
6
|
+
import { execFileNoThrowSync } from '../../utils/execFileNoThrow.js';
|
|
7
|
+
import { detectClaudeCli, getClaudeCliDiagnostic, getClaudeCliSuggestions } from '../../utils/claude-cli-detector.js';
|
|
8
|
+
import { AdapterLoader } from '../../adapters/adapter-loader.js';
|
|
9
|
+
import { ClaudeMdGenerator } from '../../adapters/claude-md-generator.js';
|
|
10
|
+
import { AgentsMdGenerator } from '../../adapters/agents-md-generator.js';
|
|
11
|
+
import { getDirname } from '../../utils/esm-helpers.js';
|
|
12
|
+
import { LanguageManager, isLanguageSupported, getSupportedLanguages, getSystemPromptForLanguage } from '../../core/i18n/language-manager.js';
|
|
13
|
+
import { getLocaleManager } from '../../core/i18n/locale-manager.js';
|
|
14
|
+
const __dirname = getDirname(import.meta.url);
|
|
15
|
+
export async function initCommand(projectName, options = {}) {
|
|
16
|
+
// Validate and normalize language option
|
|
17
|
+
const language = options.language?.toLowerCase() || 'en';
|
|
18
|
+
// Validate language if provided
|
|
19
|
+
if (options.language && !isLanguageSupported(language)) {
|
|
20
|
+
const locale = getLocaleManager('en'); // Use English for error messages about invalid language
|
|
21
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.invalidLanguage', { language: options.language })}`));
|
|
22
|
+
console.error(chalk.yellow(`${locale.t('cli', 'init.errors.supportedLanguages', { languages: getSupportedLanguages().join(', ') })}\n`));
|
|
23
|
+
process.exit(1);
|
|
24
|
+
}
|
|
25
|
+
// Initialize LanguageManager and LocaleManager
|
|
26
|
+
const i18n = new LanguageManager({ defaultLanguage: language });
|
|
27
|
+
const locale = getLocaleManager(language);
|
|
28
|
+
// Display welcome message in user's language
|
|
29
|
+
console.log(chalk.blue.bold(`\n${locale.t('cli', 'init.welcome')}\n`));
|
|
30
|
+
let targetDir;
|
|
31
|
+
let finalProjectName;
|
|
32
|
+
let usedDotNotation = false;
|
|
33
|
+
// Handle "." for current directory initialization
|
|
34
|
+
if (projectName === '.') {
|
|
35
|
+
usedDotNotation = true;
|
|
36
|
+
targetDir = process.cwd();
|
|
37
|
+
const dirName = path.basename(targetDir);
|
|
38
|
+
// Validate directory name is suitable for project name
|
|
39
|
+
if (!/^[a-z0-9-]+$/.test(dirName)) {
|
|
40
|
+
console.log(chalk.yellow(`\n${locale.t('cli', 'init.warnings.invalidDirName', { dirName })}`));
|
|
41
|
+
const suggestedName = dirName.toLowerCase().replace(/[^a-z0-9-]/g, '-');
|
|
42
|
+
const { name } = await inquirer.prompt([
|
|
43
|
+
{
|
|
44
|
+
type: 'input',
|
|
45
|
+
name: 'name',
|
|
46
|
+
message: 'Project name (for templates):',
|
|
47
|
+
default: suggestedName,
|
|
48
|
+
validate: (input) => {
|
|
49
|
+
if (/^[a-z0-9-]+$/.test(input))
|
|
50
|
+
return true;
|
|
51
|
+
return 'Project name must be lowercase letters, numbers, and hyphens only';
|
|
52
|
+
},
|
|
53
|
+
},
|
|
54
|
+
]);
|
|
55
|
+
finalProjectName = name;
|
|
56
|
+
}
|
|
57
|
+
else {
|
|
58
|
+
finalProjectName = dirName;
|
|
59
|
+
}
|
|
60
|
+
// Safety: Warn if directory is not empty
|
|
61
|
+
const allFiles = fs.readdirSync(targetDir);
|
|
62
|
+
const existingFiles = allFiles.filter(f => !f.startsWith('.')); // Ignore hidden files
|
|
63
|
+
if (existingFiles.length > 0) {
|
|
64
|
+
console.log(chalk.yellow(`\n${locale.t('cli', 'init.warnings.directoryNotEmpty', { count: existingFiles.length, plural: existingFiles.length === 1 ? '' : 's' })}`));
|
|
65
|
+
const { confirm } = await inquirer.prompt([
|
|
66
|
+
{
|
|
67
|
+
type: 'confirm',
|
|
68
|
+
name: 'confirm',
|
|
69
|
+
message: 'Initialize SpecWeave in current directory?',
|
|
70
|
+
default: false,
|
|
71
|
+
},
|
|
72
|
+
]);
|
|
73
|
+
if (!confirm) {
|
|
74
|
+
console.log(chalk.yellow(locale.t('cli', 'init.errors.cancelled')));
|
|
75
|
+
process.exit(0);
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
// Check if .specweave already exists
|
|
79
|
+
if (fs.existsSync(path.join(targetDir, '.specweave'))) {
|
|
80
|
+
const { overwrite } = await inquirer.prompt([
|
|
81
|
+
{
|
|
82
|
+
type: 'confirm',
|
|
83
|
+
name: 'overwrite',
|
|
84
|
+
message: '.specweave directory already exists. Overwrite?',
|
|
85
|
+
default: false,
|
|
86
|
+
},
|
|
87
|
+
]);
|
|
88
|
+
if (!overwrite) {
|
|
89
|
+
console.log(chalk.yellow(locale.t('cli', 'init.errors.cancelled')));
|
|
90
|
+
process.exit(0);
|
|
91
|
+
}
|
|
92
|
+
fs.removeSync(path.join(targetDir, '.specweave'));
|
|
93
|
+
if (fs.existsSync(path.join(targetDir, '.claude'))) {
|
|
94
|
+
fs.removeSync(path.join(targetDir, '.claude'));
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
else {
|
|
99
|
+
// Original behavior: create subdirectory
|
|
100
|
+
// 1. Get project name if not provided
|
|
101
|
+
if (!projectName) {
|
|
102
|
+
const answers = await inquirer.prompt([
|
|
103
|
+
{
|
|
104
|
+
type: 'input',
|
|
105
|
+
name: 'projectName',
|
|
106
|
+
message: 'Project name:',
|
|
107
|
+
default: 'my-saas',
|
|
108
|
+
validate: (input) => {
|
|
109
|
+
if (/^[a-z0-9-]+$/.test(input))
|
|
110
|
+
return true;
|
|
111
|
+
return 'Project name must be lowercase letters, numbers, and hyphens only';
|
|
112
|
+
},
|
|
113
|
+
},
|
|
114
|
+
]);
|
|
115
|
+
projectName = answers.projectName;
|
|
116
|
+
}
|
|
117
|
+
targetDir = path.resolve(process.cwd(), projectName);
|
|
118
|
+
finalProjectName = projectName;
|
|
119
|
+
// 2. Check if directory exists
|
|
120
|
+
if (fs.existsSync(targetDir)) {
|
|
121
|
+
const { overwrite } = await inquirer.prompt([
|
|
122
|
+
{
|
|
123
|
+
type: 'confirm',
|
|
124
|
+
name: 'overwrite',
|
|
125
|
+
message: `Directory ${projectName} already exists. Overwrite?`,
|
|
126
|
+
default: false,
|
|
127
|
+
},
|
|
128
|
+
]);
|
|
129
|
+
if (!overwrite) {
|
|
130
|
+
console.log(chalk.yellow(locale.t('cli', 'init.errors.cancelled')));
|
|
131
|
+
process.exit(0);
|
|
132
|
+
}
|
|
133
|
+
fs.emptyDirSync(targetDir);
|
|
134
|
+
}
|
|
135
|
+
else {
|
|
136
|
+
fs.mkdirSync(targetDir, { recursive: true });
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
// 3. Check for nested .specweave/ (CRITICAL: prevent nested folders)
|
|
140
|
+
const parentSpecweaveFolders = detectNestedSpecweave(targetDir);
|
|
141
|
+
if (parentSpecweaveFolders && parentSpecweaveFolders.length > 0) {
|
|
142
|
+
console.log('');
|
|
143
|
+
console.log(chalk.red.bold(locale.t('cli', 'init.errors.nestedNotSupported')));
|
|
144
|
+
console.log('');
|
|
145
|
+
// Show all found .specweave/ folders
|
|
146
|
+
if (parentSpecweaveFolders.length === 1) {
|
|
147
|
+
console.log(chalk.yellow(` ${locale.t('cli', 'init.errors.parentFound')}`));
|
|
148
|
+
console.log(chalk.white(` ${parentSpecweaveFolders[0].path}`));
|
|
149
|
+
}
|
|
150
|
+
else {
|
|
151
|
+
console.log(chalk.yellow(` Found ${parentSpecweaveFolders.length} parent .specweave/ folders:`));
|
|
152
|
+
console.log('');
|
|
153
|
+
// Sort by depth (closest first)
|
|
154
|
+
const sortedFolders = [...parentSpecweaveFolders].sort((a, b) => a.depth - b.depth);
|
|
155
|
+
sortedFolders.forEach((folder, index) => {
|
|
156
|
+
const marker = index === 0 ? chalk.green('✓ CLOSEST') : chalk.gray(` ${folder.depth} level${folder.depth > 1 ? 's' : ''} up`);
|
|
157
|
+
console.log(` ${marker}: ${chalk.white(folder.path)}`);
|
|
158
|
+
});
|
|
159
|
+
}
|
|
160
|
+
console.log('');
|
|
161
|
+
console.log(chalk.cyan(` ${locale.t('cli', 'init.info.nestedEnforcement')}`));
|
|
162
|
+
console.log(chalk.gray(` ${locale.t('cli', 'init.info.nestedBullet1')}`));
|
|
163
|
+
console.log(chalk.gray(` ${locale.t('cli', 'init.info.nestedBullet2')}`));
|
|
164
|
+
console.log(chalk.gray(` ${locale.t('cli', 'init.info.nestedBullet3')}`));
|
|
165
|
+
console.log('');
|
|
166
|
+
// Suggest using the CLOSEST folder (most relevant)
|
|
167
|
+
const closestFolder = parentSpecweaveFolders.reduce((closest, current) => current.depth < closest.depth ? current : closest);
|
|
168
|
+
console.log(chalk.cyan(` ${locale.t('cli', 'init.info.nestedToFix')}`));
|
|
169
|
+
console.log(chalk.green.bold(` Recommended: Use the CLOSEST .specweave/ folder`));
|
|
170
|
+
console.log(chalk.white(` ${locale.t('cli', 'init.nestedCdCommand', { path: closestFolder.path })}`));
|
|
171
|
+
console.log(chalk.white(` ${locale.t('cli', 'init.nestedIncCommand')}`));
|
|
172
|
+
console.log('');
|
|
173
|
+
// Provide cleanup option if user has multiple unnecessary folders
|
|
174
|
+
if (parentSpecweaveFolders.length > 1) {
|
|
175
|
+
console.log(chalk.yellow.bold(` 💡 Tip: Multiple .specweave/ folders detected`));
|
|
176
|
+
console.log(chalk.gray(` If some are unnecessary, consider removing them:`));
|
|
177
|
+
console.log('');
|
|
178
|
+
parentSpecweaveFolders.forEach(folder => {
|
|
179
|
+
console.log(chalk.gray(` rm -rf "${folder.path}/.specweave" # Remove if not needed`));
|
|
180
|
+
});
|
|
181
|
+
console.log('');
|
|
182
|
+
}
|
|
183
|
+
process.exit(1);
|
|
184
|
+
}
|
|
185
|
+
const spinner = ora('Creating SpecWeave project...').start();
|
|
186
|
+
try {
|
|
187
|
+
// 4. Detect or select tool
|
|
188
|
+
const adapterLoader = new AdapterLoader();
|
|
189
|
+
let toolName;
|
|
190
|
+
if (options.adapter) {
|
|
191
|
+
// User explicitly chose a tool via --adapter flag
|
|
192
|
+
toolName = options.adapter;
|
|
193
|
+
spinner.text = `Using ${toolName}...`;
|
|
194
|
+
}
|
|
195
|
+
else {
|
|
196
|
+
// Auto-detect tool, then ASK USER to confirm or choose different
|
|
197
|
+
spinner.stop();
|
|
198
|
+
const detectedTool = await adapterLoader.detectTool();
|
|
199
|
+
console.log('');
|
|
200
|
+
console.log(chalk.cyan(`🔍 ${locale.t('cli', 'init.toolDetection.header')}`));
|
|
201
|
+
// Show different message for Claude (recommended default) vs actually detected tools
|
|
202
|
+
if (detectedTool === 'claude') {
|
|
203
|
+
console.log(chalk.gray(` Recommended: ${detectedTool} (no other tool detected)`));
|
|
204
|
+
}
|
|
205
|
+
else {
|
|
206
|
+
console.log(chalk.gray(` ${locale.t('cli', 'init.toolDetection.detected', { tool: detectedTool })}`));
|
|
207
|
+
}
|
|
208
|
+
console.log('');
|
|
209
|
+
// Check if running in CI/non-interactive environment
|
|
210
|
+
const isCI = process.env.CI === 'true' ||
|
|
211
|
+
process.env.GITHUB_ACTIONS === 'true' ||
|
|
212
|
+
process.env.GITLAB_CI === 'true' ||
|
|
213
|
+
process.env.CIRCLECI === 'true' ||
|
|
214
|
+
!process.stdin.isTTY;
|
|
215
|
+
let confirmTool = true; // Default to yes
|
|
216
|
+
if (isCI) {
|
|
217
|
+
// In CI, automatically use detected tool without prompting
|
|
218
|
+
console.log(chalk.gray(` ${locale.t('cli', 'init.toolDetection.ciAutoConfirm', { tool: detectedTool })}`));
|
|
219
|
+
toolName = detectedTool;
|
|
220
|
+
}
|
|
221
|
+
else {
|
|
222
|
+
// Interactive mode - ask for confirmation
|
|
223
|
+
const response = await inquirer.prompt([
|
|
224
|
+
{
|
|
225
|
+
type: 'confirm',
|
|
226
|
+
name: 'confirmTool',
|
|
227
|
+
message: locale.t('cli', 'init.toolDetection.confirmPrompt', { tool: detectedTool }),
|
|
228
|
+
default: true
|
|
229
|
+
}
|
|
230
|
+
]);
|
|
231
|
+
confirmTool = response.confirmTool;
|
|
232
|
+
}
|
|
233
|
+
if (!confirmTool) {
|
|
234
|
+
// Let user choose from available tools
|
|
235
|
+
const { selectedTool } = await inquirer.prompt([
|
|
236
|
+
{
|
|
237
|
+
type: 'list',
|
|
238
|
+
name: 'selectedTool',
|
|
239
|
+
message: locale.t('cli', 'init.toolDetection.selectPrompt'),
|
|
240
|
+
choices: [
|
|
241
|
+
{ name: `Claude Code (Recommended - Full automation)`, value: 'claude' },
|
|
242
|
+
{ name: 'Cursor (Partial - AGENTS.md compilation, team commands, less reliable)', value: 'cursor' },
|
|
243
|
+
{ name: 'Other (Copilot, ChatGPT, Gemini - Limited: no hooks, manual workflow, high context usage)', value: 'generic' }
|
|
244
|
+
]
|
|
245
|
+
}
|
|
246
|
+
]);
|
|
247
|
+
toolName = selectedTool;
|
|
248
|
+
}
|
|
249
|
+
else {
|
|
250
|
+
// User confirmed detected tool
|
|
251
|
+
toolName = detectedTool;
|
|
252
|
+
}
|
|
253
|
+
spinner.start(`Using ${toolName}...`);
|
|
254
|
+
}
|
|
255
|
+
// 4. Create directory structure (adapter-specific)
|
|
256
|
+
createDirectoryStructure(targetDir, toolName);
|
|
257
|
+
spinner.text = 'Directory structure created...';
|
|
258
|
+
// 5. Configure GitHub marketplace for Claude Code
|
|
259
|
+
// ✅ NEW APPROACH: Claude Code fetches plugins from GitHub (no local copying!)
|
|
260
|
+
if (toolName === 'claude') {
|
|
261
|
+
try {
|
|
262
|
+
spinner.text = 'Configuring GitHub marketplace...';
|
|
263
|
+
// Settings.json will be created by setupClaudePluginAutoRegistration()
|
|
264
|
+
// No need to copy marketplace or plugins - everything is fetched from GitHub
|
|
265
|
+
spinner.succeed('GitHub marketplace configured');
|
|
266
|
+
console.log(chalk.gray(` ✓ Marketplace: github.com/anton-abyzov/specweave/.claude-plugin`));
|
|
267
|
+
console.log(chalk.gray(` ✓ Plugins fetch on-demand (no local copies = faster init)`));
|
|
268
|
+
}
|
|
269
|
+
catch (error) {
|
|
270
|
+
// Log errors in debug mode for troubleshooting
|
|
271
|
+
if (process.env.DEBUG) {
|
|
272
|
+
spinner.stop();
|
|
273
|
+
console.error(chalk.red(`\n❌ Marketplace setup error: ${error instanceof Error ? error.message : String(error)}`));
|
|
274
|
+
if (error instanceof Error && error.stack) {
|
|
275
|
+
console.error(chalk.gray(error.stack));
|
|
276
|
+
}
|
|
277
|
+
spinner.start();
|
|
278
|
+
}
|
|
279
|
+
console.warn(chalk.yellow(`\n${locale.t('cli', 'init.warnings.marketplaceCopyFailed')}`));
|
|
280
|
+
}
|
|
281
|
+
}
|
|
282
|
+
// 6. Copy base templates (config, README, CLAUDE.md - same for all)
|
|
283
|
+
const templatesDir = findSourceDir('templates');
|
|
284
|
+
await copyTemplates(templatesDir, targetDir, finalProjectName, language);
|
|
285
|
+
spinner.text = 'Base templates copied...';
|
|
286
|
+
// 6. Install based on tool
|
|
287
|
+
if (toolName === 'claude') {
|
|
288
|
+
// DEFAULT: Native Claude Code plugins (installed globally via /plugin install)
|
|
289
|
+
// No per-project copying needed - plugins work across all projects!
|
|
290
|
+
spinner.text = 'Configuring for Claude Code...';
|
|
291
|
+
console.log(`\n${locale.t('cli', 'init.claudeNativeComplete')}`);
|
|
292
|
+
console.log(` ${locale.t('cli', 'init.claudeNativeBenefits')}`);
|
|
293
|
+
}
|
|
294
|
+
else {
|
|
295
|
+
// Use adapter for non-Claude tools
|
|
296
|
+
spinner.text = `Installing ${toolName} adapter...`;
|
|
297
|
+
const adapter = adapterLoader.getAdapter(toolName);
|
|
298
|
+
if (!adapter) {
|
|
299
|
+
throw new Error(`Adapter not found: ${toolName}`);
|
|
300
|
+
}
|
|
301
|
+
await adapterLoader.checkRequirements(toolName);
|
|
302
|
+
await adapter.install({
|
|
303
|
+
projectPath: targetDir,
|
|
304
|
+
projectName: finalProjectName,
|
|
305
|
+
techStack: options.techStack ? { language: options.techStack } : undefined,
|
|
306
|
+
docsApproach: 'incremental'
|
|
307
|
+
});
|
|
308
|
+
// 6. Copy plugins/ folder for non-Claude adapters
|
|
309
|
+
// CRITICAL: Copilot/Cursor/Generic need local plugins/ folder!
|
|
310
|
+
// AGENTS.md instructs AI to read plugins/specweave/commands/*.md
|
|
311
|
+
// Without this folder, those commands don't exist in the project!
|
|
312
|
+
if (toolName !== 'claude') {
|
|
313
|
+
spinner.start('Copying plugins folder for command execution...');
|
|
314
|
+
try {
|
|
315
|
+
const specweavePackageRoot = findPackageRoot(__dirname);
|
|
316
|
+
if (specweavePackageRoot) {
|
|
317
|
+
const sourcePluginsDir = path.join(specweavePackageRoot, 'plugins');
|
|
318
|
+
const targetPluginsDir = path.join(targetDir, 'plugins');
|
|
319
|
+
if (fs.existsSync(sourcePluginsDir)) {
|
|
320
|
+
// Copy entire plugins/ folder from SpecWeave package to user project
|
|
321
|
+
fs.copySync(sourcePluginsDir, targetPluginsDir, {
|
|
322
|
+
overwrite: true,
|
|
323
|
+
filter: (src) => {
|
|
324
|
+
// Exclude .DS_Store and other hidden files
|
|
325
|
+
const basename = path.basename(src);
|
|
326
|
+
return !basename.startsWith('.');
|
|
327
|
+
}
|
|
328
|
+
});
|
|
329
|
+
spinner.succeed('Plugins folder copied successfully');
|
|
330
|
+
console.log(chalk.green(' ✔ AI can now execute SpecWeave commands'));
|
|
331
|
+
console.log(chalk.gray(' → Copilot/Cursor will read plugins/specweave/commands/*.md'));
|
|
332
|
+
}
|
|
333
|
+
else {
|
|
334
|
+
spinner.warn('Could not find plugins/ in SpecWeave package');
|
|
335
|
+
console.log(chalk.yellow(' → Command execution may not work without plugins/ folder'));
|
|
336
|
+
}
|
|
337
|
+
}
|
|
338
|
+
else {
|
|
339
|
+
spinner.warn('Could not locate SpecWeave package');
|
|
340
|
+
console.log(chalk.yellow(' → Skipping plugins/ folder copy'));
|
|
341
|
+
}
|
|
342
|
+
}
|
|
343
|
+
catch (error) {
|
|
344
|
+
spinner.warn('Could not copy plugins folder');
|
|
345
|
+
console.log(chalk.yellow(` ${error instanceof Error ? error.message : error}`));
|
|
346
|
+
}
|
|
347
|
+
}
|
|
348
|
+
// 7. Install core plugin for non-Claude adapters
|
|
349
|
+
// CRITICAL: Cursor/Copilot/Generic need plugin files in project!
|
|
350
|
+
// Claude uses plugin system (global), but others need local files for AGENTS.md/instructions.md
|
|
351
|
+
try {
|
|
352
|
+
spinner.start('Installing SpecWeave core plugin...');
|
|
353
|
+
// Load core plugin from plugins/specweave/
|
|
354
|
+
const corePluginPath = findSourceDir('plugins/specweave');
|
|
355
|
+
const { PluginLoader } = await import('../../core/plugin-loader.js');
|
|
356
|
+
const loader = new PluginLoader();
|
|
357
|
+
const corePlugin = await loader.loadFromDirectory(corePluginPath);
|
|
358
|
+
// Compile for adapter (Cursor → AGENTS.md, Copilot → instructions.md, etc.)
|
|
359
|
+
if (adapter.supportsPlugins()) {
|
|
360
|
+
await adapter.compilePlugin(corePlugin);
|
|
361
|
+
spinner.succeed('SpecWeave core plugin installed');
|
|
362
|
+
console.log(chalk.green(' ✔ Skills, agents, commands added to project'));
|
|
363
|
+
console.log(chalk.gray(` → ${corePlugin.skills.length} skills, ${corePlugin.agents.length} agents, ${corePlugin.commands.length} commands`));
|
|
364
|
+
}
|
|
365
|
+
else {
|
|
366
|
+
spinner.warn('Adapter does not support plugins');
|
|
367
|
+
console.log(chalk.yellow(' → Core functionality may be limited'));
|
|
368
|
+
}
|
|
369
|
+
}
|
|
370
|
+
catch (error) {
|
|
371
|
+
spinner.warn('Could not install core plugin');
|
|
372
|
+
console.log(chalk.yellow(` ${error instanceof Error ? error.message : error}`));
|
|
373
|
+
console.log(chalk.gray(' → You can manually reference plugin files if needed'));
|
|
374
|
+
}
|
|
375
|
+
}
|
|
376
|
+
// 9. Initialize git (skip if .git already exists)
|
|
377
|
+
const gitDir = path.join(targetDir, '.git');
|
|
378
|
+
if (!fs.existsSync(gitDir)) {
|
|
379
|
+
// Use secure command execution for git commands
|
|
380
|
+
const gitInitResult = execFileNoThrowSync('git', ['init'], { cwd: targetDir, shell: false });
|
|
381
|
+
if (gitInitResult.success) {
|
|
382
|
+
spinner.text = 'Git repository initialized...';
|
|
383
|
+
}
|
|
384
|
+
else {
|
|
385
|
+
spinner.warn('Git initialization skipped (git not found)');
|
|
386
|
+
}
|
|
387
|
+
// 10. Create initial commit (if git init succeeded)
|
|
388
|
+
if (gitInitResult.success) {
|
|
389
|
+
const gitAddResult = execFileNoThrowSync('git', ['add', '.'], { cwd: targetDir, shell: false });
|
|
390
|
+
if (gitAddResult.success) {
|
|
391
|
+
const gitCommitResult = execFileNoThrowSync('git', [
|
|
392
|
+
'commit',
|
|
393
|
+
'-m',
|
|
394
|
+
'Initial commit with SpecWeave'
|
|
395
|
+
], { cwd: targetDir, shell: false });
|
|
396
|
+
if (gitCommitResult.success) {
|
|
397
|
+
spinner.text = 'Initial commit created...';
|
|
398
|
+
}
|
|
399
|
+
// Git commit might fail if no user configured - that's ok, no need to warn
|
|
400
|
+
}
|
|
401
|
+
}
|
|
402
|
+
}
|
|
403
|
+
else {
|
|
404
|
+
spinner.text = 'Using existing Git repository...';
|
|
405
|
+
}
|
|
406
|
+
spinner.succeed('SpecWeave project created successfully!');
|
|
407
|
+
// 11. Show tool-specific next steps
|
|
408
|
+
if (toolName !== 'claude') {
|
|
409
|
+
const adapter = adapterLoader.getAdapter(toolName);
|
|
410
|
+
if (adapter) {
|
|
411
|
+
await adapter.postInstall({
|
|
412
|
+
projectPath: targetDir,
|
|
413
|
+
projectName: finalProjectName,
|
|
414
|
+
techStack: options.techStack ? { language: options.techStack } : undefined,
|
|
415
|
+
docsApproach: 'incremental'
|
|
416
|
+
});
|
|
417
|
+
}
|
|
418
|
+
}
|
|
419
|
+
// 13. Create config.json with language setting
|
|
420
|
+
createConfigFile(targetDir, finalProjectName, toolName, language, false);
|
|
421
|
+
// 14. Setup Claude Code plugin auto-registration (if Claude detected)
|
|
422
|
+
let autoInstallSucceeded = false;
|
|
423
|
+
if (toolName === 'claude') {
|
|
424
|
+
try {
|
|
425
|
+
setupClaudePluginAutoRegistration(targetDir, language);
|
|
426
|
+
}
|
|
427
|
+
catch (error) {
|
|
428
|
+
// Non-critical - show manual instructions in next steps
|
|
429
|
+
console.warn(chalk.yellow(`\n${locale.t('cli', 'init.warnings.pluginAutoSetupFailed')}`));
|
|
430
|
+
}
|
|
431
|
+
// 15. AUTO-INSTALL ALL PLUGINS via Claude CLI (Breaking Change: No selective loading)
|
|
432
|
+
// Pre-flight check: Is Claude CLI available? (ROBUST CHECK)
|
|
433
|
+
const claudeStatus = detectClaudeCli();
|
|
434
|
+
if (!claudeStatus.available) {
|
|
435
|
+
// Claude CLI NOT working → explain clearly with actionable diagnostics
|
|
436
|
+
const diagnostic = getClaudeCliDiagnostic(claudeStatus);
|
|
437
|
+
const suggestions = getClaudeCliSuggestions(claudeStatus);
|
|
438
|
+
spinner.warn(diagnostic);
|
|
439
|
+
console.log('');
|
|
440
|
+
console.log(chalk.yellow.bold('⚠️ Claude Code CLI Issue Detected'));
|
|
441
|
+
console.log('');
|
|
442
|
+
// Show detailed diagnostic info with MORE context
|
|
443
|
+
if (claudeStatus.commandExists) {
|
|
444
|
+
console.log(chalk.white('Found command in PATH, but verification failed:'));
|
|
445
|
+
console.log('');
|
|
446
|
+
if (claudeStatus.commandPath) {
|
|
447
|
+
console.log(chalk.gray(` Path: ${claudeStatus.commandPath}`));
|
|
448
|
+
}
|
|
449
|
+
if (claudeStatus.exitCode !== undefined) {
|
|
450
|
+
console.log(chalk.gray(` Exit code: ${claudeStatus.exitCode}`));
|
|
451
|
+
}
|
|
452
|
+
console.log(chalk.gray(` Issue: ${claudeStatus.error}`));
|
|
453
|
+
console.log('');
|
|
454
|
+
// Explain what this likely means
|
|
455
|
+
if (claudeStatus.error === 'version_check_failed') {
|
|
456
|
+
console.log(chalk.yellow('⚠️ This likely means:'));
|
|
457
|
+
console.log(chalk.gray(' • You have a DIFFERENT tool named "claude" in PATH'));
|
|
458
|
+
console.log(chalk.gray(' • It\'s not the Claude Code CLI from Anthropic'));
|
|
459
|
+
console.log(chalk.gray(' • The command exists but doesn\'t respond to --version'));
|
|
460
|
+
}
|
|
461
|
+
}
|
|
462
|
+
else {
|
|
463
|
+
console.log(chalk.white('Claude CLI not found in PATH'));
|
|
464
|
+
}
|
|
465
|
+
console.log('');
|
|
466
|
+
// Show actionable suggestions
|
|
467
|
+
console.log(chalk.cyan('💡 How to fix:'));
|
|
468
|
+
console.log('');
|
|
469
|
+
suggestions.forEach(suggestion => {
|
|
470
|
+
console.log(chalk.gray(` ${suggestion}`));
|
|
471
|
+
});
|
|
472
|
+
console.log('');
|
|
473
|
+
// Only show alternatives if user is NOT using Claude already
|
|
474
|
+
if (claudeStatus.error === 'command_not_found') {
|
|
475
|
+
console.log(chalk.cyan('Alternative Options:'));
|
|
476
|
+
console.log('');
|
|
477
|
+
console.log(chalk.white('1️⃣ Use Claude Code IDE (no CLI needed):'));
|
|
478
|
+
console.log(chalk.gray(' → Open this project in Claude Code'));
|
|
479
|
+
console.log(chalk.gray(' → Run: /plugin install specweave'));
|
|
480
|
+
console.log(chalk.gray(' → Works immediately, no npm installation!'));
|
|
481
|
+
console.log('');
|
|
482
|
+
console.log(chalk.white('2️⃣ Use Different AI Tool:'));
|
|
483
|
+
console.log(chalk.gray(' → Run: specweave init --adapter cursor'));
|
|
484
|
+
console.log(chalk.gray(' → Works without Claude CLI'));
|
|
485
|
+
console.log(chalk.gray(' → Less automation but no CLI dependency'));
|
|
486
|
+
console.log('');
|
|
487
|
+
}
|
|
488
|
+
autoInstallSucceeded = false;
|
|
489
|
+
}
|
|
490
|
+
else {
|
|
491
|
+
// Claude CLI available → install ALL plugins from marketplace
|
|
492
|
+
try {
|
|
493
|
+
// Step 1: FORCE marketplace refresh - remove and re-add from GitHub
|
|
494
|
+
spinner.start('Refreshing SpecWeave marketplace...');
|
|
495
|
+
const listResult = execFileNoThrowSync('claude', [
|
|
496
|
+
'plugin',
|
|
497
|
+
'marketplace',
|
|
498
|
+
'list'
|
|
499
|
+
]);
|
|
500
|
+
const marketplaceExists = listResult.success &&
|
|
501
|
+
(listResult.stdout || '').toLowerCase().includes('specweave');
|
|
502
|
+
if (marketplaceExists) {
|
|
503
|
+
// Always remove existing marketplace to ensure fresh install
|
|
504
|
+
execFileNoThrowSync('claude', [
|
|
505
|
+
'plugin',
|
|
506
|
+
'marketplace',
|
|
507
|
+
'remove',
|
|
508
|
+
'specweave'
|
|
509
|
+
]);
|
|
510
|
+
console.log(chalk.blue(' 🔄 Removed existing marketplace'));
|
|
511
|
+
}
|
|
512
|
+
// Add marketplace from GitHub (always fresh)
|
|
513
|
+
const addResult = execFileNoThrowSync('claude', [
|
|
514
|
+
'plugin',
|
|
515
|
+
'marketplace',
|
|
516
|
+
'add',
|
|
517
|
+
'anton-abyzov/specweave'
|
|
518
|
+
]);
|
|
519
|
+
if (!addResult.success) {
|
|
520
|
+
throw new Error('Failed to add marketplace from GitHub');
|
|
521
|
+
}
|
|
522
|
+
console.log(chalk.green(' ✔ Marketplace registered from GitHub'));
|
|
523
|
+
spinner.succeed('SpecWeave marketplace refreshed');
|
|
524
|
+
// Step 2: Load marketplace.json to get ALL available plugins
|
|
525
|
+
spinner.start('Loading available plugins...');
|
|
526
|
+
const marketplaceJsonPath = findSourceDir('.claude-plugin/marketplace.json');
|
|
527
|
+
if (!fs.existsSync(marketplaceJsonPath)) {
|
|
528
|
+
throw new Error('marketplace.json not found - cannot determine plugins to install');
|
|
529
|
+
}
|
|
530
|
+
const marketplace = JSON.parse(fs.readFileSync(marketplaceJsonPath, 'utf-8'));
|
|
531
|
+
const allPlugins = marketplace.plugins || [];
|
|
532
|
+
if (allPlugins.length === 0) {
|
|
533
|
+
throw new Error('No plugins found in marketplace.json');
|
|
534
|
+
}
|
|
535
|
+
console.log(chalk.blue(` 📦 Found ${allPlugins.length} plugins to install`));
|
|
536
|
+
spinner.succeed(`Found ${allPlugins.length} plugins`);
|
|
537
|
+
// Step 3: Install ALL plugins (no selective loading!)
|
|
538
|
+
let successCount = 0;
|
|
539
|
+
let failCount = 0;
|
|
540
|
+
const failedPlugins = [];
|
|
541
|
+
for (const plugin of allPlugins) {
|
|
542
|
+
const pluginName = plugin.name;
|
|
543
|
+
spinner.start(`Installing ${pluginName}...`);
|
|
544
|
+
const installResult = execFileNoThrowSync('claude', [
|
|
545
|
+
'plugin',
|
|
546
|
+
'install',
|
|
547
|
+
pluginName
|
|
548
|
+
]);
|
|
549
|
+
if (installResult.success) {
|
|
550
|
+
successCount++;
|
|
551
|
+
spinner.succeed(`${pluginName} installed`);
|
|
552
|
+
}
|
|
553
|
+
else {
|
|
554
|
+
failCount++;
|
|
555
|
+
failedPlugins.push(pluginName);
|
|
556
|
+
spinner.warn(`${pluginName} failed (will continue)`);
|
|
557
|
+
}
|
|
558
|
+
}
|
|
559
|
+
// Step 4: Report results
|
|
560
|
+
console.log('');
|
|
561
|
+
console.log(chalk.green.bold(`✅ Plugin Installation Complete`));
|
|
562
|
+
console.log(chalk.white(` Installed: ${successCount}/${allPlugins.length} plugins`));
|
|
563
|
+
if (failCount > 0) {
|
|
564
|
+
console.log(chalk.yellow(` Failed: ${failCount} plugins`));
|
|
565
|
+
console.log(chalk.gray(` Failed plugins: ${failedPlugins.join(', ')}`));
|
|
566
|
+
console.log(chalk.gray(` → You can install these manually later`));
|
|
567
|
+
}
|
|
568
|
+
console.log('');
|
|
569
|
+
console.log(chalk.cyan('📋 Available capabilities:'));
|
|
570
|
+
console.log(chalk.gray(' • /specweave:increment - Plan new features'));
|
|
571
|
+
console.log(chalk.gray(' • /specweave:do - Execute tasks'));
|
|
572
|
+
console.log(chalk.gray(' • /specweave-github:sync - GitHub integration'));
|
|
573
|
+
console.log(chalk.gray(' • /specweave-jira:sync - JIRA integration'));
|
|
574
|
+
console.log(chalk.gray(' • /specweave:docs preview - Documentation preview'));
|
|
575
|
+
console.log(chalk.gray(' • ...and more!'));
|
|
576
|
+
autoInstallSucceeded = successCount > 0;
|
|
577
|
+
}
|
|
578
|
+
catch (error) {
|
|
579
|
+
// Installation failed - provide helpful diagnostics
|
|
580
|
+
spinner.warn('Could not auto-install plugins');
|
|
581
|
+
console.log('');
|
|
582
|
+
// Diagnose error and provide actionable hints
|
|
583
|
+
if (error.message.includes('not found') || error.message.includes('ENOENT')) {
|
|
584
|
+
console.log(chalk.yellow(' Reason: Claude CLI found but command failed'));
|
|
585
|
+
console.log(chalk.gray(' → Try manually: /plugin install specweave'));
|
|
586
|
+
}
|
|
587
|
+
else if (error.message.includes('EACCES') || error.message.includes('permission')) {
|
|
588
|
+
console.log(chalk.yellow(' Reason: Permission denied'));
|
|
589
|
+
console.log(chalk.gray(' → Check file permissions or run with appropriate access'));
|
|
590
|
+
}
|
|
591
|
+
else if (error.message.includes('ECONNREFUSED') || error.message.includes('network')) {
|
|
592
|
+
console.log(chalk.yellow(' Reason: Network error'));
|
|
593
|
+
console.log(chalk.gray(' → Check internet connection and try again'));
|
|
594
|
+
}
|
|
595
|
+
else if (process.env.DEBUG) {
|
|
596
|
+
console.log(chalk.gray(` Error: ${error.message}`));
|
|
597
|
+
}
|
|
598
|
+
console.log('');
|
|
599
|
+
console.log(chalk.cyan('📦 Manual installation:'));
|
|
600
|
+
console.log(chalk.white(' /plugin install specweave'));
|
|
601
|
+
console.log(chalk.white(' /plugin install specweave-github'));
|
|
602
|
+
console.log(chalk.white(' ...etc.'));
|
|
603
|
+
console.log('');
|
|
604
|
+
autoInstallSucceeded = false;
|
|
605
|
+
}
|
|
606
|
+
}
|
|
607
|
+
// 10.5 Issue Tracker Integration (CRITICAL!)
|
|
608
|
+
// MUST happen AFTER plugin installation is complete
|
|
609
|
+
// Asks user: Which tracker? (GitHub/Jira/ADO/None)
|
|
610
|
+
// Collects credentials and runs smart validation
|
|
611
|
+
try {
|
|
612
|
+
const { setupIssueTracker } = await import('../helpers/issue-tracker/index.js');
|
|
613
|
+
await setupIssueTracker({
|
|
614
|
+
projectPath: targetDir,
|
|
615
|
+
language: language,
|
|
616
|
+
maxRetries: 3
|
|
617
|
+
});
|
|
618
|
+
}
|
|
619
|
+
catch (error) {
|
|
620
|
+
// Non-critical error - log but continue
|
|
621
|
+
if (process.env.DEBUG) {
|
|
622
|
+
console.error(chalk.red(`\n❌ Issue tracker setup error: ${error.message}`));
|
|
623
|
+
}
|
|
624
|
+
console.log(chalk.yellow('\n⚠️ Issue tracker setup skipped (can configure later)'));
|
|
625
|
+
}
|
|
626
|
+
}
|
|
627
|
+
showNextSteps(finalProjectName, toolName, language, usedDotNotation, toolName === 'claude' ? autoInstallSucceeded : undefined);
|
|
628
|
+
}
|
|
629
|
+
catch (error) {
|
|
630
|
+
spinner.fail('Failed to create project');
|
|
631
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.genericError')}`), error);
|
|
632
|
+
process.exit(1);
|
|
633
|
+
}
|
|
634
|
+
}
|
|
635
|
+
function createDirectoryStructure(targetDir, adapterName) {
|
|
636
|
+
const directories = [
|
|
637
|
+
// Core increment structure
|
|
638
|
+
'.specweave/increments',
|
|
639
|
+
// 6-pillar documentation structure
|
|
640
|
+
'.specweave/docs/internal/strategy', // Business specs (WHAT, WHY)
|
|
641
|
+
'.specweave/docs/internal/specs', // Feature specifications (detailed requirements)
|
|
642
|
+
'.specweave/docs/internal/architecture', // Technical design (HOW)
|
|
643
|
+
'.specweave/docs/internal/architecture/adr', // Architecture Decision Records
|
|
644
|
+
'.specweave/docs/internal/architecture/diagrams', // Architecture diagrams
|
|
645
|
+
'.specweave/docs/internal/delivery', // Roadmap, CI/CD, guides
|
|
646
|
+
'.specweave/docs/internal/operations', // Runbooks, SLOs
|
|
647
|
+
'.specweave/docs/internal/governance', // Security, compliance
|
|
648
|
+
'.specweave/docs/public', // Published documentation
|
|
649
|
+
];
|
|
650
|
+
// For Claude Code ONLY: Create .claude/ folder (for settings.json)
|
|
651
|
+
// Non-Claude adapters: NO .claude/ folder (they use plugins/ folder directly)
|
|
652
|
+
if (adapterName === 'claude') {
|
|
653
|
+
directories.push('.claude');
|
|
654
|
+
}
|
|
655
|
+
directories.forEach((dir) => {
|
|
656
|
+
fs.mkdirSync(path.join(targetDir, dir), { recursive: true });
|
|
657
|
+
});
|
|
658
|
+
}
|
|
659
|
+
async function copyTemplates(templatesDir, targetDir, projectName, language = 'en') {
|
|
660
|
+
const locale = getLocaleManager(language);
|
|
661
|
+
// Verify templates directory exists
|
|
662
|
+
if (!fs.existsSync(templatesDir)) {
|
|
663
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.templatesNotFound', { path: templatesDir })}`));
|
|
664
|
+
const packageRoot = findPackageRoot(__dirname);
|
|
665
|
+
if (packageRoot) {
|
|
666
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.packageRoot', { root: packageRoot })}`));
|
|
667
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.tryingAlternate')}`));
|
|
668
|
+
// Try src/templates as fallback
|
|
669
|
+
const altPath = path.join(packageRoot, 'src', 'templates');
|
|
670
|
+
if (fs.existsSync(altPath)) {
|
|
671
|
+
console.error(chalk.yellow(` ${locale.t('cli', 'init.errors.foundTemplatesAt', { path: altPath })}`));
|
|
672
|
+
templatesDir = altPath;
|
|
673
|
+
}
|
|
674
|
+
else {
|
|
675
|
+
throw new Error('Failed to locate templates directory');
|
|
676
|
+
}
|
|
677
|
+
}
|
|
678
|
+
else {
|
|
679
|
+
throw new Error('Failed to locate templates directory and package root');
|
|
680
|
+
}
|
|
681
|
+
}
|
|
682
|
+
// Copy README.md
|
|
683
|
+
const readmeTemplate = path.join(templatesDir, 'README.md.template');
|
|
684
|
+
if (fs.existsSync(readmeTemplate)) {
|
|
685
|
+
let readme = fs.readFileSync(readmeTemplate, 'utf-8');
|
|
686
|
+
readme = readme.replace(/{{PROJECT_NAME}}/g, projectName);
|
|
687
|
+
fs.writeFileSync(path.join(targetDir, 'README.md'), readme);
|
|
688
|
+
}
|
|
689
|
+
// Generate CLAUDE.md - PRIMARY instruction file for Claude Code
|
|
690
|
+
// CRITICAL: Claude Code ONLY reads CLAUDE.md (NOT AGENTS.md!)
|
|
691
|
+
// This is the native/baseline experience - skills, agents, hooks, slash commands
|
|
692
|
+
const skillsDir = findSourceDir('skills');
|
|
693
|
+
const agentsDir = findSourceDir('agents');
|
|
694
|
+
const commandsDir = findSourceDir('commands');
|
|
695
|
+
const claudeMdTemplatePath = path.normalize(path.join(templatesDir, 'CLAUDE.md.template'));
|
|
696
|
+
const claudeGen = new ClaudeMdGenerator(skillsDir, agentsDir, commandsDir);
|
|
697
|
+
const claudeMd = await claudeGen.generate({
|
|
698
|
+
projectName,
|
|
699
|
+
projectPath: targetDir,
|
|
700
|
+
templatePath: fs.existsSync(claudeMdTemplatePath) ? claudeMdTemplatePath : undefined
|
|
701
|
+
});
|
|
702
|
+
fs.writeFileSync(path.join(targetDir, 'CLAUDE.md'), claudeMd);
|
|
703
|
+
// Generate AGENTS.md - Universal file for ALL OTHER AI tools
|
|
704
|
+
// Following agents.md standard: https://agents.md/
|
|
705
|
+
// Used by: Cursor, Gemini CLI, Codex, GitHub Copilot, and ANY non-Claude tool
|
|
706
|
+
// NOTE: Claude Code does NOT read this file - it only reads CLAUDE.md above
|
|
707
|
+
// Replaces: .cursorrules, instructions.md, and other tool-specific files
|
|
708
|
+
const agentsMdTemplatePath = path.normalize(path.join(templatesDir, 'AGENTS.md.template'));
|
|
709
|
+
const agentsGen = new AgentsMdGenerator(skillsDir, agentsDir, commandsDir);
|
|
710
|
+
const agentsMd = await agentsGen.generate({
|
|
711
|
+
projectName,
|
|
712
|
+
projectPath: targetDir,
|
|
713
|
+
templatePath: fs.existsSync(agentsMdTemplatePath) ? agentsMdTemplatePath : undefined
|
|
714
|
+
});
|
|
715
|
+
fs.writeFileSync(path.join(targetDir, 'AGENTS.md'), agentsMd);
|
|
716
|
+
// Copy .gitignore
|
|
717
|
+
const gitignoreTemplate = path.join(templatesDir, '.gitignore.template');
|
|
718
|
+
if (fs.existsSync(gitignoreTemplate)) {
|
|
719
|
+
fs.copyFileSync(gitignoreTemplate, path.join(targetDir, '.gitignore'));
|
|
720
|
+
}
|
|
721
|
+
// Copy .gitattributes (forces LF line endings on all platforms, prevents Windows CRLF warnings)
|
|
722
|
+
const gitattributesTemplate = path.join(templatesDir, '.gitattributes.template');
|
|
723
|
+
if (fs.existsSync(gitattributesTemplate)) {
|
|
724
|
+
fs.copyFileSync(gitattributesTemplate, path.join(targetDir, '.gitattributes'));
|
|
725
|
+
}
|
|
726
|
+
}
|
|
727
|
+
/**
|
|
728
|
+
* Detect ALL parent directories that contain .specweave/ folders
|
|
729
|
+
* SpecWeave ONLY supports root-level .specweave/ folders
|
|
730
|
+
* Nested .specweave/ folders are NOT supported
|
|
731
|
+
*
|
|
732
|
+
* @param targetDir - Directory where user wants to initialize
|
|
733
|
+
* @returns Array of paths to parent .specweave/ folders with depth info, or null if none found
|
|
734
|
+
*/
|
|
735
|
+
function detectNestedSpecweave(targetDir) {
|
|
736
|
+
const foundFolders = [];
|
|
737
|
+
// Start from parent of target directory
|
|
738
|
+
let currentDir = path.dirname(path.resolve(targetDir));
|
|
739
|
+
const root = path.parse(currentDir).root;
|
|
740
|
+
let depth = 1;
|
|
741
|
+
// Walk up the directory tree and find ALL .specweave/ folders
|
|
742
|
+
while (currentDir !== root) {
|
|
743
|
+
const specweavePath = path.join(currentDir, '.specweave');
|
|
744
|
+
// Check if .specweave/ exists at this level
|
|
745
|
+
if (fs.existsSync(specweavePath)) {
|
|
746
|
+
foundFolders.push({ path: currentDir, depth });
|
|
747
|
+
}
|
|
748
|
+
// Move up one level
|
|
749
|
+
const parentDir = path.dirname(currentDir);
|
|
750
|
+
if (parentDir === currentDir)
|
|
751
|
+
break; // Reached root
|
|
752
|
+
currentDir = parentDir;
|
|
753
|
+
depth++;
|
|
754
|
+
}
|
|
755
|
+
return foundFolders.length > 0 ? foundFolders : null;
|
|
756
|
+
}
|
|
757
|
+
/**
|
|
758
|
+
* Find the package root by walking up the directory tree looking for package.json
|
|
759
|
+
* This works reliably on all platforms including Windows with UNC paths
|
|
760
|
+
*/
|
|
761
|
+
function findPackageRoot(startDir) {
|
|
762
|
+
let currentDir = startDir;
|
|
763
|
+
const root = path.parse(currentDir).root;
|
|
764
|
+
while (currentDir !== root) {
|
|
765
|
+
const packageJsonPath = path.join(currentDir, 'package.json');
|
|
766
|
+
if (fs.existsSync(packageJsonPath)) {
|
|
767
|
+
try {
|
|
768
|
+
const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));
|
|
769
|
+
// Verify this is the specweave package
|
|
770
|
+
if (packageJson.name === 'specweave') {
|
|
771
|
+
return currentDir;
|
|
772
|
+
}
|
|
773
|
+
}
|
|
774
|
+
catch (error) {
|
|
775
|
+
// Not a valid package.json, continue searching
|
|
776
|
+
}
|
|
777
|
+
}
|
|
778
|
+
const parentDir = path.dirname(currentDir);
|
|
779
|
+
if (parentDir === currentDir)
|
|
780
|
+
break; // Reached root
|
|
781
|
+
currentDir = parentDir;
|
|
782
|
+
}
|
|
783
|
+
return null;
|
|
784
|
+
}
|
|
785
|
+
/**
|
|
786
|
+
* Find the source directory, trying multiple possible locations
|
|
787
|
+
* Handles both development and installed package scenarios
|
|
788
|
+
* Windows-compatible with proper path normalization
|
|
789
|
+
*/
|
|
790
|
+
function findSourceDir(relativePath) {
|
|
791
|
+
// First, try to find package root by walking up from __dirname
|
|
792
|
+
const packageRoot = findPackageRoot(__dirname);
|
|
793
|
+
if (packageRoot) {
|
|
794
|
+
// Try directly in package root FIRST (for plugins/, .claude-plugin/)
|
|
795
|
+
// This is critical because package.json includes these folders for npm publish
|
|
796
|
+
const rootPath = path.normalize(path.join(packageRoot, relativePath));
|
|
797
|
+
if (fs.existsSync(rootPath)) {
|
|
798
|
+
return rootPath;
|
|
799
|
+
}
|
|
800
|
+
// Try src/ directory (for templates/, utils/, etc.)
|
|
801
|
+
const srcPath = path.normalize(path.join(packageRoot, 'src', relativePath));
|
|
802
|
+
if (fs.existsSync(srcPath)) {
|
|
803
|
+
return srcPath;
|
|
804
|
+
}
|
|
805
|
+
// Try dist/ directory (fallback for compiled outputs)
|
|
806
|
+
const distPath = path.normalize(path.join(packageRoot, 'dist', relativePath));
|
|
807
|
+
if (fs.existsSync(distPath)) {
|
|
808
|
+
return distPath;
|
|
809
|
+
}
|
|
810
|
+
}
|
|
811
|
+
// Fallback: Try multiple possible locations relative to __dirname
|
|
812
|
+
const possiblePaths = [
|
|
813
|
+
// Development: dist/cli/commands -> src/
|
|
814
|
+
path.normalize(path.join(__dirname, '../../..', relativePath)),
|
|
815
|
+
// Installed: node_modules/specweave/dist/cli/commands -> node_modules/specweave/src/
|
|
816
|
+
path.normalize(path.join(__dirname, '../../../src', relativePath)),
|
|
817
|
+
// Alternative: go up from dist/ to package root, then to src/
|
|
818
|
+
path.normalize(path.join(__dirname, '../../..', 'src', relativePath)),
|
|
819
|
+
// Absolute from package root (for global installs)
|
|
820
|
+
path.resolve(__dirname, '../../../src', relativePath),
|
|
821
|
+
];
|
|
822
|
+
for (const testPath of possiblePaths) {
|
|
823
|
+
if (fs.existsSync(testPath)) {
|
|
824
|
+
return testPath;
|
|
825
|
+
}
|
|
826
|
+
}
|
|
827
|
+
// If nothing found, return the first path and let the caller handle the error
|
|
828
|
+
return possiblePaths[0];
|
|
829
|
+
}
|
|
830
|
+
function copyCommands(commandsDir, targetCommandsDir, language) {
|
|
831
|
+
const locale = getLocaleManager(language);
|
|
832
|
+
// v0.4.0+: Commands moved to plugins/specweave/commands/
|
|
833
|
+
const sourceDir = findSourceDir('plugins/specweave/commands');
|
|
834
|
+
if (!fs.existsSync(sourceDir)) {
|
|
835
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.sourceNotFound', { type: 'commands' })}`));
|
|
836
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.expectedAt', { path: sourceDir })}`));
|
|
837
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.dirname', { path: __dirname })}`));
|
|
838
|
+
const packageRoot = findPackageRoot(__dirname);
|
|
839
|
+
if (packageRoot) {
|
|
840
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.packageRoot', { root: packageRoot })}`));
|
|
841
|
+
}
|
|
842
|
+
else {
|
|
843
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.couldNotFindRoot')}`));
|
|
844
|
+
}
|
|
845
|
+
throw new Error('Failed to locate source commands directory. This may be a Windows path resolution issue.');
|
|
846
|
+
}
|
|
847
|
+
// Validate source directory contains files
|
|
848
|
+
const sourceFiles = fs.readdirSync(sourceDir).filter(f => f.endsWith('.md'));
|
|
849
|
+
if (sourceFiles.length === 0) {
|
|
850
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.sourceEmpty', { type: 'commands' })}`));
|
|
851
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.directory', { path: sourceDir })}`));
|
|
852
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.installationIssue')}`));
|
|
853
|
+
throw new Error('Source commands directory exists but contains no .md files');
|
|
854
|
+
}
|
|
855
|
+
try {
|
|
856
|
+
// Ensure target directory exists
|
|
857
|
+
fs.ensureDirSync(targetCommandsDir);
|
|
858
|
+
// Copy each command file and inject system prompts if needed
|
|
859
|
+
for (const file of sourceFiles) {
|
|
860
|
+
const sourcePath = path.join(sourceDir, file);
|
|
861
|
+
const targetPath = path.join(targetCommandsDir, file);
|
|
862
|
+
// Read, potentially inject, and write
|
|
863
|
+
const content = fs.readFileSync(sourcePath, 'utf-8');
|
|
864
|
+
const modifiedContent = language !== 'en'
|
|
865
|
+
? injectSystemPromptForInit(content, language)
|
|
866
|
+
: content;
|
|
867
|
+
fs.writeFileSync(targetPath, modifiedContent, 'utf-8');
|
|
868
|
+
}
|
|
869
|
+
// Validate files were copied
|
|
870
|
+
const copiedFiles = fs.readdirSync(targetCommandsDir).filter(f => f.endsWith('.md'));
|
|
871
|
+
if (copiedFiles.length === 0) {
|
|
872
|
+
throw new Error(`Copy completed but no files found in target directory: ${targetCommandsDir}`);
|
|
873
|
+
}
|
|
874
|
+
console.log(chalk.gray(` ${locale.t('cli', 'init.info.copiedFiles', { count: copiedFiles.length })}`));
|
|
875
|
+
}
|
|
876
|
+
catch (error) {
|
|
877
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.errorCopying', { type: 'commands', error: error.message })}`));
|
|
878
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.source', { path: sourceDir })}`));
|
|
879
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.target', { path: targetCommandsDir })}`));
|
|
880
|
+
throw error;
|
|
881
|
+
}
|
|
882
|
+
}
|
|
883
|
+
function copyAgents(agentsDir, targetAgentsDir, language) {
|
|
884
|
+
const locale = getLocaleManager(language);
|
|
885
|
+
// v0.4.0+: Agents moved to plugins/specweave/agents/
|
|
886
|
+
const sourceDir = findSourceDir('plugins/specweave/agents');
|
|
887
|
+
if (!fs.existsSync(sourceDir)) {
|
|
888
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.sourceNotFound', { type: 'agents' })}`));
|
|
889
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.expectedAt', { path: sourceDir })}`));
|
|
890
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.dirname', { path: __dirname })}`));
|
|
891
|
+
const packageRoot = findPackageRoot(__dirname);
|
|
892
|
+
if (packageRoot) {
|
|
893
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.packageRoot', { root: packageRoot })}`));
|
|
894
|
+
}
|
|
895
|
+
else {
|
|
896
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.couldNotFindRoot')}`));
|
|
897
|
+
}
|
|
898
|
+
throw new Error('Failed to locate source agents directory. This may be a Windows path resolution issue.');
|
|
899
|
+
}
|
|
900
|
+
// Validate source directory contains subdirectories with AGENT.md files
|
|
901
|
+
const agentDirs = fs.readdirSync(sourceDir, { withFileTypes: true })
|
|
902
|
+
.filter(dirent => dirent.isDirectory());
|
|
903
|
+
if (agentDirs.length === 0) {
|
|
904
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.sourceEmpty', { type: 'agents' })}`));
|
|
905
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.directory', { path: sourceDir })}`));
|
|
906
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.installationIssue')}`));
|
|
907
|
+
throw new Error('Source agents directory exists but contains no agent subdirectories');
|
|
908
|
+
}
|
|
909
|
+
try {
|
|
910
|
+
// Ensure target directory exists
|
|
911
|
+
fs.ensureDirSync(targetAgentsDir);
|
|
912
|
+
// Copy each agent directory and inject system prompts if needed
|
|
913
|
+
for (const agentDir of agentDirs) {
|
|
914
|
+
const sourcePath = path.join(sourceDir, agentDir.name);
|
|
915
|
+
const targetPath = path.join(targetAgentsDir, agentDir.name);
|
|
916
|
+
// Copy entire agent directory first
|
|
917
|
+
fs.copySync(sourcePath, targetPath, {
|
|
918
|
+
overwrite: true,
|
|
919
|
+
errorOnExist: false
|
|
920
|
+
});
|
|
921
|
+
// Then inject system prompt into AGENT.md if language !== 'en'
|
|
922
|
+
if (language !== 'en') {
|
|
923
|
+
const agentMdPath = path.join(targetPath, 'AGENT.md');
|
|
924
|
+
if (fs.existsSync(agentMdPath)) {
|
|
925
|
+
const content = fs.readFileSync(agentMdPath, 'utf-8');
|
|
926
|
+
const modifiedContent = injectSystemPromptForInit(content, language);
|
|
927
|
+
fs.writeFileSync(agentMdPath, modifiedContent, 'utf-8');
|
|
928
|
+
}
|
|
929
|
+
}
|
|
930
|
+
}
|
|
931
|
+
// Validate subdirectories were copied
|
|
932
|
+
const copiedDirs = fs.readdirSync(targetAgentsDir, { withFileTypes: true })
|
|
933
|
+
.filter(dirent => dirent.isDirectory());
|
|
934
|
+
if (copiedDirs.length === 0) {
|
|
935
|
+
throw new Error(`Copy completed but no agent directories found in target: ${targetAgentsDir}`);
|
|
936
|
+
}
|
|
937
|
+
console.log(chalk.gray(` ${locale.t('cli', 'init.info.copiedAgents', { count: copiedDirs.length })}`));
|
|
938
|
+
}
|
|
939
|
+
catch (error) {
|
|
940
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.errorCopying', { type: 'agents', error: error.message })}`));
|
|
941
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.source', { path: sourceDir })}`));
|
|
942
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.target', { path: targetAgentsDir })}`));
|
|
943
|
+
throw error;
|
|
944
|
+
}
|
|
945
|
+
}
|
|
946
|
+
/**
|
|
947
|
+
* Inject system prompt for non-English languages
|
|
948
|
+
*/
|
|
949
|
+
function injectSystemPromptForInit(content, language) {
|
|
950
|
+
if (language === 'en') {
|
|
951
|
+
return content; // No changes for English
|
|
952
|
+
}
|
|
953
|
+
const systemPrompt = getSystemPromptForLanguage(language);
|
|
954
|
+
// Inject after YAML frontmatter if present
|
|
955
|
+
if (content.startsWith('---')) {
|
|
956
|
+
const endOfFrontmatter = content.indexOf('---', 3);
|
|
957
|
+
if (endOfFrontmatter !== -1) {
|
|
958
|
+
const frontmatter = content.substring(0, endOfFrontmatter + 3);
|
|
959
|
+
const body = content.substring(endOfFrontmatter + 3);
|
|
960
|
+
return `${frontmatter}\n\n${systemPrompt}\n${body}`;
|
|
961
|
+
}
|
|
962
|
+
}
|
|
963
|
+
// No frontmatter - inject at the top
|
|
964
|
+
return `${systemPrompt}\n\n${content}`;
|
|
965
|
+
}
|
|
966
|
+
function copySkills(skillsDir, targetSkillsDir, language) {
|
|
967
|
+
const locale = getLocaleManager(language);
|
|
968
|
+
// v0.4.0+: Skills moved to plugins/specweave/skills/
|
|
969
|
+
const sourceDir = findSourceDir('plugins/specweave/skills');
|
|
970
|
+
if (!fs.existsSync(sourceDir)) {
|
|
971
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.sourceNotFound', { type: 'skills' })}`));
|
|
972
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.expectedAt', { path: sourceDir })}`));
|
|
973
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.dirname', { path: __dirname })}`));
|
|
974
|
+
const packageRoot = findPackageRoot(__dirname);
|
|
975
|
+
if (packageRoot) {
|
|
976
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.packageRoot', { root: packageRoot })}`));
|
|
977
|
+
}
|
|
978
|
+
else {
|
|
979
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.couldNotFindRoot')}`));
|
|
980
|
+
}
|
|
981
|
+
throw new Error('Failed to locate source skills directory. This may be a Windows path resolution issue.');
|
|
982
|
+
}
|
|
983
|
+
// Validate source directory contains subdirectories with SKILL.md files
|
|
984
|
+
const skillDirs = fs.readdirSync(sourceDir, { withFileTypes: true })
|
|
985
|
+
.filter(dirent => dirent.isDirectory());
|
|
986
|
+
if (skillDirs.length === 0) {
|
|
987
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.sourceEmpty', { type: 'skills' })}`));
|
|
988
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.directory', { path: sourceDir })}`));
|
|
989
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.installationIssue')}`));
|
|
990
|
+
throw new Error('Source skills directory exists but contains no skill subdirectories');
|
|
991
|
+
}
|
|
992
|
+
try {
|
|
993
|
+
// Ensure target directory exists
|
|
994
|
+
fs.ensureDirSync(targetSkillsDir);
|
|
995
|
+
// Copy each skill directory and inject system prompts if needed
|
|
996
|
+
for (const skillDir of skillDirs) {
|
|
997
|
+
const sourcePath = path.join(sourceDir, skillDir.name);
|
|
998
|
+
const targetPath = path.join(targetSkillsDir, skillDir.name);
|
|
999
|
+
// Copy entire skill directory first
|
|
1000
|
+
fs.copySync(sourcePath, targetPath, {
|
|
1001
|
+
overwrite: true,
|
|
1002
|
+
errorOnExist: false
|
|
1003
|
+
});
|
|
1004
|
+
// Then inject system prompt into SKILL.md if language !== 'en'
|
|
1005
|
+
if (language !== 'en') {
|
|
1006
|
+
const skillMdPath = path.join(targetPath, 'SKILL.md');
|
|
1007
|
+
if (fs.existsSync(skillMdPath)) {
|
|
1008
|
+
const content = fs.readFileSync(skillMdPath, 'utf-8');
|
|
1009
|
+
const modifiedContent = injectSystemPromptForInit(content, language);
|
|
1010
|
+
fs.writeFileSync(skillMdPath, modifiedContent, 'utf-8');
|
|
1011
|
+
}
|
|
1012
|
+
}
|
|
1013
|
+
}
|
|
1014
|
+
// Validate subdirectories were copied
|
|
1015
|
+
const copiedDirs = fs.readdirSync(targetSkillsDir, { withFileTypes: true })
|
|
1016
|
+
.filter(dirent => dirent.isDirectory());
|
|
1017
|
+
if (copiedDirs.length === 0) {
|
|
1018
|
+
throw new Error(`Copy completed but no skill directories found in target: ${targetSkillsDir}`);
|
|
1019
|
+
}
|
|
1020
|
+
console.log(chalk.gray(` ${locale.t('cli', 'init.info.copiedSkills', { count: copiedDirs.length })}`));
|
|
1021
|
+
}
|
|
1022
|
+
catch (error) {
|
|
1023
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.errorCopying', { type: 'skills', error: error.message })}`));
|
|
1024
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.source', { path: sourceDir })}`));
|
|
1025
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.target', { path: targetSkillsDir })}`));
|
|
1026
|
+
throw error;
|
|
1027
|
+
}
|
|
1028
|
+
}
|
|
1029
|
+
function copyHooks(hooksDir, targetHooksDir, language = 'en') {
|
|
1030
|
+
const locale = getLocaleManager(language);
|
|
1031
|
+
// v0.4.0+: Hooks moved to plugins/specweave/hooks/
|
|
1032
|
+
const sourceDir = findSourceDir('plugins/specweave/hooks');
|
|
1033
|
+
if (!fs.existsSync(sourceDir)) {
|
|
1034
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.sourceNotFound', { type: 'hooks' })}`));
|
|
1035
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.expectedAt', { path: sourceDir })}`));
|
|
1036
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.dirname', { path: __dirname })}`));
|
|
1037
|
+
const packageRoot = findPackageRoot(__dirname);
|
|
1038
|
+
if (packageRoot) {
|
|
1039
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.packageRoot', { root: packageRoot })}`));
|
|
1040
|
+
}
|
|
1041
|
+
else {
|
|
1042
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.couldNotFindRoot')}`));
|
|
1043
|
+
}
|
|
1044
|
+
throw new Error('Failed to locate source hooks directory. This may be a Windows path resolution issue.');
|
|
1045
|
+
}
|
|
1046
|
+
// Validate source directory contains hook files
|
|
1047
|
+
const hookFiles = fs.readdirSync(sourceDir).filter(f => f.endsWith('.sh') || f === 'README.md');
|
|
1048
|
+
if (hookFiles.length === 0) {
|
|
1049
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.sourceEmpty', { type: 'hooks' })}`));
|
|
1050
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.directory', { path: sourceDir })}`));
|
|
1051
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.installationIssue')}`));
|
|
1052
|
+
throw new Error('Source hooks directory exists but contains no hook files');
|
|
1053
|
+
}
|
|
1054
|
+
try {
|
|
1055
|
+
// Ensure target directory exists
|
|
1056
|
+
fs.ensureDirSync(targetHooksDir);
|
|
1057
|
+
// Copy all files from source to target
|
|
1058
|
+
fs.copySync(sourceDir, targetHooksDir, {
|
|
1059
|
+
overwrite: true,
|
|
1060
|
+
errorOnExist: false
|
|
1061
|
+
});
|
|
1062
|
+
// Validate files were copied
|
|
1063
|
+
const copiedFiles = fs.readdirSync(targetHooksDir).filter(f => f.endsWith('.sh') || f === 'README.md');
|
|
1064
|
+
if (copiedFiles.length === 0) {
|
|
1065
|
+
throw new Error(`Copy completed but no hook files found in target: ${targetHooksDir}`);
|
|
1066
|
+
}
|
|
1067
|
+
console.log(chalk.gray(` ${locale.t('cli', 'init.info.copiedHooks', { count: copiedFiles.length })}`));
|
|
1068
|
+
}
|
|
1069
|
+
catch (error) {
|
|
1070
|
+
console.error(chalk.red(`\n${locale.t('cli', 'init.errors.errorCopying', { type: 'hooks', error: error.message })}`));
|
|
1071
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.source', { path: sourceDir })}`));
|
|
1072
|
+
console.error(chalk.red(` ${locale.t('cli', 'init.errors.target', { path: targetHooksDir })}`));
|
|
1073
|
+
throw error;
|
|
1074
|
+
}
|
|
1075
|
+
}
|
|
1076
|
+
/**
|
|
1077
|
+
* Create .specweave/config.json with project settings
|
|
1078
|
+
*/
|
|
1079
|
+
function createConfigFile(targetDir, projectName, adapter, language, enableDocsPreview = true) {
|
|
1080
|
+
const configPath = path.join(targetDir, '.specweave', 'config.json');
|
|
1081
|
+
const config = {
|
|
1082
|
+
project: {
|
|
1083
|
+
name: projectName,
|
|
1084
|
+
version: '0.1.0',
|
|
1085
|
+
},
|
|
1086
|
+
adapters: {
|
|
1087
|
+
default: adapter,
|
|
1088
|
+
},
|
|
1089
|
+
// Documentation preview settings (for Claude Code only)
|
|
1090
|
+
...(adapter === 'claude' && {
|
|
1091
|
+
documentation: {
|
|
1092
|
+
preview: {
|
|
1093
|
+
enabled: enableDocsPreview,
|
|
1094
|
+
autoInstall: false, // Lazy install on first use
|
|
1095
|
+
port: 3015, // Internal docs (avoid port 3000 - used by React/Next.js/Vite)
|
|
1096
|
+
openBrowser: true,
|
|
1097
|
+
theme: 'default',
|
|
1098
|
+
excludeFolders: ['legacy', 'node_modules']
|
|
1099
|
+
}
|
|
1100
|
+
}
|
|
1101
|
+
}),
|
|
1102
|
+
// Only include language if non-English
|
|
1103
|
+
...(language !== 'en' && {
|
|
1104
|
+
language,
|
|
1105
|
+
translation: {
|
|
1106
|
+
method: 'in-session',
|
|
1107
|
+
autoTranslateLivingDocs: false,
|
|
1108
|
+
keepFrameworkTerms: true,
|
|
1109
|
+
keepTechnicalTerms: true,
|
|
1110
|
+
translateCodeComments: true,
|
|
1111
|
+
translateVariableNames: false,
|
|
1112
|
+
},
|
|
1113
|
+
}),
|
|
1114
|
+
};
|
|
1115
|
+
fs.writeJsonSync(configPath, config, { spaces: 2 });
|
|
1116
|
+
}
|
|
1117
|
+
/**
|
|
1118
|
+
* Setup Claude Code automatic plugin registration
|
|
1119
|
+
* Creates .claude/settings.json with extraKnownMarketplaces
|
|
1120
|
+
* This triggers Claude's native auto-install when users trust the folder
|
|
1121
|
+
*/
|
|
1122
|
+
function setupClaudePluginAutoRegistration(targetDir, language) {
|
|
1123
|
+
const locale = getLocaleManager(language);
|
|
1124
|
+
const settingsPath = path.join(targetDir, '.claude', 'settings.json');
|
|
1125
|
+
// Create settings.json with GitHub marketplace registration
|
|
1126
|
+
// ✅ Claude Code fetches plugins from GitHub (no local marketplace files needed!)
|
|
1127
|
+
const settings = {
|
|
1128
|
+
extraKnownMarketplaces: {
|
|
1129
|
+
specweave: {
|
|
1130
|
+
source: {
|
|
1131
|
+
source: 'github',
|
|
1132
|
+
repo: 'anton-abyzov/specweave',
|
|
1133
|
+
path: '.claude-plugin'
|
|
1134
|
+
}
|
|
1135
|
+
}
|
|
1136
|
+
}
|
|
1137
|
+
};
|
|
1138
|
+
try {
|
|
1139
|
+
fs.writeJsonSync(settingsPath, settings, { spaces: 2 });
|
|
1140
|
+
console.log(chalk.green(`\n✅ ${locale.t('cli', 'init.success.pluginAutoSetup')}`));
|
|
1141
|
+
console.log(chalk.gray(` Marketplace: github.com/anton-abyzov/specweave/.claude-plugin`));
|
|
1142
|
+
console.log(chalk.gray(` Plugins will be fetched from GitHub (always up-to-date)`));
|
|
1143
|
+
}
|
|
1144
|
+
catch (error) {
|
|
1145
|
+
throw new Error(`Failed to create .claude/settings.json: ${error.message}`);
|
|
1146
|
+
}
|
|
1147
|
+
}
|
|
1148
|
+
function showNextSteps(projectName, adapterName, language, usedDotNotation = false, pluginAutoInstalled = false) {
|
|
1149
|
+
const locale = getLocaleManager(language);
|
|
1150
|
+
console.log('');
|
|
1151
|
+
console.log(chalk.cyan.bold(locale.t('cli', 'init.nextSteps.header')));
|
|
1152
|
+
console.log('');
|
|
1153
|
+
let stepNumber = 1;
|
|
1154
|
+
// Only show "cd" step if we created a subdirectory
|
|
1155
|
+
if (!usedDotNotation) {
|
|
1156
|
+
console.log(` ${stepNumber}. ${chalk.white(locale.t('cli', 'init.nextSteps.cd', { projectName }))}`);
|
|
1157
|
+
console.log('');
|
|
1158
|
+
stepNumber++;
|
|
1159
|
+
}
|
|
1160
|
+
// Adapter-specific instructions
|
|
1161
|
+
if (adapterName === 'claude') {
|
|
1162
|
+
console.log(` ${stepNumber}. ${chalk.white(locale.t('cli', 'init.nextSteps.claude.step1'))}`);
|
|
1163
|
+
console.log('');
|
|
1164
|
+
stepNumber++;
|
|
1165
|
+
// Only show manual install if auto-install failed
|
|
1166
|
+
if (!pluginAutoInstalled) {
|
|
1167
|
+
console.log(` ${stepNumber}. ${chalk.yellow.bold('⚠️ ' + locale.t('cli', 'init.nextSteps.claude.step2'))}`);
|
|
1168
|
+
console.log(` ${chalk.cyan.bold(locale.t('cli', 'init.nextSteps.claude.installCore'))}`);
|
|
1169
|
+
console.log(` ${chalk.gray('↑ Required for slash commands like /specweave:increment')}`);
|
|
1170
|
+
console.log('');
|
|
1171
|
+
stepNumber++;
|
|
1172
|
+
}
|
|
1173
|
+
console.log(` ${stepNumber}. ${chalk.white('All plugins are already installed!')}`);
|
|
1174
|
+
console.log(` ${chalk.gray('✔ All 19+ SpecWeave plugins installed automatically')}`);
|
|
1175
|
+
console.log(` ${chalk.gray('✔ No need to install additional plugins manually')}`);
|
|
1176
|
+
console.log(` ${chalk.gray('✔ Full capabilities available immediately')}`);
|
|
1177
|
+
console.log('');
|
|
1178
|
+
stepNumber++;
|
|
1179
|
+
console.log(` ${stepNumber}. ${chalk.white(locale.t('cli', 'init.nextSteps.claude.step4'))}`);
|
|
1180
|
+
console.log(` ${chalk.cyan(locale.t('cli', 'init.nextSteps.claude.example'))}`);
|
|
1181
|
+
console.log(` ${chalk.gray(locale.t('cli', 'init.nextSteps.claude.autoActivate'))}`);
|
|
1182
|
+
}
|
|
1183
|
+
else if (adapterName === 'cursor') {
|
|
1184
|
+
console.log(` ${stepNumber}. ${chalk.white(locale.t('cli', 'init.nextSteps.cursor.step1'))}`);
|
|
1185
|
+
console.log('');
|
|
1186
|
+
console.log(` ${stepNumber + 1}. ${chalk.white(locale.t('cli', 'init.nextSteps.cursor.step2'))}`);
|
|
1187
|
+
console.log(` ${locale.t('cli', 'init.nextSteps.cursor.guide')}`);
|
|
1188
|
+
console.log('');
|
|
1189
|
+
console.log(` ${stepNumber + 2}. ${chalk.white(locale.t('cli', 'init.nextSteps.cursor.step3'))}`);
|
|
1190
|
+
console.log(` ${locale.t('cli', 'init.nextSteps.cursor.shortcuts')}`);
|
|
1191
|
+
}
|
|
1192
|
+
else if (adapterName === 'generic') {
|
|
1193
|
+
console.log(` ${stepNumber}. ${chalk.white(locale.t('cli', 'init.nextSteps.generic.step1'))}`);
|
|
1194
|
+
console.log('');
|
|
1195
|
+
console.log(` ${stepNumber + 1}. ${chalk.white(locale.t('cli', 'init.nextSteps.generic.step2'))}`);
|
|
1196
|
+
console.log(` ${locale.t('cli', 'init.nextSteps.generic.compatibility')}`);
|
|
1197
|
+
}
|
|
1198
|
+
console.log('');
|
|
1199
|
+
console.log(chalk.green.bold(locale.t('cli', 'init.nextSteps.footer')));
|
|
1200
|
+
console.log('');
|
|
1201
|
+
console.log(chalk.gray(locale.t('cli', 'init.nextSteps.docsLink')));
|
|
1202
|
+
console.log(chalk.gray(locale.t('cli', 'init.nextSteps.githubLink')));
|
|
1203
|
+
console.log('');
|
|
1204
|
+
}
|
|
1205
|
+
//# sourceMappingURL=init.js.map
|