vibecodingmachine-core 2026.2.20-438 → 2026.2.26-1642

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (202) hide show
  1. package/README.md +240 -0
  2. package/package.json +10 -2
  3. package/src/agents/Agent.js +300 -0
  4. package/src/agents/AgentAdditionService.js +311 -0
  5. package/src/agents/AgentCheckService.js +690 -0
  6. package/src/agents/AgentInstallationService.js +140 -0
  7. package/src/agents/AgentSetupService.js +467 -0
  8. package/src/agents/AgentStatus.js +183 -0
  9. package/src/agents/AgentVerificationService.js +634 -0
  10. package/src/agents/ConfigurationSchemaValidator.js +543 -0
  11. package/src/agents/EnvironmentConfigurationManager.js +602 -0
  12. package/src/agents/InstallationErrorHandler.js +372 -0
  13. package/src/agents/InstallationLog.js +363 -0
  14. package/src/agents/InstallationMethod.js +510 -0
  15. package/src/agents/InstallationOrchestrator.js +352 -0
  16. package/src/agents/InstallationProgressReporter.js +372 -0
  17. package/src/agents/InstallationRetryManager.js +322 -0
  18. package/src/agents/InstallationType.js +254 -0
  19. package/src/agents/OperationTypes.js +310 -0
  20. package/src/agents/PerformanceMetricsCollector.js +493 -0
  21. package/src/agents/SecurityValidationService.js +534 -0
  22. package/src/agents/VerificationTest.js +354 -0
  23. package/src/agents/VerificationType.js +226 -0
  24. package/src/agents/WindowsPermissionHandler.js +518 -0
  25. package/src/agents/config/AgentConfigManager.js +393 -0
  26. package/src/agents/config/AgentDefaultsRegistry.js +373 -0
  27. package/src/agents/config/ConfigValidator.js +281 -0
  28. package/src/agents/discovery/AgentDiscoveryService.js +707 -0
  29. package/src/agents/logging/AgentLogger.js +511 -0
  30. package/src/agents/status/AgentStatusManager.js +481 -0
  31. package/src/agents/storage/FileManager.js +454 -0
  32. package/src/agents/verification/AgentCommunicationTester.js +474 -0
  33. package/src/agents/verification/BaseVerifier.js +430 -0
  34. package/src/agents/verification/CommandVerifier.js +480 -0
  35. package/src/agents/verification/FileOperationVerifier.js +453 -0
  36. package/src/agents/verification/ResultAnalyzer.js +707 -0
  37. package/src/agents/verification/TestRequirementManager.js +495 -0
  38. package/src/agents/verification/VerificationRunner.js +433 -0
  39. package/src/agents/windows/BaseWindowsInstaller.js +441 -0
  40. package/src/agents/windows/ChocolateyInstaller.js +509 -0
  41. package/src/agents/windows/DirectInstaller.js +443 -0
  42. package/src/agents/windows/InstallerFactory.js +391 -0
  43. package/src/agents/windows/NpmInstaller.js +505 -0
  44. package/src/agents/windows/PowerShellInstaller.js +458 -0
  45. package/src/agents/windows/WinGetInstaller.js +390 -0
  46. package/src/analysis/analysis-reporter.js +132 -0
  47. package/src/analysis/boundary-detector.js +712 -0
  48. package/src/analysis/categorizer.js +340 -0
  49. package/src/analysis/codebase-scanner.js +384 -0
  50. package/src/analysis/line-counter.js +513 -0
  51. package/src/analysis/priority-calculator.js +679 -0
  52. package/src/analysis/report/analysis-report.js +250 -0
  53. package/src/analysis/report/package-analyzer.js +278 -0
  54. package/src/analysis/report/recommendation-generator.js +382 -0
  55. package/src/analysis/report/statistics-generator.js +515 -0
  56. package/src/analysis/reports/analysis-report-model.js +101 -0
  57. package/src/analysis/reports/recommendation-generator.js +283 -0
  58. package/src/analysis/reports/report-generators.js +191 -0
  59. package/src/analysis/reports/statistics-calculator.js +231 -0
  60. package/src/analysis/reports/trend-analyzer.js +219 -0
  61. package/src/analysis/strategy-generator.js +814 -0
  62. package/src/auto-mode/AutoModeBusinessLogic.js +836 -0
  63. package/src/config/refactoring-config.js +307 -0
  64. package/src/health-tracking/json-storage.js +38 -2
  65. package/src/ide-integration/applescript-manager-core.js +233 -0
  66. package/src/ide-integration/applescript-manager.cjs +357 -28
  67. package/src/ide-integration/applescript-manager.js +89 -3599
  68. package/src/ide-integration/cdp-manager.js +306 -0
  69. package/src/ide-integration/claude-code-cli-manager.cjs +1 -1
  70. package/src/ide-integration/continuation-handler.js +337 -0
  71. package/src/ide-integration/ide-status-checker.js +292 -0
  72. package/src/ide-integration/macos-ide-manager.js +627 -0
  73. package/src/ide-integration/macos-text-sender.js +528 -0
  74. package/src/ide-integration/response-reader.js +548 -0
  75. package/src/ide-integration/windows-automation-manager.js +121 -0
  76. package/src/ide-integration/windows-ide-manager.js +373 -0
  77. package/src/index.cjs +25 -3
  78. package/src/index.js +15 -1
  79. package/src/llm/direct-llm-manager.cjs +90 -2
  80. package/src/models/compliance-report.js +538 -0
  81. package/src/models/file-analysis.js +681 -0
  82. package/src/models/refactoring-plan.js +770 -0
  83. package/src/monitoring/alert-system.js +834 -0
  84. package/src/monitoring/compliance-progress-tracker.js +437 -0
  85. package/src/monitoring/continuous-scan-notifications.js +661 -0
  86. package/src/monitoring/continuous-scanner.js +279 -0
  87. package/src/monitoring/file-monitor/file-analyzer.js +262 -0
  88. package/src/monitoring/file-monitor/file-monitor.js +237 -0
  89. package/src/monitoring/file-monitor/watcher.js +194 -0
  90. package/src/monitoring/file-monitor.js +17 -0
  91. package/src/monitoring/notification-manager.js +437 -0
  92. package/src/monitoring/scanner-core.js +368 -0
  93. package/src/monitoring/scanner-events.js +214 -0
  94. package/src/monitoring/violation-notification-system.js +515 -0
  95. package/src/refactoring/boundaries/cohesion-analyzer.js +316 -0
  96. package/src/refactoring/boundaries/extraction-result.js +285 -0
  97. package/src/refactoring/boundaries/extraction-strategies.js +392 -0
  98. package/src/refactoring/boundaries/module-boundary.js +209 -0
  99. package/src/refactoring/boundary/boundary-detector.js +741 -0
  100. package/src/refactoring/boundary/boundary-types.js +405 -0
  101. package/src/refactoring/boundary/extraction-strategies.js +554 -0
  102. package/src/refactoring/boundary-extraction-result.js +77 -0
  103. package/src/refactoring/boundary-extraction-strategies.js +330 -0
  104. package/src/refactoring/boundary-extractor.js +384 -0
  105. package/src/refactoring/boundary-types.js +46 -0
  106. package/src/refactoring/circular/circular-dependency.js +88 -0
  107. package/src/refactoring/circular/cycle-detection.js +147 -0
  108. package/src/refactoring/circular/dependency-node.js +82 -0
  109. package/src/refactoring/circular/dependency-result.js +107 -0
  110. package/src/refactoring/circular/dependency-types.js +58 -0
  111. package/src/refactoring/circular/graph-builder.js +213 -0
  112. package/src/refactoring/circular/resolution-strategy.js +72 -0
  113. package/src/refactoring/circular/strategy-generator.js +229 -0
  114. package/src/refactoring/circular-dependency-resolver-original.js +809 -0
  115. package/src/refactoring/circular-dependency-resolver.js +200 -0
  116. package/src/refactoring/code-mover.js +761 -0
  117. package/src/refactoring/file-splitter.js +696 -0
  118. package/src/refactoring/functionality-validator.js +816 -0
  119. package/src/refactoring/import-manager.js +774 -0
  120. package/src/refactoring/module-boundary.js +107 -0
  121. package/src/refactoring/refactoring-executor.js +672 -0
  122. package/src/refactoring/refactoring-rollback.js +614 -0
  123. package/src/refactoring/test-validator.js +631 -0
  124. package/src/requirement-management/default-requirement-manager.js +321 -0
  125. package/src/requirement-management/requirement-file-parser.js +159 -0
  126. package/src/requirement-management/requirement-sequencer.js +221 -0
  127. package/src/rui/commands/AgentCommandParser.js +600 -0
  128. package/src/rui/commands/AgentCommands.js +487 -0
  129. package/src/rui/commands/AgentResponseFormatter.js +832 -0
  130. package/src/scripts/verify-full-compliance.js +269 -0
  131. package/src/sync/sync-engine-core.js +1 -0
  132. package/src/sync/sync-engine-remote-handlers.js +135 -0
  133. package/src/task-generation/automated-task-generator.js +351 -0
  134. package/src/task-generation/prioritizer.js +287 -0
  135. package/src/task-generation/task-list-updater.js +215 -0
  136. package/src/task-generation/task-management-integration.js +480 -0
  137. package/src/task-generation/task-manager-integration.js +270 -0
  138. package/src/task-generation/violation-task-generator.js +474 -0
  139. package/src/task-management/continuous-scan-integration.js +342 -0
  140. package/src/timeout-management/index.js +12 -3
  141. package/src/timeout-management/response-time-tracker.js +167 -0
  142. package/src/timeout-management/timeout-calculator.js +159 -0
  143. package/src/timeout-management/timeout-config-manager.js +172 -0
  144. package/src/utils/ast-analyzer.js +417 -0
  145. package/src/utils/current-requirement-manager.js +276 -0
  146. package/src/utils/current-requirement-operations.js +472 -0
  147. package/src/utils/dependency-mapper.js +456 -0
  148. package/src/utils/download-with-progress.js +4 -2
  149. package/src/utils/electron-update-checker.js +4 -1
  150. package/src/utils/file-size-analyzer.js +272 -0
  151. package/src/utils/import-updater.js +280 -0
  152. package/src/utils/refactoring-tools.js +512 -0
  153. package/src/utils/report-generator.js +569 -0
  154. package/src/utils/reports/report-analysis.js +218 -0
  155. package/src/utils/reports/report-types.js +55 -0
  156. package/src/utils/reports/summary-generators.js +102 -0
  157. package/src/utils/requirement-file-management.js +157 -0
  158. package/src/utils/requirement-helpers/requirement-file-ops.js +392 -0
  159. package/src/utils/requirement-helpers/requirement-mover.js +414 -0
  160. package/src/utils/requirement-helpers/requirement-parser.js +326 -0
  161. package/src/utils/requirement-helpers/requirement-status.js +320 -0
  162. package/src/utils/requirement-helpers-new.js +55 -0
  163. package/src/utils/requirement-helpers-refactored.js +367 -0
  164. package/src/utils/requirement-helpers.js +291 -1191
  165. package/src/utils/requirement-movement-operations.js +450 -0
  166. package/src/utils/requirement-movement.js +312 -0
  167. package/src/utils/requirement-parsing-helpers.js +56 -0
  168. package/src/utils/requirement-statistics.js +200 -0
  169. package/src/utils/requirement-text-utils.js +58 -0
  170. package/src/utils/rollback/rollback-handlers.js +125 -0
  171. package/src/utils/rollback/rollback-operation.js +63 -0
  172. package/src/utils/rollback/rollback-recorder.js +166 -0
  173. package/src/utils/rollback/rollback-state-manager.js +175 -0
  174. package/src/utils/rollback/rollback-types.js +33 -0
  175. package/src/utils/rollback/rollback-utils.js +110 -0
  176. package/src/utils/rollback-manager-original.js +569 -0
  177. package/src/utils/rollback-manager.js +202 -0
  178. package/src/utils/smoke-test-cli.js +362 -0
  179. package/src/utils/smoke-test-gui.js +351 -0
  180. package/src/utils/smoke-test-orchestrator.js +321 -0
  181. package/src/utils/smoke-test-runner.js +60 -0
  182. package/src/utils/smoke-test-web.js +347 -0
  183. package/src/utils/specification-helpers.js +39 -13
  184. package/src/utils/specification-migration.js +97 -0
  185. package/src/utils/test-runner.js +579 -0
  186. package/src/utils/validation-framework.js +518 -0
  187. package/src/validation/compliance-analyzer.js +197 -0
  188. package/src/validation/compliance-report-generator.js +343 -0
  189. package/src/validation/compliance-reporter.js +711 -0
  190. package/src/validation/compliance-rules.js +127 -0
  191. package/src/validation/constitution-validator-new.js +196 -0
  192. package/src/validation/constitution-validator.js +17 -0
  193. package/src/validation/file-validators.js +170 -0
  194. package/src/validation/line-limit/file-analyzer.js +201 -0
  195. package/src/validation/line-limit/line-limit-validator.js +208 -0
  196. package/src/validation/line-limit/validation-result.js +144 -0
  197. package/src/validation/line-limit-core.js +225 -0
  198. package/src/validation/line-limit-reporter.js +134 -0
  199. package/src/validation/line-limit-result.js +125 -0
  200. package/src/validation/line-limit-validator.js +41 -0
  201. package/src/validation/metrics-calculator.js +660 -0
  202. package/src/sync/sync-engine-backup.js +0 -559
@@ -0,0 +1,712 @@
1
+ /**
2
+ * Logical Boundary Detector
3
+ *
4
+ * Uses AST analysis to detect logical boundaries in files for refactoring.
5
+ * Identifies functions, classes, modules, and other logical segments.
6
+ */
7
+
8
+ const fs = require('fs');
9
+ const path = require('path');
10
+
11
+ /**
12
+ * Boundary types
13
+ */
14
+ const BOUNDARY_TYPES = {
15
+ FUNCTION: 'function',
16
+ CLASS: 'class',
17
+ MODULE: 'module',
18
+ BLOCK: 'block',
19
+ IMPORT: 'import',
20
+ EXPORT: 'export',
21
+ COMMENT: 'comment',
22
+ UTILITY: 'utility',
23
+ CONSTANT: 'constant'
24
+ };
25
+
26
+ /**
27
+ * Boundary detection result class
28
+ */
29
+ class BoundaryDetectionResult {
30
+ constructor(filePath) {
31
+ this.filePath = filePath;
32
+ this.boundaries = [];
33
+ this.metadata = {
34
+ totalBoundaries: 0,
35
+ byType: {},
36
+ complexity: 'unknown',
37
+ cohesion: 'unknown',
38
+ coupling: 'unknown'
39
+ };
40
+ }
41
+
42
+ addBoundary(boundary) {
43
+ this.boundaries.push(boundary);
44
+ this.metadata.totalBoundaries++;
45
+
46
+ if (!this.metadata.byType[boundary.type]) {
47
+ this.metadata.byType[boundary.type] = 0;
48
+ }
49
+ this.metadata.byType[boundary.type]++;
50
+ }
51
+
52
+ getBoundariesByType(type) {
53
+ return this.boundaries.filter(b => b.type === type);
54
+ }
55
+
56
+ getLargestBoundaries(count = 5) {
57
+ return this.boundaries
58
+ .sort((a, b) => b.lineCount - a.lineCount)
59
+ .slice(0, count);
60
+ }
61
+
62
+ getRefactoringCandidates() {
63
+ return this.boundaries.filter(b =>
64
+ b.lineCount > 50 && // Reasonable size
65
+ (b.type === BOUNDARY_TYPES.FUNCTION || b.type === BOUNDARY_TYPES.CLASS)
66
+ );
67
+ }
68
+ }
69
+
70
+ /**
71
+ * Boundary class
72
+ */
73
+ class Boundary {
74
+ constructor(type, startLine, endLine, name = '') {
75
+ this.type = type;
76
+ this.startLine = startLine;
77
+ this.endLine = endLine;
78
+ this.name = name;
79
+ this.lineCount = endLine - startLine + 1;
80
+ this.complexity = 0;
81
+ this.dependencies = [];
82
+ this.exports = [];
83
+ this.comments = [];
84
+ this.metadata = {};
85
+ }
86
+
87
+ addDependency(dependency) {
88
+ this.dependencies.push(dependency);
89
+ }
90
+
91
+ addExport(exportName) {
92
+ this.exports.push(exportName);
93
+ }
94
+
95
+ addComment(comment) {
96
+ this.comments.push(comment);
97
+ }
98
+
99
+ setComplexity(complexity) {
100
+ this.complexity = complexity;
101
+ }
102
+
103
+ canExtract() {
104
+ // Basic criteria for extraction
105
+ return this.lineCount >= 10 &&
106
+ this.name !== '' &&
107
+ (this.type === BOUNDARY_TYPES.FUNCTION || this.type === BOUNDARY_TYPES.CLASS);
108
+ }
109
+ }
110
+
111
+ /**
112
+ * Logical boundary detector class
113
+ */
114
+ class BoundaryDetector {
115
+ constructor(options = {}) {
116
+ this.options = {
117
+ minFunctionSize: 5,
118
+ minClassSize: 10,
119
+ detectComments: true,
120
+ detectUtilities: true,
121
+ ...options
122
+ };
123
+ }
124
+
125
+ /**
126
+ * Detect boundaries in a file
127
+ */
128
+ async detectBoundaries(filePath) {
129
+ const result = new BoundaryDetectionResult(filePath);
130
+
131
+ try {
132
+ const content = fs.readFileSync(filePath, 'utf8');
133
+ const lines = content.split('\n');
134
+
135
+ // Detect based on file type
136
+ const ext = path.extname(filePath).toLowerCase();
137
+
138
+ if (['.js', '.jsx', '.ts', '.tsx'].includes(ext)) {
139
+ await this.detectJavaScriptBoundaries(content, lines, result);
140
+ } else if (ext === '.md') {
141
+ await this.detectMarkdownBoundaries(content, lines, result);
142
+ } else {
143
+ await this.detectTextBoundaries(content, lines, result);
144
+ }
145
+
146
+ // Analyze overall structure
147
+ this.analyzeStructure(result);
148
+
149
+ } catch (error) {
150
+ console.error(`Error detecting boundaries in ${filePath}: ${error.message}`);
151
+ }
152
+
153
+ return result;
154
+ }
155
+
156
+ /**
157
+ * Detect boundaries in JavaScript/TypeScript files
158
+ */
159
+ async detectJavaScriptBoundaries(content, lines, result) {
160
+ // Detect imports
161
+ this.detectImports(lines, result);
162
+
163
+ // Detect exports
164
+ this.detectExports(lines, result);
165
+
166
+ // Detect functions
167
+ this.detectFunctions(lines, result);
168
+
169
+ // Detect classes
170
+ this.detectClasses(lines, result);
171
+
172
+ // Detect utility sections
173
+ if (this.options.detectUtilities) {
174
+ this.detectUtilities(lines, result);
175
+ }
176
+
177
+ // Detect comment blocks
178
+ if (this.options.detectComments) {
179
+ this.detectCommentBlocks(lines, result);
180
+ }
181
+ }
182
+
183
+ /**
184
+ * Detect import statements
185
+ */
186
+ detectImports(lines, result) {
187
+ let currentImport = null;
188
+
189
+ for (let i = 0; i < lines.length; i++) {
190
+ const line = lines[i].trim();
191
+
192
+ if (line.startsWith('import ')) {
193
+ if (currentImport) {
194
+ // Close previous import
195
+ currentImport.endLine = i - 1;
196
+ currentImport.lineCount = currentImport.endLine - currentImport.startLine + 1;
197
+ result.addBoundary(currentImport);
198
+ }
199
+
200
+ // Start new import
201
+ const match = line.match(/import\s+(?:.*?\s+from\s+)?['"]([^'"]+)['"]/);
202
+ currentImport = new Boundary(
203
+ BOUNDARY_TYPES.IMPORT,
204
+ i,
205
+ i,
206
+ match ? match[1] : 'import'
207
+ );
208
+ } else if (currentImport && (line.startsWith('from ') || line.endsWith(';'))) {
209
+ // End of import statement
210
+ currentImport.endLine = i;
211
+ currentImport.lineCount = currentImport.endLine - currentImport.startLine + 1;
212
+ result.addBoundary(currentImport);
213
+ currentImport = null;
214
+ }
215
+ }
216
+
217
+ // Handle unclosed import
218
+ if (currentImport) {
219
+ currentImport.endLine = lines.length - 1;
220
+ currentImport.lineCount = currentImport.endLine - currentImport.startLine + 1;
221
+ result.addBoundary(currentImport);
222
+ }
223
+ }
224
+
225
+ /**
226
+ * Detect export statements
227
+ */
228
+ detectExports(lines, result) {
229
+ for (let i = 0; i < lines.length; i++) {
230
+ const line = lines[i].trim();
231
+
232
+ if (line.startsWith('export ')) {
233
+ const match = line.match(/export\s+(?:default\s+)?(?:function|class|const|let|var)\s+(\w+)/);
234
+ const name = match ? match[1] : 'export';
235
+
236
+ const boundary = new Boundary(
237
+ BOUNDARY_TYPES.EXPORT,
238
+ i,
239
+ i,
240
+ name
241
+ );
242
+
243
+ result.addBoundary(boundary);
244
+ }
245
+ }
246
+ }
247
+
248
+ /**
249
+ * Detect function boundaries
250
+ */
251
+ detectFunctions(lines, result) {
252
+ for (let i = 0; i < lines.length; i++) {
253
+ const line = lines[i].trim();
254
+
255
+ // Function declarations
256
+ const funcMatch = line.match(/^(?:async\s+)?function\s+(\w+)/);
257
+ if (funcMatch) {
258
+ const boundary = this.findFunctionBoundary(lines, i, funcMatch[1], 'declaration');
259
+ if (boundary) result.addBoundary(boundary);
260
+ continue;
261
+ }
262
+
263
+ // Function expressions
264
+ const exprMatch = line.match(/^(?:const|let|var)\s+(\w+)\s*=\s*(?:async\s+)?function/);
265
+ if (exprMatch) {
266
+ const boundary = this.findFunctionBoundary(lines, i, exprMatch[1], 'expression');
267
+ if (boundary) result.addBoundary(boundary);
268
+ continue;
269
+ }
270
+
271
+ // Arrow functions
272
+ const arrowMatch = line.match(/^(?:const|let|var)\s+(\w+)\s*=\s*(?:async\s+)?\(/);
273
+ if (arrowMatch) {
274
+ const boundary = this.findArrowFunctionBoundary(lines, i, arrowMatch[1]);
275
+ if (boundary) result.addBoundary(boundary);
276
+ continue;
277
+ }
278
+
279
+ // Method definitions in classes
280
+ const methodMatch = line.match(/^(\w+)\s*\(/);
281
+ if (methodMatch && this.isInClass(lines, i)) {
282
+ const boundary = this.findMethodBoundary(lines, i, methodMatch[1]);
283
+ if (boundary) result.addBoundary(boundary);
284
+ }
285
+ }
286
+ }
287
+
288
+ /**
289
+ * Find function boundary
290
+ */
291
+ findFunctionBoundary(lines, startLine, name, type) {
292
+ let braceCount = 0;
293
+ let foundBrace = false;
294
+
295
+ for (let i = startLine; i < lines.length; i++) {
296
+ const line = lines[i];
297
+
298
+ for (let j = 0; j < line.length; j++) {
299
+ if (line[j] === '{') {
300
+ braceCount++;
301
+ foundBrace = true;
302
+ } else if (line[j] === '}') {
303
+ braceCount--;
304
+ if (foundBrace && braceCount === 0) {
305
+ const boundary = new Boundary(
306
+ BOUNDARY_TYPES.FUNCTION,
307
+ startLine,
308
+ i,
309
+ name
310
+ );
311
+ boundary.metadata.type = type;
312
+ return boundary;
313
+ }
314
+ }
315
+ }
316
+ }
317
+
318
+ return null;
319
+ }
320
+
321
+ /**
322
+ * Find arrow function boundary
323
+ */
324
+ findArrowFunctionBoundary(lines, startLine, name) {
325
+ let braceCount = 0;
326
+ let foundBrace = false;
327
+ let foundArrow = false;
328
+
329
+ for (let i = startLine; i < lines.length; i++) {
330
+ const line = lines[i];
331
+
332
+ if (line.includes('=>')) {
333
+ foundArrow = true;
334
+ }
335
+
336
+ for (let j = 0; j < line.length; j++) {
337
+ if (line[j] === '{') {
338
+ braceCount++;
339
+ foundBrace = true;
340
+ } else if (line[j] === '}') {
341
+ braceCount--;
342
+ if (foundBrace && foundArrow && braceCount === 0) {
343
+ const boundary = new Boundary(
344
+ BOUNDARY_TYPES.FUNCTION,
345
+ startLine,
346
+ i,
347
+ name
348
+ );
349
+ boundary.metadata.type = 'arrow';
350
+ return boundary;
351
+ }
352
+ }
353
+ }
354
+ }
355
+
356
+ return null;
357
+ }
358
+
359
+ /**
360
+ * Find method boundary
361
+ */
362
+ findMethodBoundary(lines, startLine, name) {
363
+ let braceCount = 0;
364
+ let foundBrace = false;
365
+
366
+ for (let i = startLine; i < lines.length; i++) {
367
+ const line = lines[i];
368
+
369
+ for (let j = 0; j < line.length; j++) {
370
+ if (line[j] === '{') {
371
+ braceCount++;
372
+ foundBrace = true;
373
+ } else if (line[j] === '}') {
374
+ braceCount--;
375
+ if (foundBrace && braceCount === 0) {
376
+ const boundary = new Boundary(
377
+ BOUNDARY_TYPES.FUNCTION,
378
+ startLine,
379
+ i,
380
+ name
381
+ );
382
+ boundary.metadata.type = 'method';
383
+ return boundary;
384
+ }
385
+ }
386
+ }
387
+ }
388
+
389
+ return null;
390
+ }
391
+
392
+ /**
393
+ * Detect class boundaries
394
+ */
395
+ detectClasses(lines, result) {
396
+ for (let i = 0; i < lines.length; i++) {
397
+ const line = lines[i].trim();
398
+
399
+ const classMatch = line.match(/^class\s+(\w+)/);
400
+ if (classMatch) {
401
+ const boundary = this.findClassBoundary(lines, i, classMatch[1]);
402
+ if (boundary) result.addBoundary(boundary);
403
+ }
404
+ }
405
+ }
406
+
407
+ /**
408
+ * Find class boundary
409
+ */
410
+ findClassBoundary(lines, startLine, name) {
411
+ let braceCount = 0;
412
+ let foundBrace = false;
413
+
414
+ for (let i = startLine; i < lines.length; i++) {
415
+ const line = lines[i];
416
+
417
+ for (let j = 0; j < line.length; j++) {
418
+ if (line[j] === '{') {
419
+ braceCount++;
420
+ foundBrace = true;
421
+ } else if (line[j] === '}') {
422
+ braceCount--;
423
+ if (foundBrace && braceCount === 0) {
424
+ return new Boundary(
425
+ BOUNDARY_TYPES.CLASS,
426
+ startLine,
427
+ i,
428
+ name
429
+ );
430
+ }
431
+ }
432
+ }
433
+ }
434
+
435
+ return null;
436
+ }
437
+
438
+ /**
439
+ * Detect utility sections
440
+ */
441
+ detectUtilities(lines, result) {
442
+ // Look for sections with utility functions
443
+ let utilityStart = null;
444
+ let utilityName = null;
445
+
446
+ for (let i = 0; i < lines.length; i++) {
447
+ const line = lines[i].trim();
448
+
449
+ // Detect utility section comments
450
+ if (line.startsWith('//') && (line.includes('utility') || line.includes('helper'))) {
451
+ if (utilityStart) {
452
+ // Close previous utility section
453
+ const boundary = new Boundary(
454
+ BOUNDARY_TYPES.UTILITY,
455
+ utilityStart,
456
+ i - 1,
457
+ utilityName || 'utilities'
458
+ );
459
+ result.addBoundary(boundary);
460
+ }
461
+
462
+ utilityStart = i;
463
+ utilityName = line.replace('//', '').trim();
464
+ }
465
+ }
466
+
467
+ // Close final utility section
468
+ if (utilityStart) {
469
+ const boundary = new Boundary(
470
+ BOUNDARY_TYPES.UTILITY,
471
+ utilityStart,
472
+ lines.length - 1,
473
+ utilityName || 'utilities'
474
+ );
475
+ result.addBoundary(boundary);
476
+ }
477
+ }
478
+
479
+ /**
480
+ * Detect comment blocks
481
+ */
482
+ detectCommentBlocks(lines, result) {
483
+ let commentStart = null;
484
+ let commentType = null;
485
+
486
+ for (let i = 0; i < lines.length; i++) {
487
+ const line = lines[i].trim();
488
+
489
+ if (line.startsWith('/*')) {
490
+ commentStart = i;
491
+ commentType = 'block';
492
+ } else if (line.startsWith('//')) {
493
+ // Single line comment
494
+ const boundary = new Boundary(
495
+ BOUNDARY_TYPES.COMMENT,
496
+ i,
497
+ i,
498
+ 'single-line-comment'
499
+ );
500
+ result.addBoundary(boundary);
501
+ } else if (commentStart && line.endsWith('*/')) {
502
+ // End of block comment
503
+ const boundary = new Boundary(
504
+ BOUNDARY_TYPES.COMMENT,
505
+ commentStart,
506
+ i,
507
+ 'block-comment'
508
+ );
509
+ result.addBoundary(boundary);
510
+ commentStart = null;
511
+ commentType = null;
512
+ }
513
+ }
514
+ }
515
+
516
+ /**
517
+ * Detect boundaries in Markdown files
518
+ */
519
+ async detectMarkdownBoundaries(content, lines, result) {
520
+ for (let i = 0; i < lines.length; i++) {
521
+ const line = lines[i];
522
+
523
+ // Headers
524
+ const headerMatch = line.match(/^(#{1,6})\s+(.+)$/);
525
+ if (headerMatch) {
526
+ const level = headerMatch[1].length;
527
+ const title = headerMatch[2];
528
+
529
+ const boundary = new Boundary(
530
+ BOUNDARY_TYPES.MODULE,
531
+ i,
532
+ i,
533
+ title
534
+ );
535
+ boundary.metadata.level = level;
536
+ result.addBoundary(boundary);
537
+ }
538
+
539
+ // Code blocks
540
+ if (line.startsWith('```')) {
541
+ const boundary = new Boundary(
542
+ BOUNDARY_TYPES.BLOCK,
543
+ i,
544
+ i,
545
+ 'code-block'
546
+ );
547
+ result.addBoundary(boundary);
548
+ }
549
+ }
550
+ }
551
+
552
+ /**
553
+ * Detect boundaries in text files
554
+ */
555
+ async detectTextBoundaries(content, lines, result) {
556
+ // Simple paragraph detection
557
+ let paragraphStart = null;
558
+
559
+ for (let i = 0; i < lines.length; i++) {
560
+ const line = lines[i].trim();
561
+
562
+ if (line !== '') {
563
+ if (paragraphStart === null) {
564
+ paragraphStart = i;
565
+ }
566
+ } else {
567
+ if (paragraphStart !== null) {
568
+ const boundary = new Boundary(
569
+ BOUNDARY_TYPES.BLOCK,
570
+ paragraphStart,
571
+ i - 1,
572
+ 'paragraph'
573
+ );
574
+ result.addBoundary(boundary);
575
+ paragraphStart = null;
576
+ }
577
+ }
578
+ }
579
+
580
+ // Handle final paragraph
581
+ if (paragraphStart !== null) {
582
+ const boundary = new Boundary(
583
+ BOUNDARY_TYPES.BLOCK,
584
+ paragraphStart,
585
+ lines.length - 1,
586
+ 'paragraph'
587
+ );
588
+ result.addBoundary(boundary);
589
+ }
590
+ }
591
+
592
+ /**
593
+ * Check if line is inside a class
594
+ */
595
+ isInClass(lines, lineIndex) {
596
+ // Simple check - look backwards for class declaration
597
+ for (let i = lineIndex - 1; i >= 0; i--) {
598
+ const line = lines[i].trim();
599
+ if (line.startsWith('class ')) {
600
+ return true;
601
+ }
602
+ if (line.startsWith('function ') || line.startsWith('const ')) {
603
+ return false;
604
+ }
605
+ }
606
+ return false;
607
+ }
608
+
609
+ /**
610
+ * Analyze overall structure
611
+ */
612
+ analyzeStructure(result) {
613
+ // Calculate complexity metrics
614
+ const functions = result.getBoundariesByType(BOUNDARY_TYPES.FUNCTION);
615
+ const classes = result.getBoundariesByType(BOUNDARY_TYPES.CLASS);
616
+
617
+ let totalComplexity = 0;
618
+ let totalSize = 0;
619
+
620
+ for (const boundary of [...functions, ...classes]) {
621
+ // Simple complexity estimation based on size
622
+ boundary.complexity = Math.min(10, Math.ceil(boundary.lineCount / 20));
623
+ totalComplexity += boundary.complexity;
624
+ totalSize += boundary.lineCount;
625
+ }
626
+
627
+ result.metadata.complexity = totalComplexity > 20 ? 'high' :
628
+ totalComplexity > 10 ? 'medium' : 'low';
629
+
630
+ result.metadata.cohesion = this.assessCohesion(result);
631
+ result.metadata.coupling = this.assessCoupling(result);
632
+ }
633
+
634
+ /**
635
+ * Assess cohesion
636
+ */
637
+ assessCohesion(result) {
638
+ // Simple cohesion assessment based on boundary distribution
639
+ const functions = result.getBoundariesByType(BOUNDARY_TYPES.FUNCTION);
640
+ const avgFunctionSize = functions.length > 0 ?
641
+ functions.reduce((sum, f) => sum + f.lineCount, 0) / functions.length : 0;
642
+
643
+ if (avgFunctionSize > 100) return 'low';
644
+ if (avgFunctionSize > 50) return 'medium';
645
+ return 'high';
646
+ }
647
+
648
+ /**
649
+ * Assess coupling
650
+ */
651
+ assessCoupling(result) {
652
+ // Simple coupling assessment based on imports
653
+ const imports = result.getBoundariesByType(BOUNDARY_TYPES.IMPORT);
654
+
655
+ if (imports.length > 10) return 'high';
656
+ if (imports.length > 5) return 'medium';
657
+ return 'low';
658
+ }
659
+
660
+ /**
661
+ * Get refactoring recommendations
662
+ */
663
+ getRefactoringRecommendations(result) {
664
+ const recommendations = [];
665
+
666
+ // Large functions
667
+ const largeFunctions = result.getBoundariesByType(BOUNDARY_TYPES.FUNCTION)
668
+ .filter(f => f.lineCount > 50);
669
+
670
+ if (largeFunctions.length > 0) {
671
+ recommendations.push({
672
+ type: 'extract_functions',
673
+ priority: 'high',
674
+ description: `${largeFunctions.length} functions are too large and should be split`,
675
+ boundaries: largeFunctions.map(f => ({ name: f.name, lineCount: f.lineCount }))
676
+ });
677
+ }
678
+
679
+ // Large classes
680
+ const largeClasses = result.getBoundariesByType(BOUNDARY_TYPES.CLASS)
681
+ .filter(c => c.lineCount > 200);
682
+
683
+ if (largeClasses.length > 0) {
684
+ recommendations.push({
685
+ type: 'split_classes',
686
+ priority: 'medium',
687
+ description: `${largeClasses.length} classes are too large and should be split`,
688
+ boundaries: largeClasses.map(c => ({ name: c.name, lineCount: c.lineCount }))
689
+ });
690
+ }
691
+
692
+ // Utility extraction
693
+ const utilities = result.getBoundariesByType(BOUNDARY_TYPES.UTILITY);
694
+ if (utilities.length === 0 && result.metadata.totalBoundaries > 5) {
695
+ recommendations.push({
696
+ type: 'extract_utilities',
697
+ priority: 'low',
698
+ description: 'Consider extracting utility functions to separate modules',
699
+ boundaries: []
700
+ });
701
+ }
702
+
703
+ return recommendations;
704
+ }
705
+ }
706
+
707
+ module.exports = {
708
+ BoundaryDetector,
709
+ BoundaryDetectionResult,
710
+ Boundary,
711
+ BOUNDARY_TYPES
712
+ };