@modus-ai/modus 0.1.4 → 0.1.5

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.
Files changed (39) hide show
  1. package/README.md +76 -28
  2. package/dist/cli/index.js +188 -12
  3. package/dist/cli/index.js.map +1 -1
  4. package/dist/commands/doctor.d.ts +2 -0
  5. package/dist/commands/doctor.d.ts.map +1 -0
  6. package/dist/commands/doctor.js +180 -0
  7. package/dist/commands/doctor.js.map +1 -0
  8. package/dist/commands/init.d.ts +12 -0
  9. package/dist/commands/init.d.ts.map +1 -1
  10. package/dist/commands/init.js +260 -6
  11. package/dist/commands/init.js.map +1 -1
  12. package/dist/commands/skill.d.ts +7 -0
  13. package/dist/commands/skill.d.ts.map +1 -0
  14. package/dist/commands/skill.js +175 -0
  15. package/dist/commands/skill.js.map +1 -0
  16. package/dist/commands/status.d.ts +2 -0
  17. package/dist/commands/status.d.ts.map +1 -0
  18. package/dist/commands/status.js +133 -0
  19. package/dist/commands/status.js.map +1 -0
  20. package/dist/generators/codebuddy.d.ts +7 -0
  21. package/dist/generators/codebuddy.d.ts.map +1 -1
  22. package/dist/generators/codebuddy.js +35 -3
  23. package/dist/generators/codebuddy.js.map +1 -1
  24. package/dist/utils/analytics.d.ts +14 -0
  25. package/dist/utils/analytics.d.ts.map +1 -0
  26. package/dist/utils/analytics.js +81 -0
  27. package/dist/utils/analytics.js.map +1 -0
  28. package/dist/utils/config.d.ts +10 -0
  29. package/dist/utils/config.d.ts.map +1 -1
  30. package/dist/utils/config.js.map +1 -1
  31. package/package.json +1 -1
  32. package/templates/commands/auto.md +38 -0
  33. package/templates/commands/modus.md +14 -2
  34. package/templates/hooks/session-start.py +52 -0
  35. package/templates/hooks/stop-update-skills.py +58 -0
  36. package/templates/skills/modus-auto/SKILL.md +210 -0
  37. package/templates/skills/modus-init/SKILL.md +133 -11
  38. package/templates/skills/modus-plan/SKILL.md +132 -19
  39. package/templates/skills/modus-spec/SKILL.md +109 -6
package/README.md CHANGED
@@ -22,34 +22,30 @@
22
22
 
23
23
  **需要 Node.js 18.0.0 或以上版本。**
24
24
 
25
- 全局安装 Modus:
25
+ 全局安装并初始化:
26
26
 
27
27
  ```bash
28
28
  npm install -g @modus-ai/modus
29
- ```
30
-
31
- 进入你的项目目录并初始化:
32
-
33
- ```bash
34
29
  cd your-project
35
- modus init
30
+ modus init # CLI 初始化,生成框架文件和配置
36
31
  ```
37
32
 
38
- 然后在 CodeBuddy IDE 中运行:
33
+ 然后在 CodeBuddy IDE 对话框中运行:
39
34
 
40
35
  ```
41
- /modus:init
36
+ /modus:init # 扫描代码,生成业务知识库
42
37
  ```
43
38
 
44
- ## 5 个核心命令
39
+ ## 6 个核心命令
45
40
 
46
- | 命令 | 用途 |
47
- |------|------|
48
- | `/modus:init` | 分析项目,生成业务/团队/技术三层知识库 + 知识目录 |
49
- | `/modus:vibe` | 氛围编程,三级渐进加载业务上下文(`--quick` 快速模式)|
50
- | `/modus:plan` | 功能规划,生成 proposal/design/tasks,支持断点续跑 |
51
- | `/modus:spec` | 规范开发,生成 delta specs(场景驱动验收)+ 知识提取 |
52
- | `/modus:harness` | 全自动双 Loop 多智能体流程,含知识注入/提取闭环 |
41
+ | 命令 | 用途 | 产出物位置 |
42
+ |------|------|-----------|
43
+ | `/modus:init` | 扫描项目,生成业务/团队/技术三层知识库 + 知识目录 | `.codebuddy/skills/` + `modus/knowledge-catalog.md` |
44
+ | `/modus:vibe` | 氛围编程,渐进式加载业务上下文后直接编码 | 直接修改代码,无新增文件 |
45
+ | `/modus:plan` | 功能规划,复杂度自动分级,含 ADR 决策记录和 pitfall 风险提示 | `modus/plans/{name}/` |
46
+ | `/modus:spec` | 规范开发,delta specs + GIVEN/WHEN/THEN 验收,含可选 verify + 冲突检测 | `modus/changes/{name}/`,归档合并到 `modus/specs/` |
47
+ | `/modus:auto` | 智能模式推荐:读 TAPD Story,四维评分,推荐 vibe/plan/spec/harness | 启动所选模式后按该模式产出 |
48
+ | `/modus:harness` | 全自动双 Loop 多智能体流程,8 个 SubAgent 协作,含知识沉淀闭环 | `modus/plans/active/{story-id}/` |
53
49
 
54
50
  ## 典型工作流
55
51
 
@@ -65,8 +61,8 @@ AI: 识别到 3 个业务域:order, payment, user
65
61
  你: /modus:vibe 帮我给订单模块加一个批量审批接口
66
62
  AI: [Level 1] 读取知识目录(200 tokens)
67
63
  [Level 2] 加载 order 域业务知识(3000 tokens,仅此一个域)
64
+ [Level 3] 按需读取 OrderService.java、OrderMapper.java
68
65
  我来实现批量审批接口...
69
- 📝 Skill 更新建议:发现 OrderStatus.PENDING_REVIEW 状态,建议更新 Skill
70
66
 
71
67
  你: /modus:harness https://tapd.cn/xxx/stories/view/1234567
72
68
  AI: [INIT] 注入知识:order[verified] | payment[proven]
@@ -88,28 +84,80 @@ Modus 的知识体系让 AI 从「冷启动」变为「越用越快」:
88
84
  ```
89
85
 
90
86
  **三层知识结构:**
91
- - **Layer 0-T** `modus-team-conventions` — 团队约定(代码规范、提交规范)
92
- - **Layer 1** `modus-tech-wiki` — 技术知识(架构决策、反模式库,跨项目积累)
93
- - **Layer 2** `modus-biz-*` — 业务知识(领域模型、业务规则、API 契约)
94
87
 
95
- **知识成熟度:** `draft` `verified` `proven`(自动提升 + 自动衰减,保持知识库健康)
88
+ | 层级 | Skill 文件 | 内容 | 生命周期 |
89
+ |------|-----------|------|---------|
90
+ | Layer 0-T | `modus-team-conventions` | 编码规范、提交规范、硬性约束 | 人工维护为主 |
91
+ | Layer 1 | `modus-tech-wiki` | 架构决策、反模式库(跨项目积累) | 工作流 ARCHIVE 自动积累 |
92
+ | Layer 2 | `modus-biz-{domain}` | 领域模型、业务规则、API 契约 | 每次 plan/spec/harness 后回写 |
93
+
94
+ **知识成熟度:** `draft` → `verified` → `proven`(在工作流中被引用后自动晋升,长期未引用自动衰减)
96
95
 
97
- **渐进加载:** Level 1(catalog,~200 tokens)→ Level 2(Skill,~3000 tokens/个)→ Level 3(代码文件,按需)节省约 59% token。
96
+ **渐进加载:** Level 1(catalog,~200 tokens)→ Level 2(Skill,~3000 tokens/个)→ Level 3(代码文件,按需),节省约 59% token。
98
97
 
99
98
  **项目宪法:** `modus/config.yaml` 的 `constitution.hard_rules` 是所有 SubAgent 的最高优先级约束,一次配置,永久生效。
100
99
 
100
+ ```yaml
101
+ constitution:
102
+ tech_stack: "Java 17 + Spring Boot 3 + MyBatis"
103
+ build_command: "mvn clean compile -q"
104
+ hard_rules:
105
+ - "Mapper 接口必须在 dao 包下"
106
+ - "金额字段使用 Long(单位:分)"
107
+ ```
108
+
109
+ ## `/modus:harness` 流程一览
110
+
111
+ ```
112
+ Loop 1(生产)
113
+ INIT → SA01 需求分析 → SA02 代码开发 → Gate A(编译)
114
+ → SA03/04/05 并行(测试/性能/安全)→ Gate B → SA06 代码评审 → Gate C
115
+
116
+ Loop 2(修复,有 P1/P2 时触发)
117
+ 精准重入受影响的 Sprint → Gate A → SA03/04/05 → SA06
118
+
119
+ 收尾
120
+ SA07 部署验证 → ARCHIVE 知识沉淀 → 人工 Final Review
121
+ ```
122
+
123
+ 每个 SubAgent 的产出物(`01-analysis.md` 至 `07-deploy-status.md` + `cr-report.md`)均存放在 `modus/plans/active/{story-id}/`,支持断点续跑。
124
+
125
+ ## 文件结构
126
+
127
+ ```
128
+ your-project/
129
+ ├── .codebuddy/
130
+ │ ├── skills/
131
+ │ │ ├── modus-team-conventions/SKILL.md ← Layer 0-T
132
+ │ │ ├── modus-tech-wiki/SKILL.md ← Layer 1
133
+ │ │ ├── modus-biz-{domain}/SKILL.md ← Layer 2(每域一个)
134
+ │ │ └── modus-harness-*/SKILL.md ← 8 个 SubAgent Skill
135
+ │ └── commands/modus/ ← 斜杠命令入口
136
+
137
+ └── modus/
138
+ ├── config.yaml ← 项目宪法
139
+ ├── knowledge-catalog.md ← 全景索引(~200 tokens)
140
+ ├── specs/{domain}/spec.md ← 主规格库(/spec 归档后)
141
+ ├── plans/{name}/ ← /plan 活跃目录
142
+ ├── plans/active/{story-id}/ ← /harness 产出物
143
+ ├── plans/archive/ ← /plan 归档
144
+ └── changes/ ← /spec 产出物及归档
145
+ ```
146
+
101
147
  ## 文档
102
148
 
103
- → **[Getting Started](docs/getting-started.md)**: 第一步
104
- → **[Commands](docs/commands.md)**: 命令详情
105
- → **[Concepts](docs/concepts.md)**: 核心概念(含知识分层架构)
106
- → **[Harness](docs/harness.md)**: 双 Loop 多智能体原理(含 HANDOFF 协议)
107
- → **[Knowledge](docs/knowledge.md)**: 知识体系详解
149
+ → **[Getting Started](docs/getting-started.md)**: 安装与第一步
150
+ → **[Commands Manual](docs/modus-commands-manual.md)**: 5 个命令完整用法(执行步骤、产出物、示例)
151
+ → **[Concepts](docs/concepts.md)**: 核心概念(知识分层、渐进加载、Project Constitution)
152
+ → **[Harness](docs/harness.md)**: 双 Loop 多智能体原理(含 HANDOFF 协议、Gate 规则)
153
+ → **[Knowledge](docs/knowledge.md)**: 知识体系生命周期与最佳实践
154
+ → **[Commands Reference](docs/commands.md)**: 命令快速参考
108
155
 
109
156
  ## CLI 命令
110
157
 
111
158
  ```bash
112
159
  modus init # 初始化项目(生成 .codebuddy/ 文件 + 知识目录)
160
+ modus rehook # 修复 hook 路径(git clone 到新机器/路径后执行)
113
161
  modus update # 升级后刷新文件
114
162
  modus config show # 查看当前配置
115
163
  modus config profile # 选择启用哪些命令
package/dist/cli/index.js CHANGED
@@ -5,24 +5,39 @@ import { runInit } from '../commands/init.js';
5
5
  import { runUpdate } from '../commands/update.js';
6
6
  import { runConfig } from '../commands/config.js';
7
7
  import { runGlobalInit, runGlobalList } from '../commands/global.js';
8
+ import { runStatus } from '../commands/status.js';
9
+ import { runDoctor } from '../commands/doctor.js';
10
+ import chalk from 'chalk';
11
+ import { runSkillList, runSkillShow, runSkillRefresh } from '../commands/skill.js';
12
+ import { rehookProject } from '../generators/codebuddy.js';
13
+ import { track } from '../utils/analytics.js';
14
+ import { loadConfig } from '../utils/config.js';
8
15
  const require = createRequire(import.meta.url);
9
16
  const pkg = require('../../package.json');
10
17
  const program = new Command();
11
18
  program
12
19
  .name('modus')
13
- .description('Modus — Business-grounded AI coding accelerator for CodeBuddy IDE')
20
+ .description('Modus — Business-grounded AI coding accelerator for CodeBuddy IDE\n\n' +
21
+ ' Quick start:\n' +
22
+ ' modus init Initialize project and generate .codebuddy/ files\n' +
23
+ ' /modus:init (in CodeBuddy) Scan codebase, build business Skills\n' +
24
+ ' /modus:auto [tapd-url] Smart mode recommendation — reads TAPD, picks best command\n\n' +
25
+ ' After git clone to a new machine:\n' +
26
+ ' modus rehook Fix hook script paths in .codebuddy/settings.json')
14
27
  .version(pkg.version);
15
28
  program
16
29
  .command('init')
17
- .description('Initialize Modus in the current project (generates .codebuddy/ files)')
30
+ .description('Initialize Modus in the current project\n' +
31
+ ' Generates .codebuddy/ Skills, commands, agents, hooks, rules and settings.json.\n' +
32
+ ' After CLI init, run /modus:init in CodeBuddy to scan codebase and build business Skills.')
18
33
  .option('--root <path>', 'Project root directory', process.cwd())
19
34
  .option('-y, --yes', 'Skip all prompts; use flags + defaults (non-interactive)')
20
- .option('--tech-stack <stack>', 'Tech stack description, written to modus/config.yaml')
21
- .option('--context <text>', 'One-line project description used as AI context')
22
- .option('--tapd-project-id <id>', 'TAPD project ID (optional, for /harness command)')
35
+ .option('--tech-stack <stack>', 'Tech stack, e.g. "Java Spring Boot, MySQL, Redis"')
36
+ .option('--context <text>', 'One-line project description used as AI background context')
37
+ .option('--tapd-project-id <id>', 'TAPD project ID (optional, enables /modus:harness Bug creation)')
23
38
  .option('--team-name <name>', 'Team name — copies Skills from ~/.codebuddy/team/<name>/')
24
- .option('--commands <csv>', 'Comma-separated list of commands to enable (default: all)')
25
- .option('--force', 'Re-generate files even if already initialized (use with --yes)')
39
+ .option('--commands <csv>', 'Commands to enable, e.g. "init,vibe,plan,spec,auto,harness" (default: all)')
40
+ .option('--force', 'Re-generate all files even if already initialized (use with --yes)')
26
41
  .option('--sync-scopes', 'Re-sync Skills from global/team directories (overwrites project copies)')
27
42
  .action(async (opts) => {
28
43
  const projectRoot = path.resolve(opts.root);
@@ -39,20 +54,28 @@ program
39
54
  });
40
55
  program
41
56
  .command('update')
42
- .description('Re-generate .codebuddy/ skill and command files from latest templates')
57
+ .description('Re-generate .codebuddy/ files from latest Modus templates\n' +
58
+ ' Run after upgrading the modus package to pull in new Skill/command templates.\n' +
59
+ ' Business Skills (modus-biz-*) are never overwritten.')
43
60
  .option('--root <path>', 'Project root directory', process.cwd())
44
- .option('--sync-scopes', 'Re-sync Skills/Rules from global/team directories (overwrites project copies)')
61
+ .option('--sync-scopes', 'Also re-sync Skills/Rules from global/team directories')
45
62
  .action(async (opts) => {
46
63
  const projectRoot = path.resolve(opts.root);
64
+ track(projectRoot, { event_type: 'command.executed', command: 'update' });
47
65
  const updateOpts = { syncScopes: Boolean(opts.syncScopes) };
48
66
  await runUpdate(projectRoot, updateOpts);
49
67
  });
50
68
  program
51
69
  .command('config [subcommand]')
52
- .description('View or update Modus config. Subcommands: show | profile | set')
70
+ .description('View or edit modus/config.yaml\n' +
71
+ ' Subcommands:\n' +
72
+ ' show Print current config\n' +
73
+ ' profile Select which /modus:* commands to enable\n' +
74
+ ' set Update a single config key, e.g. modus config set tapdProjectId 12345')
53
75
  .option('--root <path>', 'Project root directory', process.cwd())
54
76
  .action(async (subcommand, opts) => {
55
77
  const projectRoot = path.resolve(opts.root);
78
+ track(projectRoot, { event_type: 'command.executed', command: 'config' });
56
79
  await runConfig(projectRoot, subcommand);
57
80
  });
58
81
  // ---------------------------------------------------------------------------
@@ -60,11 +83,14 @@ program
60
83
  // ---------------------------------------------------------------------------
61
84
  const globalCmd = program
62
85
  .command('global')
63
- .description('Manage global (~/.codebuddy/global/) and team-level (~/.codebuddy/team/) Skills');
86
+ .description('Manage shared Skills across projects via global/team scopes\n' +
87
+ ' Global scope ~/.codebuddy/global/ shared by all your projects\n' +
88
+ ' Team scope ~/.codebuddy/team/<name>/ shared by team members\n' +
89
+ ' Subcommands: init | list');
64
90
  globalCmd
65
91
  .command('init')
66
92
  .description('Initialize global or team-level Modus directory with starter Skills')
67
- .option('--team <name>', 'Target a team-level directory (~/.codebuddy/team/<name>/)')
93
+ .option('--team <name>', 'Target a team scope, e.g. --team backend-squad')
68
94
  .action(async (opts) => {
69
95
  await runGlobalInit({ team: opts.team });
70
96
  });
@@ -74,5 +100,155 @@ globalCmd
74
100
  .action(async () => {
75
101
  await runGlobalList();
76
102
  });
103
+ // ---------------------------------------------------------------------------
104
+ // modus status — show project state at a glance
105
+ // ---------------------------------------------------------------------------
106
+ program
107
+ .command('status')
108
+ .description('Show Modus project state at a glance\n' +
109
+ ' Reports: initialized Skills, active plans/changes, knowledge freshness, stale Skills')
110
+ .option('--root <path>', 'Project root directory', process.cwd())
111
+ .action(async (opts) => {
112
+ const projectRoot = path.resolve(opts.root);
113
+ track(projectRoot, { event_type: 'command.executed', command: 'status' });
114
+ await runStatus(projectRoot);
115
+ });
116
+ // ---------------------------------------------------------------------------
117
+ // modus doctor — diagnose environment and project setup
118
+ // ---------------------------------------------------------------------------
119
+ program
120
+ .command('doctor')
121
+ .description('Diagnose Modus installation, config, and Skills integrity\n' +
122
+ ' Checks: Node version, templates, config.yaml, hook scripts, Skill file health')
123
+ .option('--root <path>', 'Project root directory', process.cwd())
124
+ .action(async (opts) => {
125
+ const projectRoot = path.resolve(opts.root);
126
+ track(projectRoot, { event_type: 'command.executed', command: 'doctor' });
127
+ await runDoctor(projectRoot);
128
+ });
129
+ // ---------------------------------------------------------------------------
130
+ // modus skill — project-level Skill management
131
+ // ---------------------------------------------------------------------------
132
+ const skillCmd = program
133
+ .command('skill')
134
+ .description('Manage project-level Business Skills (modus-biz-*)\n' +
135
+ ' Subcommands: list | show <name> | refresh [name]');
136
+ skillCmd
137
+ .command('list')
138
+ .description('List all Modus Skills (framework + business) with maturity and last-referenced date')
139
+ .option('--root <path>', 'Project root directory', process.cwd())
140
+ .option('--filter <keyword>', 'Filter Skills by name keyword')
141
+ .option('--json', 'Output as JSON')
142
+ .action(async (opts) => {
143
+ const projectRoot = path.resolve(opts.root);
144
+ track(projectRoot, { event_type: 'command.executed', command: 'skill.list' });
145
+ await runSkillList(projectRoot, { filter: opts.filter, json: opts.json });
146
+ });
147
+ skillCmd
148
+ .command('show <name>')
149
+ .description('Print the full content of a Skill (accepts partial name, e.g. "order" → modus-biz-order)')
150
+ .option('--root <path>', 'Project root directory', process.cwd())
151
+ .action(async (name, opts) => {
152
+ const projectRoot = path.resolve(opts.root);
153
+ track(projectRoot, { event_type: 'command.executed', command: 'skill.show' });
154
+ await runSkillShow(projectRoot, name);
155
+ });
156
+ skillCmd
157
+ .command('refresh [name]')
158
+ .description('Clear last_hash to force re-scan on next AI command\n' +
159
+ ' Omit name to refresh all business Skills at once')
160
+ .option('--root <path>', 'Project root directory', process.cwd())
161
+ .action(async (name, opts) => {
162
+ const projectRoot = path.resolve(opts.root);
163
+ track(projectRoot, { event_type: 'command.executed', command: 'skill.refresh' });
164
+ await runSkillRefresh(projectRoot, name);
165
+ });
166
+ // ---------------------------------------------------------------------------
167
+ // modus rehook — update hook paths after git clone / path change
168
+ // ---------------------------------------------------------------------------
169
+ program
170
+ .command('rehook')
171
+ .description('Fix hook script paths in .codebuddy/settings.json\n' +
172
+ ' Run this after git clone to a different machine or directory path')
173
+ .option('--root <path>', 'Project root directory', process.cwd())
174
+ .action((opts) => {
175
+ const projectRoot = path.resolve(opts.root);
176
+ track(projectRoot, { event_type: 'command.executed', command: 'rehook' });
177
+ rehookProject(projectRoot);
178
+ });
179
+ // ---------------------------------------------------------------------------
180
+ // modus commands — list available CodeBuddy slash commands
181
+ // ---------------------------------------------------------------------------
182
+ program
183
+ .command('commands')
184
+ .description('List the /modus:* slash commands available inside CodeBuddy IDE\n' +
185
+ ' These are AI commands triggered in the chat window, not terminal commands')
186
+ .option('--root <path>', 'Project root directory', process.cwd())
187
+ .action((opts) => {
188
+ const projectRoot = path.resolve(opts.root);
189
+ track(projectRoot, { event_type: 'command.executed', command: 'commands' });
190
+ printSlashCommands(projectRoot);
191
+ });
192
+ // ---------------------------------------------------------------------------
193
+ // helpers
194
+ // ---------------------------------------------------------------------------
195
+ /** Print available /modus:* slash commands with descriptions. */
196
+ function printSlashCommands(projectRoot) {
197
+ let enabled = [];
198
+ try {
199
+ const config = loadConfig(projectRoot);
200
+ enabled = config.commands?.enabled ?? [];
201
+ }
202
+ catch {
203
+ // not initialized — show all
204
+ }
205
+ const all = [
206
+ {
207
+ cmd: '/modus:init',
208
+ description: 'Scan codebase, classify business domains, generate Business Skills + knowledge catalog',
209
+ note: 'Run once per project (or after major code changes)',
210
+ },
211
+ {
212
+ cmd: '/modus:vibe',
213
+ description: 'Context-aware coding — loads relevant business Skills before editing code',
214
+ note: 'Best for daily bug fixes and small feature tasks',
215
+ },
216
+ {
217
+ cmd: '/modus:plan',
218
+ description: 'Feature planning with complexity grading → proposal + design (ADR) + tasks',
219
+ note: 'Use when you need design docs but not formal specs',
220
+ },
221
+ {
222
+ cmd: '/modus:spec',
223
+ description: 'Spec-driven development — generates delta specs (ADDED/MODIFIED/REMOVED) with GIVEN/WHEN/THEN scenarios',
224
+ note: 'Use when changing interface contracts or needing testable acceptance criteria',
225
+ },
226
+ {
227
+ cmd: '/modus:auto',
228
+ description: 'Smart mode selector — reads TAPD Story, scores 4 dimensions, recommends vibe/plan/spec/harness',
229
+ note: 'Use when unsure which mode fits the TAPD story',
230
+ },
231
+ {
232
+ cmd: '/modus:harness',
233
+ description: 'Full dual-loop multi-agent pipeline: requirements → code → tests → security → review → deploy',
234
+ note: 'Use for full-cycle delivery from a TAPD Story URL',
235
+ },
236
+ ];
237
+ console.log(chalk.bold('\n /modus:* Slash Commands (run inside CodeBuddy IDE chat)\n'));
238
+ for (const item of all) {
239
+ const isEnabled = enabled.length === 0 || enabled.includes(item.cmd.replace('/modus:', ''));
240
+ const status = isEnabled ? chalk.green('✓') : chalk.dim('○');
241
+ console.log(` ${status} ${chalk.yellow(item.cmd.padEnd(18))} ${item.description}`);
242
+ if (item.note) {
243
+ console.log(` ${' '.repeat(18)} ${chalk.dim(item.note)}`);
244
+ }
245
+ }
246
+ if (enabled.length > 0) {
247
+ console.log(chalk.dim('\n ✓ = enabled in this project ○ = disabled (modus config profile to change)\n'));
248
+ }
249
+ else {
250
+ console.log(chalk.dim('\n Run `modus init` first to configure which commands are enabled.\n'));
251
+ }
252
+ }
77
253
  program.parse(process.argv);
78
254
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/cli/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,OAAO,IAAI,MAAM,WAAW,CAAC;AAC7B,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAC5C,OAAO,EAAE,OAAO,EAAE,MAAM,qBAAqB,CAAC;AAC9C,OAAO,EAAE,SAAS,EAAyB,MAAM,uBAAuB,CAAC;AACzE,OAAO,EAAE,SAAS,EAAE,MAAM,uBAAuB,CAAC;AAClD,OAAO,EAAE,aAAa,EAAE,aAAa,EAAE,MAAM,uBAAuB,CAAC;AAErE,MAAM,OAAO,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AAC/C,MAAM,GAAG,GAAG,OAAO,CAAC,oBAAoB,CAAC,CAAC;AAE1C,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAC;AAE9B,OAAO;KACJ,IAAI,CAAC,OAAO,CAAC;KACb,WAAW,CAAC,mEAAmE,CAAC;KAChF,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;AAExB,OAAO;KACJ,OAAO,CAAC,MAAM,CAAC;KACf,WAAW,CAAC,uEAAuE,CAAC;KACpF,MAAM,CAAC,eAAe,EAAE,wBAAwB,EAAE,OAAO,CAAC,GAAG,EAAE,CAAC;KAChE,MAAM,CAAC,WAAW,EAAE,0DAA0D,CAAC;KAC/E,MAAM,CAAC,sBAAsB,EAAE,sDAAsD,CAAC;KACtF,MAAM,CAAC,kBAAkB,EAAE,iDAAiD,CAAC;KAC7E,MAAM,CAAC,wBAAwB,EAAE,kDAAkD,CAAC;KACpF,MAAM,CAAC,oBAAoB,EAAE,0DAA0D,CAAC;KACxF,MAAM,CAAC,kBAAkB,EAAE,2DAA2D,CAAC;KACvF,MAAM,CAAC,SAAS,EAAE,gEAAgE,CAAC;KACnF,MAAM,CAAC,eAAe,EAAE,yEAAyE,CAAC;KAClG,MAAM,CAAC,KAAK,EAAE,IAAI,EAAE,EAAE;IACrB,MAAM,WAAW,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC5C,MAAM,OAAO,CAAC,WAAW,EAAE;QACzB,GAAG,EAAE,IAAI,CAAC,GAAG;QACb,SAAS,EAAE,IAAI,CAAC,SAAS;QACzB,OAAO,EAAE,IAAI,CAAC,OAAO;QACrB,aAAa,EAAE,IAAI,CAAC,aAAa;QACjC,QAAQ,EAAE,IAAI,CAAC,QAAQ;QACvB,QAAQ,EAAE,IAAI,CAAC,QAAQ;QACvB,KAAK,EAAE,IAAI,CAAC,KAAK;QACjB,UAAU,EAAE,IAAI,CAAC,UAAU;KAC5B,CAAC,CAAC;AACL,CAAC,CAAC,CAAC;AAEL,OAAO;KACJ,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CAAC,uEAAuE,CAAC;KACpF,MAAM,CAAC,eAAe,EAAE,wBAAwB,EAAE,OAAO,CAAC,GAAG,EAAE,CAAC;KAChE,MAAM,CAAC,eAAe,EAAE,+EAA+E,CAAC;KACxG,MAAM,CAAC,KAAK,EAAE,IAAI,EAAE,EAAE;IACrB,MAAM,WAAW,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC5C,MAAM,UAAU,GAAqB,EAAE,UAAU,EAAE,OAAO,CAAC,IAAI,CAAC,UAAU,CAAC,EAAE,CAAC;IAC9E,MAAM,SAAS,CAAC,WAAW,EAAE,UAAU,CAAC,CAAC;AAC3C,CAAC,CAAC,CAAC;AAEL,OAAO;KACJ,OAAO,CAAC,qBAAqB,CAAC;KAC9B,WAAW,CAAC,gEAAgE,CAAC;KAC7E,MAAM,CAAC,eAAe,EAAE,wBAAwB,EAAE,OAAO,CAAC,GAAG,EAAE,CAAC;KAChE,MAAM,CAAC,KAAK,EAAE,UAAU,EAAE,IAAI,EAAE,EAAE;IACjC,MAAM,WAAW,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC5C,MAAM,SAAS,CAAC,WAAW,EAAE,UAAU,CAAC,CAAC;AAC3C,CAAC,CAAC,CAAC;AAEL,8EAA8E;AAC9E,6DAA6D;AAC7D,8EAA8E;AAE9E,MAAM,SAAS,GAAG,OAAO;KACtB,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CAAC,iFAAiF,CAAC,CAAC;AAElG,SAAS;KACN,OAAO,CAAC,MAAM,CAAC;KACf,WAAW,CAAC,qEAAqE,CAAC;KAClF,MAAM,CAAC,eAAe,EAAE,2DAA2D,CAAC;KACpF,MAAM,CAAC,KAAK,EAAE,IAAI,EAAE,EAAE;IACrB,MAAM,aAAa,CAAC,EAAE,IAAI,EAAE,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC;AAC3C,CAAC,CAAC,CAAC;AAEL,SAAS;KACN,OAAO,CAAC,MAAM,CAAC;KACf,WAAW,CAAC,0DAA0D,CAAC;KACvE,MAAM,CAAC,KAAK,IAAI,EAAE;IACjB,MAAM,aAAa,EAAE,CAAC;AACxB,CAAC,CAAC,CAAC;AAEL,OAAO,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/cli/index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function runDoctor(projectRoot: string): Promise<void>;
2
+ //# sourceMappingURL=doctor.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"doctor.d.ts","sourceRoot":"","sources":["../../src/commands/doctor.ts"],"names":[],"mappings":"AA6LA,wBAAsB,SAAS,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAuDlE"}
@@ -0,0 +1,180 @@
1
+ import path from 'node:path';
2
+ import fs from 'node:fs';
3
+ import { execSync } from 'node:child_process';
4
+ import chalk from 'chalk';
5
+ import { loadConfig, getConfigPath } from '../utils/config.js';
6
+ import { fileExists, listDirs, readFile } from '../utils/file-system.js';
7
+ function check(label, pass, detail, fix) {
8
+ return { label, pass, detail, fix };
9
+ }
10
+ function printCheck(result) {
11
+ const icon = result.pass ? chalk.green(' ✓') : chalk.red(' ✗');
12
+ const labelStr = result.pass ? chalk.white(result.label) : chalk.red(result.label);
13
+ console.log(`${icon} ${labelStr}${result.detail ? chalk.gray(` — ${result.detail}`) : ''}`);
14
+ if (!result.pass && result.fix) {
15
+ console.log(chalk.dim(` Fix: ${result.fix}`));
16
+ }
17
+ }
18
+ function printSection(title) {
19
+ console.log(chalk.bold(`\n ${title}`));
20
+ }
21
+ // ── Environment Checks ────────────────────────────────────────────────────────
22
+ function checkNodeVersion() {
23
+ const ver = process.version;
24
+ const major = parseInt(ver.replace('v', '').split('.')[0] ?? '0', 10);
25
+ return check(`Node.js ${ver}`, major >= 18, major >= 18 ? 'supported' : 'requires ≥18', 'Upgrade Node.js: https://nodejs.org');
26
+ }
27
+ function checkNpmAvailable() {
28
+ try {
29
+ const version = execSync('npm --version', { stdio: 'pipe' }).toString().trim();
30
+ return check(`npm ${version}`, true);
31
+ }
32
+ catch {
33
+ return check('npm', false, 'not found in PATH', 'Install Node.js (npm is bundled)');
34
+ }
35
+ }
36
+ // ── Project Checks ────────────────────────────────────────────────────────────
37
+ function checkInitialized(projectRoot) {
38
+ const configPath = getConfigPath(projectRoot);
39
+ return check('Modus initialized', fileExists(configPath), fileExists(configPath) ? configPath.replace(projectRoot, '.') : undefined, 'Run `modus init` to initialize the project');
40
+ }
41
+ function checkConfigValid(projectRoot) {
42
+ const configPath = getConfigPath(projectRoot);
43
+ if (!fileExists(configPath)) {
44
+ return check('Config valid', false, 'config.yaml missing', 'Run `modus init`');
45
+ }
46
+ try {
47
+ const cfg = loadConfig(projectRoot);
48
+ if (!cfg.version)
49
+ return check('Config valid', false, 'missing "version" field', 'Check modus/config.yaml');
50
+ if (!Array.isArray(cfg.commands?.enabled)) {
51
+ return check('Config valid', false, 'commands.enabled must be an array', 'Check modus/config.yaml');
52
+ }
53
+ return check('Config valid', true, `version=${cfg.version}, commands=${cfg.commands.enabled.length}`);
54
+ }
55
+ catch (err) {
56
+ return check('Config valid', false, String(err), 'Fix YAML syntax in modus/config.yaml');
57
+ }
58
+ }
59
+ function checkKnowledgeCatalog(projectRoot) {
60
+ const catalogPath = path.join(projectRoot, 'modus', 'knowledge-catalog.md');
61
+ if (!fileExists(catalogPath)) {
62
+ return check('Knowledge catalog', false, 'not generated', 'Run `modus init` or `/modus:init`');
63
+ }
64
+ const stat = fs.statSync(catalogPath);
65
+ const ageDays = Math.floor((Date.now() - stat.mtimeMs) / (1000 * 60 * 60 * 24));
66
+ const stale = ageDays > 30;
67
+ return check('Knowledge catalog', !stale, stale ? `stale (${ageDays}d old)` : `up to date (${ageDays}d old)`, stale ? 'Run `modus update` or `/modus:init` to refresh' : undefined);
68
+ }
69
+ function checkCodeBuddyDir(projectRoot) {
70
+ const codeBuddyDir = path.join(projectRoot, '.codebuddy');
71
+ const skillsDir = path.join(codeBuddyDir, 'skills');
72
+ const commandsDir = path.join(codeBuddyDir, 'commands', 'modus');
73
+ const hasSkills = fs.existsSync(skillsDir);
74
+ const hasCommands = fs.existsSync(commandsDir);
75
+ const ok = hasSkills && hasCommands;
76
+ return check('.codebuddy/ directory', ok, ok ? 'skills/ and commands/ present' : `missing: ${!hasSkills ? 'skills/' : ''}${!hasCommands ? ' commands/modus/' : ''}`.trim(), 'Run `modus init` or `modus update`');
77
+ }
78
+ function checkSkillsIntegrity(projectRoot) {
79
+ const skillsDir = path.join(projectRoot, '.codebuddy', 'skills');
80
+ if (!fs.existsSync(skillsDir)) {
81
+ return check('Skills integrity', false, 'skills directory missing', 'Run `modus init`');
82
+ }
83
+ const modusSkillDirs = listDirs(skillsDir).filter(d => d.startsWith('modus-'));
84
+ if (modusSkillDirs.length === 0) {
85
+ return check('Skills integrity', false, 'no modus Skills found', 'Run `modus init` to generate Skills');
86
+ }
87
+ const broken = [];
88
+ for (const skillDir of modusSkillDirs) {
89
+ const skillPath = path.join(skillsDir, skillDir, 'SKILL.md');
90
+ if (!fileExists(skillPath)) {
91
+ broken.push(skillDir);
92
+ continue;
93
+ }
94
+ // Check frontmatter exists
95
+ const content = readFile(skillPath);
96
+ if (!content.startsWith('---')) {
97
+ broken.push(skillDir);
98
+ }
99
+ }
100
+ return check('Skills integrity', broken.length === 0, broken.length === 0
101
+ ? `${modusSkillDirs.length} Skills OK`
102
+ : `${broken.length} broken: ${broken.slice(0, 3).join(', ')}${broken.length > 3 ? '...' : ''}`, broken.length > 0 ? 'Run `modus update` to regenerate broken Skills' : undefined);
103
+ }
104
+ function checkCommandFiles(projectRoot) {
105
+ const commandsDir = path.join(projectRoot, '.codebuddy', 'commands', 'modus');
106
+ if (!fs.existsSync(commandsDir)) {
107
+ return check('Command files', false, 'commands/modus/ missing', 'Run `modus init` or `modus update`');
108
+ }
109
+ const config = loadConfig(projectRoot);
110
+ const enabled = config.commands?.enabled ?? [];
111
+ const missing = enabled.filter(cmd => {
112
+ const cmdFile = path.join(commandsDir, `${cmd}.md`);
113
+ return !fileExists(cmdFile);
114
+ });
115
+ return check('Command files', missing.length === 0, missing.length === 0
116
+ ? `all ${enabled.length} command files present`
117
+ : `missing: ${missing.join(', ')}`, missing.length > 0 ? 'Run `modus update` to regenerate command files' : undefined);
118
+ }
119
+ // ── Analytics Config ──────────────────────────────────────────────────────────
120
+ function checkAnalyticsConfig(projectRoot) {
121
+ if (!fileExists(getConfigPath(projectRoot))) {
122
+ return check('Analytics config', false, 'config.yaml missing', 'Run `modus init`');
123
+ }
124
+ const config = loadConfig(projectRoot);
125
+ if (config.analytics?.enabled === false) {
126
+ return check('Analytics config', true, 'disabled (opt-out)');
127
+ }
128
+ if (config.analytics?.collectorUrl) {
129
+ return check('Analytics config', true, `collector: ${config.analytics.collectorUrl}`);
130
+ }
131
+ return check('Analytics config', true, 'default (no collector configured)');
132
+ }
133
+ // ── Entry Point ───────────────────────────────────────────────────────────────
134
+ export async function runDoctor(projectRoot) {
135
+ console.log(chalk.bold('\n modus doctor\n'));
136
+ console.log(chalk.gray(` Diagnosing project at: ${projectRoot}\n`));
137
+ const allResults = [];
138
+ printSection('Environment');
139
+ const nodeCheck = checkNodeVersion();
140
+ printCheck(nodeCheck);
141
+ allResults.push(nodeCheck);
142
+ const npmCheck = checkNpmAvailable();
143
+ printCheck(npmCheck);
144
+ allResults.push(npmCheck);
145
+ printSection('Project Setup');
146
+ const initCheck = checkInitialized(projectRoot);
147
+ printCheck(initCheck);
148
+ allResults.push(initCheck);
149
+ const configCheck = checkConfigValid(projectRoot);
150
+ printCheck(configCheck);
151
+ allResults.push(configCheck);
152
+ const codeBuddyCheck = checkCodeBuddyDir(projectRoot);
153
+ printCheck(codeBuddyCheck);
154
+ allResults.push(codeBuddyCheck);
155
+ const commandsCheck = checkCommandFiles(projectRoot);
156
+ printCheck(commandsCheck);
157
+ allResults.push(commandsCheck);
158
+ printSection('Knowledge Base');
159
+ const catalogCheck = checkKnowledgeCatalog(projectRoot);
160
+ printCheck(catalogCheck);
161
+ allResults.push(catalogCheck);
162
+ const skillsCheck = checkSkillsIntegrity(projectRoot);
163
+ printCheck(skillsCheck);
164
+ allResults.push(skillsCheck);
165
+ printSection('Analytics');
166
+ const analyticsCheck = checkAnalyticsConfig(projectRoot);
167
+ printCheck(analyticsCheck);
168
+ allResults.push(analyticsCheck);
169
+ // ── Summary ────────────────────────────────────────────────────────────────
170
+ const failed = allResults.filter(r => !r.pass);
171
+ console.log('');
172
+ if (failed.length === 0) {
173
+ console.log(chalk.green(` ✓ All checks passed. Modus is healthy.\n`));
174
+ }
175
+ else {
176
+ console.log(chalk.red(` ✗ ${failed.length} check${failed.length > 1 ? 's' : ''} failed.\n`));
177
+ process.exitCode = 1;
178
+ }
179
+ }
180
+ //# sourceMappingURL=doctor.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"doctor.js","sourceRoot":"","sources":["../../src/commands/doctor.ts"],"names":[],"mappings":"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"}