@rajat-rastogi/maestro 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (175) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +254 -0
  3. package/defaults/agents/documentation.txt +18 -0
  4. package/defaults/agents/implementation.txt +16 -0
  5. package/defaults/agents/quality.txt +19 -0
  6. package/defaults/agents/simplification.txt +19 -0
  7. package/defaults/agents/testing.txt +16 -0
  8. package/defaults/config +46 -0
  9. package/defaults/plan-tips.md +50 -0
  10. package/defaults/prompts/finalize.txt +14 -0
  11. package/defaults/prompts/hint_analysis.txt +38 -0
  12. package/defaults/prompts/plan_create.txt +36 -0
  13. package/defaults/prompts/review_first.txt +37 -0
  14. package/defaults/prompts/review_second.txt +36 -0
  15. package/defaults/prompts/task.txt +23 -0
  16. package/dist/backend/backend.d.ts +29 -0
  17. package/dist/backend/backend.d.ts.map +1 -0
  18. package/dist/backend/backend.js +9 -0
  19. package/dist/backend/backend.js.map +1 -0
  20. package/dist/backend/claude.d.ts +12 -0
  21. package/dist/backend/claude.d.ts.map +1 -0
  22. package/dist/backend/claude.js +155 -0
  23. package/dist/backend/claude.js.map +1 -0
  24. package/dist/backend/copilot.d.ts +11 -0
  25. package/dist/backend/copilot.d.ts.map +1 -0
  26. package/dist/backend/copilot.js +110 -0
  27. package/dist/backend/copilot.js.map +1 -0
  28. package/dist/backend/factory.d.ts +4 -0
  29. package/dist/backend/factory.d.ts.map +1 -0
  30. package/dist/backend/factory.js +13 -0
  31. package/dist/backend/factory.js.map +1 -0
  32. package/dist/config/configserver.d.ts +9 -0
  33. package/dist/config/configserver.d.ts.map +1 -0
  34. package/dist/config/configserver.js +141 -0
  35. package/dist/config/configserver.js.map +1 -0
  36. package/dist/config/dump.d.ts +2 -0
  37. package/dist/config/dump.d.ts.map +1 -0
  38. package/dist/config/dump.js +24 -0
  39. package/dist/config/dump.js.map +1 -0
  40. package/dist/config/loader.d.ts +11 -0
  41. package/dist/config/loader.d.ts.map +1 -0
  42. package/dist/config/loader.js +119 -0
  43. package/dist/config/loader.js.map +1 -0
  44. package/dist/config/prompts.d.ts +19 -0
  45. package/dist/config/prompts.d.ts.map +1 -0
  46. package/dist/config/prompts.js +128 -0
  47. package/dist/config/prompts.js.map +1 -0
  48. package/dist/config/reset.d.ts +3 -0
  49. package/dist/config/reset.d.ts.map +1 -0
  50. package/dist/config/reset.js +23 -0
  51. package/dist/config/reset.js.map +1 -0
  52. package/dist/config/template.d.ts +5 -0
  53. package/dist/config/template.d.ts.map +1 -0
  54. package/dist/config/template.js +11 -0
  55. package/dist/config/template.js.map +1 -0
  56. package/dist/config/types.d.ts +35 -0
  57. package/dist/config/types.d.ts.map +1 -0
  58. package/dist/config/types.js +42 -0
  59. package/dist/config/types.js.map +1 -0
  60. package/dist/config/write.d.ts +5 -0
  61. package/dist/config/write.d.ts.map +1 -0
  62. package/dist/config/write.js +59 -0
  63. package/dist/config/write.js.map +1 -0
  64. package/dist/dashboard/assets/config.html +1012 -0
  65. package/dist/dashboard/assets/dashboard.html +871 -0
  66. package/dist/dashboard/assets/help.html +657 -0
  67. package/dist/dashboard/assets.d.ts +2 -0
  68. package/dist/dashboard/assets.d.ts.map +1 -0
  69. package/dist/dashboard/assets.js +5 -0
  70. package/dist/dashboard/assets.js.map +1 -0
  71. package/dist/dashboard/event-bus.d.ts +11 -0
  72. package/dist/dashboard/event-bus.d.ts.map +1 -0
  73. package/dist/dashboard/event-bus.js +4 -0
  74. package/dist/dashboard/event-bus.js.map +1 -0
  75. package/dist/dashboard/replay-parser.d.ts +6 -0
  76. package/dist/dashboard/replay-parser.d.ts.map +1 -0
  77. package/dist/dashboard/replay-parser.js +56 -0
  78. package/dist/dashboard/replay-parser.js.map +1 -0
  79. package/dist/dashboard/server.d.ts +14 -0
  80. package/dist/dashboard/server.d.ts.map +1 -0
  81. package/dist/dashboard/server.js +178 -0
  82. package/dist/dashboard/server.js.map +1 -0
  83. package/dist/dashboard/watcher.d.ts +17 -0
  84. package/dist/dashboard/watcher.d.ts.map +1 -0
  85. package/dist/dashboard/watcher.js +73 -0
  86. package/dist/dashboard/watcher.js.map +1 -0
  87. package/dist/executor/hints.d.ts +21 -0
  88. package/dist/executor/hints.d.ts.map +1 -0
  89. package/dist/executor/hints.js +102 -0
  90. package/dist/executor/hints.js.map +1 -0
  91. package/dist/executor/task.d.ts +19 -0
  92. package/dist/executor/task.d.ts.map +1 -0
  93. package/dist/executor/task.js +119 -0
  94. package/dist/executor/task.js.map +1 -0
  95. package/dist/executor/validation.d.ts +18 -0
  96. package/dist/executor/validation.d.ts.map +1 -0
  97. package/dist/executor/validation.js +73 -0
  98. package/dist/executor/validation.js.map +1 -0
  99. package/dist/git/branch.d.ts +23 -0
  100. package/dist/git/branch.d.ts.map +1 -0
  101. package/dist/git/branch.js +64 -0
  102. package/dist/git/branch.js.map +1 -0
  103. package/dist/git/commit.d.ts +21 -0
  104. package/dist/git/commit.d.ts.map +1 -0
  105. package/dist/git/commit.js +37 -0
  106. package/dist/git/commit.js.map +1 -0
  107. package/dist/git/diff.d.ts +15 -0
  108. package/dist/git/diff.d.ts.map +1 -0
  109. package/dist/git/diff.js +26 -0
  110. package/dist/git/diff.js.map +1 -0
  111. package/dist/git/git.d.ts +9 -0
  112. package/dist/git/git.d.ts.map +1 -0
  113. package/dist/git/git.js +20 -0
  114. package/dist/git/git.js.map +1 -0
  115. package/dist/git/gitignore.d.ts +2 -0
  116. package/dist/git/gitignore.d.ts.map +1 -0
  117. package/dist/git/gitignore.js +66 -0
  118. package/dist/git/gitignore.js.map +1 -0
  119. package/dist/git/worktree.d.ts +3 -0
  120. package/dist/git/worktree.d.ts.map +1 -0
  121. package/dist/git/worktree.js +17 -0
  122. package/dist/git/worktree.js.map +1 -0
  123. package/dist/main.d.ts +3 -0
  124. package/dist/main.d.ts.map +1 -0
  125. package/dist/main.js +212 -0
  126. package/dist/main.js.map +1 -0
  127. package/dist/orchestrator/orchestrator.d.ts +21 -0
  128. package/dist/orchestrator/orchestrator.d.ts.map +1 -0
  129. package/dist/orchestrator/orchestrator.js +218 -0
  130. package/dist/orchestrator/orchestrator.js.map +1 -0
  131. package/dist/plan/creator.d.ts +27 -0
  132. package/dist/plan/creator.d.ts.map +1 -0
  133. package/dist/plan/creator.js +251 -0
  134. package/dist/plan/creator.js.map +1 -0
  135. package/dist/plan/parser.d.ts +11 -0
  136. package/dist/plan/parser.d.ts.map +1 -0
  137. package/dist/plan/parser.js +151 -0
  138. package/dist/plan/parser.js.map +1 -0
  139. package/dist/plan/types.d.ts +23 -0
  140. package/dist/plan/types.d.ts.map +1 -0
  141. package/dist/plan/types.js +2 -0
  142. package/dist/plan/types.js.map +1 -0
  143. package/dist/plan/updater.d.ts +16 -0
  144. package/dist/plan/updater.d.ts.map +1 -0
  145. package/dist/plan/updater.js +59 -0
  146. package/dist/plan/updater.js.map +1 -0
  147. package/dist/progress/colors.d.ts +9 -0
  148. package/dist/progress/colors.d.ts.map +1 -0
  149. package/dist/progress/colors.js +39 -0
  150. package/dist/progress/colors.js.map +1 -0
  151. package/dist/progress/logger.d.ts +17 -0
  152. package/dist/progress/logger.d.ts.map +1 -0
  153. package/dist/progress/logger.js +101 -0
  154. package/dist/progress/logger.js.map +1 -0
  155. package/dist/progress/notify.d.ts +2 -0
  156. package/dist/progress/notify.d.ts.map +1 -0
  157. package/dist/progress/notify.js +37 -0
  158. package/dist/progress/notify.js.map +1 -0
  159. package/dist/progress/timestamp.d.ts +5 -0
  160. package/dist/progress/timestamp.d.ts.map +1 -0
  161. package/dist/progress/timestamp.js +13 -0
  162. package/dist/progress/timestamp.js.map +1 -0
  163. package/dist/review/agents.d.ts +18 -0
  164. package/dist/review/agents.d.ts.map +1 -0
  165. package/dist/review/agents.js +43 -0
  166. package/dist/review/agents.js.map +1 -0
  167. package/dist/review/pipeline.d.ts +36 -0
  168. package/dist/review/pipeline.d.ts.map +1 -0
  169. package/dist/review/pipeline.js +210 -0
  170. package/dist/review/pipeline.js.map +1 -0
  171. package/dist/sea.d.ts +19 -0
  172. package/dist/sea.d.ts.map +1 -0
  173. package/dist/sea.js +41 -0
  174. package/dist/sea.js.map +1 -0
  175. package/package.json +57 -0
@@ -0,0 +1,657 @@
1
+ <!DOCTYPE html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="UTF-8">
5
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
6
+ <title>Maestro Docs</title>
7
+ <style>
8
+ *, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }
9
+
10
+ :root {
11
+ --task: #00ff00;
12
+ --review: #00ffff;
13
+ --signal: #ff6464;
14
+ --warn: #ffff00;
15
+ --error: #ff0000;
16
+ --info: #b4b4b4;
17
+ --ts: #8a8a8a;
18
+ --bg: #1a1a1a;
19
+ --section-bg: #252525;
20
+ --border: #3a3a3a;
21
+ --header-bg: #111;
22
+ --sidebar-bg: #1e1e1e;
23
+ --code-bg: #0d0d0d;
24
+ --link: #64aaff;
25
+ }
26
+
27
+ body {
28
+ background: var(--bg);
29
+ color: var(--info);
30
+ font-family: 'Consolas', 'Courier New', monospace;
31
+ font-size: 13px;
32
+ line-height: 1.6;
33
+ overflow-x: hidden;
34
+ }
35
+
36
+ /* ── Top bar ── */
37
+ #topbar {
38
+ position: fixed;
39
+ top: 0; left: 0; right: 0;
40
+ height: 40px;
41
+ background: var(--header-bg);
42
+ border-bottom: 1px solid var(--border);
43
+ display: flex;
44
+ align-items: center;
45
+ padding: 0 16px;
46
+ gap: 12px;
47
+ z-index: 200;
48
+ }
49
+ #topbar-title {
50
+ font-weight: bold;
51
+ font-size: 14px;
52
+ color: var(--task);
53
+ }
54
+ #topbar-cmd {
55
+ color: var(--ts);
56
+ font-size: 12px;
57
+ }
58
+
59
+ /* ── Sidebar ── */
60
+ #sidebar {
61
+ position: fixed;
62
+ top: 40px; left: 0; bottom: 0;
63
+ width: 220px;
64
+ background: var(--sidebar-bg);
65
+ border-right: 1px solid var(--border);
66
+ overflow-y: auto;
67
+ padding: 16px 0;
68
+ z-index: 100;
69
+ }
70
+ #sidebar ul {
71
+ list-style: none;
72
+ }
73
+ #sidebar li a {
74
+ display: block;
75
+ padding: 5px 16px;
76
+ color: var(--info);
77
+ text-decoration: none;
78
+ font-size: 12px;
79
+ border-left: 2px solid transparent;
80
+ transition: color 0.15s, border-color 0.15s;
81
+ }
82
+ #sidebar li a:hover {
83
+ color: var(--task);
84
+ border-left-color: var(--task);
85
+ background: #282828;
86
+ }
87
+ #sidebar .toc-section {
88
+ margin-top: 4px;
89
+ color: var(--ts);
90
+ font-size: 11px;
91
+ padding: 8px 16px 2px;
92
+ text-transform: uppercase;
93
+ letter-spacing: 0.05em;
94
+ }
95
+
96
+ /* ── Main content ── */
97
+ #main {
98
+ margin-left: 220px;
99
+ margin-top: 40px;
100
+ padding: 32px 48px 64px;
101
+ max-width: 860px;
102
+ }
103
+
104
+ /* ── Headings ── */
105
+ h1 { color: var(--task); font-size: 22px; margin-bottom: 8px; }
106
+ h2 { color: var(--review); font-size: 16px; margin: 32px 0 12px; padding-bottom: 4px;
107
+ border-bottom: 1px solid var(--border); }
108
+ h3 { color: var(--warn); font-size: 13px; margin: 20px 0 8px; }
109
+ h4 { color: var(--info); font-size: 12px; margin: 12px 0 6px; }
110
+
111
+ /* ── Paragraphs / lists ── */
112
+ p { margin-bottom: 10px; }
113
+ ul, ol { padding-left: 20px; margin-bottom: 10px; }
114
+ li { margin-bottom: 3px; }
115
+
116
+ /* ── Code ── */
117
+ code {
118
+ background: var(--code-bg);
119
+ color: var(--task);
120
+ padding: 1px 5px;
121
+ border-radius: 3px;
122
+ font-size: 12px;
123
+ }
124
+ pre {
125
+ background: var(--code-bg);
126
+ border: 1px solid var(--border);
127
+ border-radius: 4px;
128
+ padding: 14px 16px;
129
+ overflow-x: auto;
130
+ margin: 10px 0 16px;
131
+ line-height: 1.5;
132
+ }
133
+ pre code {
134
+ background: none;
135
+ color: var(--info);
136
+ padding: 0;
137
+ font-size: 12px;
138
+ }
139
+ pre code .kw { color: var(--review); }
140
+ pre code .cm { color: var(--ts); font-style: italic; }
141
+ pre code .str { color: var(--warn); }
142
+ pre code .hd { color: var(--task); font-weight: bold; }
143
+ pre code .cb { color: var(--signal); }
144
+
145
+ /* ── Tables ── */
146
+ table {
147
+ border-collapse: collapse;
148
+ width: 100%;
149
+ margin: 10px 0 16px;
150
+ font-size: 12px;
151
+ }
152
+ th {
153
+ background: var(--section-bg);
154
+ color: var(--review);
155
+ text-align: left;
156
+ padding: 6px 10px;
157
+ border: 1px solid var(--border);
158
+ }
159
+ td {
160
+ padding: 5px 10px;
161
+ border: 1px solid var(--border);
162
+ vertical-align: top;
163
+ }
164
+ tr:nth-child(even) td { background: #202020; }
165
+ td code { font-size: 11px; }
166
+
167
+ /* ── Callout box ── */
168
+ .callout {
169
+ background: var(--section-bg);
170
+ border-left: 3px solid var(--task);
171
+ padding: 10px 14px;
172
+ margin: 12px 0;
173
+ border-radius: 0 4px 4px 0;
174
+ }
175
+ .callout.warn { border-color: var(--warn); }
176
+ .callout.info { border-color: var(--review); }
177
+
178
+ /* ── Flow diagram ── */
179
+ .flow {
180
+ background: var(--code-bg);
181
+ border: 1px solid var(--border);
182
+ border-radius: 4px;
183
+ padding: 14px 16px;
184
+ color: var(--ts);
185
+ font-size: 12px;
186
+ overflow-x: auto;
187
+ white-space: pre;
188
+ margin: 10px 0 16px;
189
+ }
190
+ .flow .phase { color: var(--task); }
191
+ .flow .arrow { color: var(--border); }
192
+
193
+ /* ── Section divider ── */
194
+ hr { border: none; border-top: 1px solid var(--border); margin: 28px 0; }
195
+
196
+ /* ── Search ── */
197
+ #search-wrap {
198
+ margin-left: auto;
199
+ display: flex;
200
+ align-items: center;
201
+ gap: 8px;
202
+ }
203
+ #search-input {
204
+ background: #2a2a2a;
205
+ border: 1px solid var(--border);
206
+ color: var(--info);
207
+ font-family: inherit;
208
+ font-size: 12px;
209
+ padding: 4px 8px;
210
+ border-radius: 3px;
211
+ width: 200px;
212
+ outline: none;
213
+ transition: border-color 0.15s;
214
+ }
215
+ #search-input:focus { border-color: var(--task); }
216
+ #search-input::placeholder { color: var(--ts); }
217
+ #search-count {
218
+ color: var(--ts);
219
+ font-size: 11px;
220
+ min-width: 56px;
221
+ white-space: nowrap;
222
+ }
223
+ .search-nav {
224
+ background: #2a2a2a;
225
+ border: 1px solid var(--border);
226
+ color: var(--info);
227
+ font-size: 12px;
228
+ padding: 3px 7px;
229
+ border-radius: 3px;
230
+ cursor: pointer;
231
+ line-height: 1;
232
+ }
233
+ .search-nav:hover:not(:disabled) { background: #3a3a3a; color: var(--task); border-color: var(--task); }
234
+ .search-nav:disabled { opacity: 0.3; cursor: default; }
235
+ mark {
236
+ background: #4a3f00;
237
+ color: var(--warn);
238
+ border-radius: 2px;
239
+ padding: 0 1px;
240
+ }
241
+ mark.current {
242
+ background: var(--warn);
243
+ color: #111;
244
+ }
245
+
246
+ /* ── Scrollbar ── */
247
+ ::-webkit-scrollbar { width: 6px; height: 6px; }
248
+ ::-webkit-scrollbar-track { background: var(--bg); }
249
+ ::-webkit-scrollbar-thumb { background: #444; border-radius: 3px; }
250
+ </style>
251
+ </head>
252
+ <body>
253
+
254
+ <!-- Top bar -->
255
+ <div id="topbar">
256
+ <span id="topbar-title">Maestro</span>
257
+ <span id="topbar-cmd">maestro --docs</span>
258
+ <div id="search-wrap">
259
+ <input id="search-input" type="search" placeholder="Search… (/)" spellcheck="false" autocomplete="off">
260
+ <button class="search-nav" id="search-prev" title="Previous match (Shift+Enter)" disabled>↑</button>
261
+ <button class="search-nav" id="search-next" title="Next match (Enter)" disabled>↓</button>
262
+ <span id="search-count"></span>
263
+ </div>
264
+ </div>
265
+
266
+ <!-- Sidebar TOC -->
267
+ <nav id="sidebar">
268
+ <ul>
269
+ <li class="toc-section">Reference</li>
270
+ <li><a href="#overview">Overview</a></li>
271
+ <li><a href="#how-it-works">How It Works</a></li>
272
+ <li><a href="#prerequisites">Prerequisites</a></li>
273
+ <li><a href="#installation">Installation</a></li>
274
+ <li><a href="#quick-start">Quick Start</a></li>
275
+ <li class="toc-section">Usage</li>
276
+ <li><a href="#plan-format">Plan Format</a></li>
277
+ <li><a href="#cli-reference">CLI Reference</a></li>
278
+ <li><a href="#configuration">Configuration</a></li>
279
+ <li class="toc-section">Providers</li>
280
+ <li><a href="#ai-providers">AI Providers</a></li>
281
+ <li class="toc-section">Tools</li>
282
+ <li><a href="#web-dashboard">Web Dashboard</a></li>
283
+ <li><a href="#tips">Writing Good Plans</a></li>
284
+ </ul>
285
+ </nav>
286
+
287
+ <!-- Main content -->
288
+ <main id="main">
289
+
290
+ <h1 id="overview">Maestro</h1>
291
+ <p>
292
+ <strong>Autonomous AI coding orchestrator.</strong> Maestro reads a markdown plan file,
293
+ executes each task using a fresh Claude Code or GitHub Copilot session, validates after
294
+ every step, commits the result, and runs a multi-phase code review — all without human
295
+ intervention.
296
+ </p>
297
+
298
+ <hr>
299
+
300
+ <h2 id="how-it-works">How It Works</h2>
301
+
302
+ <div class="flow"><span class="phase">Plan File</span> <span class="arrow">→</span> <span class="phase">Phase 1: Tasks</span> <span class="arrow">→</span> <span class="phase">Phase 2: First Review</span> <span class="arrow">→</span> <span class="phase">Phase 3: Second Review</span> <span class="arrow">→</span> <span class="phase">Phase 4: Finalize</span>
303
+ (N tasks, (single agent, (multi-agent, (optional
304
+ validate + broad pass) targeted pass) cleanup)
305
+ commit each)</div>
306
+
307
+ <ol>
308
+ <li><strong>Parse</strong> — Maestro reads your markdown plan and extracts tasks (checkboxes) and validation commands.</li>
309
+ <li><strong>Execute</strong> — Each task is sent to a fresh AI session. The session runs until all checkboxes are marked complete.</li>
310
+ <li><strong>Validate</strong> — After each task, shell validation commands run. On failure, a retry is triggered (up to <code>task_retry_count</code>).</li>
311
+ <li><strong>Commit</strong> — A git commit is made after each successful task.</li>
312
+ <li><strong>Review</strong> — Two review phases run over the full diff: Phase 2 catches broad issues, Phase 3 runs multiple specialist agents on targeted concerns.</li>
313
+ <li><strong>Finalize</strong> — Optional cleanup pass (disabled by default).</li>
314
+ </ol>
315
+
316
+ <hr>
317
+
318
+ <h2 id="prerequisites">Prerequisites</h2>
319
+ <ul>
320
+ <li><strong>Node.js ≥ 22</strong></li>
321
+ <li><strong>Git</strong></li>
322
+ <li>At least one AI provider:
323
+ <ul>
324
+ <li><strong>Claude Code:</strong> <code>npm install -g @anthropic-ai/claude-code</code> — then <code>claude login</code></li>
325
+ <li><strong>GitHub Copilot:</strong> <code>npm install -g @github/copilot</code> — then <code>gh auth login</code></li>
326
+ </ul>
327
+ </li>
328
+ </ul>
329
+
330
+ <hr>
331
+
332
+ <h2 id="installation">Installation</h2>
333
+ <pre><code>npm install -g @rajat-rastogi/maestro</code></pre>
334
+
335
+ <hr>
336
+
337
+ <h2 id="quick-start">Quick Start</h2>
338
+
339
+ <p><strong>1. Write a plan file</strong> (<code>docs/plans/my-feature.md</code>):</p>
340
+
341
+ <pre><code><span class="hd"># Plan: Add greeting endpoint</span>
342
+
343
+ <span class="hd">## Overview</span>
344
+ Add a /greet route that returns a personalised JSON greeting.
345
+
346
+ <span class="hd">## Validation Commands</span>
347
+ - `npm run build`
348
+ - `npm test`
349
+
350
+ <span class="hd">### Task 1: Create the route handler</span>
351
+ <span class="cb">- [ ]</span> Create `src/routes/greet.ts` with a `GET /greet?name=` handler
352
+ <span class="cb">- [ ]</span> Export `greetRouter` from the file
353
+ <span class="cb">- [ ]</span> Add unit test in `src/routes/greet.test.ts`
354
+
355
+ <span class="hd">### Task 2: Wire into Express app</span>
356
+ <span class="cb">- [ ]</span> Import `greetRouter` in `src/app.ts`
357
+ <span class="cb">- [ ]</span> Register at `/greet` before the catch-all handler</code></pre>
358
+
359
+ <p><strong>2. Run it:</strong></p>
360
+ <pre><code>maestro docs/plans/my-feature.md</code></pre>
361
+
362
+ <p><strong>3. Watch the output</strong> — each task is executed, validated, and committed
363
+ automatically. When all tasks are done Maestro prints <code>ALL_TASKS_DONE</code> and kicks
364
+ off the review phases.</p>
365
+
366
+ <hr>
367
+
368
+ <h2 id="plan-format">Plan File Format</h2>
369
+
370
+ <pre><code><span class="hd"># Plan: &lt;Title&gt;</span>
371
+
372
+ <span class="hd">## Overview</span>
373
+ One-paragraph description of the goal.
374
+
375
+ <span class="hd">## Validation Commands</span>
376
+ <span class="cm"># Runs after EVERY task</span>
377
+ - `command that must pass after every task`
378
+ - `another command`
379
+
380
+ <span class="hd">### Task 1: &lt;Title&gt;</span>
381
+ <span class="cb">- [ ]</span> Specific, verifiable deliverable
382
+ <span class="cb">- [ ]</span> Another deliverable
383
+
384
+ <span class="hd">#### Validation Commands</span>
385
+ <span class="cm"># Runs only after this task</span>
386
+ - `command that only runs after Task 1`
387
+
388
+ <span class="hd">### Task 2: &lt;Title&gt;</span>
389
+ <span class="cb">- [ ]</span> Deliverable</code></pre>
390
+
391
+ <h3>Rules</h3>
392
+ <ul>
393
+ <li><code>## Validation Commands</code> (top-level) — runs after <strong>every</strong> task.</li>
394
+ <li><code>#### Validation Commands</code> (under a task heading) — runs only after that specific task.</li>
395
+ <li>Each checkbox must be a specific, observable outcome — the AI marks it <code>[x]</code> when done.</li>
396
+ <li>Every task should leave the codebase in a compilable, passing state.</li>
397
+ </ul>
398
+
399
+ <hr>
400
+
401
+ <h2 id="cli-reference">CLI Reference</h2>
402
+
403
+ <table>
404
+ <thead>
405
+ <tr><th>Flag</th><th>Description</th><th>Default</th></tr>
406
+ </thead>
407
+ <tbody>
408
+ <tr><td><code>[plan-file]</code></td><td>Path to the markdown plan to execute</td><td>—</td></tr>
409
+ <tr><td><code>--provider &lt;name&gt;</code></td><td>AI provider: <code>copilot</code> or <code>claude</code></td><td><code>copilot</code></td></tr>
410
+ <tr><td><code>-m, --max-iterations &lt;n&gt;</code></td><td>Maximum task execution iterations</td><td><code>50</code></td></tr>
411
+ <tr><td><code>--max-external-iterations &lt;n&gt;</code></td><td>Second-review iteration limit (0 = auto)</td><td><code>0</code></td></tr>
412
+ <tr><td><code>-r, --review</code></td><td>Skip tasks; run review pipeline on current branch</td><td>—</td></tr>
413
+ <tr><td><code>-t, --tasks-only</code></td><td>Run tasks only; skip all reviews</td><td>—</td></tr>
414
+ <tr><td><code>-b, --base-ref &lt;ref&gt;</code></td><td>Override default branch for review diffs</td><td>auto</td></tr>
415
+ <tr><td><code>--skip-finalize</code></td><td>Skip finalize step</td><td>—</td></tr>
416
+ <tr><td><code>--worktree</code></td><td>Run in an isolated git worktree</td><td>—</td></tr>
417
+ <tr><td><code>--plan &lt;description&gt;</code></td><td>Create a plan file interactively via AI</td><td>—</td></tr>
418
+ <tr><td><code>-s, --serve</code></td><td>Start live web dashboard</td><td>—</td></tr>
419
+ <tr><td><code>--replay</code></td><td>Browse completed runs in offline dashboard</td><td>—</td></tr>
420
+ <tr><td><code>-p, --port &lt;n&gt;</code></td><td>Web dashboard port</td><td><code>8080</code></td></tr>
421
+ <tr><td><code>-w, --watch &lt;dir&gt;</code></td><td>Extra directory to watch for progress files</td><td>—</td></tr>
422
+ <tr><td><code>-d, --debug</code></td><td>Enable debug logging</td><td>—</td></tr>
423
+ <tr><td><code>--no-color</code></td><td>Disable ANSI color output</td><td>—</td></tr>
424
+ <tr><td><code>--plan-tips</code></td><td>Show plan authoring best practices</td><td>—</td></tr>
425
+ <tr><td><code>--docs</code></td><td>Open full reference documentation in browser</td><td>—</td></tr>
426
+ <tr><td><code>--config</code></td><td>Open web UI to view/edit configuration</td><td>—</td></tr>
427
+ <tr><td><code>--reset</code></td><td>Interactively reset global config to defaults</td><td>—</td></tr>
428
+ <tr><td><code>--dump-defaults &lt;dir&gt;</code></td><td>Extract embedded defaults to a directory</td><td>—</td></tr>
429
+ <tr><td><code>--config-dir &lt;dir&gt;</code></td><td>Override config directory</td><td>—</td></tr>
430
+ </tbody>
431
+ </table>
432
+
433
+ <hr>
434
+
435
+ <h2 id="configuration">Configuration</h2>
436
+
437
+ <p>Maestro merges configuration from four layers (highest priority first):</p>
438
+ <ol>
439
+ <li><strong>CLI flags</strong> — <code>--provider</code>, <code>--max-iterations</code>, etc.</li>
440
+ <li><strong>Project config</strong> — <code>.maestro/config</code> in the current working directory</li>
441
+ <li><strong>Global config</strong> — <code>~/.config/maestro/config</code></li>
442
+ <li><strong>Embedded defaults</strong> — shipped inside the package</li>
443
+ </ol>
444
+
445
+ <p>Config files use INI format. You only need to set keys that differ from the defaults.</p>
446
+
447
+ <pre><code><span class="cm"># .maestro/config (project-level overrides)</span>
448
+ ai_provider = copilot
449
+ max_iterations = 30
450
+ port = 9000</code></pre>
451
+
452
+ <p>Edit your global config in a browser UI:</p>
453
+ <pre><code>maestro --config</code></pre>
454
+
455
+ <h3>Config Keys</h3>
456
+ <table>
457
+ <thead>
458
+ <tr><th>Key</th><th>Default</th><th>Description</th></tr>
459
+ </thead>
460
+ <tbody>
461
+ <tr><td><code>ai_provider</code></td><td><code>copilot</code></td><td><code>copilot</code> or <code>claude</code></td></tr>
462
+ <tr><td><code>claude_command</code></td><td><code>claude</code></td><td>Claude Code executable</td></tr>
463
+ <tr><td><code>claude_args</code></td><td>(see defaults)</td><td>Extra args passed to Claude</td></tr>
464
+ <tr><td><code>claude_error_patterns</code></td><td>(see defaults)</td><td>Patterns that signal a fatal Claude error</td></tr>
465
+ <tr><td><code>copilot_command</code></td><td><code>copilot</code></td><td>Copilot executable</td></tr>
466
+ <tr><td><code>copilot_args</code></td><td><code>--autopilot --allow-all</code></td><td>Extra args passed to Copilot</td></tr>
467
+ <tr><td><code>copilot_error_patterns</code></td><td>(see defaults)</td><td>Patterns that signal a fatal Copilot error</td></tr>
468
+ <tr><td><code>max_iterations</code></td><td><code>50</code></td><td>Max AI iterations per task</td></tr>
469
+ <tr><td><code>max_external_iterations</code></td><td><code>0</code></td><td>Review iteration limit (0 = auto)</td></tr>
470
+ <tr><td><code>iteration_delay_ms</code></td><td><code>2000</code></td><td>Delay between iterations (ms)</td></tr>
471
+ <tr><td><code>task_retry_count</code></td><td><code>1</code></td><td>Retries on validation failure</td></tr>
472
+ <tr><td><code>validation_timeout_ms</code></td><td><code>60000</code></td><td>Validation command timeout (0 = unlimited)</td></tr>
473
+ <tr><td><code>finalize_enabled</code></td><td><code>false</code></td><td>Enable Phase 4 finalize step</td></tr>
474
+ <tr><td><code>use_worktree</code></td><td><code>false</code></td><td>Run in isolated git worktree</td></tr>
475
+ <tr><td><code>plans_dir</code></td><td><code>docs/plans</code></td><td>Default directory for plan files</td></tr>
476
+ <tr><td><code>default_branch</code></td><td>(auto)</td><td>Base branch for review diffs</td></tr>
477
+ <tr><td><code>vcs_command</code></td><td><code>git</code></td><td>VCS executable</td></tr>
478
+ <tr><td><code>push_on_complete</code></td><td><code>false</code></td><td>Push branch after all phases complete</td></tr>
479
+ <tr><td><code>port</code></td><td><code>8080</code></td><td>Web dashboard port</td></tr>
480
+ <tr><td><code>watch_dirs</code></td><td>—</td><td>Comma-separated extra dirs for dashboard</td></tr>
481
+ <tr><td><code>color_task</code></td><td><code>#00ff00</code></td><td>Task phase color</td></tr>
482
+ <tr><td><code>color_review</code></td><td><code>#00ffff</code></td><td>Review phase color</td></tr>
483
+ <tr><td><code>color_signal</code></td><td><code>#ff6464</code></td><td>Signal color (ALL_TASKS_DONE etc.)</td></tr>
484
+ <tr><td><code>color_warn</code></td><td><code>#ffff00</code></td><td>Warning color</td></tr>
485
+ <tr><td><code>color_error</code></td><td><code>#ff0000</code></td><td>Error color</td></tr>
486
+ <tr><td><code>color_info</code></td><td><code>#b4b4b4</code></td><td>Info / default text color</td></tr>
487
+ <tr><td><code>color_timestamp</code></td><td><code>#8a8a8a</code></td><td>Timestamp color</td></tr>
488
+ </tbody>
489
+ </table>
490
+
491
+ <hr>
492
+
493
+ <h2 id="ai-providers">AI Providers</h2>
494
+
495
+ <h3>Claude Code</h3>
496
+ <pre><code>npm install -g @anthropic-ai/claude-code
497
+ claude login</code></pre>
498
+ <p>Set in config: <code>ai_provider = claude</code>.</p>
499
+
500
+ <h3>GitHub Copilot</h3>
501
+ <pre><code>npm install -g @github/copilot
502
+ gh auth login</code></pre>
503
+ <p>Set in config: <code>ai_provider = copilot</code> (this is the default).</p>
504
+
505
+ <hr>
506
+
507
+ <h2 id="web-dashboard">Web Dashboard</h2>
508
+
509
+ <table>
510
+ <thead>
511
+ <tr><th>Command</th><th>What it does</th></tr>
512
+ </thead>
513
+ <tbody>
514
+ <tr><td><code>maestro &lt;plan&gt; --serve</code></td><td>Live dashboard — streams task progress in real time</td></tr>
515
+ <tr><td><code>maestro --replay</code></td><td>Offline dashboard — browse completed run logs</td></tr>
516
+ <tr><td><code>maestro --config</code></td><td>Config editor — view and change all settings in a browser UI</td></tr>
517
+ </tbody>
518
+ </table>
519
+
520
+ <p>All dashboards run locally on <code>http://localhost:8080</code> (or your configured port).</p>
521
+
522
+ <hr>
523
+
524
+ <h2 id="tips">Writing Good Plans</h2>
525
+
526
+ <p>Run <code>maestro --plan-tips</code> for the full guide. Key principles:</p>
527
+
528
+ <h3>Validation must pass at every step</h3>
529
+ <p>Global validation commands run after <em>every</em> task — not just the last one. If a
530
+ command references a file created by a later task, wrap it conditionally:</p>
531
+
532
+ <pre><code><span class="cm"># incremental validation pattern</span>
533
+ node --input-type=module -e "
534
+ import { existsSync } from 'fs';
535
+ if (existsSync('./src/index.js')) {
536
+ const m = await import('./src/index.js');
537
+ console.log(m.greet('world'));
538
+ } else {
539
+ console.log('partial build ok');
540
+ }
541
+ "</code></pre>
542
+
543
+ <h3>Checkboxes are verifiable outcomes</h3>
544
+ <ul>
545
+ <li>✓ <code>Create src/foo.ts with exported bar() function</code></li>
546
+ <li>✗ <code>Work on the foo module</code> — too vague, the AI may not mark it done</li>
547
+ </ul>
548
+
549
+ <h3>Each task should leave the build green</h3>
550
+ <p>Avoid tasks that intentionally break the build temporarily. Design tasks so the
551
+ codebase compiles and existing tests pass after every task.</p>
552
+
553
+ <h3>Prefer independent tasks</h3>
554
+ <p>Tasks that don't depend on files from other tasks are safer, easier to retry, and
555
+ useful with <code>--tasks-only</code> at any stopping point.</p>
556
+
557
+ <h3>Sequential dependencies</h3>
558
+ <p>If Task 3 imports a file created by Task 1, use the incremental validation pattern
559
+ so Task 2 doesn't fail.</p>
560
+
561
+ <div class="callout info">
562
+ <strong>Tip:</strong> Use <code>maestro --plan "description of what you want"</code> to
563
+ have the AI draft a plan file for you, then review and edit before running.
564
+ </div>
565
+
566
+ </main>
567
+
568
+ <script>
569
+ (function () {
570
+ const main = document.getElementById('main');
571
+ const input = document.getElementById('search-input');
572
+ const countEl = document.getElementById('search-count');
573
+ const btnPrev = document.getElementById('search-prev');
574
+ const btnNext = document.getElementById('search-next');
575
+ const origHTML = main.innerHTML;
576
+
577
+ let marks = [];
578
+ let current = -1;
579
+
580
+ function escRe(s) {
581
+ return s.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
582
+ }
583
+
584
+ function walk(node, re) {
585
+ if (node.nodeType === 3) {
586
+ const text = node.textContent;
587
+ if (!re.test(text)) return;
588
+ re.lastIndex = 0;
589
+ const frag = document.createDocumentFragment();
590
+ let last = 0, m;
591
+ while ((m = re.exec(text)) !== null) {
592
+ frag.appendChild(document.createTextNode(text.slice(last, m.index)));
593
+ const mk = document.createElement('mark');
594
+ mk.textContent = m[0];
595
+ frag.appendChild(mk);
596
+ last = m.index + m[0].length;
597
+ }
598
+ frag.appendChild(document.createTextNode(text.slice(last)));
599
+ node.parentNode.replaceChild(frag, node);
600
+ } else if (node.nodeType === 1 && !/^(script|style)$/i.test(node.tagName)) {
601
+ Array.from(node.childNodes).forEach(c => walk(c, re));
602
+ }
603
+ }
604
+
605
+ function highlight(query) {
606
+ main.innerHTML = origHTML;
607
+ marks = [];
608
+ current = -1;
609
+ if (!query) { countEl.textContent = ''; return; }
610
+
611
+ const re = new RegExp(escRe(query), 'gi');
612
+ walk(main, re);
613
+ marks = Array.from(main.querySelectorAll('mark'));
614
+
615
+ if (marks.length) {
616
+ current = 0;
617
+ marks[0].classList.add('current');
618
+ marks[0].scrollIntoView({ behavior: 'smooth', block: 'center' });
619
+ countEl.textContent = `1 / ${marks.length}`;
620
+ } else {
621
+ countEl.textContent = 'no matches';
622
+ }
623
+ const hasMatches = marks.length > 0;
624
+ btnPrev.disabled = !hasMatches;
625
+ btnNext.disabled = !hasMatches;
626
+ }
627
+
628
+ function goTo(idx) {
629
+ if (!marks.length) return;
630
+ marks[current].classList.remove('current');
631
+ current = ((idx % marks.length) + marks.length) % marks.length;
632
+ marks[current].classList.add('current');
633
+ marks[current].scrollIntoView({ behavior: 'smooth', block: 'center' });
634
+ countEl.textContent = `${current + 1} / ${marks.length}`;
635
+ }
636
+
637
+ input.addEventListener('input', () => highlight(input.value.trim()));
638
+
639
+ input.addEventListener('keydown', e => {
640
+ if (e.key === 'Enter') { e.preventDefault(); goTo(current + (e.shiftKey ? -1 : 1)); }
641
+ if (e.key === 'Escape') { input.value = ''; highlight(''); input.blur(); }
642
+ });
643
+
644
+ btnNext.addEventListener('click', () => goTo(current + 1));
645
+ btnPrev.addEventListener('click', () => goTo(current - 1));
646
+
647
+ document.addEventListener('keydown', e => {
648
+ if (e.key === '/' && document.activeElement !== input) {
649
+ e.preventDefault();
650
+ input.focus();
651
+ input.select();
652
+ }
653
+ });
654
+ }());
655
+ </script>
656
+ </body>
657
+ </html>
@@ -0,0 +1,2 @@
1
+ export declare function readEmbeddedHtml(): string;
2
+ //# sourceMappingURL=assets.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"assets.d.ts","sourceRoot":"","sources":["../../src/dashboard/assets.ts"],"names":[],"mappings":"AAEA,wBAAgB,gBAAgB,IAAI,MAAM,CAEzC"}
@@ -0,0 +1,5 @@
1
+ import { readHtmlAsset } from '../sea.js';
2
+ export function readEmbeddedHtml() {
3
+ return readHtmlAsset('dashboard.html');
4
+ }
5
+ //# sourceMappingURL=assets.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"assets.js","sourceRoot":"","sources":["../../src/dashboard/assets.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC;AAE1C,MAAM,UAAU,gBAAgB;IAC9B,OAAO,aAAa,CAAC,gBAAgB,CAAC,CAAC;AACzC,CAAC"}