vibecodingmachine-cli 2026.3.14-1537 → 2026.6.17-1956
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/bin/auth/auth-compliance.js +7 -7
- package/bin/commands/agent-commands.js +15 -15
- package/bin/commands/auto-commands.js +3 -3
- package/bin/commands/command-aliases.js +13 -4
- package/bin/config/cli-config.js +15 -5
- package/bin/update/update-checker.js +5 -5
- package/bin/vibecodingmachine.js +2 -2
- package/package.json +2 -2
- package/src/commands/agents/add.js +5 -5
- package/src/commands/agents/check.js +19 -19
- package/src/commands/agents/list.js +24 -24
- package/src/commands/agents/remove.js +4 -4
- package/src/commands/agents-check.js +1 -1
- package/src/commands/analyze-file-sizes.js +43 -43
- package/src/commands/auto-direct/auto-provider-manager.js +19 -19
- package/src/commands/auto-direct/auto-start-phases.js +493 -0
- package/src/commands/auto-direct/auto-status-display.js +35 -35
- package/src/commands/auto-direct/auto-utils.js +50 -50
- package/src/commands/auto-direct/cline-installer.js +56 -0
- package/src/commands/auto-direct/code-processor.js +27 -27
- package/src/commands/auto-direct/file-scanner.js +19 -19
- package/src/commands/auto-direct/ide-completion-waiter.js +485 -0
- package/src/commands/auto-direct/ide-fallback-runner.js +226 -0
- package/src/commands/auto-direct/ide-provider-runner.js +103 -0
- package/src/commands/auto-direct/iteration-handlers.js +189 -0
- package/src/commands/auto-direct/iteration-runner.js +485 -0
- package/src/commands/auto-direct/provider-config.js +38 -7
- package/src/commands/auto-direct/provider-manager.js +132 -6
- package/src/commands/auto-direct/requirement-manager.js +169 -104
- package/src/commands/auto-direct/requirement-mover.js +350 -0
- package/src/commands/auto-direct/spec-handlers.js +155 -0
- package/src/commands/auto-direct/spec-ide-runner.js +318 -0
- package/src/commands/auto-direct/spec-processing.js +203 -0
- package/src/commands/auto-direct/status-display.js +9 -9
- package/src/commands/auto-direct/utils.js +83 -1
- package/src/commands/auto-direct-refactored.js +1 -413
- package/src/commands/auto-direct.js +127 -4119
- package/src/commands/auto-execution.js +21 -21
- package/src/commands/auto-status-helpers.js +0 -2
- package/src/commands/auto.js +22 -22
- package/src/commands/check-compliance.js +65 -65
- package/src/commands/computers.js +39 -39
- package/src/commands/continuous-scan.js +19 -19
- package/src/commands/ide.js +4 -4
- package/src/commands/locale.js +7 -7
- package/src/commands/refactor-file.js +59 -59
- package/src/commands/requirements/commands.js +17 -17
- package/src/commands/requirements/default-handlers.js +30 -30
- package/src/commands/requirements/disable.js +3 -3
- package/src/commands/requirements/enable.js +3 -3
- package/src/commands/requirements/utils.js +6 -6
- package/src/commands/requirements-refactored.js +3 -3
- package/src/commands/requirements-remote.js +38 -38
- package/src/commands/requirements.js +3 -3
- package/src/commands/settings.js +111 -0
- package/src/commands/specs/count.js +60 -0
- package/src/commands/specs/disable.js +3 -3
- package/src/commands/specs/enable.js +3 -3
- package/src/commands/status.js +10 -10
- package/src/commands/sync.js +25 -25
- package/src/commands/timeout.js +35 -35
- package/src/trui/TruiInterface.js +2 -2
- package/src/trui/agents/AgentInterface.js +4 -4
- package/src/trui/agents/handlers/CommandHandler.js +4 -4
- package/src/trui/agents/handlers/ContextManager.js +1 -1
- package/src/trui/agents/handlers/DisplayHandler.js +11 -11
- package/src/trui/agents/handlers/HelpHandler.js +1 -1
- package/src/utils/agent-selector.js +6 -6
- package/src/utils/antigravity-installer.js +4 -4
- package/src/utils/asset-cleanup.js +1 -1
- package/src/utils/auth.js +9 -12
- package/src/utils/clarification-actions.js +4 -4
- package/src/utils/cline-js-handler.js +5 -5
- package/src/utils/compliance-check.js +6 -6
- package/src/utils/config.js +12 -12
- package/src/utils/display-formatters-complete.js +2 -2
- package/src/utils/display-formatters-extracted.js +2 -2
- package/src/utils/display-formatters.js +2 -2
- package/src/utils/feedback-handler.js +2 -2
- package/src/utils/first-run.js +7 -7
- package/src/utils/ide-detection.js +1 -1
- package/src/utils/ide-handlers.js +6 -6
- package/src/utils/interactive/clarification-actions.js +3 -3
- package/src/utils/interactive/core-ui.js +7 -7
- package/src/utils/interactive/file-backup.js +6 -6
- package/src/utils/interactive/file-import-export.js +49 -49
- package/src/utils/interactive/file-operations.js +3 -3
- package/src/utils/interactive/file-validation.js +41 -41
- package/src/utils/interactive/interactive-prompts.js +41 -41
- package/src/utils/interactive/requirement-actions.js +5 -5
- package/src/utils/interactive/requirement-crud.js +4 -4
- package/src/utils/interactive/requirements-navigation.js +10 -10
- package/src/utils/interactive-broken.js +6 -6
- package/src/utils/interactive.js +37 -37
- package/src/utils/keyboard-handler.js +4 -4
- package/src/utils/prompt-helper.js +6 -6
- package/src/utils/provider-checker/agent-checker.js +1 -1
- package/src/utils/provider-checker/agent-runner.js +203 -314
- package/src/utils/provider-checker/agents-file-lock.js +134 -0
- package/src/utils/provider-checker/agents-manager.js +224 -36
- package/src/utils/provider-checker/cli-installer.js +28 -28
- package/src/utils/provider-checker/cli-utils.js +2 -2
- package/src/utils/provider-checker/cursor-approval-clicker.js +108 -0
- package/src/utils/provider-checker/format-utils.js +4 -4
- package/src/utils/provider-checker/ide-installer-helper.js +96 -0
- package/src/utils/provider-checker/ide-manager.js +19 -8
- package/src/utils/provider-checker/ide-quota-checker.js +120 -0
- package/src/utils/provider-checker/ide-utils.js +2 -2
- package/src/utils/provider-checker/node-detector.js +4 -4
- package/src/utils/provider-checker/node-utils.js +5 -5
- package/src/utils/provider-checker/opencode-checker.js +107 -73
- package/src/utils/provider-checker/process-utils.js +1 -1
- package/src/utils/provider-checker/provider-validator.js +11 -11
- package/src/utils/provider-checker/quota-checker.js +5 -5
- package/src/utils/provider-checker/quota-detector.js +5 -5
- package/src/utils/provider-checker/requirements-manager.js +6 -6
- package/src/utils/provider-checker/test-requirements.js +1 -1
- package/src/utils/provider-checker/vscode-approval-clicker.js +328 -0
- package/src/utils/provider-checker-new.js +6 -6
- package/src/utils/provider-checker.js +6 -6
- package/src/utils/provider-checkers/ide-manager.js +13 -13
- package/src/utils/provider-checkers/node-executable-finder.js +4 -4
- package/src/utils/provider-checkers/provider-checker-core.js +5 -5
- package/src/utils/provider-checkers/provider-checker-main.js +17 -17
- package/src/utils/provider-registry.js +5 -6
- package/src/utils/provider-utils.js +12 -12
- package/src/utils/quota-detectors.js +32 -32
- package/src/utils/requirement-action-handlers.js +12 -12
- package/src/utils/requirement-actions/requirement-operations.js +3 -3
- package/src/utils/requirement-actions.js +1 -1
- package/src/utils/requirement-file-operations.js +5 -5
- package/src/utils/requirement-helpers.js +1 -1
- package/src/utils/requirement-management.js +5 -5
- package/src/utils/requirement-navigation.js +2 -2
- package/src/utils/requirement-organization.js +3 -3
- package/src/utils/rui-trui-adapter.js +14 -14
- package/src/utils/simple-trui.js +3 -3
- package/src/utils/status-helpers-extracted.js +3 -3
- package/src/utils/trui-clarifications.js +11 -11
- package/src/utils/trui-debug.js +3 -2
- package/src/utils/trui-devin.js +217 -0
- package/src/utils/trui-feedback.js +7 -7
- package/src/utils/trui-kiro-integration.js +34 -34
- package/src/utils/trui-main-handlers.js +20 -21
- package/src/utils/trui-main-menu.js +19 -19
- package/src/utils/trui-nav-agents.js +59 -8
- package/src/utils/trui-nav-requirements.js +3 -3
- package/src/utils/trui-nav-settings.js +10 -10
- package/src/utils/trui-nav-specifications.js +1 -1
- package/src/utils/trui-navigation-backup.js +11 -11
- package/src/utils/trui-navigation.js +9 -9
- package/src/utils/trui-provider-health.js +25 -25
- package/src/utils/trui-provider-manager.js +28 -28
- package/src/utils/trui-quick-menu.js +2 -2
- package/src/utils/trui-req-actions-backup.js +21 -21
- package/src/utils/trui-req-actions.js +20 -20
- package/src/utils/trui-req-editor.js +10 -10
- package/src/utils/trui-req-file-ops.js +3 -3
- package/src/utils/trui-req-tree.js +7 -7
- package/src/utils/trui-windsurf.js +103 -103
- package/src/utils/user-tracking.js +15 -15
- package/src/utils/trui-req-tree-old.js +0 -719
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Auto Mode Status Display
|
|
3
|
-
*
|
|
3
|
+
*
|
|
4
4
|
* Handles status display and UI components for auto mode
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
7
|
const chalk = require('chalk');
|
|
8
|
-
const { getStages, DEFAULT_STAGES } = require('
|
|
8
|
+
const { getStages, DEFAULT_STAGES } = require('../../utils/config');
|
|
9
9
|
const { stripAnsi, padToVisualWidth } = require('./auto-utils');
|
|
10
10
|
|
|
11
11
|
// Global status mode tracking
|
|
@@ -16,36 +16,36 @@ let currentStatusMode = 'active';
|
|
|
16
16
|
*/
|
|
17
17
|
function printStatusCard(currentTitle, currentStatus, mode = 'active') {
|
|
18
18
|
currentStatusMode = mode; // Update global mode tracking
|
|
19
|
-
|
|
19
|
+
|
|
20
20
|
const stages = configuredStages || DEFAULT_STAGES;
|
|
21
21
|
const currentStageIndex = stages.indexOf(currentStatus);
|
|
22
|
-
|
|
22
|
+
|
|
23
23
|
// Build status card
|
|
24
24
|
const width = 60;
|
|
25
25
|
const border = '─'.repeat(width);
|
|
26
|
-
|
|
26
|
+
|
|
27
27
|
console.log(chalk.cyan(`┌─ ${border} ─┐`));
|
|
28
28
|
console.log(chalk.cyan('│') + padToVisualWidth(` 🤖 Auto Mode Status`, width - 4) + chalk.cyan('│'));
|
|
29
29
|
console.log(chalk.cyan(`├─ ${border} ─┤`));
|
|
30
|
-
|
|
30
|
+
|
|
31
31
|
// Current requirement
|
|
32
32
|
if (currentTitle) {
|
|
33
33
|
const titleLine = ` 📋 ${currentTitle}`;
|
|
34
34
|
console.log(chalk.cyan('│') + padToVisualWidth(titleLine, width - 4) + chalk.cyan('│'));
|
|
35
35
|
}
|
|
36
|
-
|
|
36
|
+
|
|
37
37
|
// Current stage
|
|
38
38
|
const statusIcon = getStatusIcon(currentStatus, mode);
|
|
39
39
|
const statusLine = ` ${statusIcon} ${currentStatus}`;
|
|
40
40
|
console.log(chalk.cyan('│') + padToVisualWidth(statusLine, width - 4) + chalk.cyan('│'));
|
|
41
|
-
|
|
41
|
+
|
|
42
42
|
// Progress bar
|
|
43
43
|
if (currentStageIndex >= 0) {
|
|
44
44
|
const progress = ((currentStageIndex + 1) / stages.length) * 100;
|
|
45
45
|
const progressBar = createProgressBar(progress, width - 8);
|
|
46
46
|
console.log(chalk.cyan('│') + padToVisualWidth(` ${progressBar}`, width - 4) + chalk.cyan('│'));
|
|
47
47
|
}
|
|
48
|
-
|
|
48
|
+
|
|
49
49
|
console.log(chalk.cyan(`└─ ${border} ─┘`));
|
|
50
50
|
}
|
|
51
51
|
|
|
@@ -61,15 +61,15 @@ function getStatusIcon(status, mode) {
|
|
|
61
61
|
'VERIFY': '✅',
|
|
62
62
|
'DONE': '🎉'
|
|
63
63
|
};
|
|
64
|
-
|
|
64
|
+
|
|
65
65
|
const baseIcon = statusIcons[status] || '❓';
|
|
66
|
-
|
|
66
|
+
|
|
67
67
|
if (mode === 'waiting') {
|
|
68
68
|
return '⏳';
|
|
69
69
|
} else if (mode === 'stopped') {
|
|
70
70
|
return '⏹️';
|
|
71
71
|
}
|
|
72
|
-
|
|
72
|
+
|
|
73
73
|
return baseIcon;
|
|
74
74
|
}
|
|
75
75
|
|
|
@@ -79,10 +79,10 @@ function getStatusIcon(status, mode) {
|
|
|
79
79
|
function createProgressBar(percentage, width) {
|
|
80
80
|
const filled = Math.round((percentage / 100) * width);
|
|
81
81
|
const empty = width - filled;
|
|
82
|
-
|
|
82
|
+
|
|
83
83
|
const filledBar = '█'.repeat(filled);
|
|
84
84
|
const emptyBar = '░'.repeat(empty);
|
|
85
|
-
|
|
85
|
+
|
|
86
86
|
return chalk.green(filledBar) + chalk.gray(emptyBar) + ` ${Math.round(percentage)}%`;
|
|
87
87
|
}
|
|
88
88
|
|
|
@@ -92,17 +92,17 @@ function createProgressBar(percentage, width) {
|
|
|
92
92
|
function printWorkflowStages(currentStatus) {
|
|
93
93
|
const stages = configuredStages || DEFAULT_STAGES;
|
|
94
94
|
const currentIndex = stages.indexOf(currentStatus);
|
|
95
|
-
|
|
95
|
+
|
|
96
96
|
console.log(chalk.blue('\n🔄 Workflow Stages:'));
|
|
97
|
-
|
|
97
|
+
|
|
98
98
|
stages.forEach((stage, index) => {
|
|
99
99
|
const isCurrent = index === currentIndex;
|
|
100
100
|
const isCompleted = index < currentIndex;
|
|
101
101
|
const isPending = index > currentIndex;
|
|
102
|
-
|
|
102
|
+
|
|
103
103
|
let icon = '⭕';
|
|
104
104
|
let color = chalk.gray;
|
|
105
|
-
|
|
105
|
+
|
|
106
106
|
if (isCurrent) {
|
|
107
107
|
icon = '🔵';
|
|
108
108
|
color = chalk.blue;
|
|
@@ -113,11 +113,11 @@ function printWorkflowStages(currentStatus) {
|
|
|
113
113
|
icon = '⭕';
|
|
114
114
|
color = chalk.gray;
|
|
115
115
|
}
|
|
116
|
-
|
|
116
|
+
|
|
117
117
|
const stageText = `${icon} ${stage}`;
|
|
118
118
|
console.log(color(` ${stageText}`));
|
|
119
119
|
});
|
|
120
|
-
|
|
120
|
+
|
|
121
121
|
console.log();
|
|
122
122
|
}
|
|
123
123
|
|
|
@@ -127,19 +127,19 @@ function printWorkflowStages(currentStatus) {
|
|
|
127
127
|
function printProviderInfo(providerName, providerConfig) {
|
|
128
128
|
console.log(chalk.blue('\n🔌 Provider Information:'));
|
|
129
129
|
console.log(chalk.cyan(` Provider: ${providerName}`));
|
|
130
|
-
|
|
130
|
+
|
|
131
131
|
if (providerConfig.model) {
|
|
132
132
|
console.log(chalk.cyan(` Model: ${providerConfig.model}`));
|
|
133
133
|
}
|
|
134
|
-
|
|
134
|
+
|
|
135
135
|
if (providerConfig.baseUrl) {
|
|
136
136
|
console.log(chalk.cyan(` Base URL: ${providerConfig.baseUrl}`));
|
|
137
137
|
}
|
|
138
|
-
|
|
138
|
+
|
|
139
139
|
if (providerConfig.region) {
|
|
140
140
|
console.log(chalk.cyan(` Region: ${providerConfig.region}`));
|
|
141
141
|
}
|
|
142
|
-
|
|
142
|
+
|
|
143
143
|
console.log();
|
|
144
144
|
}
|
|
145
145
|
|
|
@@ -159,11 +159,11 @@ function printRateLimitWarning(providerName, waitTime) {
|
|
|
159
159
|
function printError(error, context = '') {
|
|
160
160
|
console.log(chalk.red(`\n❌ Error${context ? ` (${context})` : ''}:`));
|
|
161
161
|
console.log(chalk.red(` ${error.message}`));
|
|
162
|
-
|
|
162
|
+
|
|
163
163
|
if (error.stack && process.env.DEBUG) {
|
|
164
164
|
console.log(chalk.gray(` Stack trace:\n${error.stack}`));
|
|
165
165
|
}
|
|
166
|
-
|
|
166
|
+
|
|
167
167
|
console.log();
|
|
168
168
|
}
|
|
169
169
|
|
|
@@ -206,7 +206,7 @@ function printDebug(message) {
|
|
|
206
206
|
function createSpinner(text) {
|
|
207
207
|
const frames = ['⠋', '⠙', '⠹', '⠸', '⠼', '⠴', '⠦', '⠧', '⠇', '⠏'];
|
|
208
208
|
let index = 0;
|
|
209
|
-
|
|
209
|
+
|
|
210
210
|
return {
|
|
211
211
|
start: () => {
|
|
212
212
|
process.stdout.write(`\r${frames[index]} ${text}`);
|
|
@@ -225,19 +225,19 @@ function printFileChangeSummary(changes) {
|
|
|
225
225
|
if (!changes || changes.length === 0) {
|
|
226
226
|
return;
|
|
227
227
|
}
|
|
228
|
-
|
|
228
|
+
|
|
229
229
|
console.log(chalk.blue('\n📁 File Changes:'));
|
|
230
|
-
|
|
230
|
+
|
|
231
231
|
changes.forEach(change => {
|
|
232
232
|
const icon = getFileChangeIcon(change.type);
|
|
233
233
|
const color = getFileChangeColor(change.type);
|
|
234
234
|
console.log(color(` ${icon} ${change.path}`));
|
|
235
|
-
|
|
235
|
+
|
|
236
236
|
if (change.type === 'modify' && change.linesAdded) {
|
|
237
237
|
console.log(chalk.gray(` +${change.linesAdded} -${change.linesRemoved || 0} lines`));
|
|
238
238
|
}
|
|
239
239
|
});
|
|
240
|
-
|
|
240
|
+
|
|
241
241
|
console.log();
|
|
242
242
|
}
|
|
243
243
|
|
|
@@ -252,7 +252,7 @@ function getFileChangeIcon(type) {
|
|
|
252
252
|
'move': '📂',
|
|
253
253
|
'copy': '📋'
|
|
254
254
|
};
|
|
255
|
-
|
|
255
|
+
|
|
256
256
|
return icons[type] || '📄';
|
|
257
257
|
}
|
|
258
258
|
|
|
@@ -267,7 +267,7 @@ function getFileChangeColor(type) {
|
|
|
267
267
|
'move': chalk.blue,
|
|
268
268
|
'copy': chalk.cyan
|
|
269
269
|
};
|
|
270
|
-
|
|
270
|
+
|
|
271
271
|
return colors[type] || chalk.gray;
|
|
272
272
|
}
|
|
273
273
|
|
|
@@ -277,7 +277,7 @@ function getFileChangeColor(type) {
|
|
|
277
277
|
function printIterationSummary(iteration, total, title, status) {
|
|
278
278
|
const percentage = Math.round((iteration / total) * 100);
|
|
279
279
|
const icon = status === 'completed' ? '✅' : '🔄';
|
|
280
|
-
|
|
280
|
+
|
|
281
281
|
console.log(chalk.blue(`${icon} Iteration ${iteration}/${total} (${percentage}%) - ${title}`));
|
|
282
282
|
}
|
|
283
283
|
|
|
@@ -289,7 +289,7 @@ function printTiming(startTime, endTime) {
|
|
|
289
289
|
const seconds = Math.round(duration / 1000);
|
|
290
290
|
const minutes = Math.floor(seconds / 60);
|
|
291
291
|
const remainingSeconds = seconds % 60;
|
|
292
|
-
|
|
292
|
+
|
|
293
293
|
if (minutes > 0) {
|
|
294
294
|
console.log(chalk.gray(`⏱️ Duration: ${minutes}m ${remainingSeconds}s`));
|
|
295
295
|
} else {
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Auto Mode Utilities
|
|
3
|
-
*
|
|
3
|
+
*
|
|
4
4
|
* Shared utility functions for auto mode operations
|
|
5
5
|
*/
|
|
6
6
|
|
|
@@ -33,7 +33,7 @@ function getLogTimestamp(date = new Date()) {
|
|
|
33
33
|
minute: '2-digit',
|
|
34
34
|
timeZoneName: 'short'
|
|
35
35
|
});
|
|
36
|
-
|
|
36
|
+
|
|
37
37
|
return `${datePart} ${timePart}`;
|
|
38
38
|
}
|
|
39
39
|
|
|
@@ -49,7 +49,7 @@ function translateStage(stage) {
|
|
|
49
49
|
'VERIFY': 'workflow.stage.verify',
|
|
50
50
|
'DONE': 'workflow.stage.done'
|
|
51
51
|
};
|
|
52
|
-
|
|
52
|
+
|
|
53
53
|
return stageMap[stage] || stage;
|
|
54
54
|
}
|
|
55
55
|
|
|
@@ -134,11 +134,11 @@ async function updateRequirementsStatus(repoPath, status) {
|
|
|
134
134
|
}
|
|
135
135
|
|
|
136
136
|
let content = await fs.readFile(reqPath, 'utf8');
|
|
137
|
-
|
|
137
|
+
|
|
138
138
|
// Find and update status line
|
|
139
139
|
const statusLineRegex = /^## Current Status:.*$/m;
|
|
140
140
|
const newStatusLine = `## Current Status: ${status}`;
|
|
141
|
-
|
|
141
|
+
|
|
142
142
|
if (statusLineRegex.test(content)) {
|
|
143
143
|
content = content.replace(statusLineRegex, newStatusLine);
|
|
144
144
|
} else {
|
|
@@ -147,7 +147,7 @@ async function updateRequirementsStatus(repoPath, status) {
|
|
|
147
147
|
lines.splice(1, 0, newStatusLine);
|
|
148
148
|
content = lines.join('\n');
|
|
149
149
|
}
|
|
150
|
-
|
|
150
|
+
|
|
151
151
|
await fs.writeFile(reqPath, content, 'utf8');
|
|
152
152
|
} catch (error) {
|
|
153
153
|
console.error('Error updating requirements status:', error.message);
|
|
@@ -166,29 +166,29 @@ async function getCurrentRequirement(repoPath) {
|
|
|
166
166
|
|
|
167
167
|
const content = await fs.readFile(reqPath, 'utf8');
|
|
168
168
|
const lines = content.split('\n');
|
|
169
|
-
|
|
169
|
+
|
|
170
170
|
// Look for current status section
|
|
171
171
|
let currentSection = null;
|
|
172
172
|
let currentRequirement = null;
|
|
173
|
-
|
|
173
|
+
|
|
174
174
|
for (let i = 0; i < lines.length; i++) {
|
|
175
175
|
const line = lines[i].trim();
|
|
176
|
-
|
|
176
|
+
|
|
177
177
|
if (line.startsWith('## Current Status:')) {
|
|
178
178
|
currentSection = 'current';
|
|
179
179
|
continue;
|
|
180
180
|
}
|
|
181
|
-
|
|
181
|
+
|
|
182
182
|
if (line.startsWith('##') && currentSection === 'current') {
|
|
183
183
|
break;
|
|
184
184
|
}
|
|
185
|
-
|
|
185
|
+
|
|
186
186
|
if (currentSection === 'current' && line.startsWith('###')) {
|
|
187
187
|
currentRequirement = line.replace(/^###\s*/, '').trim();
|
|
188
188
|
break;
|
|
189
189
|
}
|
|
190
190
|
}
|
|
191
|
-
|
|
191
|
+
|
|
192
192
|
return currentRequirement;
|
|
193
193
|
} catch (error) {
|
|
194
194
|
console.error('Error getting current requirement:', error.message);
|
|
@@ -208,27 +208,27 @@ async function countTodoRequirements(repoPath) {
|
|
|
208
208
|
|
|
209
209
|
const content = await fs.readFile(reqPath, 'utf8');
|
|
210
210
|
const lines = content.split('\n');
|
|
211
|
-
|
|
211
|
+
|
|
212
212
|
let inTodoSection = false;
|
|
213
213
|
let count = 0;
|
|
214
|
-
|
|
214
|
+
|
|
215
215
|
for (const line of lines) {
|
|
216
216
|
const trimmed = line.trim();
|
|
217
|
-
|
|
217
|
+
|
|
218
218
|
if (trimmed === '## TODO') {
|
|
219
219
|
inTodoSection = true;
|
|
220
220
|
continue;
|
|
221
221
|
}
|
|
222
|
-
|
|
222
|
+
|
|
223
223
|
if (trimmed.startsWith('##') && inTodoSection) {
|
|
224
224
|
break;
|
|
225
225
|
}
|
|
226
|
-
|
|
226
|
+
|
|
227
227
|
if (inTodoSection && trimmed.startsWith('###')) {
|
|
228
228
|
count++;
|
|
229
229
|
}
|
|
230
230
|
}
|
|
231
|
-
|
|
231
|
+
|
|
232
232
|
return count;
|
|
233
233
|
} catch (error) {
|
|
234
234
|
console.error('Error counting TODO requirements:', error.message);
|
|
@@ -248,31 +248,31 @@ async function moveRequirementToVerify(repoPath, requirementText) {
|
|
|
248
248
|
|
|
249
249
|
const content = await fs.readFile(reqPath, 'utf8');
|
|
250
250
|
const lines = content.split('\n');
|
|
251
|
-
|
|
251
|
+
|
|
252
252
|
// Find the requirement by its title
|
|
253
253
|
const normalizedRequirement = requirementText.trim();
|
|
254
254
|
const snippet = normalizedRequirement.substring(0, 80);
|
|
255
255
|
let requirementStartIndex = -1;
|
|
256
256
|
let requirementEndIndex = -1;
|
|
257
257
|
let inTodoSection = false;
|
|
258
|
-
|
|
258
|
+
|
|
259
259
|
for (let i = 0; i < lines.length; i++) {
|
|
260
260
|
const line = lines[i];
|
|
261
|
-
|
|
261
|
+
|
|
262
262
|
if (line.trim() === '## TODO') {
|
|
263
263
|
inTodoSection = true;
|
|
264
264
|
continue;
|
|
265
265
|
}
|
|
266
|
-
|
|
266
|
+
|
|
267
267
|
if (line.trim().startsWith('##') && inTodoSection) {
|
|
268
268
|
break;
|
|
269
269
|
}
|
|
270
|
-
|
|
270
|
+
|
|
271
271
|
if (inTodoSection && line.trim().startsWith('###')) {
|
|
272
272
|
const title = line.replace(/^###\s*/, '').trim();
|
|
273
273
|
if (title.includes(snippet) || title === normalizedRequirement) {
|
|
274
274
|
requirementStartIndex = i;
|
|
275
|
-
|
|
275
|
+
|
|
276
276
|
// Find end of requirement
|
|
277
277
|
for (let j = i + 1; j < lines.length; j++) {
|
|
278
278
|
if (lines[j].trim().startsWith('###') || lines[j].trim().startsWith('##')) {
|
|
@@ -280,27 +280,27 @@ async function moveRequirementToVerify(repoPath, requirementText) {
|
|
|
280
280
|
break;
|
|
281
281
|
}
|
|
282
282
|
}
|
|
283
|
-
|
|
283
|
+
|
|
284
284
|
if (requirementEndIndex === -1) {
|
|
285
285
|
requirementEndIndex = lines.length;
|
|
286
286
|
}
|
|
287
|
-
|
|
287
|
+
|
|
288
288
|
break;
|
|
289
289
|
}
|
|
290
290
|
}
|
|
291
291
|
}
|
|
292
|
-
|
|
292
|
+
|
|
293
293
|
if (requirementStartIndex === -1) {
|
|
294
294
|
console.warn('Requirement not found in TODO section:', requirementText);
|
|
295
295
|
return;
|
|
296
296
|
}
|
|
297
|
-
|
|
297
|
+
|
|
298
298
|
// Extract the requirement block
|
|
299
299
|
const requirementBlock = lines.slice(requirementStartIndex, requirementEndIndex);
|
|
300
|
-
|
|
300
|
+
|
|
301
301
|
// Remove from TODO
|
|
302
302
|
lines.splice(requirementStartIndex, requirementEndIndex - requirementStartIndex);
|
|
303
|
-
|
|
303
|
+
|
|
304
304
|
// Find TO VERIFY BY HUMAN section and add requirement
|
|
305
305
|
let verifyIndex = -1;
|
|
306
306
|
for (let i = 0; i < lines.length; i++) {
|
|
@@ -309,19 +309,19 @@ async function moveRequirementToVerify(repoPath, requirementText) {
|
|
|
309
309
|
break;
|
|
310
310
|
}
|
|
311
311
|
}
|
|
312
|
-
|
|
312
|
+
|
|
313
313
|
if (verifyIndex === -1) {
|
|
314
314
|
// Create section if it doesn't exist
|
|
315
315
|
lines.push('## TO VERIFY BY HUMAN');
|
|
316
316
|
verifyIndex = lines.length;
|
|
317
317
|
}
|
|
318
|
-
|
|
318
|
+
|
|
319
319
|
// Insert requirement
|
|
320
320
|
lines.splice(verifyIndex, 0, ...requirementBlock);
|
|
321
|
-
|
|
321
|
+
|
|
322
322
|
// Write back to file
|
|
323
323
|
await fs.writeFile(reqPath, lines.join('\n'), 'utf8');
|
|
324
|
-
|
|
324
|
+
|
|
325
325
|
console.log(chalk.green(`Moved requirement to verify: ${requirementText}`));
|
|
326
326
|
} catch (error) {
|
|
327
327
|
console.error('Error moving requirement to verify:', error.message);
|
|
@@ -340,31 +340,31 @@ async function moveRequirementToRecycle(repoPath, requirementText) {
|
|
|
340
340
|
|
|
341
341
|
const content = await fs.readFile(reqPath, 'utf8');
|
|
342
342
|
const lines = content.split('\n');
|
|
343
|
-
|
|
343
|
+
|
|
344
344
|
// Find and remove requirement from current section
|
|
345
345
|
const normalizedRequirement = requirementText.trim();
|
|
346
346
|
const snippet = normalizedRequirement.substring(0, 80);
|
|
347
347
|
let requirementStartIndex = -1;
|
|
348
348
|
let requirementEndIndex = -1;
|
|
349
349
|
let inCurrentSection = false;
|
|
350
|
-
|
|
350
|
+
|
|
351
351
|
for (let i = 0; i < lines.length; i++) {
|
|
352
352
|
const line = lines[i];
|
|
353
|
-
|
|
353
|
+
|
|
354
354
|
if (line.trim().startsWith('## Current Status:')) {
|
|
355
355
|
inCurrentSection = true;
|
|
356
356
|
continue;
|
|
357
357
|
}
|
|
358
|
-
|
|
358
|
+
|
|
359
359
|
if (line.trim().startsWith('##') && inCurrentSection) {
|
|
360
360
|
break;
|
|
361
361
|
}
|
|
362
|
-
|
|
362
|
+
|
|
363
363
|
if (inCurrentSection && line.trim().startsWith('###')) {
|
|
364
364
|
const title = line.replace(/^###\s*/, '').trim();
|
|
365
365
|
if (title.includes(snippet) || title === normalizedRequirement) {
|
|
366
366
|
requirementStartIndex = i;
|
|
367
|
-
|
|
367
|
+
|
|
368
368
|
// Find end of requirement
|
|
369
369
|
for (let j = i + 1; j < lines.length; j++) {
|
|
370
370
|
if (lines[j].trim().startsWith('###') || lines[j].trim().startsWith('##')) {
|
|
@@ -372,27 +372,27 @@ async function moveRequirementToRecycle(repoPath, requirementText) {
|
|
|
372
372
|
break;
|
|
373
373
|
}
|
|
374
374
|
}
|
|
375
|
-
|
|
375
|
+
|
|
376
376
|
if (requirementEndIndex === -1) {
|
|
377
377
|
requirementEndIndex = lines.length;
|
|
378
378
|
}
|
|
379
|
-
|
|
379
|
+
|
|
380
380
|
break;
|
|
381
381
|
}
|
|
382
382
|
}
|
|
383
383
|
}
|
|
384
|
-
|
|
384
|
+
|
|
385
385
|
if (requirementStartIndex === -1) {
|
|
386
386
|
console.warn('Requirement not found in current section:', requirementText);
|
|
387
387
|
return;
|
|
388
388
|
}
|
|
389
|
-
|
|
389
|
+
|
|
390
390
|
// Extract the requirement block
|
|
391
391
|
const requirementBlock = lines.slice(requirementStartIndex, requirementEndIndex);
|
|
392
|
-
|
|
392
|
+
|
|
393
393
|
// Remove from current section
|
|
394
394
|
lines.splice(requirementStartIndex, requirementEndIndex - requirementStartIndex);
|
|
395
|
-
|
|
395
|
+
|
|
396
396
|
// Find RECYCLED section and add requirement
|
|
397
397
|
let recycleIndex = -1;
|
|
398
398
|
for (let i = 0; i < lines.length; i++) {
|
|
@@ -401,20 +401,20 @@ async function moveRequirementToRecycle(repoPath, requirementText) {
|
|
|
401
401
|
break;
|
|
402
402
|
}
|
|
403
403
|
}
|
|
404
|
-
|
|
404
|
+
|
|
405
405
|
if (recycleIndex === -1) {
|
|
406
406
|
// Create section if it doesn't exist
|
|
407
407
|
lines.push('## RECYCLED');
|
|
408
408
|
recycleIndex = lines.length;
|
|
409
409
|
}
|
|
410
|
-
|
|
410
|
+
|
|
411
411
|
// Add timestamp and requirement
|
|
412
412
|
const timestamp = new Date().toISOString();
|
|
413
413
|
lines.splice(recycleIndex, 0, `### ${requirementText}`, `*Recycled: ${timestamp}*`);
|
|
414
|
-
|
|
414
|
+
|
|
415
415
|
// Write back to file
|
|
416
416
|
await fs.writeFile(reqPath, lines.join('\n'), 'utf8');
|
|
417
|
-
|
|
417
|
+
|
|
418
418
|
console.log(chalk.yellow(`Recycled requirement: ${requirementText}`));
|
|
419
419
|
} catch (error) {
|
|
420
420
|
console.error('Error recycling requirement:', error.message);
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Cline Installer - Auto-installation of Cline CLI
|
|
3
|
+
*
|
|
4
|
+
* Extracted from iteration-handlers.js for constitutional compliance (<555 lines per file)
|
|
5
|
+
* Handles auto-installation of Cline CLI when not available on the system.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
const chalk = require('chalk');
|
|
9
|
+
const { DirectLLMManager } = require('vibecodingmachine-core');
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* Auto-install Cline CLI if not available
|
|
13
|
+
* @param {boolean} forceInstall - Force installation even if already available
|
|
14
|
+
* @returns {Promise<boolean>} - Returns true if Cline CLI is available after installation
|
|
15
|
+
*/
|
|
16
|
+
async function ensureClineInstalled(forceInstall = false) {
|
|
17
|
+
const llm = new DirectLLMManager();
|
|
18
|
+
|
|
19
|
+
// Check if already available
|
|
20
|
+
if (!forceInstall && await llm.isClineAvailable()) {
|
|
21
|
+
return true;
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
const ora = require('ora');
|
|
25
|
+
const { execSync } = require('child_process');
|
|
26
|
+
|
|
27
|
+
const spinner = ora('Installing Cline CLI...').start();
|
|
28
|
+
|
|
29
|
+
try {
|
|
30
|
+
// Install Cline CLI globally
|
|
31
|
+
execSync('npm install -g cline', { stdio: 'pipe', encoding: 'utf8' });
|
|
32
|
+
|
|
33
|
+
// Verify installation
|
|
34
|
+
const isAvailable = await llm.isClineAvailable();
|
|
35
|
+
|
|
36
|
+
if (isAvailable) {
|
|
37
|
+
spinner.succeed('Cline CLI installed successfully');
|
|
38
|
+
console.log(chalk.green('✓ Cline CLI is now ready to use'));
|
|
39
|
+
return true;
|
|
40
|
+
} else {
|
|
41
|
+
spinner.fail('Cline CLI installation failed');
|
|
42
|
+
console.log(chalk.yellow('⚠ Installation completed but Cline CLI not found in PATH'));
|
|
43
|
+
console.log(chalk.gray(' You may need to restart your terminal or manually add npm global bin to PATH'));
|
|
44
|
+
return false;
|
|
45
|
+
}
|
|
46
|
+
} catch (error) {
|
|
47
|
+
spinner.fail('Cline CLI installation failed');
|
|
48
|
+
console.log(chalk.red('✗ Failed to install Cline CLI:'), error.message);
|
|
49
|
+
console.log(chalk.yellow(' You can manually install with: npm install -g cline'));
|
|
50
|
+
return false;
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
module.exports = {
|
|
55
|
+
ensureClineInstalled
|
|
56
|
+
};
|