@thedecipherist/mdd 1.0.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.
@@ -0,0 +1,347 @@
1
+ ## PLAN-INITIATIVE MODE — `/mdd plan-initiative`
2
+
3
+ Triggered when arguments start with `plan-initiative`. Creates a new initiative doc.
4
+
5
+ ### Phase PI1 — Mode choice
6
+
7
+ Ask the user:
8
+ ```
9
+ How do you want to create this initiative?
10
+ (a) Guide me — I'll ask questions and build the file
11
+ (b) Template — generate a blank file I'll fill out manually
12
+ ```
13
+
14
+ **If (b) Template:**
15
+ 1. Ask for a title (e.g. "Auth System") → slugify to `auth-system`
16
+ 2. Check for slug collision: if `initiatives/auth-system.md` already exists → hard stop:
17
+ *"An initiative with this name already exists (`initiatives/auth-system.md`)."*
18
+ - Check all wave docs for active feature docs (`wave_status` not `complete`/`archived`/`deprecated`)
19
+ - If active docs found → *"This initiative has active feature docs. Deprecate them first before re-initialising."* List them.
20
+ - If no active docs → ask "Overwrite? (yes/no)"
21
+ 3. Create `.mdd/initiatives/<slug>.md` with blank template (all sections as placeholders, `version: 1`, `hash: ` empty)
22
+ 4. Tell user: *"Fill it out in your editor, then run `/mdd plan-sync` to register the hash, then `/mdd plan-wave <wave-slug>` when ready."*
23
+ 5. Stop.
24
+
25
+ **If (a) Guide me:** proceed to Phase PI2.
26
+
27
+ ### Phase PI2 — Questions
28
+
29
+ Ask all questions in a single interaction:
30
+ 1. "What is the title of this initiative?"
31
+ 2. "Describe it — what does it deliver and why does it exist?"
32
+ 3. "Roughly how many waves do you think this needs? (2–6 is typical)"
33
+ 4. For each wave: "Wave N — name and one-sentence demo-state (what can the user DO when this wave is done?)"
34
+ 5. "What's still undecided that could affect architecture?" → these become open product questions (unchecked `- [ ]` items)
35
+
36
+ ### Phase PI3 — Write initiative doc
37
+
38
+ **Slug format:** lowercase, hyphens, no special characters. "Auth System" → `auth-system`.
39
+
40
+ **Collision check:** same as template mode above.
41
+
42
+ Create `.mdd/initiatives/<slug>.md`:
43
+
44
+ ```markdown
45
+ ---
46
+ id: <slug>
47
+ title: <title>
48
+ status: active
49
+ version: 1
50
+ hash:
51
+ created: <YYYY-MM-DD>
52
+ ---
53
+
54
+ # <title>
55
+
56
+ ## Overview
57
+ <description>
58
+
59
+ ## Open Product Questions
60
+ - [ ] <question 1>
61
+ - [ ] <question 2>
62
+
63
+ ## Waves
64
+ | Wave | File | Demo-state | Status |
65
+ |------|------|------------|--------|
66
+ | Wave 1 | waves/<slug>-wave-1.md | <demo-state> | planned |
67
+ | Wave 2 | waves/<slug>-wave-2.md | <demo-state> | planned |
68
+ ```
69
+
70
+ Compute and write `hash:` field after writing (hash of file content excluding the hash line).
71
+
72
+ Rebuild `.mdd/.startup.md`.
73
+
74
+ ### Phase PI4 — Chain to plan-wave
75
+
76
+ Show the created doc to the user. Ask:
77
+ *"Want to plan Wave 1 now? (yes / no — I'll run /mdd plan-wave <slug>-wave-1 later)"*
78
+
79
+ If yes → run Phase PW1 inline for `<slug>-wave-1`.
80
+
81
+ ---
82
+
83
+ ## PLAN-WAVE MODE — `/mdd plan-wave <wave-slug>`
84
+
85
+ Triggered when arguments start with `plan-wave`. Takes a wave slug (e.g. `auth-system-wave-2`), resolves the parent initiative from it.
86
+
87
+ ### Phase PW1 — Load and validate
88
+
89
+ 1. Parse `<wave-slug>` from arguments — hard stop *"Wave slug required. Usage: /mdd plan-wave <wave-slug>"* if missing.
90
+ 2. Derive initiative slug: everything before `-wave-N` (e.g. `auth-system-wave-2` → `auth-system`).
91
+ 3. Read `initiatives/<initiative-slug>.md` fresh from disk — hard stop *"Initiative does not exist: `initiatives/<slug>.md`"* if not found.
92
+ 4. **Hash check:** compute hash of initiative file (excluding `hash:` line), compare to stored `hash:` field. If mismatch → hard stop: *"Initiative file has been manually edited since last sync. Run `/mdd plan-sync` first."*
93
+ 5. **Open questions gate:** check for any unchecked `- [ ]` items in Open Product Questions. If found → hard stop, quote each unchecked question back: *"These questions must be answered before planning a wave."*
94
+ 6. **Depends-on gate:** read existing wave docs for this initiative. If the new wave's `depends_on` wave exists and is not `complete` → hard stop.
95
+ 7. Surface context summary to user: initiative title, overview, wave count, which waves are done.
96
+
97
+ ### Phase PW2 — Mode choice
98
+
99
+ Same as PI1: ask "(a) Guide me / (b) Template".
100
+
101
+ **If (b) Template:** create `waves/<wave-slug>.md` with blank template, tell user to fill it out and run `/mdd plan-sync` then `/mdd plan-execute <wave-slug>`.
102
+
103
+ **If (a) Guide me:** proceed to Phase PW3.
104
+
105
+ ### Phase PW3 — Questions
106
+
107
+ Ask in a single interaction:
108
+ 1. "Here's the demo-state from the initiative: [X]. Does this need sharpening for this wave?"
109
+ 2. "List the features needed to reach that demo-state — name + one-line description each."
110
+ 3. "Do any features depend on other features within this wave?"
111
+ 4. "Any open research questions before building? Or none?"
112
+
113
+ ### Phase PW4 — Write wave doc
114
+
115
+ Create `waves/<wave-slug>.md`:
116
+
117
+ ```markdown
118
+ ---
119
+ id: <wave-slug>
120
+ title: "Wave N: <title>"
121
+ initiative: <initiative-slug>
122
+ initiative_version: <current initiative version>
123
+ status: planned
124
+ depends_on: none
125
+ demo_state: "<demo-state>"
126
+ created: <YYYY-MM-DD>
127
+ hash:
128
+ ---
129
+
130
+ # Wave N: <title>
131
+
132
+ ## Demo-State
133
+ <demo-state>
134
+ *(This wave is not complete until this can be manually demonstrated.)*
135
+
136
+ ## Features
137
+ | # | Feature | Doc | Status | Depends on |
138
+ |---|---------|-----|--------|------------|
139
+ | 1 | <feature-slug> | — | planned | — |
140
+ | 2 | <feature-slug> | — | planned | <dep-slug or —> |
141
+
142
+ ## Open Research
143
+ <research items or (none)>
144
+ ```
145
+
146
+ Compute and write `hash:` field. Update the Waves table in `initiatives/<slug>.md` to add this wave row. Increment `version` and recompute `hash` on the initiative file.
147
+
148
+ Rebuild `.mdd/.startup.md`.
149
+
150
+ ### Phase PW5 — Chain
151
+
152
+ Ask: *"Want to plan Wave N+1 now? (yes / no)"*
153
+ If yes → run Phase PW1 inline for the next wave slug.
154
+
155
+ ---
156
+
157
+ ## PLAN-EXECUTE MODE — `/mdd plan-execute <wave-slug>`
158
+
159
+ Triggered when arguments start with `plan-execute`. Runs the full MDD build flow for each feature in the wave.
160
+
161
+ ### Phase PE1 — Load and validate
162
+
163
+ 1. Parse `<wave-slug>` — hard stop *"Wave does not exist"* if `waves/<wave-slug>.md` not found.
164
+ 2. Read the wave doc.
165
+ 3. Derive and read the parent initiative — hard stop if not found.
166
+ 4. **Hash check:** verify both initiative and wave file hashes. Hard stop on any mismatch: *"File has been manually edited since last sync. Run `/mdd plan-sync` first."*
167
+ 5. **Depends-on gate:** if wave's `depends_on` is not `none`, verify that wave is `complete`. Hard stop if not.
168
+ 6. **Feature ordering check (Gap 4):** build dependency graph of features within the wave. If any ordering violation found → hard stop, explain exact conflict, offer auto-reorder.
169
+
170
+ ### Phase PE2 — Interaction mode
171
+
172
+ Ask:
173
+ ```
174
+ How do you want to run this wave?
175
+ (a) Automated — minimal interruptions, pauses only on errors
176
+ (b) Interactive — full MDD gates on every feature
177
+ ```
178
+
179
+ **Automated:** data flow shown but not gated, build plan shown but not gated, green gate runs silently. On 5-iteration failure or integration failure → pause and surface to user with options (continue / narrow scope / stop). Does NOT fail the whole wave.
180
+
181
+ **Interactive:** full Phase 2 gate, Phase 5 plan confirmation, green gate iteration prompts on every feature.
182
+
183
+ ### Phase PE3 — Execute features
184
+
185
+ For each feature in the wave's feature table, in dependency order, skipping `complete` features:
186
+
187
+ 1. Tell user: *"Starting Feature N: <feature-slug>"*
188
+ 2. Flip `wave_status: active` for this feature in the wave doc immediately.
189
+ 3. Update the wave doc's `Doc` column with the feature doc path (once created in MDD Phase 3).
190
+ 4. Run full MDD Build Mode (Phases 1–7) for the feature, at the chosen interaction level.
191
+ - Feature doc is auto-numbered from `.mdd/docs/` and gets `initiative`, `wave`, `wave_status` fields added.
192
+ 5. After Phase 7 verify: flip `wave_status: complete` in wave doc.
193
+ 6. Ask: *"Feature N done ✓. Start Feature N+1? (yes / pause here)"*
194
+
195
+ **Resume behaviour (Gap 2):** if re-run on a partially complete wave, read each feature's `wave_status`. Skip `complete`. Resume at first `active` or `planned`. If `active` but no doc exists → restart from Phase 1.
196
+
197
+ ### Phase PE4 — Wave completion
198
+
199
+ When all features are `complete`:
200
+ 1. Show the demo-state: *"Wave complete. Demo-state: '<demo-state>'. Have you verified this?"*
201
+ 2. User confirms → flip wave `status: complete` in both `waves/<slug>.md` AND the waves table in `initiatives/<slug>.md`.
202
+ 3. Recompute hashes for both files.
203
+ 4. If all waves in initiative are `complete` → ask: *"All waves done. Mark initiative complete? (yes / no)"*
204
+ 5. Rebuild `.mdd/.startup.md`.
205
+
206
+ ---
207
+
208
+ ## PLAN-SYNC MODE — `/mdd plan-sync`
209
+
210
+ Triggered when arguments start with `plan-sync`. Detects manual edits to initiative/wave files via hash comparison and reconciles them.
211
+
212
+ ### Phase PS1 — Scan all files
213
+
214
+ Read every file in `.mdd/initiatives/` and `.mdd/waves/` (including `archive/`). For each, compute the hash of the file content (excluding the `hash:` line). Compare against stored `hash:` field.
215
+
216
+ Build a change table:
217
+ ```
218
+ Initiative / Wave | Stored hash | Computed hash | Changed?
219
+ auth-system.md | a3f5b2c1 | a3f5b2c1 | No
220
+ auth-system-wave-1.md | def456 | abc999 | YES
221
+ billing-module.md | (empty) | xyz111 | YES (new — no hash yet)
222
+ ```
223
+
224
+ ### Phase PS2 — Present changes + confirm
225
+
226
+ Show the full change table. Tell the user what will happen:
227
+
228
+ - **Initiative changed:** version incremented, hash updated, completed waves with old `initiative_version` flagged for review
229
+ - **Wave changed:** hash updated, completed features in that wave flagged for review
230
+ - **No hash yet (new file):** hash computed and written — no version bump needed
231
+
232
+ Ask: *"Apply these updates? (yes / review each / cancel)"*
233
+
234
+ ### Phase PS3 — Apply
235
+
236
+ For each changed file, in initiative-first order:
237
+
238
+ **Initiative changed:**
239
+ 1. Increment `version` field
240
+ 2. Rewrite `hash:` field
241
+ 3. Find all wave docs for this initiative where `status: complete` AND `initiative_version` < new version
242
+ 4. Prompt: *"Initiative updated (v1 → v2) since these waves were completed: [list]. Mark them back to in_progress for review? (yes / no / skip)"*
243
+ - `yes` → flip those waves back to `in_progress`
244
+ - `no` / `skip` → leave them complete
245
+
246
+ **Wave changed:**
247
+ 1. Rewrite `hash:` field
248
+ 2. Find all features in this wave with `wave_status: complete`
249
+ 3. Prompt: *"Wave file edited since these features were completed: [list]. Flag for review? (yes / no)"*
250
+ - `yes` → add a `known_issues` entry to each feature doc: *"Wave file was manually edited after this feature completed — review for consistency."*
251
+
252
+ **New file (no hash):**
253
+ 1. Write computed hash to `hash:` field — no other changes
254
+
255
+ Rebuild `.mdd/.startup.md`.
256
+
257
+ Report:
258
+ ```
259
+ ✅ plan-sync complete
260
+
261
+ auth-system.md — no change
262
+ auth-system-wave-1.md — hash updated, 2 features flagged
263
+ billing-module.md — hash written (new file)
264
+ ```
265
+
266
+ ---
267
+
268
+ ## PLAN-REMOVE-FEATURE MODE — `/mdd plan-remove-feature <wave-slug> <feature-slug>`
269
+
270
+ Triggered when arguments start with `plan-remove-feature`.
271
+
272
+ ### Phase PRF1 — Load and validate
273
+
274
+ 1. Parse `<wave-slug>` and `<feature-slug>` from arguments.
275
+ 2. Read wave doc — hard stop *"Wave does not exist"* if not found.
276
+ 3. Find the feature row — hard stop *"Feature `<slug>` does not exist in wave `<wave-slug>`"* if not found.
277
+ 4. **Dependency guard:** check if any other feature in the wave lists `<feature-slug>` in its `Depends on` column. If so → hard stop: *"`<other-feature>` depends on `<feature-slug>`. Remove or reassign that dependency first."*
278
+
279
+ ### Phase PRF2 — Confirm and remove
280
+
281
+ Show summary:
282
+ ```
283
+ Remove feature from wave?
284
+
285
+ Feature: auth-login
286
+ Wave: auth-system-wave-1
287
+ Doc: docs/02-auth-login.md (draft)
288
+ Status: planned
289
+
290
+ Remove from wave? (yes/no)
291
+ ```
292
+
293
+ If yes and a feature doc exists: *"Archive feature doc? (yes/no)"*
294
+
295
+ If confirmed:
296
+ 1. Remove the feature row from the wave doc table.
297
+ 2. Renumber the `#` column sequentially (cosmetic — `Depends on` uses slugs, not numbers, so renumbering is safe).
298
+ 3. If archiving doc: move to `.mdd/docs/archive/`, set `status: archived`, `wave_status: archived`.
299
+ 4. Recompute and update `hash:` on wave doc.
300
+ 5. Tell user: *"Re-run `/mdd plan-execute <wave-slug>` to continue the wave."*
301
+
302
+ Rebuild `.mdd/.startup.md`.
303
+
304
+ ---
305
+
306
+ ## PLAN-CANCEL-INITIATIVE MODE — `/mdd plan-cancel-initiative <slug>`
307
+
308
+ Triggered when arguments start with `plan-cancel-initiative`.
309
+
310
+ ### Phase PCI1 — Load
311
+
312
+ 1. Parse `<slug>` — hard stop *"Initiative does not exist"* if `initiatives/<slug>.md` not found.
313
+ 2. Read initiative doc. Count: waves, wave statuses, associated feature docs (those with `initiative: <slug>` frontmatter).
314
+
315
+ ### Phase PCI2 — Confirm
316
+
317
+ Show summary:
318
+ ```
319
+ Cancel initiative: Auth System
320
+
321
+ Status: active
322
+ Waves: 3 (1 complete, 2 active)
323
+ Feature docs: 5 created
324
+
325
+ Cancel this initiative? (yes/no)
326
+ ```
327
+
328
+ If yes:
329
+
330
+ ### Phase PCI3 — Cancel
331
+
332
+ 1. Set `status: cancelled` in initiative frontmatter. Recompute hash.
333
+ 2. Ask: *"Archive wave docs? (yes/no)"* — if yes, move all wave files to `.mdd/waves/archive/`
334
+ 3. Ask: *"Flag feature docs with a warning? (yes/no)"* — if yes, add to each associated feature doc's `known_issues`: `"Initiative <slug> was cancelled — review whether this feature is still needed."`
335
+
336
+ Rebuild `.mdd/.startup.md`.
337
+
338
+ Report:
339
+ ```
340
+ ✅ Initiative cancelled: auth-system
341
+
342
+ Status set: cancelled
343
+ Wave docs: archived (3 files)
344
+ Feature docs: 5 flagged with known_issues warning
345
+ ```
346
+
347
+ ---
@@ -0,0 +1,152 @@
1
+ ---
2
+ description: "MDD workflow — Document → Audit → Fix → Verify. Build features or audit existing code using Manual-Driven Development."
3
+ scope: project
4
+ argument-hint: "<feature-description> or audit [section]"
5
+ allowed-tools: Read, Write, Edit, Grep, Glob, Bash, AskUserQuestion, Agent
6
+ mdd_version: 8
7
+ ---
8
+
9
+ # MDD — Manual-Driven Development Workflow
10
+
11
+ **$ARGUMENTS**
12
+
13
+ MDD is the core development workflow. Each feature is driven by its document — written before a line of code, referenced throughout development, and kept in sync as the feature evolves. The document is the single source of truth for what is being built and why. Every fix starts with an audit. No exceptions.
14
+
15
+ ## Step 0 — Worktree Check (before everything else)
16
+
17
+ Before any other work, offer worktree isolation for parallel `/mdd` sessions:
18
+
19
+ 1. Check current branch: `git branch --show-current`
20
+ 2. Ask the user via AskUserQuestion:
21
+ - **Question:** "Do you want to work in an isolated worktree? This lets you run multiple `/mdd` sessions in parallel."
22
+ - **Options:**
23
+ - **"No, continue here" (Recommended)** — proceed in current directory with auto-branch as usual
24
+ - **"Yes, create a worktree"** — create an isolated worktree, then the user re-runs `/mdd` there
25
+ 3. If the user selects **"Yes, create a worktree"**:
26
+ - Derive a slug from `$ARGUMENTS` (e.g., `add-auth` from "add auth system"). If no arguments, ask for a name.
27
+ - Run: `/worktree mdd-<feature-slug>` (this creates a sibling directory with its own branch)
28
+ - Tell the user: "Worktree created. Open a new Claude Code session in the worktree directory and run `/mdd $ARGUMENTS` there."
29
+ - **STOP here** — do not continue in the current session (the working directory hasn't changed)
30
+ 4. If the user selects **"No, continue here"** — proceed to Step 0a below.
31
+
32
+ ## Step 0a — Bootstrap Check (silent, automatic)
33
+
34
+ Before detecting mode or doing anything else, ensure the `.mdd/` directory structure exists. This runs silently — no user prompt, no confirmation. If everything already exists, nothing happens.
35
+
36
+ ```bash
37
+ # Check and create missing pieces
38
+ [ -d .mdd ] || mkdir -p .mdd
39
+ [ -d .mdd/docs ] || mkdir -p .mdd/docs
40
+ [ -d .mdd/audits ] || mkdir -p .mdd/audits
41
+ [ -d .mdd/ops ] || mkdir -p .mdd/ops
42
+ [ -d .mdd/jobs ] || mkdir -p .mdd/jobs
43
+ ```
44
+
45
+ **If `.mdd/.startup.md` does not exist**, create it with the default template:
46
+
47
+ ```markdown
48
+ ## Project Snapshot
49
+ Generated: (run /mdd status to populate) | Branch: (unknown)
50
+
51
+ ## Stack
52
+ Framework: (unknown) | DB: (unknown) | Host: (unknown)
53
+
54
+ ## Features Documented
55
+ (none yet — run /mdd <feature> to create your first doc)
56
+
57
+ ## Last Audit
58
+ (no audit run yet — run /mdd audit to generate findings)
59
+
60
+ ## Rules Summary
61
+ Read CLAUDE.md for the full rulebook. Key rules:
62
+ - TypeScript always, strict mode, no any
63
+ - StrictDB only — no raw database drivers
64
+ - /api/v1/ prefix on all endpoints
65
+ - No file > 300 lines, no function > 50 lines
66
+ - Never commit .env or secrets
67
+ - Always branch — never commit to main
68
+
69
+ ---
70
+
71
+ ## Notes
72
+ (add notes with: /mdd note "your note here")
73
+ ```
74
+
75
+ **If `.gitignore` exists**, check whether `.mdd/audits/` and `.mdd/jobs/` are already ignored. For any that are missing, append:
76
+ ```
77
+ # MDD audit reports (ephemeral — regenerated by /mdd audit)
78
+ .mdd/audits/
79
+ # MDD active jobs (ephemeral — deleted on completion)
80
+ .mdd/jobs/
81
+ ```
82
+
83
+ **Report only if something was created** (skip entirely if everything already existed):
84
+ ```
85
+ 📁 MDD structure initialised:
86
+ .mdd/docs/ ✓ created
87
+ .mdd/audits/ ✓ created
88
+ .mdd/ops/ ✓ created
89
+ .mdd/jobs/ ✓ created
90
+ .mdd/.startup.md ✓ created
91
+ .gitignore ✓ updated (.mdd/audits/ and .mdd/jobs/ added)
92
+ ```
93
+
94
+ This bootstrap runs for **all modes** — build, audit, scan, update, and every other mode — so no mode ever fails due to a missing `.mdd/` structure.
95
+
96
+ ## Step 0b — Detect Mode
97
+
98
+ The user's full arguments are: **$ARGUMENTS**
99
+
100
+ Parse these arguments to determine the mode. **Before doing anything else, read the appropriate mode file listed below.** The mode file contains the complete instructions for that mode. When mode file instructions reference `$ARGUMENTS`, treat it as the arguments stated above.
101
+
102
+ Find the MDD commands directory by checking `~/.claude/commands/` (global install via `npm install -g mdd`).
103
+
104
+ - If arguments start with `audit` →
105
+ **Read `~/.claude/commands/mdd-audit.md` then follow its AUDIT MODE instructions.**
106
+
107
+ - If arguments start with `status`, `note`, `scan`, `update`, or `deprecate` →
108
+ **Read `~/.claude/commands/mdd-manage.md` then follow the relevant mode instructions.**
109
+
110
+ - If arguments start with `reverse-engineer`, `reverse`, `graph`, or `upgrade` →
111
+ **Read `~/.claude/commands/mdd-lifecycle.md` then follow the relevant mode instructions.**
112
+
113
+ - If arguments start with `plan-` →
114
+ **Read `~/.claude/commands/mdd-plan.md` then follow the relevant PLAN mode instructions.**
115
+
116
+ - If arguments start with `ops`, `runop`, `update-op`, or `commands` →
117
+ **Read `~/.claude/commands/mdd-ops.md` then follow the relevant OPS/COMMANDS mode instructions.**
118
+
119
+ - If arguments are empty → ask the user what they want to do (build a feature, run an audit, check status, etc.)
120
+
121
+ - Otherwise → **Read `~/.claude/commands/mdd-build.md` then follow BUILD MODE instructions.**
122
+
123
+ ---
124
+
125
+ ## Auto-Branch (All Modes)
126
+
127
+ **If the user already chose a worktree in Step 0, skip auto-branch entirely** — the worktree was created with its own dedicated branch.
128
+
129
+ Otherwise, before creating or modifying any files, check the current branch:
130
+
131
+ ```bash
132
+ git branch --show-current
133
+ ```
134
+
135
+ **Default behavior** (`auto_branch = true` in `claude-mastery-project.conf`):
136
+ - If on `main` or `master`:
137
+ - Build mode: `git checkout -b feat/<feature-name>`
138
+ - Audit mode: `git checkout -b fix/mdd-audit-<date>`
139
+ - If already on a feature branch: proceed
140
+
141
+ ---
142
+
143
+ ## CLAUDE.md Update Trigger
144
+
145
+ After ANY MDD operation that changes code, check if new patterns were established that should be added to CLAUDE.md. If so, suggest the addition:
146
+
147
+ ```
148
+ 💡 New pattern detected: <description>
149
+ Add to CLAUDE.md? (yes / no)
150
+ ```
151
+
152
+ This is the MDD feedback loop — every project interaction improves future interactions.
package/dist/cli.d.ts ADDED
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=cli.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":""}
package/dist/cli.js ADDED
@@ -0,0 +1,27 @@
1
+ #!/usr/bin/env node
2
+ import { Command } from 'commander';
3
+ import { install } from './install.js';
4
+ import { readFileSync } from 'fs';
5
+ import { fileURLToPath } from 'url';
6
+ import { join, dirname } from 'path';
7
+ const __filename = fileURLToPath(import.meta.url);
8
+ const __dirname = dirname(__filename);
9
+ const pkg = JSON.parse(readFileSync(join(__dirname, '../package.json'), 'utf-8'));
10
+ const program = new Command();
11
+ program
12
+ .name('mdd')
13
+ .description('MDD — Manual-Driven Development workflow for Claude Code')
14
+ .version(pkg.version);
15
+ program
16
+ .command('install')
17
+ .description('Install MDD Claude commands to ~/.claude/commands/')
18
+ .option('--dir <path>', 'Custom install directory (default: ~/.claude/commands)', '~/.claude/commands')
19
+ .option('--force', 'Overwrite existing files even if already up to date', false)
20
+ .action(install);
21
+ program
22
+ .command('update')
23
+ .description('Update MDD commands to latest version (alias for install --force)')
24
+ .option('--dir <path>', 'Custom install directory', '~/.claude/commands')
25
+ .action((options) => install({ ...options, force: true }));
26
+ program.parse();
27
+ //# sourceMappingURL=cli.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AACvC,OAAO,EAAE,YAAY,EAAE,MAAM,IAAI,CAAC;AAClC,OAAO,EAAE,aAAa,EAAE,MAAM,KAAK,CAAC;AACpC,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,MAAM,CAAC;AAErC,MAAM,UAAU,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AAClD,MAAM,SAAS,GAAG,OAAO,CAAC,UAAU,CAAC,CAAC;AAEtC,MAAM,GAAG,GAAG,IAAI,CAAC,KAAK,CAAC,YAAY,CAAC,IAAI,CAAC,SAAS,EAAE,iBAAiB,CAAC,EAAE,OAAO,CAAC,CAAwB,CAAC;AAEzG,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAC;AAE9B,OAAO;KACJ,IAAI,CAAC,KAAK,CAAC;KACX,WAAW,CAAC,0DAA0D,CAAC;KACvE,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;AAExB,OAAO;KACJ,OAAO,CAAC,SAAS,CAAC;KAClB,WAAW,CAAC,oDAAoD,CAAC;KACjE,MAAM,CAAC,cAAc,EAAE,wDAAwD,EAAE,oBAAoB,CAAC;KACtG,MAAM,CAAC,SAAS,EAAE,qDAAqD,EAAE,KAAK,CAAC;KAC/E,MAAM,CAAC,OAAO,CAAC,CAAC;AAEnB,OAAO;KACJ,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CAAC,mEAAmE,CAAC;KAChF,MAAM,CAAC,cAAc,EAAE,0BAA0B,EAAE,oBAAoB,CAAC;KACxE,MAAM,CAAC,CAAC,OAAwB,EAAE,EAAE,CAAC,OAAO,CAAC,EAAE,GAAG,OAAO,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC;AAE9E,OAAO,CAAC,KAAK,EAAE,CAAC"}
@@ -0,0 +1,7 @@
1
+ interface InstallOptions {
2
+ dir: string;
3
+ force?: boolean;
4
+ }
5
+ export declare function install(options: InstallOptions): void;
6
+ export {};
7
+ //# sourceMappingURL=install.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"install.d.ts","sourceRoot":"","sources":["../src/install.ts"],"names":[],"mappings":"AASA,UAAU,cAAc;IACtB,GAAG,EAAE,MAAM,CAAC;IACZ,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB;AAUD,wBAAgB,OAAO,CAAC,OAAO,EAAE,cAAc,GAAG,IAAI,CAwErD"}
@@ -0,0 +1,91 @@
1
+ import { copyFileSync, mkdirSync, existsSync, readdirSync, readFileSync } from 'fs';
2
+ import { join, resolve } from 'path';
3
+ import { homedir } from 'os';
4
+ import { fileURLToPath } from 'url';
5
+ import { dirname } from 'path';
6
+ const __filename = fileURLToPath(import.meta.url);
7
+ const __dirname = dirname(__filename);
8
+ export function install(options) {
9
+ const destDir = resolve(options.dir.replace('~', homedir()));
10
+ const srcDir = join(__dirname, '../commands');
11
+ const version = getPackageVersion();
12
+ mkdirSync(destDir, { recursive: true });
13
+ const files = readdirSync(srcDir)
14
+ .filter(f => f.endsWith('.md'))
15
+ .sort((a, b) => {
16
+ // mdd.md first, then alphabetical
17
+ if (a === 'mdd.md')
18
+ return -1;
19
+ if (b === 'mdd.md')
20
+ return 1;
21
+ return a.localeCompare(b);
22
+ });
23
+ const results = [];
24
+ for (const file of files) {
25
+ const src = join(srcDir, file);
26
+ const dest = join(destDir, file);
27
+ try {
28
+ if (existsSync(dest) && !options.force) {
29
+ if (file === 'mdd.md') {
30
+ const srcVer = getMddVersion(readFileSync(src, 'utf-8'));
31
+ const destVer = getMddVersion(readFileSync(dest, 'utf-8'));
32
+ if (srcVer <= destVer) {
33
+ results.push({ file, status: 'skipped', reason: `v${destVer} already up to date` });
34
+ continue;
35
+ }
36
+ copyFileSync(src, dest);
37
+ results.push({ file, status: 'updated', fromVersion: destVer, toVersion: srcVer });
38
+ }
39
+ else {
40
+ // For mode files: compare modification — just overwrite silently
41
+ copyFileSync(src, dest);
42
+ results.push({ file, status: 'updated' });
43
+ }
44
+ }
45
+ else {
46
+ copyFileSync(src, dest);
47
+ results.push({ file, status: existsSync(dest) ? 'updated' : 'installed' });
48
+ }
49
+ }
50
+ catch (err) {
51
+ results.push({ file, status: 'error', reason: String(err) });
52
+ }
53
+ }
54
+ console.log(`\nMDD v${version} — Claude Code workflow installer`);
55
+ console.log(`Install directory: ${destDir}\n`);
56
+ for (const r of results) {
57
+ const icon = r.status === 'error' ? '✗' : r.status === 'skipped' ? '·' : '✓';
58
+ const detail = r.status === 'updated' && r.fromVersion !== undefined
59
+ ? ` (v${r.fromVersion} → v${r.toVersion})`
60
+ : r.reason ? ` — ${r.reason}` : '';
61
+ console.log(` ${icon} ${r.file}${detail}`);
62
+ }
63
+ const installed = results.filter(r => r.status === 'installed' || r.status === 'updated').length;
64
+ const skipped = results.filter(r => r.status === 'skipped').length;
65
+ const errors = results.filter(r => r.status === 'error').length;
66
+ console.log('');
67
+ if (errors > 0) {
68
+ console.log(` ${errors} error(s) — check the output above`);
69
+ }
70
+ else if (installed === 0) {
71
+ console.log(' Already up to date.');
72
+ }
73
+ else {
74
+ console.log(` ${installed} file(s) installed/updated${skipped > 0 ? `, ${skipped} skipped` : ''}`);
75
+ }
76
+ console.log('\nOpen Claude Code and run /mdd to get started.\n');
77
+ }
78
+ function getMddVersion(content) {
79
+ const match = content.match(/^mdd_version:\s*(\d+)/m);
80
+ return match ? parseInt(match[1], 10) : 0;
81
+ }
82
+ function getPackageVersion() {
83
+ try {
84
+ const pkg = JSON.parse(readFileSync(join(__dirname, '../package.json'), 'utf-8'));
85
+ return pkg.version;
86
+ }
87
+ catch {
88
+ return 'unknown';
89
+ }
90
+ }
91
+ //# sourceMappingURL=install.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"install.js","sourceRoot":"","sources":["../src/install.ts"],"names":[],"mappings":"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"}