popeye-cli 1.8.0 → 1.9.1

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 (68) hide show
  1. package/README.md +47 -3
  2. package/cheatsheet.md +33 -0
  3. package/dist/cli/commands/index.d.ts +1 -0
  4. package/dist/cli/commands/index.d.ts.map +1 -1
  5. package/dist/cli/commands/index.js +1 -0
  6. package/dist/cli/commands/index.js.map +1 -1
  7. package/dist/cli/commands/review.d.ts +31 -0
  8. package/dist/cli/commands/review.d.ts.map +1 -0
  9. package/dist/cli/commands/review.js +156 -0
  10. package/dist/cli/commands/review.js.map +1 -0
  11. package/dist/cli/index.d.ts.map +1 -1
  12. package/dist/cli/index.js +2 -1
  13. package/dist/cli/index.js.map +1 -1
  14. package/dist/cli/interactive.d.ts.map +1 -1
  15. package/dist/cli/interactive.js +122 -61
  16. package/dist/cli/interactive.js.map +1 -1
  17. package/dist/types/audit.d.ts +623 -0
  18. package/dist/types/audit.d.ts.map +1 -0
  19. package/dist/types/audit.js +240 -0
  20. package/dist/types/audit.js.map +1 -0
  21. package/dist/types/workflow.d.ts +15 -0
  22. package/dist/types/workflow.d.ts.map +1 -1
  23. package/dist/types/workflow.js +5 -0
  24. package/dist/types/workflow.js.map +1 -1
  25. package/dist/workflow/audit-analyzer.d.ts +58 -0
  26. package/dist/workflow/audit-analyzer.d.ts.map +1 -0
  27. package/dist/workflow/audit-analyzer.js +438 -0
  28. package/dist/workflow/audit-analyzer.js.map +1 -0
  29. package/dist/workflow/audit-mode.d.ts +28 -0
  30. package/dist/workflow/audit-mode.d.ts.map +1 -0
  31. package/dist/workflow/audit-mode.js +169 -0
  32. package/dist/workflow/audit-mode.js.map +1 -0
  33. package/dist/workflow/audit-recovery.d.ts +61 -0
  34. package/dist/workflow/audit-recovery.d.ts.map +1 -0
  35. package/dist/workflow/audit-recovery.js +242 -0
  36. package/dist/workflow/audit-recovery.js.map +1 -0
  37. package/dist/workflow/audit-reporter.d.ts +65 -0
  38. package/dist/workflow/audit-reporter.d.ts.map +1 -0
  39. package/dist/workflow/audit-reporter.js +301 -0
  40. package/dist/workflow/audit-reporter.js.map +1 -0
  41. package/dist/workflow/audit-scanner.d.ts +87 -0
  42. package/dist/workflow/audit-scanner.d.ts.map +1 -0
  43. package/dist/workflow/audit-scanner.js +768 -0
  44. package/dist/workflow/audit-scanner.js.map +1 -0
  45. package/dist/workflow/index.d.ts +5 -0
  46. package/dist/workflow/index.d.ts.map +1 -1
  47. package/dist/workflow/index.js +5 -0
  48. package/dist/workflow/index.js.map +1 -1
  49. package/package.json +1 -1
  50. package/src/cli/commands/index.ts +1 -0
  51. package/src/cli/commands/review.ts +187 -0
  52. package/src/cli/index.ts +2 -0
  53. package/src/cli/interactive.ts +72 -4
  54. package/src/types/audit.ts +294 -0
  55. package/src/types/workflow.ts +15 -0
  56. package/src/workflow/audit-analyzer.ts +510 -0
  57. package/src/workflow/audit-mode.ts +240 -0
  58. package/src/workflow/audit-recovery.ts +284 -0
  59. package/src/workflow/audit-reporter.ts +370 -0
  60. package/src/workflow/audit-scanner.ts +873 -0
  61. package/src/workflow/index.ts +5 -0
  62. package/tests/cli/commands/review.test.ts +52 -0
  63. package/tests/types/audit.test.ts +250 -0
  64. package/tests/workflow/audit-analyzer.test.ts +281 -0
  65. package/tests/workflow/audit-mode.test.ts +114 -0
  66. package/tests/workflow/audit-recovery.test.ts +237 -0
  67. package/tests/workflow/audit-reporter.test.ts +254 -0
  68. package/tests/workflow/audit-scanner.test.ts +270 -0
@@ -0,0 +1,438 @@
1
+ /**
2
+ * AI-powered project analyzer for the audit system.
3
+ *
4
+ * Constructs analysis prompts, executes them through Claude with Serena-first
5
+ * search strategy (with retries and fallback), parses findings, and scores.
6
+ */
7
+ import { executePrompt } from '../adapters/claude.js';
8
+ import { AuditFindingSchema } from '../types/audit.js';
9
+ // ---------------------------------------------------------------------------
10
+ // Constants
11
+ // ---------------------------------------------------------------------------
12
+ const SERENA_TOOLS = [
13
+ 'mcp__serena__find_symbol',
14
+ 'mcp__serena__get_symbols_overview',
15
+ 'mcp__serena__search_symbol',
16
+ 'mcp__serena__get_file_symbols',
17
+ ];
18
+ const FALLBACK_TOOLS = [
19
+ 'Read', 'Glob', 'Grep',
20
+ ];
21
+ const ALL_AUDIT_TOOLS = [...SERENA_TOOLS, ...FALLBACK_TOOLS];
22
+ const MAX_SERENA_RETRIES = 2;
23
+ const CATEGORY_WEIGHTS = {
24
+ 'feature-completeness': 25,
25
+ 'integration-wiring': 15,
26
+ 'test-coverage': 15,
27
+ 'config-deployment': 10,
28
+ 'dependency-sanity': 10,
29
+ 'consistency': 10,
30
+ 'security': 10,
31
+ 'documentation': 5,
32
+ };
33
+ const SEVERITY_DEDUCTIONS = {
34
+ critical: 20,
35
+ major: 10,
36
+ minor: 3,
37
+ info: 0,
38
+ };
39
+ // ---------------------------------------------------------------------------
40
+ // Prompt construction
41
+ // ---------------------------------------------------------------------------
42
+ /**
43
+ * Build the analysis prompt for Claude, embedding scan results and context.
44
+ *
45
+ * @param scan - The project scan result.
46
+ * @param state - Current project state.
47
+ * @param depth - Audit depth (1=shallow, 2=standard, 3=deep).
48
+ * @param strict - Whether to use strict scoring.
49
+ * @returns The complete analysis prompt string.
50
+ */
51
+ export function buildAnalysisPrompt(scan, state, depth, strict) {
52
+ const sections = [];
53
+ sections.push(`# Project Audit Analysis
54
+
55
+ You are auditing the project "${state.name}" (language: ${scan.language}).
56
+ Depth level: ${depth} (1=shallow checks, 2=standard, 3=deep investigation).
57
+ ${strict ? 'STRICT MODE: Apply higher standards for all checks.' : ''}
58
+
59
+ ## Instructions
60
+ Analyze the project and return findings as a JSON array of objects. Each finding must have:
61
+ - id: string (format "AUD-NNN")
62
+ - category: one of "feature-completeness", "integration-wiring", "test-coverage", "config-deployment", "dependency-sanity", "consistency", "security", "documentation"
63
+ - severity: one of "critical", "major", "minor", "info"
64
+ - title: short summary
65
+ - description: detailed explanation
66
+ - evidence: array of { file: string, line?: number, snippet?: string, description?: string }
67
+ - recommendation: actionable fix
68
+ - autoFixable: boolean
69
+
70
+ Use Serena tools first for code navigation. If they fail, fall back to Read/Glob/Grep.
71
+
72
+ Return ONLY a JSON array wrapped in \`\`\`json fences. No other text.`);
73
+ // Component structure
74
+ sections.push(`## Component Structure
75
+ Components detected: ${scan.detectedComposition.join(', ')}
76
+ State language: ${scan.stateLanguage}
77
+ Composition mismatch: ${scan.compositionMismatch}
78
+
79
+ ${scan.components.map((c) => `### ${c.kind} (${c.rootDir})
80
+ - Language: ${c.language}${c.framework ? `, Framework: ${c.framework}` : ''}
81
+ - Source files: ${c.sourceFiles.length}
82
+ - Test files: ${c.testFiles.length}
83
+ - Entry points: ${c.entryPoints.join(', ') || 'none'}
84
+ - Route files: ${c.routeFiles.join(', ') || 'none'}
85
+ - Dependencies: ${c.dependencyManifests.map((d) => d.file).join(', ') || 'none'}`).join('\n\n')}`);
86
+ // File tree
87
+ sections.push(`## Project Tree (truncated)
88
+ \`\`\`
89
+ ${scan.tree}
90
+ \`\`\``);
91
+ // Totals
92
+ sections.push(`## Totals
93
+ - Source files: ${scan.totalSourceFiles}
94
+ - Test files: ${scan.totalTestFiles}
95
+ - Lines of code: ${scan.totalLinesOfCode}
96
+ - Lines of tests: ${scan.totalLinesOfTests}
97
+ - Config files: ${scan.configFiles.join(', ') || 'none'}`);
98
+ // CLAUDE.md context
99
+ if (scan.claudeMdContent) {
100
+ sections.push(`## CLAUDE.md (project instructions)
101
+ \`\`\`
102
+ ${scan.claudeMdContent.slice(0, 3000)}
103
+ \`\`\``);
104
+ }
105
+ // README
106
+ if (scan.readmeContent) {
107
+ sections.push(`## README.md
108
+ \`\`\`
109
+ ${scan.readmeContent.slice(0, 3000)}
110
+ \`\`\``);
111
+ }
112
+ // Specification from state
113
+ if (state.specification) {
114
+ sections.push(`## Project Specification
115
+ \`\`\`
116
+ ${state.specification.slice(0, 3000)}
117
+ \`\`\``);
118
+ }
119
+ // Milestone status
120
+ if (state.milestones && state.milestones.length > 0) {
121
+ sections.push(`## Milestone Status
122
+ ${state.milestones.map((m) => `- ${m.name}: ${m.status} (${m.tasks.filter((t) => t.status === 'complete').length}/${m.tasks.length} tasks)`).join('\n')}`);
123
+ }
124
+ // Wiring matrix pre-analysis
125
+ if (scan.wiring) {
126
+ sections.push(`## FE<->BE Wiring Matrix
127
+ - Frontend API env keys: ${scan.wiring.frontendApiBaseEnvKeys.join(', ') || 'none'}
128
+ - Frontend API resolved: ${scan.wiring.frontendApiBaseResolved || 'not set'}
129
+ - Backend CORS origins: ${scan.wiring.backendCorsOrigins?.join(', ') || 'not found'}
130
+ - Backend API prefix: ${scan.wiring.backendApiPrefix || 'not found'}
131
+ - Detected mismatches: ${scan.wiring.potentialMismatches.length}`);
132
+ }
133
+ // Env + Docker
134
+ if (scan.envExampleContent) {
135
+ sections.push(`## .env.example
136
+ \`\`\`
137
+ ${scan.envExampleContent}
138
+ \`\`\``);
139
+ }
140
+ if (scan.dockerComposeContent) {
141
+ sections.push(`## docker-compose.yml
142
+ \`\`\`
143
+ ${scan.dockerComposeContent}
144
+ \`\`\``);
145
+ }
146
+ // Framework-specific checks
147
+ const frameworks = scan.components.map((c) => c.framework).filter(Boolean);
148
+ if (frameworks.some((f) => f === 'next')) {
149
+ sections.push(`## Next.js-Specific Checks (IMPORTANT)
150
+ - Check for hydration mismatches: event handlers (onClick, onSubmit, onChange) in Server Components (files WITHOUT 'use client' directive) cause hydration errors
151
+ - Check for \`new Date()\`, \`Date.now()\`, \`Math.random()\` in Server Components — these produce different values on server vs client
152
+ - Check for \`typeof window\`, \`localStorage\`, \`navigator\` usage in render path of Server Components
153
+ - Check for invalid HTML nesting: \`<p>\` inside \`<p>\`, \`<div>\` inside \`<p>\`, block elements inside inline elements
154
+ - Verify that components with hooks (useState, useEffect, useRef) have 'use client' directive
155
+ - Check for proper 'use client' boundary — interactive components (forms, buttons with handlers) must be Client Components`);
156
+ }
157
+ if (frameworks.some((f) => f === 'react' || f === 'vue' || f === 'svelte')) {
158
+ sections.push(`## Frontend Framework Checks
159
+ - Check for missing key props on list items
160
+ - Verify error boundaries exist for critical routes
161
+ - Check for potential memory leaks (event listeners not cleaned up)
162
+ - Verify environment variables used at runtime are prefixed correctly (VITE_, NEXT_PUBLIC_, REACT_APP_)`);
163
+ }
164
+ // Depth-specific instructions
165
+ if (depth >= 2) {
166
+ sections.push(`## Depth-2 Checks
167
+ - Verify test coverage for all route handlers
168
+ - Check for missing error boundaries / error handling
169
+ - Validate dependency versions are not wildly outdated
170
+ - Confirm env variables used in code match .env.example`);
171
+ }
172
+ if (depth >= 3) {
173
+ sections.push(`## Depth-3 Checks
174
+ - Trace data flow from API endpoints to database
175
+ - Check for security issues (OWASP Top 10)
176
+ - Verify all imports resolve correctly
177
+ - Check for dead code and unused exports`);
178
+ }
179
+ return sections.join('\n\n');
180
+ }
181
+ // ---------------------------------------------------------------------------
182
+ // JSON parsing
183
+ // ---------------------------------------------------------------------------
184
+ /**
185
+ * Parse AI response into validated AuditFinding objects.
186
+ *
187
+ * Handles JSON wrapped in code fences, partial JSON, and malformed responses.
188
+ *
189
+ * @param rawResponse - Raw AI response text.
190
+ * @returns Array of validated findings.
191
+ */
192
+ export function parseAuditFindings(rawResponse) {
193
+ // Extract JSON from code fences
194
+ const jsonMatch = rawResponse.match(/```(?:json)?\s*\n?([\s\S]*?)\n?```/);
195
+ const jsonStr = jsonMatch ? jsonMatch[1].trim() : rawResponse.trim();
196
+ let parsed;
197
+ try {
198
+ parsed = JSON.parse(jsonStr);
199
+ }
200
+ catch {
201
+ // Attempt to find a JSON array in the response
202
+ const arrayMatch = jsonStr.match(/\[[\s\S]*\]/);
203
+ if (arrayMatch) {
204
+ try {
205
+ parsed = JSON.parse(arrayMatch[0]);
206
+ }
207
+ catch {
208
+ return [];
209
+ }
210
+ }
211
+ else {
212
+ return [];
213
+ }
214
+ }
215
+ if (!Array.isArray(parsed)) {
216
+ return [];
217
+ }
218
+ const findings = [];
219
+ for (const item of parsed) {
220
+ try {
221
+ const finding = AuditFindingSchema.parse(item);
222
+ findings.push(finding);
223
+ }
224
+ catch {
225
+ // Skip malformed findings — partial results better than none
226
+ }
227
+ }
228
+ return findings;
229
+ }
230
+ // ---------------------------------------------------------------------------
231
+ // Deterministic findings from wiring/composition
232
+ // ---------------------------------------------------------------------------
233
+ /**
234
+ * Generate deterministic findings from wiring mismatches and composition issues.
235
+ *
236
+ * @param scan - The project scan result.
237
+ * @returns Array of deterministic findings.
238
+ */
239
+ function generateDeterministicFindings(scan) {
240
+ const findings = [];
241
+ let counter = 900; // Reason: Start at 900 to avoid ID collision with AI findings
242
+ // Composition mismatch
243
+ if (scan.compositionMismatch) {
244
+ findings.push({
245
+ id: `AUD-${counter++}`,
246
+ category: 'consistency',
247
+ severity: 'major',
248
+ title: 'Workspace composition mismatch',
249
+ description: `State language is "${scan.stateLanguage}" but filesystem shows components: [${scan.detectedComposition.join(', ')}]. This may indicate an incomplete workspace setup or a stale state file.`,
250
+ evidence: [
251
+ { file: '.popeye/state.json', description: `language: "${scan.stateLanguage}"` },
252
+ ],
253
+ recommendation: 'Verify that all expected workspace apps are created and update project language if needed.',
254
+ autoFixable: false,
255
+ });
256
+ }
257
+ // Wiring mismatches
258
+ if (scan.wiring) {
259
+ for (const mismatch of scan.wiring.potentialMismatches) {
260
+ findings.push(wiringMismatchToFinding(mismatch, counter++));
261
+ }
262
+ }
263
+ // No test files at all
264
+ if (scan.totalTestFiles === 0 && scan.totalSourceFiles > 0) {
265
+ findings.push({
266
+ id: `AUD-${counter++}`,
267
+ category: 'test-coverage',
268
+ severity: 'critical',
269
+ title: 'No test files found',
270
+ description: `Project has ${scan.totalSourceFiles} source files but zero test files.`,
271
+ evidence: [],
272
+ recommendation: 'Add unit tests for critical paths.',
273
+ autoFixable: false,
274
+ });
275
+ }
276
+ // No README
277
+ if (!scan.readmeContent) {
278
+ findings.push({
279
+ id: `AUD-${counter++}`,
280
+ category: 'documentation',
281
+ severity: 'minor',
282
+ title: 'Missing README.md',
283
+ description: 'No README.md file found in project root.',
284
+ evidence: [],
285
+ recommendation: 'Add a README.md with project overview, setup, and usage instructions.',
286
+ autoFixable: true,
287
+ });
288
+ }
289
+ // No .env.example for multi-component projects
290
+ if (!scan.envExampleContent && scan.components.length > 1) {
291
+ findings.push({
292
+ id: `AUD-${counter++}`,
293
+ category: 'config-deployment',
294
+ severity: 'major',
295
+ title: 'Missing .env.example for workspace project',
296
+ description: 'Multi-component project should have a .env.example documenting required environment variables.',
297
+ evidence: [],
298
+ recommendation: 'Create .env.example with all required env variables and comments.',
299
+ autoFixable: true,
300
+ });
301
+ }
302
+ return findings;
303
+ }
304
+ /**
305
+ * Convert a wiring mismatch into an audit finding.
306
+ *
307
+ * @param mismatch - The wiring mismatch.
308
+ * @param counter - Finding ID counter.
309
+ * @returns An audit finding.
310
+ */
311
+ function wiringMismatchToFinding(mismatch, counter) {
312
+ return {
313
+ id: `AUD-${counter}`,
314
+ category: 'integration-wiring',
315
+ severity: 'major',
316
+ title: `Wiring issue: ${mismatch.type}`,
317
+ description: mismatch.details,
318
+ evidence: mismatch.evidence,
319
+ recommendation: 'Update CORS or API base URL configuration to ensure frontend and backend can communicate.',
320
+ autoFixable: true,
321
+ };
322
+ }
323
+ // ---------------------------------------------------------------------------
324
+ // Scoring
325
+ // ---------------------------------------------------------------------------
326
+ /**
327
+ * Calculate audit scores from findings and scan data.
328
+ *
329
+ * @param findings - All audit findings (AI + deterministic).
330
+ * @param scan - The project scan result.
331
+ * @returns Overall score (0-100) and per-category scores.
332
+ */
333
+ export function calculateAuditScores(findings, _scan) {
334
+ const categories = Object.keys(CATEGORY_WEIGHTS);
335
+ const categoryScores = {};
336
+ for (const cat of categories) {
337
+ const catFindings = findings.filter((f) => f.category === cat);
338
+ let score = 100;
339
+ for (const f of catFindings) {
340
+ score -= SEVERITY_DEDUCTIONS[f.severity] ?? 0;
341
+ }
342
+ categoryScores[cat] = Math.max(0, Math.min(100, score));
343
+ }
344
+ // Weighted average
345
+ let overallScore = 0;
346
+ let totalWeight = 0;
347
+ for (const cat of categories) {
348
+ overallScore += (categoryScores[cat] ?? 100) * CATEGORY_WEIGHTS[cat];
349
+ totalWeight += CATEGORY_WEIGHTS[cat];
350
+ }
351
+ overallScore = Math.round(overallScore / totalWeight);
352
+ return {
353
+ overallScore: Math.max(0, Math.min(100, overallScore)),
354
+ categoryScores: categoryScores,
355
+ };
356
+ }
357
+ // ---------------------------------------------------------------------------
358
+ // Main analyzer
359
+ // ---------------------------------------------------------------------------
360
+ /**
361
+ * Analyze the project using AI with Serena-first search strategy.
362
+ *
363
+ * The analysis flow:
364
+ * 1. Build prompt from scan data and state
365
+ * 2. Execute through Claude with Serena tools + fallback tools
366
+ * 3. Parse AI findings from the response
367
+ * 4. Merge with deterministic findings (wiring, composition, missing tests)
368
+ * 5. Track Serena usage in SearchMetadata
369
+ *
370
+ * @param scan - The project scan result from audit-scanner.
371
+ * @param state - Current project state.
372
+ * @param options - Audit mode options (depth, strict, etc.).
373
+ * @returns Findings array and search metadata.
374
+ */
375
+ export async function analyzeProject(scan, state, options) {
376
+ const metadata = {
377
+ serenaUsed: false,
378
+ serenaRetries: 0,
379
+ serenaErrors: [],
380
+ fallbackUsed: false,
381
+ fallbackTool: '',
382
+ searchQueries: [],
383
+ };
384
+ const prompt = buildAnalysisPrompt(scan, state, options.depth, options.strict);
385
+ metadata.searchQueries.push('audit-analysis-prompt');
386
+ // Attempt execution with Serena tools
387
+ let result;
388
+ let serenaAttempt = 0;
389
+ while (serenaAttempt <= MAX_SERENA_RETRIES) {
390
+ try {
391
+ result = await executePrompt(prompt, {
392
+ cwd: options.projectDir,
393
+ allowedTools: ALL_AUDIT_TOOLS,
394
+ permissionMode: 'bypassPermissions',
395
+ timeout: 120_000,
396
+ });
397
+ if (result.success) {
398
+ metadata.serenaUsed = true;
399
+ break;
400
+ }
401
+ // Serena failure: retry with alternate approach
402
+ metadata.serenaRetries++;
403
+ metadata.serenaErrors.push(result.error ?? 'Unknown error');
404
+ serenaAttempt++;
405
+ }
406
+ catch (err) {
407
+ metadata.serenaRetries++;
408
+ metadata.serenaErrors.push(err instanceof Error ? err.message : 'Unknown error');
409
+ serenaAttempt++;
410
+ }
411
+ }
412
+ // Fallback: use only Read/Glob/Grep if Serena failed
413
+ if (!result?.success) {
414
+ metadata.fallbackUsed = true;
415
+ metadata.fallbackTool = 'grep';
416
+ try {
417
+ result = await executePrompt(prompt, {
418
+ cwd: options.projectDir,
419
+ allowedTools: FALLBACK_TOOLS,
420
+ permissionMode: 'bypassPermissions',
421
+ timeout: 120_000,
422
+ });
423
+ }
424
+ catch {
425
+ // Complete failure — proceed with deterministic findings only
426
+ }
427
+ }
428
+ // Parse AI findings
429
+ let aiFindings = [];
430
+ if (result?.success && result.response) {
431
+ aiFindings = parseAuditFindings(result.response);
432
+ }
433
+ // Merge with deterministic findings
434
+ const deterministicFindings = generateDeterministicFindings(scan);
435
+ const allFindings = [...aiFindings, ...deterministicFindings];
436
+ return { findings: allFindings, searchMetadata: metadata };
437
+ }
438
+ //# sourceMappingURL=audit-analyzer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit-analyzer.js","sourceRoot":"","sources":["../../src/workflow/audit-analyzer.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,28 @@
1
+ /**
2
+ * Audit mode orchestrator.
3
+ *
4
+ * Coordinates the three audit stages:
5
+ * Stage 1: Scan + Summary
6
+ * Stage 2: Analyze + Report
7
+ * Stage 3: Recovery (evidence-based trigger)
8
+ *
9
+ * Pattern follows plan-mode.ts orchestration style.
10
+ */
11
+ import type { ConsensusConfig } from '../types/consensus.js';
12
+ import type { AuditModeOptions, AuditModeResult } from '../types/audit.js';
13
+ export interface AuditModeRunOptions extends AuditModeOptions {
14
+ consensusConfig?: Partial<ConsensusConfig>;
15
+ onProgress?: (stage: string, message: string) => void;
16
+ }
17
+ /**
18
+ * Run a full audit of the project.
19
+ *
20
+ * Stage 1: Scan the filesystem deterministically
21
+ * Stage 2: Analyze with AI (Serena-first + fallback)
22
+ * Stage 3: Generate recovery plan if evidence warrants it
23
+ *
24
+ * @param options - Audit configuration options.
25
+ * @returns The complete audit result.
26
+ */
27
+ export declare function runAuditMode(options: AuditModeRunOptions): Promise<AuditModeResult>;
28
+ //# sourceMappingURL=audit-mode.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit-mode.d.ts","sourceRoot":"","sources":["../../src/workflow/audit-mode.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAIH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAE7D,OAAO,KAAK,EACV,gBAAgB,EAChB,eAAe,EAEhB,MAAM,mBAAmB,CAAC;AAsB3B,MAAM,WAAW,mBAAoB,SAAQ,gBAAgB;IAC3D,eAAe,CAAC,EAAE,OAAO,CAAC,eAAe,CAAC,CAAC;IAC3C,UAAU,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,KAAK,IAAI,CAAC;CACvD;AAMD;;;;;;;;;GASG;AACH,wBAAsB,YAAY,CAAC,OAAO,EAAE,mBAAmB,GAAG,OAAO,CAAC,eAAe,CAAC,CAuHzF"}
@@ -0,0 +1,169 @@
1
+ /**
2
+ * Audit mode orchestrator.
3
+ *
4
+ * Coordinates the three audit stages:
5
+ * Stage 1: Scan + Summary
6
+ * Stage 2: Analyze + Report
7
+ * Stage 3: Recovery (evidence-based trigger)
8
+ *
9
+ * Pattern follows plan-mode.ts orchestration style.
10
+ */
11
+ import { randomUUID } from 'node:crypto';
12
+ import { loadProject, updateState } from '../state/index.js';
13
+ import { scanProject } from './audit-scanner.js';
14
+ import { analyzeProject, calculateAuditScores } from './audit-analyzer.js';
15
+ import { buildSummaryReport, buildAuditReport, writeAuditMarkdown, writeAuditJson, writeRecoveryMarkdown, writeRecoveryJson, } from './audit-reporter.js';
16
+ import { shouldTriggerRecovery, generateRecoveryPlan, recoveryToMilestones, injectRecoveryIntoState, } from './audit-recovery.js';
17
+ // ---------------------------------------------------------------------------
18
+ // Orchestrator
19
+ // ---------------------------------------------------------------------------
20
+ /**
21
+ * Run a full audit of the project.
22
+ *
23
+ * Stage 1: Scan the filesystem deterministically
24
+ * Stage 2: Analyze with AI (Serena-first + fallback)
25
+ * Stage 3: Generate recovery plan if evidence warrants it
26
+ *
27
+ * @param options - Audit configuration options.
28
+ * @returns The complete audit result.
29
+ */
30
+ export async function runAuditMode(options) {
31
+ const { projectDir, onProgress } = options;
32
+ const depth = options.depth ?? 2;
33
+ const strict = options.strict ?? false;
34
+ const format = options.format ?? 'both';
35
+ const autoRecover = options.autoRecover ?? true;
36
+ const auditRunId = randomUUID();
37
+ let state;
38
+ try {
39
+ state = await loadProject(projectDir);
40
+ }
41
+ catch (err) {
42
+ const errorMsg = err instanceof Error ? err.message : 'Failed to load project';
43
+ return makeErrorResult(errorMsg);
44
+ }
45
+ // -----------------------------------------------------------------------
46
+ // Stage 1: Scan + Summary
47
+ // -----------------------------------------------------------------------
48
+ onProgress?.('stage-1', 'Starting project scan...');
49
+ const scan = await scanProject(projectDir, state.language, (msg) => onProgress?.('stage-1', msg));
50
+ const summary = buildSummaryReport(scan, state);
51
+ onProgress?.('stage-1', `Scan complete: ${scan.totalSourceFiles} source files, ${scan.totalLinesOfCode} LOC, ${scan.components.length} component(s)`);
52
+ // -----------------------------------------------------------------------
53
+ // Stage 2: Analyze + Report
54
+ // -----------------------------------------------------------------------
55
+ onProgress?.('stage-2', 'Starting AI analysis...');
56
+ const { findings, searchMetadata } = await analyzeProject(scan, state, {
57
+ depth,
58
+ strict,
59
+ projectDir,
60
+ });
61
+ const scores = calculateAuditScores(findings, scan);
62
+ const auditReport = buildAuditReport(summary, findings, scores, searchMetadata, { strict }, auditRunId);
63
+ // Write report artifacts
64
+ const reportPaths = {};
65
+ if (format === 'md' || format === 'both') {
66
+ reportPaths.auditMd = await writeAuditMarkdown(projectDir, auditReport);
67
+ }
68
+ if (format === 'json' || format === 'both') {
69
+ reportPaths.auditJson = await writeAuditJson(projectDir, auditReport);
70
+ }
71
+ // Update state with audit report path
72
+ await updateState(projectDir, {
73
+ auditReportPath: reportPaths.auditJson ?? reportPaths.auditMd,
74
+ auditLastRunAt: new Date().toISOString(),
75
+ auditRunId,
76
+ });
77
+ onProgress?.('stage-2', `Analysis complete: score ${scores.overallScore}%, ${findings.length} findings (serena: ${searchMetadata.serenaUsed ? 'used' : 'fallback'})`);
78
+ // -----------------------------------------------------------------------
79
+ // Stage 3: Recovery (evidence-based trigger)
80
+ // -----------------------------------------------------------------------
81
+ let recovery;
82
+ if (shouldTriggerRecovery(auditReport, strict)) {
83
+ onProgress?.('stage-3', 'Generating recovery plan...');
84
+ recovery = generateRecoveryPlan(auditReport);
85
+ // Write recovery artifacts
86
+ if (format === 'md' || format === 'both') {
87
+ reportPaths.recoveryMd = await writeRecoveryMarkdown(projectDir, recovery);
88
+ }
89
+ if (format === 'json' || format === 'both') {
90
+ reportPaths.recoveryJson = await writeRecoveryJson(projectDir, recovery);
91
+ }
92
+ // Auto-recover: inject milestones and switch to execution
93
+ if (autoRecover && recovery.milestones.length > 0) {
94
+ onProgress?.('stage-3', 'Injecting recovery milestones...');
95
+ const milestones = recoveryToMilestones(recovery, state.language);
96
+ await injectRecoveryIntoState(projectDir, milestones, auditRunId);
97
+ onProgress?.('stage-3', `Injected ${milestones.length} recovery milestone(s) — ready for execution`);
98
+ }
99
+ onProgress?.('stage-3', `Recovery plan: ${recovery.milestones.length} milestone(s), estimated ${recovery.estimatedEffort}`);
100
+ }
101
+ else {
102
+ onProgress?.('stage-3', 'No recovery needed based on findings.');
103
+ }
104
+ return {
105
+ success: true,
106
+ summary,
107
+ audit: auditReport,
108
+ recovery,
109
+ reportPaths,
110
+ };
111
+ }
112
+ // ---------------------------------------------------------------------------
113
+ // Helpers
114
+ // ---------------------------------------------------------------------------
115
+ /**
116
+ * Create an error result with minimal valid structure.
117
+ *
118
+ * @param error - Error message.
119
+ * @returns An AuditModeResult indicating failure.
120
+ */
121
+ function makeErrorResult(error) {
122
+ const emptySummary = {
123
+ projectName: 'unknown',
124
+ language: 'unknown',
125
+ totalSourceFiles: 0,
126
+ totalTestFiles: 0,
127
+ totalLinesOfCode: 0,
128
+ totalLinesOfTests: 0,
129
+ componentCount: 0,
130
+ detectedComposition: [],
131
+ entryPointCount: 0,
132
+ routeCount: 0,
133
+ dependencyCount: 0,
134
+ hasDocker: false,
135
+ hasEnvExample: false,
136
+ hasCiConfig: false,
137
+ };
138
+ return {
139
+ success: false,
140
+ summary: emptySummary,
141
+ audit: {
142
+ projectName: 'unknown',
143
+ language: 'unknown',
144
+ auditedAt: new Date().toISOString(),
145
+ auditRunId: 'error',
146
+ summary: emptySummary,
147
+ findings: [],
148
+ overallScore: 0,
149
+ categoryScores: {},
150
+ criticalCount: 0,
151
+ majorCount: 0,
152
+ minorCount: 0,
153
+ infoCount: 0,
154
+ passedChecks: [],
155
+ searchMetadata: {
156
+ serenaUsed: false,
157
+ serenaRetries: 0,
158
+ serenaErrors: [],
159
+ fallbackUsed: false,
160
+ fallbackTool: '',
161
+ searchQueries: [],
162
+ },
163
+ recommendation: 'major-rework',
164
+ },
165
+ reportPaths: {},
166
+ error,
167
+ };
168
+ }
169
+ //# sourceMappingURL=audit-mode.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit-mode.js","sourceRoot":"","sources":["../../src/workflow/audit-mode.ts"],"names":[],"mappings":"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"}