vibecodingmachine-core 2026.2.20-438 → 2026.2.26-1739
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 +240 -0
- package/package.json +10 -2
- package/src/agents/Agent.js +300 -0
- package/src/agents/AgentAdditionService.js +311 -0
- package/src/agents/AgentCheckService.js +690 -0
- package/src/agents/AgentInstallationService.js +140 -0
- package/src/agents/AgentSetupService.js +467 -0
- package/src/agents/AgentStatus.js +183 -0
- package/src/agents/AgentVerificationService.js +634 -0
- package/src/agents/ConfigurationSchemaValidator.js +543 -0
- package/src/agents/EnvironmentConfigurationManager.js +602 -0
- package/src/agents/InstallationErrorHandler.js +372 -0
- package/src/agents/InstallationLog.js +363 -0
- package/src/agents/InstallationMethod.js +510 -0
- package/src/agents/InstallationOrchestrator.js +352 -0
- package/src/agents/InstallationProgressReporter.js +372 -0
- package/src/agents/InstallationRetryManager.js +322 -0
- package/src/agents/InstallationType.js +254 -0
- package/src/agents/OperationTypes.js +310 -0
- package/src/agents/PerformanceMetricsCollector.js +493 -0
- package/src/agents/SecurityValidationService.js +534 -0
- package/src/agents/VerificationTest.js +354 -0
- package/src/agents/VerificationType.js +226 -0
- package/src/agents/WindowsPermissionHandler.js +518 -0
- package/src/agents/config/AgentConfigManager.js +393 -0
- package/src/agents/config/AgentDefaultsRegistry.js +373 -0
- package/src/agents/config/ConfigValidator.js +281 -0
- package/src/agents/discovery/AgentDiscoveryService.js +707 -0
- package/src/agents/logging/AgentLogger.js +511 -0
- package/src/agents/status/AgentStatusManager.js +481 -0
- package/src/agents/storage/FileManager.js +454 -0
- package/src/agents/verification/AgentCommunicationTester.js +474 -0
- package/src/agents/verification/BaseVerifier.js +430 -0
- package/src/agents/verification/CommandVerifier.js +480 -0
- package/src/agents/verification/FileOperationVerifier.js +453 -0
- package/src/agents/verification/ResultAnalyzer.js +707 -0
- package/src/agents/verification/TestRequirementManager.js +495 -0
- package/src/agents/verification/VerificationRunner.js +433 -0
- package/src/agents/windows/BaseWindowsInstaller.js +441 -0
- package/src/agents/windows/ChocolateyInstaller.js +509 -0
- package/src/agents/windows/DirectInstaller.js +443 -0
- package/src/agents/windows/InstallerFactory.js +391 -0
- package/src/agents/windows/NpmInstaller.js +505 -0
- package/src/agents/windows/PowerShellInstaller.js +458 -0
- package/src/agents/windows/WinGetInstaller.js +390 -0
- package/src/analysis/analysis-reporter.js +132 -0
- package/src/analysis/boundary-detector.js +712 -0
- package/src/analysis/categorizer.js +340 -0
- package/src/analysis/codebase-scanner.js +384 -0
- package/src/analysis/line-counter.js +513 -0
- package/src/analysis/priority-calculator.js +679 -0
- package/src/analysis/report/analysis-report.js +250 -0
- package/src/analysis/report/package-analyzer.js +278 -0
- package/src/analysis/report/recommendation-generator.js +382 -0
- package/src/analysis/report/statistics-generator.js +515 -0
- package/src/analysis/reports/analysis-report-model.js +101 -0
- package/src/analysis/reports/recommendation-generator.js +283 -0
- package/src/analysis/reports/report-generators.js +191 -0
- package/src/analysis/reports/statistics-calculator.js +231 -0
- package/src/analysis/reports/trend-analyzer.js +219 -0
- package/src/analysis/strategy-generator.js +814 -0
- package/src/auto-mode/AutoModeBusinessLogic.js +836 -0
- package/src/config/refactoring-config.js +307 -0
- package/src/health-tracking/json-storage.js +38 -2
- package/src/ide-integration/applescript-manager-core.js +233 -0
- package/src/ide-integration/applescript-manager.cjs +357 -28
- package/src/ide-integration/applescript-manager.js +89 -3599
- package/src/ide-integration/cdp-manager.js +306 -0
- package/src/ide-integration/claude-code-cli-manager.cjs +1 -1
- package/src/ide-integration/continuation-handler.js +337 -0
- package/src/ide-integration/ide-status-checker.js +292 -0
- package/src/ide-integration/macos-ide-manager.js +627 -0
- package/src/ide-integration/macos-text-sender.js +528 -0
- package/src/ide-integration/response-reader.js +548 -0
- package/src/ide-integration/windows-automation-manager.js +121 -0
- package/src/ide-integration/windows-ide-manager.js +373 -0
- package/src/index.cjs +25 -3
- package/src/index.js +15 -1
- package/src/llm/direct-llm-manager.cjs +90 -2
- package/src/models/compliance-report.js +538 -0
- package/src/models/file-analysis.js +681 -0
- package/src/models/refactoring-plan.js +770 -0
- package/src/monitoring/alert-system.js +834 -0
- package/src/monitoring/compliance-progress-tracker.js +437 -0
- package/src/monitoring/continuous-scan-notifications.js +661 -0
- package/src/monitoring/continuous-scanner.js +279 -0
- package/src/monitoring/file-monitor/file-analyzer.js +262 -0
- package/src/monitoring/file-monitor/file-monitor.js +237 -0
- package/src/monitoring/file-monitor/watcher.js +194 -0
- package/src/monitoring/file-monitor.js +17 -0
- package/src/monitoring/notification-manager.js +437 -0
- package/src/monitoring/scanner-core.js +368 -0
- package/src/monitoring/scanner-events.js +214 -0
- package/src/monitoring/violation-notification-system.js +515 -0
- package/src/refactoring/boundaries/cohesion-analyzer.js +316 -0
- package/src/refactoring/boundaries/extraction-result.js +285 -0
- package/src/refactoring/boundaries/extraction-strategies.js +392 -0
- package/src/refactoring/boundaries/module-boundary.js +209 -0
- package/src/refactoring/boundary/boundary-detector.js +741 -0
- package/src/refactoring/boundary/boundary-types.js +405 -0
- package/src/refactoring/boundary/extraction-strategies.js +554 -0
- package/src/refactoring/boundary-extraction-result.js +77 -0
- package/src/refactoring/boundary-extraction-strategies.js +330 -0
- package/src/refactoring/boundary-extractor.js +384 -0
- package/src/refactoring/boundary-types.js +46 -0
- package/src/refactoring/circular/circular-dependency.js +88 -0
- package/src/refactoring/circular/cycle-detection.js +147 -0
- package/src/refactoring/circular/dependency-node.js +82 -0
- package/src/refactoring/circular/dependency-result.js +107 -0
- package/src/refactoring/circular/dependency-types.js +58 -0
- package/src/refactoring/circular/graph-builder.js +213 -0
- package/src/refactoring/circular/resolution-strategy.js +72 -0
- package/src/refactoring/circular/strategy-generator.js +229 -0
- package/src/refactoring/circular-dependency-resolver-original.js +809 -0
- package/src/refactoring/circular-dependency-resolver.js +200 -0
- package/src/refactoring/code-mover.js +761 -0
- package/src/refactoring/file-splitter.js +696 -0
- package/src/refactoring/functionality-validator.js +816 -0
- package/src/refactoring/import-manager.js +774 -0
- package/src/refactoring/module-boundary.js +107 -0
- package/src/refactoring/refactoring-executor.js +672 -0
- package/src/refactoring/refactoring-rollback.js +614 -0
- package/src/refactoring/test-validator.js +631 -0
- package/src/requirement-management/default-requirement-manager.js +321 -0
- package/src/requirement-management/requirement-file-parser.js +159 -0
- package/src/requirement-management/requirement-sequencer.js +221 -0
- package/src/rui/commands/AgentCommandParser.js +600 -0
- package/src/rui/commands/AgentCommands.js +487 -0
- package/src/rui/commands/AgentResponseFormatter.js +832 -0
- package/src/scripts/verify-full-compliance.js +269 -0
- package/src/sync/sync-engine-core.js +1 -0
- package/src/sync/sync-engine-remote-handlers.js +135 -0
- package/src/task-generation/automated-task-generator.js +351 -0
- package/src/task-generation/prioritizer.js +287 -0
- package/src/task-generation/task-list-updater.js +215 -0
- package/src/task-generation/task-management-integration.js +480 -0
- package/src/task-generation/task-manager-integration.js +270 -0
- package/src/task-generation/violation-task-generator.js +474 -0
- package/src/task-management/continuous-scan-integration.js +342 -0
- package/src/timeout-management/index.js +12 -3
- package/src/timeout-management/response-time-tracker.js +167 -0
- package/src/timeout-management/timeout-calculator.js +159 -0
- package/src/timeout-management/timeout-config-manager.js +172 -0
- package/src/utils/ast-analyzer.js +417 -0
- package/src/utils/current-requirement-manager.js +276 -0
- package/src/utils/current-requirement-operations.js +472 -0
- package/src/utils/dependency-mapper.js +456 -0
- package/src/utils/download-with-progress.js +4 -2
- package/src/utils/electron-update-checker.js +4 -1
- package/src/utils/file-size-analyzer.js +272 -0
- package/src/utils/import-updater.js +280 -0
- package/src/utils/refactoring-tools.js +512 -0
- package/src/utils/report-generator.js +569 -0
- package/src/utils/reports/report-analysis.js +218 -0
- package/src/utils/reports/report-types.js +55 -0
- package/src/utils/reports/summary-generators.js +102 -0
- package/src/utils/requirement-file-management.js +157 -0
- package/src/utils/requirement-helpers/requirement-file-ops.js +392 -0
- package/src/utils/requirement-helpers/requirement-mover.js +414 -0
- package/src/utils/requirement-helpers/requirement-parser.js +326 -0
- package/src/utils/requirement-helpers/requirement-status.js +320 -0
- package/src/utils/requirement-helpers-new.js +55 -0
- package/src/utils/requirement-helpers-refactored.js +367 -0
- package/src/utils/requirement-helpers.js +291 -1191
- package/src/utils/requirement-movement-operations.js +450 -0
- package/src/utils/requirement-movement.js +312 -0
- package/src/utils/requirement-parsing-helpers.js +56 -0
- package/src/utils/requirement-statistics.js +200 -0
- package/src/utils/requirement-text-utils.js +58 -0
- package/src/utils/rollback/rollback-handlers.js +125 -0
- package/src/utils/rollback/rollback-operation.js +63 -0
- package/src/utils/rollback/rollback-recorder.js +166 -0
- package/src/utils/rollback/rollback-state-manager.js +175 -0
- package/src/utils/rollback/rollback-types.js +33 -0
- package/src/utils/rollback/rollback-utils.js +110 -0
- package/src/utils/rollback-manager-original.js +569 -0
- package/src/utils/rollback-manager.js +202 -0
- package/src/utils/smoke-test-cli.js +362 -0
- package/src/utils/smoke-test-gui.js +351 -0
- package/src/utils/smoke-test-orchestrator.js +321 -0
- package/src/utils/smoke-test-runner.js +60 -0
- package/src/utils/smoke-test-web.js +347 -0
- package/src/utils/specification-helpers.js +39 -13
- package/src/utils/specification-migration.js +97 -0
- package/src/utils/test-runner.js +579 -0
- package/src/utils/validation-framework.js +518 -0
- package/src/validation/compliance-analyzer.js +197 -0
- package/src/validation/compliance-report-generator.js +343 -0
- package/src/validation/compliance-reporter.js +711 -0
- package/src/validation/compliance-rules.js +127 -0
- package/src/validation/constitution-validator-new.js +196 -0
- package/src/validation/constitution-validator.js +17 -0
- package/src/validation/file-validators.js +170 -0
- package/src/validation/line-limit/file-analyzer.js +201 -0
- package/src/validation/line-limit/line-limit-validator.js +208 -0
- package/src/validation/line-limit/validation-result.js +144 -0
- package/src/validation/line-limit-core.js +225 -0
- package/src/validation/line-limit-reporter.js +134 -0
- package/src/validation/line-limit-result.js +125 -0
- package/src/validation/line-limit-validator.js +41 -0
- package/src/validation/metrics-calculator.js +660 -0
- package/src/sync/sync-engine-backup.js +0 -559
|
@@ -0,0 +1,392 @@
|
|
|
1
|
+
const fs = require('fs-extra');
|
|
2
|
+
const path = require('path');
|
|
3
|
+
const os = require('os');
|
|
4
|
+
const { getRequirementsPath } = require('../repo-helpers.cjs');
|
|
5
|
+
const { logger } = require('../logger.cjs');
|
|
6
|
+
const { DEFAULT_INSTRUCTION_TEXT } = require('./requirement-parser.js');
|
|
7
|
+
|
|
8
|
+
/**
|
|
9
|
+
* Requirement File Operations
|
|
10
|
+
* Handles file-level operations for requirements management
|
|
11
|
+
*/
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* Get the requirements file path for the current hostname
|
|
15
|
+
* @param {string} repoPath - Repository path (optional)
|
|
16
|
+
* @returns {string} Requirements file path
|
|
17
|
+
*/
|
|
18
|
+
function getRequirementsFilePath(repoPath = null) {
|
|
19
|
+
if (repoPath) {
|
|
20
|
+
const hostname = os.hostname();
|
|
21
|
+
return path.join(repoPath, '.vibecodingmachine', `REQUIREMENTS-${hostname}.md`);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
return getRequirementsPath();
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
/**
|
|
28
|
+
* Check if requirements file exists
|
|
29
|
+
* @param {string} repoPath - Repository path (optional)
|
|
30
|
+
* @returns {boolean} Whether the file exists
|
|
31
|
+
*/
|
|
32
|
+
function requirementsFileExists(repoPath = null) {
|
|
33
|
+
const reqPath = getRequirementsFilePath(repoPath);
|
|
34
|
+
return fs.pathExistsSync(reqPath);
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* Create requirements file with default structure
|
|
39
|
+
* @param {string} repoPath - Repository path
|
|
40
|
+
* @returns {Promise<boolean>} Success status
|
|
41
|
+
*/
|
|
42
|
+
async function createRequirementsFile(repoPath) {
|
|
43
|
+
try {
|
|
44
|
+
const reqPath = getRequirementsFilePath(repoPath);
|
|
45
|
+
const vibecodingmachineDir = path.dirname(reqPath);
|
|
46
|
+
|
|
47
|
+
// Ensure .vibecodingmachine directory exists
|
|
48
|
+
await fs.ensureDir(vibecodingmachineDir);
|
|
49
|
+
|
|
50
|
+
// Check if file already exists
|
|
51
|
+
if (await fs.pathExists(reqPath)) {
|
|
52
|
+
logger.log(`Requirements file already exists: ${reqPath}`);
|
|
53
|
+
return true;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
// Create default content
|
|
57
|
+
const defaultContent = `# Vibe Coding Machine Requirements
|
|
58
|
+
|
|
59
|
+
## 🚦 Current Status
|
|
60
|
+
|
|
61
|
+
PREPARE
|
|
62
|
+
|
|
63
|
+
## 🔨 Current In Progress Requirement
|
|
64
|
+
|
|
65
|
+
*No requirement currently in progress*
|
|
66
|
+
|
|
67
|
+
## ⏳ Requirements not yet completed
|
|
68
|
+
|
|
69
|
+
- Add your first requirement here
|
|
70
|
+
|
|
71
|
+
## ✅ Verified by AI screenshot. Needs Human to Verify and move to CHANGELOG
|
|
72
|
+
|
|
73
|
+
*No requirements verified yet*
|
|
74
|
+
|
|
75
|
+
---
|
|
76
|
+
|
|
77
|
+
## Instructions
|
|
78
|
+
|
|
79
|
+
${DEFAULT_INSTRUCTION_TEXT}
|
|
80
|
+
|
|
81
|
+
## Status Progression
|
|
82
|
+
|
|
83
|
+
Work through these stages in order:
|
|
84
|
+
1. **PREPARE** - Take screenshots, review code, understand requirements
|
|
85
|
+
2. **CREATE** - Implement the actual code/functionality
|
|
86
|
+
3. **CLEAN UP** - Clean up code, remove duplicates, apply best practices
|
|
87
|
+
4. **VERIFY** - Run automation, take screenshots to verify functionality
|
|
88
|
+
5. **DONE** - Everything is working perfectly, requirement completed
|
|
89
|
+
|
|
90
|
+
**CRITICAL**: You MUST update the status at each stage and SAVE the file. The VibeCodingMachine app depends on this for autonomous operation.
|
|
91
|
+
`;
|
|
92
|
+
|
|
93
|
+
await fs.writeFile(reqPath, defaultContent, 'utf-8');
|
|
94
|
+
logger.log(`✅ Created requirements file: ${reqPath}`);
|
|
95
|
+
return true;
|
|
96
|
+
|
|
97
|
+
} catch (error) {
|
|
98
|
+
logger.error(`Error creating requirements file: ${error.message}`);
|
|
99
|
+
return false;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
/**
|
|
104
|
+
* Read requirements file content
|
|
105
|
+
* @param {string} repoPath - Repository path (optional)
|
|
106
|
+
* @returns {Promise<string|null>} File content or null if error
|
|
107
|
+
*/
|
|
108
|
+
async function readRequirementsFile(repoPath = null) {
|
|
109
|
+
try {
|
|
110
|
+
const reqPath = getRequirementsFilePath(repoPath);
|
|
111
|
+
|
|
112
|
+
if (!(await fs.pathExists(reqPath))) {
|
|
113
|
+
logger.warn(`Requirements file does not exist: ${reqPath}`);
|
|
114
|
+
return null;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
const content = await fs.readFile(reqPath, 'utf-8');
|
|
118
|
+
return content;
|
|
119
|
+
|
|
120
|
+
} catch (error) {
|
|
121
|
+
logger.error(`Error reading requirements file: ${error.message}`);
|
|
122
|
+
return null;
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
/**
|
|
127
|
+
* Write requirements file content
|
|
128
|
+
* @param {string} content - Content to write
|
|
129
|
+
* @param {string} repoPath - Repository path (optional)
|
|
130
|
+
* @returns {Promise<boolean>} Success status
|
|
131
|
+
*/
|
|
132
|
+
async function writeRequirementsFile(content, repoPath = null) {
|
|
133
|
+
try {
|
|
134
|
+
const reqPath = getRequirementsFilePath(repoPath);
|
|
135
|
+
const vibecodingmachineDir = path.dirname(reqPath);
|
|
136
|
+
|
|
137
|
+
// Ensure directory exists
|
|
138
|
+
await fs.ensureDir(vibecodingmachineDir);
|
|
139
|
+
|
|
140
|
+
await fs.writeFile(reqPath, content, 'utf-8');
|
|
141
|
+
logger.log(`✅ Wrote requirements file: ${reqPath}`);
|
|
142
|
+
return true;
|
|
143
|
+
|
|
144
|
+
} catch (error) {
|
|
145
|
+
logger.error(`Error writing requirements file: ${error.message}`);
|
|
146
|
+
return false;
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
/**
|
|
151
|
+
* Backup requirements file
|
|
152
|
+
* @param {string} repoPath - Repository path (optional)
|
|
153
|
+
* @param {string} suffix - Backup suffix (default: .backup)
|
|
154
|
+
* @returns {Promise<string|null>} Backup file path or null if error
|
|
155
|
+
*/
|
|
156
|
+
async function backupRequirementsFile(repoPath = null, suffix = '.backup') {
|
|
157
|
+
try {
|
|
158
|
+
const reqPath = getRequirementsFilePath(repoPath);
|
|
159
|
+
const backupPath = reqPath + suffix;
|
|
160
|
+
|
|
161
|
+
if (!(await fs.pathExists(reqPath))) {
|
|
162
|
+
logger.warn(`Cannot backup non-existent requirements file: ${reqPath}`);
|
|
163
|
+
return null;
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
await fs.copy(reqPath, backupPath);
|
|
167
|
+
logger.log(`✅ Backed up requirements file to: ${backupPath}`);
|
|
168
|
+
return backupPath;
|
|
169
|
+
|
|
170
|
+
} catch (error) {
|
|
171
|
+
logger.error(`Error backing up requirements file: ${error.message}`);
|
|
172
|
+
return null;
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
/**
|
|
177
|
+
* Get requirements file statistics
|
|
178
|
+
* @param {string} repoPath - Repository path (optional)
|
|
179
|
+
* @returns {Promise<Object>} File statistics
|
|
180
|
+
*/
|
|
181
|
+
async function getRequirementsFileStats(repoPath = null) {
|
|
182
|
+
try {
|
|
183
|
+
const reqPath = getRequirementsFilePath(repoPath);
|
|
184
|
+
|
|
185
|
+
if (!(await fs.pathExists(reqPath))) {
|
|
186
|
+
return {
|
|
187
|
+
exists: false,
|
|
188
|
+
path: reqPath,
|
|
189
|
+
size: 0,
|
|
190
|
+
lines: 0,
|
|
191
|
+
lastModified: null,
|
|
192
|
+
created: null
|
|
193
|
+
};
|
|
194
|
+
}
|
|
195
|
+
|
|
196
|
+
const stats = await fs.stat(reqPath);
|
|
197
|
+
const content = await fs.readFile(reqPath, 'utf-8');
|
|
198
|
+
|
|
199
|
+
return {
|
|
200
|
+
exists: true,
|
|
201
|
+
path: reqPath,
|
|
202
|
+
size: stats.size,
|
|
203
|
+
lines: content.split('\n').length,
|
|
204
|
+
lastModified: stats.mtime,
|
|
205
|
+
created: stats.birthtime || stats.ctime
|
|
206
|
+
};
|
|
207
|
+
|
|
208
|
+
} catch (error) {
|
|
209
|
+
logger.error(`Error getting requirements file stats: ${error.message}`);
|
|
210
|
+
return {
|
|
211
|
+
exists: false,
|
|
212
|
+
path: getRequirementsFilePath(repoPath),
|
|
213
|
+
size: 0,
|
|
214
|
+
lines: 0,
|
|
215
|
+
lastModified: null,
|
|
216
|
+
created: null,
|
|
217
|
+
error: error.message
|
|
218
|
+
};
|
|
219
|
+
}
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
/**
|
|
223
|
+
* Validate requirements file format
|
|
224
|
+
* @param {string} repoPath - Repository path (optional)
|
|
225
|
+
* @returns {Promise<Object>} Validation result
|
|
226
|
+
*/
|
|
227
|
+
async function validateRequirementsFile(repoPath = null) {
|
|
228
|
+
try {
|
|
229
|
+
const content = await readRequirementsFile(repoPath);
|
|
230
|
+
|
|
231
|
+
if (!content) {
|
|
232
|
+
return {
|
|
233
|
+
isValid: false,
|
|
234
|
+
errors: ['Requirements file does not exist or cannot be read'],
|
|
235
|
+
warnings: []
|
|
236
|
+
};
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
const result = {
|
|
240
|
+
isValid: true,
|
|
241
|
+
errors: [],
|
|
242
|
+
warnings: []
|
|
243
|
+
};
|
|
244
|
+
|
|
245
|
+
const lines = content.split('\n');
|
|
246
|
+
|
|
247
|
+
// Check for required sections
|
|
248
|
+
const requiredSections = [
|
|
249
|
+
'## 🚦 Current Status',
|
|
250
|
+
'## 🔨 Current In Progress Requirement',
|
|
251
|
+
'## ⏳ Requirements not yet completed',
|
|
252
|
+
'## ✅ Verified by AI screenshot. Needs Human to Verify and move to CHANGELOG'
|
|
253
|
+
];
|
|
254
|
+
|
|
255
|
+
for (const section of requiredSections) {
|
|
256
|
+
if (!content.includes(section)) {
|
|
257
|
+
result.isValid = false;
|
|
258
|
+
result.errors.push(`Missing required section: ${section}`);
|
|
259
|
+
}
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
// Check for status section content
|
|
263
|
+
if (content.includes('## 🚦 Current Status')) {
|
|
264
|
+
const statusMatch = content.match(/## 🚦 Current Status\s*\n\s*\*\*([A-Z_]+)\*\*/);
|
|
265
|
+
if (!statusMatch) {
|
|
266
|
+
result.isValid = false;
|
|
267
|
+
result.errors.push('Current Status section exists but no status value found');
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
|
|
271
|
+
// Check file size
|
|
272
|
+
if (content.length > 100000) { // 100KB
|
|
273
|
+
result.warnings.push('Requirements file is very large, consider archiving old requirements');
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
// Check for common formatting issues
|
|
277
|
+
if (content.includes(' ')) {
|
|
278
|
+
result.warnings.push('File contains double spaces');
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
if (content.includes('\t')) {
|
|
282
|
+
result.warnings.push('File contains tabs (should use spaces)');
|
|
283
|
+
}
|
|
284
|
+
|
|
285
|
+
// Check line endings
|
|
286
|
+
if (content.includes('\r\n')) {
|
|
287
|
+
result.warnings.push('File uses Windows line endings (CRLF)');
|
|
288
|
+
}
|
|
289
|
+
|
|
290
|
+
return result;
|
|
291
|
+
|
|
292
|
+
} catch (error) {
|
|
293
|
+
return {
|
|
294
|
+
isValid: false,
|
|
295
|
+
errors: [`Error validating requirements file: ${error.message}`],
|
|
296
|
+
warnings: []
|
|
297
|
+
};
|
|
298
|
+
}
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
/**
|
|
302
|
+
* Get all requirements files in repository
|
|
303
|
+
* @param {string} repoPath - Repository path
|
|
304
|
+
* @returns {Promise<Array>} Array of requirements file info
|
|
305
|
+
*/
|
|
306
|
+
async function getAllRequirementsFiles(repoPath) {
|
|
307
|
+
try {
|
|
308
|
+
const vibecodingmachineDir = path.join(repoPath, '.vibecodingmachine');
|
|
309
|
+
|
|
310
|
+
if (!(await fs.pathExists(vibecodingmachineDir))) {
|
|
311
|
+
return [];
|
|
312
|
+
}
|
|
313
|
+
|
|
314
|
+
const files = await fs.readdir(vibecodingmachineDir);
|
|
315
|
+
const requirementsFiles = [];
|
|
316
|
+
|
|
317
|
+
for (const file of files) {
|
|
318
|
+
if (file.startsWith('REQUIREMENTS-') && file.endsWith('.md')) {
|
|
319
|
+
const filePath = path.join(vibecodingmachineDir, file);
|
|
320
|
+
const stats = await fs.stat(filePath);
|
|
321
|
+
const hostname = file.replace('REQUIREMENTS-', '').replace('.md', '');
|
|
322
|
+
|
|
323
|
+
requirementsFiles.push({
|
|
324
|
+
path: filePath,
|
|
325
|
+
filename: file,
|
|
326
|
+
hostname,
|
|
327
|
+
size: stats.size,
|
|
328
|
+
lastModified: stats.mtime,
|
|
329
|
+
isCurrent: hostname === os.hostname()
|
|
330
|
+
});
|
|
331
|
+
}
|
|
332
|
+
}
|
|
333
|
+
|
|
334
|
+
return requirementsFiles.sort((a, b) => b.lastModified - a.lastModified);
|
|
335
|
+
|
|
336
|
+
} catch (error) {
|
|
337
|
+
logger.error(`Error getting all requirements files: ${error.message}`);
|
|
338
|
+
return [];
|
|
339
|
+
}
|
|
340
|
+
}
|
|
341
|
+
|
|
342
|
+
/**
|
|
343
|
+
* Clean up old backup files
|
|
344
|
+
* @param {string} repoPath - Repository path (optional)
|
|
345
|
+
* @param {number} keepCount - Number of backups to keep (default: 5)
|
|
346
|
+
* @returns {Promise<number>} Number of files cleaned up
|
|
347
|
+
*/
|
|
348
|
+
async function cleanupBackupFiles(repoPath = null, keepCount = 5) {
|
|
349
|
+
try {
|
|
350
|
+
const reqPath = getRequirementsFilePath(repoPath);
|
|
351
|
+
const dir = path.dirname(reqPath);
|
|
352
|
+
const baseName = path.basename(reqPath);
|
|
353
|
+
|
|
354
|
+
const files = await fs.readdir(dir);
|
|
355
|
+
const backupFiles = files
|
|
356
|
+
.filter(file => file.startsWith(baseName) && file.includes('.backup'))
|
|
357
|
+
.map(file => ({
|
|
358
|
+
name: file,
|
|
359
|
+
path: path.join(dir, file),
|
|
360
|
+
mtime: fs.statSync(path.join(dir, file)).mtime
|
|
361
|
+
}))
|
|
362
|
+
.sort((a, b) => b.mtime - a.mtime);
|
|
363
|
+
|
|
364
|
+
let cleanedCount = 0;
|
|
365
|
+
|
|
366
|
+
// Keep the most recent backups, delete older ones
|
|
367
|
+
for (let i = keepCount; i < backupFiles.length; i++) {
|
|
368
|
+
await fs.remove(backupFiles[i].path);
|
|
369
|
+
cleanedCount++;
|
|
370
|
+
logger.log(`🗑️ Cleaned up old backup: ${backupFiles[i].name}`);
|
|
371
|
+
}
|
|
372
|
+
|
|
373
|
+
return cleanedCount;
|
|
374
|
+
|
|
375
|
+
} catch (error) {
|
|
376
|
+
logger.error(`Error cleaning up backup files: ${error.message}`);
|
|
377
|
+
return 0;
|
|
378
|
+
}
|
|
379
|
+
}
|
|
380
|
+
|
|
381
|
+
module.exports = {
|
|
382
|
+
getRequirementsFilePath,
|
|
383
|
+
requirementsFileExists,
|
|
384
|
+
createRequirementsFile,
|
|
385
|
+
readRequirementsFile,
|
|
386
|
+
writeRequirementsFile,
|
|
387
|
+
backupRequirementsFile,
|
|
388
|
+
getRequirementsFileStats,
|
|
389
|
+
validateRequirementsFile,
|
|
390
|
+
getAllRequirementsFiles,
|
|
391
|
+
cleanupBackupFiles
|
|
392
|
+
};
|