clavix 2.7.0 → 2.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +22 -8
- package/bin/clavix.js +12 -5
- package/dist/cli/commands/archive.d.ts +5 -4
- package/dist/cli/commands/archive.js +135 -161
- package/dist/cli/commands/config.d.ts +4 -4
- package/dist/cli/commands/config.js +66 -105
- package/dist/cli/commands/deep.d.ts +3 -3
- package/dist/cli/commands/deep.js +97 -103
- package/dist/cli/commands/execute.d.ts +4 -4
- package/dist/cli/commands/execute.js +57 -63
- package/dist/cli/commands/fast.d.ts +3 -3
- package/dist/cli/commands/fast.js +122 -128
- package/dist/cli/commands/implement.d.ts +4 -4
- package/dist/cli/commands/implement.js +84 -148
- package/dist/cli/commands/init.js +87 -126
- package/dist/cli/commands/list.d.ts +5 -5
- package/dist/cli/commands/list.js +72 -111
- package/dist/cli/commands/plan.d.ts +7 -7
- package/dist/cli/commands/plan.js +92 -131
- package/dist/cli/commands/prd.d.ts +4 -4
- package/dist/cli/commands/prd.js +76 -111
- package/dist/cli/commands/prompts/clear.d.ts +6 -6
- package/dist/cli/commands/prompts/clear.js +70 -76
- package/dist/cli/commands/prompts/list.js +37 -43
- package/dist/cli/commands/show.d.ts +4 -4
- package/dist/cli/commands/show.js +72 -111
- package/dist/cli/commands/start.d.ts +3 -3
- package/dist/cli/commands/start.js +63 -101
- package/dist/cli/commands/summarize.d.ts +4 -4
- package/dist/cli/commands/summarize.js +81 -120
- package/dist/cli/commands/task-complete.d.ts +4 -4
- package/dist/cli/commands/task-complete.js +86 -123
- package/dist/cli/commands/update.d.ts +3 -3
- package/dist/cli/commands/update.js +97 -130
- package/dist/cli/commands/version.js +13 -48
- package/dist/core/adapters/agents-md-generator.js +17 -50
- package/dist/core/adapters/amp-adapter.d.ts +1 -1
- package/dist/core/adapters/amp-adapter.js +13 -21
- package/dist/core/adapters/augment-adapter.d.ts +2 -2
- package/dist/core/adapters/augment-adapter.js +16 -56
- package/dist/core/adapters/base-adapter.d.ts +1 -1
- package/dist/core/adapters/base-adapter.js +11 -47
- package/dist/core/adapters/claude-code-adapter.d.ts +2 -2
- package/dist/core/adapters/claude-code-adapter.js +19 -60
- package/dist/core/adapters/cline-adapter.d.ts +1 -1
- package/dist/core/adapters/cline-adapter.js +13 -21
- package/dist/core/adapters/codebuddy-adapter.d.ts +2 -2
- package/dist/core/adapters/codebuddy-adapter.js +17 -57
- package/dist/core/adapters/codex-adapter.d.ts +2 -2
- package/dist/core/adapters/codex-adapter.js +16 -56
- package/dist/core/adapters/copilot-instructions-generator.js +18 -51
- package/dist/core/adapters/crush-adapter.d.ts +2 -2
- package/dist/core/adapters/crush-adapter.js +13 -20
- package/dist/core/adapters/cursor-adapter.d.ts +1 -1
- package/dist/core/adapters/cursor-adapter.js +12 -20
- package/dist/core/adapters/droid-adapter.d.ts +2 -2
- package/dist/core/adapters/droid-adapter.js +14 -21
- package/dist/core/adapters/gemini-adapter.d.ts +2 -2
- package/dist/core/adapters/gemini-adapter.js +16 -52
- package/dist/core/adapters/kilocode-adapter.d.ts +1 -1
- package/dist/core/adapters/kilocode-adapter.js +12 -20
- package/dist/core/adapters/octo-md-generator.js +17 -50
- package/dist/core/adapters/opencode-adapter.d.ts +2 -2
- package/dist/core/adapters/opencode-adapter.js +14 -21
- package/dist/core/adapters/qwen-adapter.d.ts +2 -2
- package/dist/core/adapters/qwen-adapter.js +16 -52
- package/dist/core/adapters/roocode-adapter.d.ts +2 -2
- package/dist/core/adapters/roocode-adapter.js +12 -19
- package/dist/core/adapters/warp-md-generator.js +17 -50
- package/dist/core/adapters/windsurf-adapter.d.ts +1 -1
- package/dist/core/adapters/windsurf-adapter.js +12 -20
- package/dist/core/agent-manager.d.ts +1 -1
- package/dist/core/agent-manager.js +34 -38
- package/dist/core/archive-manager.js +10 -46
- package/dist/core/config-manager.d.ts +2 -2
- package/dist/core/config-manager.js +3 -40
- package/dist/core/conversation-analyzer.d.ts +1 -1
- package/dist/core/conversation-analyzer.js +1 -5
- package/dist/core/doc-injector.js +23 -60
- package/dist/core/git-manager.js +11 -48
- package/dist/core/prd-generator.js +16 -51
- package/dist/core/prompt-manager.js +6 -42
- package/dist/core/prompt-optimizer.js +1 -5
- package/dist/core/question-engine.js +6 -45
- package/dist/core/session-manager.d.ts +1 -1
- package/dist/core/session-manager.js +11 -49
- package/dist/core/task-manager.d.ts +26 -0
- package/dist/core/task-manager.js +243 -101
- package/dist/index.d.ts +2 -1
- package/dist/index.js +8 -12
- package/dist/templates/agents/agents.md +31 -2
- package/dist/templates/agents/copilot-instructions.md +1 -1
- package/dist/templates/agents/octo.md +20 -1
- package/dist/templates/agents/warp.md +1 -1
- package/dist/templates/slash-commands/_canonical/implement.md +33 -11
- package/dist/types/agent.js +1 -2
- package/dist/types/config.js +3 -8
- package/dist/types/errors.js +7 -13
- package/dist/types/session.js +1 -2
- package/dist/utils/agent-error-messages.js +1 -5
- package/dist/utils/error-utils.js +5 -12
- package/dist/utils/file-system.js +20 -57
- package/dist/utils/legacy-command-cleanup.d.ts +1 -1
- package/dist/utils/legacy-command-cleanup.js +9 -45
- package/dist/utils/template-loader.d.ts +1 -1
- package/dist/utils/template-loader.js +9 -41
- package/dist/utils/toml-templates.js +1 -4
- package/package.json +12 -7
- package/dist/core/adapters 2/agents-md-generator.d.ts +0 -26
- package/dist/core/adapters 2/agents-md-generator.js +0 -102
- package/dist/core/adapters 2/amp-adapter.d.ts +0 -27
- package/dist/core/adapters 2/amp-adapter.js +0 -42
- package/dist/core/adapters 2/augment-adapter.d.ts +0 -22
- package/dist/core/adapters 2/augment-adapter.js +0 -77
- package/dist/core/adapters 2/base-adapter.d.ts +0 -45
- package/dist/core/adapters 2/base-adapter.js +0 -142
- package/dist/core/adapters 2/claude-code-adapter.d.ts +0 -32
- package/dist/core/adapters 2/claude-code-adapter.js +0 -116
- package/dist/core/adapters 2/cline-adapter.d.ts +0 -34
- package/dist/core/adapters 2/cline-adapter.js +0 -52
- package/dist/core/adapters 2/codebuddy-adapter.d.ts +0 -24
- package/dist/core/adapters 2/codebuddy-adapter.js +0 -82
- package/dist/core/adapters 2/codex-adapter.d.ts +0 -24
- package/dist/core/adapters 2/codex-adapter.js +0 -79
- package/dist/core/adapters 2/copilot-instructions-generator.d.ts +0 -26
- package/dist/core/adapters 2/copilot-instructions-generator.js +0 -104
- package/dist/core/adapters 2/crush-adapter.d.ts +0 -35
- package/dist/core/adapters 2/crush-adapter.js +0 -49
- package/dist/core/adapters 2/cursor-adapter.d.ts +0 -25
- package/dist/core/adapters 2/cursor-adapter.js +0 -40
- package/dist/core/adapters 2/droid-adapter.d.ts +0 -33
- package/dist/core/adapters 2/droid-adapter.js +0 -57
- package/dist/core/adapters 2/gemini-adapter.d.ts +0 -27
- package/dist/core/adapters 2/gemini-adapter.js +0 -90
- package/dist/core/adapters 2/kilocode-adapter.d.ts +0 -34
- package/dist/core/adapters 2/kilocode-adapter.js +0 -49
- package/dist/core/adapters 2/octo-md-generator.d.ts +0 -26
- package/dist/core/adapters 2/octo-md-generator.js +0 -102
- package/dist/core/adapters 2/opencode-adapter.d.ts +0 -33
- package/dist/core/adapters 2/opencode-adapter.js +0 -56
- package/dist/core/adapters 2/qwen-adapter.d.ts +0 -27
- package/dist/core/adapters 2/qwen-adapter.js +0 -90
- package/dist/core/adapters 2/roocode-adapter.d.ts +0 -40
- package/dist/core/adapters 2/roocode-adapter.js +0 -68
- package/dist/core/adapters 2/warp-md-generator.d.ts +0 -17
- package/dist/core/adapters 2/warp-md-generator.js +0 -88
- package/dist/core/adapters 2/windsurf-adapter.d.ts +0 -34
- package/dist/core/adapters 2/windsurf-adapter.js +0 -49
- package/dist/core/agent-manager 2.js +0 -126
- package/dist/core/agent-manager.d 2.ts +0 -51
- package/dist/core/archive-manager 2.js +0 -338
- package/dist/core/archive-manager.d 2.ts +0 -100
- package/dist/core/conversation-analyzer.d 2.ts +0 -86
- package/dist/core/doc-injector 2.js +0 -236
- package/dist/core/doc-injector.d 2.ts +0 -51
- package/dist/core/git-manager 2.js +0 -214
- package/dist/core/git-manager.d 2.ts +0 -100
- package/dist/core/prompt-optimizer 2.js +0 -963
- package/dist/core/prompt-optimizer.d 2.ts +0 -268
- package/dist/core/question-engine 2.js +0 -395
- package/dist/core/question-engine.d 2.ts +0 -167
- package/dist/core/session-manager 2.js +0 -403
- package/dist/core/session-manager.d 2.ts +0 -139
- package/dist/core/task-manager 2.js +0 -689
- package/dist/core/task-manager.d 2.ts +0 -155
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
"use strict";
|
|
2
1
|
/**
|
|
3
2
|
* TaskManager - Manages PRD-based task generation and execution
|
|
4
3
|
*
|
|
@@ -9,45 +8,10 @@
|
|
|
9
8
|
* - Tracking task completion state
|
|
10
9
|
* - Managing session resume capability
|
|
11
10
|
*/
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
17
|
-
}
|
|
18
|
-
Object.defineProperty(o, k2, desc);
|
|
19
|
-
}) : (function(o, m, k, k2) {
|
|
20
|
-
if (k2 === undefined) k2 = k;
|
|
21
|
-
o[k2] = m[k];
|
|
22
|
-
}));
|
|
23
|
-
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
24
|
-
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
25
|
-
}) : function(o, v) {
|
|
26
|
-
o["default"] = v;
|
|
27
|
-
});
|
|
28
|
-
var __importStar = (this && this.__importStar) || (function () {
|
|
29
|
-
var ownKeys = function(o) {
|
|
30
|
-
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
31
|
-
var ar = [];
|
|
32
|
-
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
33
|
-
return ar;
|
|
34
|
-
};
|
|
35
|
-
return ownKeys(o);
|
|
36
|
-
};
|
|
37
|
-
return function (mod) {
|
|
38
|
-
if (mod && mod.__esModule) return mod;
|
|
39
|
-
var result = {};
|
|
40
|
-
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
41
|
-
__setModuleDefault(result, mod);
|
|
42
|
-
return result;
|
|
43
|
-
};
|
|
44
|
-
})();
|
|
45
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
46
|
-
exports.TaskManager = void 0;
|
|
47
|
-
const fs = __importStar(require("fs-extra"));
|
|
48
|
-
const path = __importStar(require("path"));
|
|
49
|
-
const prompt_optimizer_1 = require("./prompt-optimizer");
|
|
50
|
-
const file_system_1 = require("../utils/file-system");
|
|
11
|
+
import fs from 'fs-extra';
|
|
12
|
+
import * as path from 'path';
|
|
13
|
+
import { PromptOptimizer } from './prompt-optimizer.js';
|
|
14
|
+
import { FileSystem } from '../utils/file-system.js';
|
|
51
15
|
const SOURCE_FILE_MAP = {
|
|
52
16
|
full: ['full-prd.md', 'PRD.md', 'prd.md', 'Full-PRD.md', 'FULL_PRD.md', 'FULL-PRD.md'],
|
|
53
17
|
quick: ['quick-prd.md', 'QUICK_PRD.md'],
|
|
@@ -61,9 +25,10 @@ const ALL_KNOWN_PRD_FILES = Array.from(new Set(Object.values(SOURCE_FILE_MAP).fl
|
|
|
61
25
|
*
|
|
62
26
|
* Generates and manages implementation tasks from PRD documents
|
|
63
27
|
*/
|
|
64
|
-
class TaskManager {
|
|
28
|
+
export class TaskManager {
|
|
29
|
+
optimizer;
|
|
65
30
|
constructor() {
|
|
66
|
-
this.optimizer = new
|
|
31
|
+
this.optimizer = new PromptOptimizer();
|
|
67
32
|
}
|
|
68
33
|
/**
|
|
69
34
|
* Generate tasks.md from PRD
|
|
@@ -161,60 +126,204 @@ class TaskManager {
|
|
|
161
126
|
}
|
|
162
127
|
return null;
|
|
163
128
|
}
|
|
129
|
+
/**
|
|
130
|
+
* Generate phases from core features with intelligent grouping
|
|
131
|
+
* CRITICAL FIX: Group related features instead of 1 phase per bullet
|
|
132
|
+
*/
|
|
164
133
|
generatePhasesFromCoreFeatures(coreContent, options) {
|
|
165
134
|
const bullets = this.extractListItems(coreContent);
|
|
166
135
|
if (bullets.length === 0) {
|
|
167
136
|
return [];
|
|
168
137
|
}
|
|
169
|
-
|
|
138
|
+
// GRANULARITY CONTROL: Warn if too many bullets
|
|
139
|
+
if (bullets.length > 50) {
|
|
140
|
+
console.warn(`Warning: PRD contains ${bullets.length} top-level features. Consider grouping related items.`);
|
|
141
|
+
}
|
|
142
|
+
// Group features by type/category instead of creating separate phases
|
|
143
|
+
const groupedFeatures = this.groupFeaturesByCategory(bullets);
|
|
170
144
|
const phases = [];
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
prdReference: feature,
|
|
188
|
-
}));
|
|
189
|
-
phases.push({
|
|
190
|
-
name: phaseName,
|
|
191
|
-
tasks,
|
|
145
|
+
let phaseNumber = 1;
|
|
146
|
+
for (const [category, features] of Object.entries(groupedFeatures)) {
|
|
147
|
+
const phaseName = `Phase ${phaseNumber}: ${category}`;
|
|
148
|
+
const tasks = [];
|
|
149
|
+
// Generate tasks for each feature in this group
|
|
150
|
+
features.forEach((feature) => {
|
|
151
|
+
const taskDescriptions = this.buildFeatureTaskDescriptions(feature);
|
|
152
|
+
taskDescriptions.forEach((description) => {
|
|
153
|
+
tasks.push({
|
|
154
|
+
id: `${this.sanitizeId(phaseName)}-${tasks.length + 1}`,
|
|
155
|
+
description,
|
|
156
|
+
phase: phaseName,
|
|
157
|
+
completed: false,
|
|
158
|
+
prdReference: feature,
|
|
159
|
+
});
|
|
160
|
+
});
|
|
192
161
|
});
|
|
193
|
-
|
|
162
|
+
// GRANULARITY CONTROL: Skip empty phases
|
|
163
|
+
if (tasks.length > 0) {
|
|
164
|
+
phases.push({
|
|
165
|
+
name: phaseName,
|
|
166
|
+
tasks,
|
|
167
|
+
});
|
|
168
|
+
phaseNumber++;
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
// GRANULARITY CONTROL: Cap total tasks (merge if exceeding)
|
|
172
|
+
const totalTasks = phases.reduce((sum, p) => sum + p.tasks.length, 0);
|
|
173
|
+
if (totalTasks > 50) {
|
|
174
|
+
console.warn(`Warning: Generated ${totalTasks} tasks. Consider merging related tasks or simplifying PRD.`);
|
|
175
|
+
}
|
|
194
176
|
return phases;
|
|
195
177
|
}
|
|
178
|
+
/**
|
|
179
|
+
* Group features by category for logical phase organization
|
|
180
|
+
* Replaces "1 bullet = 1 phase" with intelligent grouping
|
|
181
|
+
*/
|
|
182
|
+
groupFeaturesByCategory(features) {
|
|
183
|
+
const groups = {
|
|
184
|
+
'Configuration & Setup': [],
|
|
185
|
+
'Core Implementation': [],
|
|
186
|
+
'Testing & Validation': [],
|
|
187
|
+
'Documentation': [],
|
|
188
|
+
'Integration & Release': [],
|
|
189
|
+
};
|
|
190
|
+
features.forEach((feature) => {
|
|
191
|
+
const lower = feature.toLowerCase();
|
|
192
|
+
// Config/setup phase
|
|
193
|
+
if (/\b(config|configuration|setup|install|package|tsconfig|dependencies|environment)\b/i.test(feature)) {
|
|
194
|
+
groups['Configuration & Setup'].push(feature);
|
|
195
|
+
}
|
|
196
|
+
// Testing phase
|
|
197
|
+
else if (/\b(test|testing|coverage|validation|verify|qa)\b/i.test(feature)) {
|
|
198
|
+
groups['Testing & Validation'].push(feature);
|
|
199
|
+
}
|
|
200
|
+
// Documentation phase
|
|
201
|
+
else if (/\b(document|documentation|readme|changelog|guide|comment)\b/i.test(feature)) {
|
|
202
|
+
groups['Documentation'].push(feature);
|
|
203
|
+
}
|
|
204
|
+
// Integration/release phase
|
|
205
|
+
else if (/\b(integrate|integration|release|deploy|publish|build|distribution)\b/i.test(feature)) {
|
|
206
|
+
groups['Integration & Release'].push(feature);
|
|
207
|
+
}
|
|
208
|
+
// Default to core implementation
|
|
209
|
+
else {
|
|
210
|
+
groups['Core Implementation'].push(feature);
|
|
211
|
+
}
|
|
212
|
+
});
|
|
213
|
+
// Remove empty groups
|
|
214
|
+
return Object.fromEntries(Object.entries(groups).filter(([_, features]) => features.length > 0));
|
|
215
|
+
}
|
|
216
|
+
/**
|
|
217
|
+
* Extract top-level list items only (ignore nested bullets)
|
|
218
|
+
* This prevents sub-bullets from being treated as separate tasks
|
|
219
|
+
*/
|
|
196
220
|
extractListItems(sectionContent) {
|
|
197
221
|
const items = [];
|
|
198
|
-
const
|
|
199
|
-
let
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
if (
|
|
203
|
-
|
|
222
|
+
const lines = sectionContent.split('\n');
|
|
223
|
+
let inCodeBlock = false;
|
|
224
|
+
for (const line of lines) {
|
|
225
|
+
// Track code blocks to ignore bullets inside them
|
|
226
|
+
if (line.trim().startsWith('```')) {
|
|
227
|
+
inCodeBlock = !inCodeBlock;
|
|
228
|
+
continue;
|
|
229
|
+
}
|
|
230
|
+
if (inCodeBlock) {
|
|
231
|
+
continue;
|
|
232
|
+
}
|
|
233
|
+
// Match ONLY top-level bullets (no indentation at all)
|
|
234
|
+
// Nested bullets (2+ spaces) are implementation details, not separate tasks
|
|
235
|
+
const topLevelMatch = line.match(/^(?:[-*]|\d+[.)])\s+(.+)$/);
|
|
236
|
+
if (topLevelMatch) {
|
|
237
|
+
const value = topLevelMatch[1].trim();
|
|
238
|
+
// Skip items that look like code examples, file paths, or implementation details
|
|
239
|
+
if (value && !this.looksLikeCodeOrPath(value) && !this.looksLikeImplementationDetail(value)) {
|
|
240
|
+
items.push(value.replace(/\s+/g, ' ').replace(/\.$/, ''));
|
|
241
|
+
}
|
|
204
242
|
}
|
|
205
243
|
}
|
|
206
244
|
return items;
|
|
207
245
|
}
|
|
246
|
+
/**
|
|
247
|
+
* Detect if a line looks like code or a file path (not a task)
|
|
248
|
+
*/
|
|
249
|
+
looksLikeCodeOrPath(text) {
|
|
250
|
+
// File paths with extensions
|
|
251
|
+
if (/\.(ts|js|json|md|tsx|jsx|mjs|cjs)/.test(text)) {
|
|
252
|
+
return true;
|
|
253
|
+
}
|
|
254
|
+
// Code-like patterns
|
|
255
|
+
if (text.includes('import ') || text.includes('export ') || text.includes('require(')) {
|
|
256
|
+
return true;
|
|
257
|
+
}
|
|
258
|
+
// JSON-like
|
|
259
|
+
if (text.trim().startsWith('{') || text.trim().startsWith('[')) {
|
|
260
|
+
return true;
|
|
261
|
+
}
|
|
262
|
+
// Very short technical commands
|
|
263
|
+
if (text.length < 15 && /^[a-z-]+:[a-z-]+$/i.test(text)) {
|
|
264
|
+
return true;
|
|
265
|
+
}
|
|
266
|
+
return false;
|
|
267
|
+
}
|
|
268
|
+
/**
|
|
269
|
+
* Detect if text is an implementation detail rather than a feature
|
|
270
|
+
* Implementation details are constraints, requirements, or sub-steps
|
|
271
|
+
*/
|
|
272
|
+
looksLikeImplementationDetail(text) {
|
|
273
|
+
const lower = text.toLowerCase();
|
|
274
|
+
// Constraints and requirements (not tasks)
|
|
275
|
+
if (lower.includes(' must ') || lower.includes(' should ') || lower.includes(' required')) {
|
|
276
|
+
return true;
|
|
277
|
+
}
|
|
278
|
+
// Very short items (< 25 chars) are likely details, not features
|
|
279
|
+
if (text.length < 25 && !lower.startsWith('implement') && !lower.startsWith('create')) {
|
|
280
|
+
return true;
|
|
281
|
+
}
|
|
282
|
+
// Specific technical constraints
|
|
283
|
+
if (/^(password|email|session|token|rate|https)/i.test(text)) {
|
|
284
|
+
return true;
|
|
285
|
+
}
|
|
286
|
+
return false;
|
|
287
|
+
}
|
|
288
|
+
/**
|
|
289
|
+
* Build context-aware task descriptions based on feature type and complexity
|
|
290
|
+
* Replaces the old 5-task boilerplate with intelligent task generation
|
|
291
|
+
*/
|
|
208
292
|
buildFeatureTaskDescriptions(feature) {
|
|
209
293
|
const formattedFeature = this.formatInlineText(feature);
|
|
210
|
-
const
|
|
294
|
+
const featureLower = feature.toLowerCase();
|
|
295
|
+
// Detect task type
|
|
296
|
+
const isConfig = /\b(config|configuration|setup|install|update.*json|tsconfig|package\.json)\b/i.test(feature);
|
|
297
|
+
const isTest = /\b(test|testing|coverage|validation|verify)\b/i.test(feature);
|
|
298
|
+
const isDocumentation = /\b(document|documentation|readme|changelog|guide)\b/i.test(feature);
|
|
299
|
+
const isConversion = /\b(convert|migrate|refactor|replace|update.*code)\b/i.test(feature);
|
|
300
|
+
// Simple tasks (config, documentation) - Single task only
|
|
301
|
+
if (isConfig) {
|
|
302
|
+
return [this.convertBehaviorToTask(feature)];
|
|
303
|
+
}
|
|
304
|
+
if (isDocumentation) {
|
|
305
|
+
return [this.convertBehaviorToTask(feature)];
|
|
306
|
+
}
|
|
307
|
+
// Testing tasks - Implementation + validation
|
|
308
|
+
if (isTest) {
|
|
309
|
+
return [
|
|
310
|
+
this.convertBehaviorToTask(feature),
|
|
311
|
+
`Verify ${formattedFeature} passes successfully`,
|
|
312
|
+
];
|
|
313
|
+
}
|
|
314
|
+
// Conversion/migration tasks - Convert + test
|
|
315
|
+
if (isConversion) {
|
|
316
|
+
return [
|
|
317
|
+
this.convertBehaviorToTask(feature),
|
|
318
|
+
`Test ${formattedFeature} works correctly`,
|
|
319
|
+
];
|
|
320
|
+
}
|
|
321
|
+
// Default for complex features - Implementation + testing only
|
|
322
|
+
// (No more "integrate into end-to-end" boilerplate)
|
|
323
|
+
return [
|
|
211
324
|
this.convertBehaviorToTask(feature),
|
|
212
325
|
`Add tests covering ${formattedFeature}`,
|
|
213
|
-
`Integrate ${formattedFeature} into the end-to-end experience`,
|
|
214
|
-
`Document ${formattedFeature} for stakeholders`,
|
|
215
|
-
`Validate ${formattedFeature} against requirements`,
|
|
216
326
|
];
|
|
217
|
-
return tasks;
|
|
218
327
|
}
|
|
219
328
|
formatInlineText(text) {
|
|
220
329
|
if (!text) {
|
|
@@ -333,8 +442,9 @@ class TaskManager {
|
|
|
333
442
|
const featuresContent = mustHaveMatch[1];
|
|
334
443
|
// Split by feature headers (#### Number. Feature Name)
|
|
335
444
|
const featureHeaders = [...featuresContent.matchAll(/####\s+(\d+)\.\s+(.+)/g)];
|
|
445
|
+
// Collect all top-level behaviors from all features
|
|
446
|
+
const allBehaviors = [];
|
|
336
447
|
for (let i = 0; i < featureHeaders.length; i++) {
|
|
337
|
-
const featureNumber = featureHeaders[i][1];
|
|
338
448
|
const featureName = featureHeaders[i][2].trim();
|
|
339
449
|
// Extract content between this header and the next one
|
|
340
450
|
const startIndex = featureHeaders[i].index;
|
|
@@ -342,10 +452,45 @@ class TaskManager {
|
|
|
342
452
|
? featureHeaders[i + 1].index
|
|
343
453
|
: featuresContent.length;
|
|
344
454
|
const featureContent = featuresContent.substring(startIndex, endIndex);
|
|
345
|
-
//
|
|
346
|
-
const
|
|
347
|
-
if (
|
|
348
|
-
|
|
455
|
+
// Extract behavior points using hierarchical parsing
|
|
456
|
+
const behaviorMatch = featureContent.match(/\*\*Behavior\*\*:([\s\S]*?)(?=\*\*|####|$)/);
|
|
457
|
+
if (behaviorMatch) {
|
|
458
|
+
const behaviors = behaviorMatch[1];
|
|
459
|
+
const bulletPoints = this.extractListItems(behaviors);
|
|
460
|
+
// Add all top-level behaviors to the list
|
|
461
|
+
allBehaviors.push(...bulletPoints);
|
|
462
|
+
}
|
|
463
|
+
else {
|
|
464
|
+
// If no Behavior section, add the feature name itself
|
|
465
|
+
allBehaviors.push(featureName);
|
|
466
|
+
}
|
|
467
|
+
}
|
|
468
|
+
// Now group all behaviors by category (instead of 1 phase per feature)
|
|
469
|
+
if (allBehaviors.length > 0) {
|
|
470
|
+
const groupedFeatures = this.groupFeaturesByCategory(allBehaviors);
|
|
471
|
+
let phaseNumber = 1;
|
|
472
|
+
for (const [category, features] of Object.entries(groupedFeatures)) {
|
|
473
|
+
const phaseName = `Phase ${phaseNumber}: ${category}`;
|
|
474
|
+
const tasks = [];
|
|
475
|
+
features.forEach((feature) => {
|
|
476
|
+
const taskDescriptions = this.buildFeatureTaskDescriptions(feature);
|
|
477
|
+
taskDescriptions.forEach((description) => {
|
|
478
|
+
tasks.push({
|
|
479
|
+
id: `${this.sanitizeId(phaseName)}-${tasks.length + 1}`,
|
|
480
|
+
description,
|
|
481
|
+
phase: phaseName,
|
|
482
|
+
completed: false,
|
|
483
|
+
prdReference: feature,
|
|
484
|
+
});
|
|
485
|
+
});
|
|
486
|
+
});
|
|
487
|
+
if (tasks.length > 0) {
|
|
488
|
+
phases.push({
|
|
489
|
+
name: phaseName,
|
|
490
|
+
tasks,
|
|
491
|
+
});
|
|
492
|
+
phaseNumber++;
|
|
493
|
+
}
|
|
349
494
|
}
|
|
350
495
|
}
|
|
351
496
|
}
|
|
@@ -360,26 +505,24 @@ class TaskManager {
|
|
|
360
505
|
*/
|
|
361
506
|
generatePhaseFromFeature(featureName, featureContent, phasePrefix) {
|
|
362
507
|
const tasks = [];
|
|
363
|
-
// Extract behavior points
|
|
508
|
+
// Extract behavior points using hierarchical parsing
|
|
364
509
|
const behaviorMatch = featureContent.match(/\*\*Behavior\*\*:([\s\S]*?)(?=\*\*|####|$)/);
|
|
365
510
|
if (behaviorMatch) {
|
|
366
511
|
const behaviors = behaviorMatch[1];
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
});
|
|
382
|
-
}
|
|
512
|
+
// Use the same hierarchical parsing as extractListItems()
|
|
513
|
+
const bulletPoints = this.extractListItems(behaviors);
|
|
514
|
+
bulletPoints.forEach((description, index) => {
|
|
515
|
+
// Skip overly long bullets (likely multi-line descriptions)
|
|
516
|
+
if (description.length < 200) {
|
|
517
|
+
tasks.push({
|
|
518
|
+
id: `${this.sanitizeId(featureName)}-${index + 1}`,
|
|
519
|
+
description: this.convertBehaviorToTask(description),
|
|
520
|
+
phase: phasePrefix,
|
|
521
|
+
completed: false,
|
|
522
|
+
prdReference: featureName,
|
|
523
|
+
});
|
|
524
|
+
}
|
|
525
|
+
});
|
|
383
526
|
}
|
|
384
527
|
// If no behavior points, try to extract from feature description
|
|
385
528
|
if (tasks.length === 0) {
|
|
@@ -490,7 +633,7 @@ class TaskManager {
|
|
|
490
633
|
// Add footer
|
|
491
634
|
content += '---\n\n';
|
|
492
635
|
content += '*Generated by Clavix /clavix:plan*\n';
|
|
493
|
-
await
|
|
636
|
+
await FileSystem.writeFileAtomic(outputPath, content);
|
|
494
637
|
}
|
|
495
638
|
/**
|
|
496
639
|
* Read tasks from tasks.md file
|
|
@@ -597,7 +740,7 @@ class TaskManager {
|
|
|
597
740
|
: '';
|
|
598
741
|
const regex = new RegExp(`^(-\\s+\\[)( )(\\]\\s+${taskDescPattern}${refPattern})$`, 'm');
|
|
599
742
|
const updatedContent = content.replace(regex, '$1x$3');
|
|
600
|
-
await
|
|
743
|
+
await FileSystem.writeFileAtomic(tasksPath, updatedContent);
|
|
601
744
|
}
|
|
602
745
|
/**
|
|
603
746
|
* Escape special regex characters
|
|
@@ -827,5 +970,4 @@ class TaskManager {
|
|
|
827
970
|
return available;
|
|
828
971
|
}
|
|
829
972
|
}
|
|
830
|
-
exports.TaskManager = TaskManager;
|
|
831
973
|
//# sourceMappingURL=task-manager.js.map
|
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -1,17 +1,13 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
async function run(argv) {
|
|
7
|
-
// Disable debug mode (stack traces) unless explicitly requested via DEBUG env var
|
|
8
|
-
if (!process.env.DEBUG) {
|
|
9
|
-
core_1.settings.debug = false;
|
|
10
|
-
}
|
|
11
|
-
return (0, core_1.run)(argv);
|
|
2
|
+
import { run, handle, settings } from '@oclif/core';
|
|
3
|
+
// Disable debug mode (stack traces) unless explicitly requested via DEBUG env var
|
|
4
|
+
if (!process.env.DEBUG) {
|
|
5
|
+
settings.debug = false;
|
|
12
6
|
}
|
|
13
7
|
// Run if called directly
|
|
14
|
-
if (
|
|
15
|
-
run().catch(
|
|
8
|
+
if (import.meta.url === `file://${process.argv[1]}`) {
|
|
9
|
+
run().catch(handle);
|
|
16
10
|
}
|
|
11
|
+
// Export for testing
|
|
12
|
+
export { run };
|
|
17
13
|
//# sourceMappingURL=index.js.map
|
|
@@ -19,7 +19,7 @@ Use these instructions when your agent can only read documentation (no slash-com
|
|
|
19
19
|
| `clavix prompts clear` | Manage prompt cleanup. Supports `--executed`, `--stale`, `--fast`, `--deep`, `--all` flags. |
|
|
20
20
|
| `clavix prd` | Guided Socratic questions that generate `full-prd.md` and `quick-prd.md`. |
|
|
21
21
|
| `clavix plan` | Transform PRDs or sessions into phase-based `tasks.md`. |
|
|
22
|
-
| `clavix implement` |
|
|
22
|
+
| `clavix implement [--commit-strategy=<type>]` | Start task execution. Git strategies: per-task, per-5-tasks, per-phase, none (default: none). |
|
|
23
23
|
| `clavix start` | Begin conversational capture session for requirements gathering. |
|
|
24
24
|
| `clavix summarize [session-id]` | Extract mini PRD and optimized prompts from saved sessions. |
|
|
25
25
|
| `clavix list` | List sessions and/or output projects (`--sessions`, `--outputs`, filters). |
|
|
@@ -32,10 +32,39 @@ Use these instructions when your agent can only read documentation (no slash-com
|
|
|
32
32
|
## Typical workflows
|
|
33
33
|
- **Improve prompts quickly:** run `clavix fast` or `clavix deep` depending on complexity.
|
|
34
34
|
- **Create strategy:** run `clavix prd` then `clavix plan` for an implementation checklist.
|
|
35
|
-
- **Execute tasks:** use `clavix implement`, commit work, repeat until tasks complete.
|
|
35
|
+
- **Execute tasks:** use `clavix implement [--commit-strategy=<type>]`, commit work, repeat until tasks complete.
|
|
36
36
|
- **Capture conversations:** record with `clavix start`, extract with `clavix summarize`.
|
|
37
37
|
- **Stay organized:** inspect with `clavix list/show`, archive with `clavix archive`, refresh docs via `clavix update`.
|
|
38
38
|
|
|
39
|
+
## Implementation with Git Strategy (Agent Workflow)
|
|
40
|
+
|
|
41
|
+
When implementing tasks with `clavix implement`:
|
|
42
|
+
|
|
43
|
+
1. **Check task count**: Read `tasks.md` and count phases
|
|
44
|
+
2. **Ask user for git preferences** (optional, only if >3 phases):
|
|
45
|
+
```
|
|
46
|
+
"I notice this implementation has [X] phases with [Y] tasks.
|
|
47
|
+
|
|
48
|
+
Git auto-commit preferences?
|
|
49
|
+
- per-task: Commit after each task (detailed history)
|
|
50
|
+
- per-5-tasks: Commit every 5 tasks (balanced)
|
|
51
|
+
- per-phase: Commit when phase completes (milestones)
|
|
52
|
+
- none: Manual git workflow (default)
|
|
53
|
+
|
|
54
|
+
I'll use 'none' if you don't specify."
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
3. **Run implement with strategy**:
|
|
58
|
+
```bash
|
|
59
|
+
# With git strategy (if user specified):
|
|
60
|
+
clavix implement --commit-strategy=per-phase
|
|
61
|
+
|
|
62
|
+
# Or without (defaults to 'none' - manual commits):
|
|
63
|
+
clavix implement
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
4. **Default behavior**: If no `--commit-strategy` flag provided, defaults to `none` (manual commits)
|
|
67
|
+
|
|
39
68
|
Artifacts are stored under `.clavix/`:
|
|
40
69
|
- `.clavix/outputs/<project>/` for PRDs, tasks, prompts
|
|
41
70
|
- `.clavix/sessions/` for captured conversations
|
|
@@ -17,7 +17,7 @@ When working with this project, you can use the following Clavix commands:
|
|
|
17
17
|
### Strategic Planning
|
|
18
18
|
- `clavix prd` - Interactive PRD generation through Socratic questioning
|
|
19
19
|
- `clavix plan` - Transform PRDs into phase-based implementation tasks
|
|
20
|
-
- `clavix implement` - Execute tasks with progress tracking
|
|
20
|
+
- `clavix implement [--commit-strategy=<type>]` - Execute tasks with progress tracking (git: per-task, per-5-tasks, per-phase, none [default])
|
|
21
21
|
|
|
22
22
|
### Conversational Workflows
|
|
23
23
|
- `clavix start` - Begin conversational session for requirements gathering
|
|
@@ -196,6 +196,25 @@ Detect user intent from keywords and trigger appropriate workflow. Use Octofrien
|
|
|
196
196
|
- Switch to thinking models when encountering complex architectural decisions or debugging
|
|
197
197
|
- Your autofix capabilities help recover from tool call failures automatically
|
|
198
198
|
|
|
199
|
+
**Git Auto-Commit Strategy (Agent-Friendly):**
|
|
200
|
+
|
|
201
|
+
When starting implementation with `clavix implement`:
|
|
202
|
+
|
|
203
|
+
1. **Check task complexity** (optional, only if >3 phases in tasks.md):
|
|
204
|
+
- Ask user: "Git auto-commit preferences? (per-task, per-5-tasks, per-phase, none)"
|
|
205
|
+
- Default to 'none' if user doesn't specify
|
|
206
|
+
|
|
207
|
+
2. **Run with explicit strategy**:
|
|
208
|
+
```bash
|
|
209
|
+
# If user wants commits:
|
|
210
|
+
clavix implement --commit-strategy=per-phase
|
|
211
|
+
|
|
212
|
+
# Otherwise (or no preference):
|
|
213
|
+
clavix implement
|
|
214
|
+
```
|
|
215
|
+
|
|
216
|
+
3. **Default behavior**: No `--commit-strategy` flag → defaults to 'none' (manual git workflow)
|
|
217
|
+
|
|
199
218
|
---
|
|
200
219
|
|
|
201
220
|
### Archive Workflow
|
|
@@ -250,7 +269,7 @@ Detect user intent from keywords and trigger appropriate workflow. Use Octofrien
|
|
|
250
269
|
| `clavix prompts clear` | Cleanup executed/stale prompts (`--executed`, `--stale`, `--fast`, `--deep`). |
|
|
251
270
|
| `clavix prd` | Guided questions to create PRDs. |
|
|
252
271
|
| `clavix plan` | Convert PRD artifacts into task lists. |
|
|
253
|
-
| `clavix implement` |
|
|
272
|
+
| `clavix implement [--commit-strategy=<type>]` | Start task execution (git: per-task, per-5-tasks, per-phase, none [default]). |
|
|
254
273
|
| `clavix start` | Capture conversational requirements. |
|
|
255
274
|
| `clavix summarize` | Extract mini PRDs and prompts from sessions. |
|
|
256
275
|
| `clavix list` | List sessions or outputs (use `--sessions`, `--outputs`, `--archived`). |
|
|
@@ -16,7 +16,7 @@ Clavix helps Warp developers turn rough ideas into CLEAR, AI-ready prompts and P
|
|
|
16
16
|
- `clavix prompts clear [--executed|--stale|--fast|--deep]` – cleanup executed or old prompts
|
|
17
17
|
- `clavix prd` – answer focused questions to create full/quick PRDs
|
|
18
18
|
- `clavix plan` – transform PRDs or sessions into task lists
|
|
19
|
-
- `clavix implement` –
|
|
19
|
+
- `clavix implement [--commit-strategy=<type>]` – execute tasks (git: per-task, per-5-tasks, per-phase, none [default])
|
|
20
20
|
- `clavix start` – capture requirement conversations in Warp
|
|
21
21
|
- `clavix summarize [session-id]` – extract mini PRDs and optimized prompts
|
|
22
22
|
- `clavix list` – list sessions/outputs (`--sessions`, `--outputs`, `--archived`)
|
|
@@ -9,21 +9,43 @@ You are helping the user implement tasks from their task plan with AI assistance
|
|
|
9
9
|
|
|
10
10
|
## Instructions
|
|
11
11
|
|
|
12
|
-
1. **First-time setup - Run CLI command
|
|
12
|
+
1. **First-time setup - Run CLI command with optional git strategy**:
|
|
13
13
|
|
|
14
14
|
Check if `.clavix-implement-config.json` exists in the PRD output folder.
|
|
15
15
|
|
|
16
16
|
**If config file does NOT exist** (first time running implement):
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
17
|
+
|
|
18
|
+
a. **Check if user wants git auto-commits** (optional, only if tasks.md has >3 phases):
|
|
19
|
+
```
|
|
20
|
+
"I notice this implementation has [X] phases with [Y] tasks total.
|
|
21
|
+
|
|
22
|
+
Would you like me to create git commits automatically as I complete tasks?
|
|
23
|
+
|
|
24
|
+
Options:
|
|
25
|
+
- per-task: Commit after each task (frequent commits, detailed history)
|
|
26
|
+
- per-5-tasks: Commit every 5 tasks (balanced approach)
|
|
27
|
+
- per-phase: Commit when each phase completes (milestone commits)
|
|
28
|
+
- none: Manual git workflow (I won't create commits)
|
|
29
|
+
|
|
30
|
+
Please choose one, or I'll proceed with 'none' (manual commits)."
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
b. **Run the CLI command to initialize**:
|
|
34
|
+
```bash
|
|
35
|
+
# With git strategy (if user specified):
|
|
36
|
+
clavix implement --commit-strategy=per-phase
|
|
37
|
+
|
|
38
|
+
# Or without (defaults to 'none' - manual commits):
|
|
39
|
+
clavix implement
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
c. **This will**:
|
|
43
|
+
- Show current progress
|
|
44
|
+
- Display the next incomplete task
|
|
45
|
+
- Create `.clavix-implement-config.json` file
|
|
46
|
+
- Set git auto-commit strategy (or default to 'none')
|
|
47
|
+
|
|
48
|
+
d. Wait for command to complete, then proceed with step 2
|
|
27
49
|
|
|
28
50
|
**If config file already exists**:
|
|
29
51
|
- Skip to step 2 (implementation loop)
|