@vibecheckai/cli 3.5.0 → 3.5.2

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 (224) hide show
  1. package/bin/registry.js +214 -237
  2. package/bin/runners/cli-utils.js +33 -2
  3. package/bin/runners/context/analyzer.js +52 -1
  4. package/bin/runners/context/generators/cursor.js +2 -49
  5. package/bin/runners/context/git-context.js +3 -1
  6. package/bin/runners/context/team-conventions.js +33 -7
  7. package/bin/runners/lib/analysis-core.js +25 -5
  8. package/bin/runners/lib/analyzers.js +431 -481
  9. package/bin/runners/lib/default-config.js +127 -0
  10. package/bin/runners/lib/doctor/modules/security.js +3 -1
  11. package/bin/runners/lib/engine/ast-cache.js +210 -0
  12. package/bin/runners/lib/engine/auth-extractor.js +211 -0
  13. package/bin/runners/lib/engine/billing-extractor.js +112 -0
  14. package/bin/runners/lib/engine/enforcement-extractor.js +100 -0
  15. package/bin/runners/lib/engine/env-extractor.js +207 -0
  16. package/bin/runners/lib/engine/express-extractor.js +208 -0
  17. package/bin/runners/lib/engine/extractors.js +849 -0
  18. package/bin/runners/lib/engine/index.js +207 -0
  19. package/bin/runners/lib/engine/repo-index.js +514 -0
  20. package/bin/runners/lib/engine/types.js +124 -0
  21. package/bin/runners/lib/engines/accessibility-engine.js +18 -218
  22. package/bin/runners/lib/engines/api-consistency-engine.js +30 -335
  23. package/bin/runners/lib/engines/cross-file-analysis-engine.js +27 -292
  24. package/bin/runners/lib/engines/empty-catch-engine.js +17 -127
  25. package/bin/runners/lib/engines/mock-data-engine.js +10 -53
  26. package/bin/runners/lib/engines/performance-issues-engine.js +36 -176
  27. package/bin/runners/lib/engines/security-vulnerabilities-engine.js +54 -382
  28. package/bin/runners/lib/engines/type-aware-engine.js +39 -263
  29. package/bin/runners/lib/engines/vibecheck-engines/index.js +13 -122
  30. package/bin/runners/lib/engines/vibecheck-engines/lib/ast-cache.js +164 -0
  31. package/bin/runners/lib/engines/vibecheck-engines/lib/code-quality-engine.js +291 -0
  32. package/bin/runners/lib/engines/vibecheck-engines/lib/console-logs-engine.js +83 -0
  33. package/bin/runners/lib/engines/vibecheck-engines/lib/dead-code-engine.js +198 -0
  34. package/bin/runners/lib/engines/vibecheck-engines/lib/deprecated-api-engine.js +275 -0
  35. package/bin/runners/lib/engines/vibecheck-engines/lib/empty-catch-engine.js +167 -0
  36. package/bin/runners/lib/engines/vibecheck-engines/lib/file-filter.js +217 -0
  37. package/bin/runners/lib/engines/vibecheck-engines/lib/hardcoded-secrets-engine.js +73 -373
  38. package/bin/runners/lib/engines/vibecheck-engines/lib/mock-data-engine.js +140 -0
  39. package/bin/runners/lib/engines/vibecheck-engines/lib/parallel-processor.js +164 -0
  40. package/bin/runners/lib/engines/vibecheck-engines/lib/performance-issues-engine.js +234 -0
  41. package/bin/runners/lib/engines/vibecheck-engines/lib/type-aware-engine.js +217 -0
  42. package/bin/runners/lib/engines/vibecheck-engines/lib/unsafe-regex-engine.js +78 -0
  43. package/bin/runners/lib/entitlements-v2.js +73 -97
  44. package/bin/runners/lib/error-handler.js +44 -3
  45. package/bin/runners/lib/error-messages.js +289 -0
  46. package/bin/runners/lib/evidence-pack.js +7 -1
  47. package/bin/runners/lib/finding-id.js +69 -0
  48. package/bin/runners/lib/finding-sorter.js +89 -0
  49. package/bin/runners/lib/html-proof-report.js +700 -350
  50. package/bin/runners/lib/missions/plan.js +6 -46
  51. package/bin/runners/lib/missions/templates.js +0 -232
  52. package/bin/runners/lib/next-action.js +560 -0
  53. package/bin/runners/lib/prerequisites.js +149 -0
  54. package/bin/runners/lib/route-detection.js +137 -68
  55. package/bin/runners/lib/scan-output.js +91 -76
  56. package/bin/runners/lib/scan-runner.js +135 -0
  57. package/bin/runners/lib/schemas/ajv-validator.js +464 -0
  58. package/bin/runners/lib/schemas/error-envelope.schema.json +105 -0
  59. package/bin/runners/lib/schemas/finding-v3.schema.json +151 -0
  60. package/bin/runners/lib/schemas/report-artifact.schema.json +120 -0
  61. package/bin/runners/lib/schemas/run-request.schema.json +108 -0
  62. package/bin/runners/lib/schemas/validator.js +27 -0
  63. package/bin/runners/lib/schemas/verdict.schema.json +140 -0
  64. package/bin/runners/lib/ship-output-enterprise.js +23 -23
  65. package/bin/runners/lib/ship-output.js +75 -31
  66. package/bin/runners/lib/terminal-ui.js +6 -113
  67. package/bin/runners/lib/truth.js +351 -10
  68. package/bin/runners/lib/unified-cli-output.js +430 -603
  69. package/bin/runners/lib/unified-output.js +13 -9
  70. package/bin/runners/runAIAgent.js +10 -5
  71. package/bin/runners/runAgent.js +0 -3
  72. package/bin/runners/runAllowlist.js +389 -0
  73. package/bin/runners/runApprove.js +0 -33
  74. package/bin/runners/runAuth.js +73 -45
  75. package/bin/runners/runCheckpoint.js +51 -11
  76. package/bin/runners/runClassify.js +85 -21
  77. package/bin/runners/runContext.js +0 -3
  78. package/bin/runners/runDoctor.js +41 -28
  79. package/bin/runners/runEvidencePack.js +362 -0
  80. package/bin/runners/runFirewall.js +0 -3
  81. package/bin/runners/runFirewallHook.js +0 -3
  82. package/bin/runners/runFix.js +66 -76
  83. package/bin/runners/runGuard.js +18 -411
  84. package/bin/runners/runInit.js +113 -30
  85. package/bin/runners/runLabs.js +424 -0
  86. package/bin/runners/runMcp.js +19 -25
  87. package/bin/runners/runPolish.js +64 -240
  88. package/bin/runners/runPromptFirewall.js +12 -5
  89. package/bin/runners/runProve.js +57 -22
  90. package/bin/runners/runQuickstart.js +531 -0
  91. package/bin/runners/runReality.js +59 -68
  92. package/bin/runners/runReport.js +38 -33
  93. package/bin/runners/runRuntime.js +8 -5
  94. package/bin/runners/runScan.js +1413 -190
  95. package/bin/runners/runShip.js +113 -719
  96. package/bin/runners/runTruth.js +0 -3
  97. package/bin/runners/runValidate.js +13 -9
  98. package/bin/runners/runWatch.js +23 -14
  99. package/bin/scan.js +6 -1
  100. package/bin/vibecheck.js +204 -185
  101. package/mcp-server/deprecation-middleware.js +282 -0
  102. package/mcp-server/handlers/index.ts +15 -0
  103. package/mcp-server/handlers/tool-handler.ts +554 -0
  104. package/mcp-server/index-v1.js +698 -0
  105. package/mcp-server/index.js +210 -238
  106. package/mcp-server/lib/cache-wrapper.cjs +383 -0
  107. package/mcp-server/lib/error-envelope.js +138 -0
  108. package/mcp-server/lib/executor.ts +499 -0
  109. package/mcp-server/lib/index.ts +19 -0
  110. package/mcp-server/lib/rate-limiter.js +166 -0
  111. package/mcp-server/lib/sandbox.test.ts +519 -0
  112. package/mcp-server/lib/sandbox.ts +395 -0
  113. package/mcp-server/lib/types.ts +267 -0
  114. package/mcp-server/package.json +12 -3
  115. package/mcp-server/registry/tool-registry.js +794 -0
  116. package/mcp-server/registry/tools.json +605 -0
  117. package/mcp-server/registry.test.ts +334 -0
  118. package/mcp-server/tests/tier-gating.test.js +297 -0
  119. package/mcp-server/tier-auth.js +378 -45
  120. package/mcp-server/tools-v3.js +353 -442
  121. package/mcp-server/tsconfig.json +37 -0
  122. package/mcp-server/vibecheck-2.0-tools.js +14 -1
  123. package/package.json +1 -1
  124. package/bin/runners/lib/agent-firewall/learning/learning-engine.js +0 -849
  125. package/bin/runners/lib/audit-logger.js +0 -532
  126. package/bin/runners/lib/authority/authorities/architecture.js +0 -364
  127. package/bin/runners/lib/authority/authorities/compliance.js +0 -341
  128. package/bin/runners/lib/authority/authorities/human.js +0 -343
  129. package/bin/runners/lib/authority/authorities/quality.js +0 -420
  130. package/bin/runners/lib/authority/authorities/security.js +0 -228
  131. package/bin/runners/lib/authority/index.js +0 -293
  132. package/bin/runners/lib/bundle/bundle-intelligence.js +0 -846
  133. package/bin/runners/lib/cli-charts.js +0 -368
  134. package/bin/runners/lib/cli-config-display.js +0 -405
  135. package/bin/runners/lib/cli-demo.js +0 -275
  136. package/bin/runners/lib/cli-errors.js +0 -438
  137. package/bin/runners/lib/cli-help-formatter.js +0 -439
  138. package/bin/runners/lib/cli-interactive-menu.js +0 -509
  139. package/bin/runners/lib/cli-prompts.js +0 -441
  140. package/bin/runners/lib/cli-scan-cards.js +0 -362
  141. package/bin/runners/lib/compliance-reporter.js +0 -710
  142. package/bin/runners/lib/conductor/index.js +0 -671
  143. package/bin/runners/lib/easy/README.md +0 -123
  144. package/bin/runners/lib/easy/index.js +0 -140
  145. package/bin/runners/lib/easy/interactive-wizard.js +0 -788
  146. package/bin/runners/lib/easy/one-click-firewall.js +0 -564
  147. package/bin/runners/lib/easy/zero-config-reality.js +0 -714
  148. package/bin/runners/lib/engines/async-patterns-engine.js +0 -444
  149. package/bin/runners/lib/engines/bundle-size-engine.js +0 -433
  150. package/bin/runners/lib/engines/confidence-scoring.js +0 -276
  151. package/bin/runners/lib/engines/context-detection.js +0 -264
  152. package/bin/runners/lib/engines/database-patterns-engine.js +0 -429
  153. package/bin/runners/lib/engines/duplicate-code-engine.js +0 -354
  154. package/bin/runners/lib/engines/env-variables-engine.js +0 -458
  155. package/bin/runners/lib/engines/error-handling-engine.js +0 -437
  156. package/bin/runners/lib/engines/false-positive-prevention.js +0 -630
  157. package/bin/runners/lib/engines/framework-adapters/index.js +0 -607
  158. package/bin/runners/lib/engines/framework-detection.js +0 -508
  159. package/bin/runners/lib/engines/import-order-engine.js +0 -429
  160. package/bin/runners/lib/engines/naming-conventions-engine.js +0 -544
  161. package/bin/runners/lib/engines/noise-reduction-engine.js +0 -452
  162. package/bin/runners/lib/engines/orchestrator.js +0 -334
  163. package/bin/runners/lib/engines/react-patterns-engine.js +0 -457
  164. package/bin/runners/lib/engines/vibecheck-engines/lib/ai-hallucination-engine.js +0 -806
  165. package/bin/runners/lib/engines/vibecheck-engines/lib/smart-fix-engine.js +0 -577
  166. package/bin/runners/lib/engines/vibecheck-engines/lib/vibe-score-engine.js +0 -543
  167. package/bin/runners/lib/engines/vibecheck-engines.js +0 -514
  168. package/bin/runners/lib/enhanced-features/index.js +0 -305
  169. package/bin/runners/lib/enhanced-output.js +0 -631
  170. package/bin/runners/lib/enterprise.js +0 -300
  171. package/bin/runners/lib/firewall/command-validator.js +0 -351
  172. package/bin/runners/lib/firewall/config.js +0 -341
  173. package/bin/runners/lib/firewall/content-validator.js +0 -519
  174. package/bin/runners/lib/firewall/index.js +0 -101
  175. package/bin/runners/lib/firewall/path-validator.js +0 -256
  176. package/bin/runners/lib/intelligence/cross-repo-intelligence.js +0 -817
  177. package/bin/runners/lib/mcp-utils.js +0 -425
  178. package/bin/runners/lib/output/index.js +0 -1022
  179. package/bin/runners/lib/policy-engine.js +0 -652
  180. package/bin/runners/lib/polish/autofix/accessibility-fixes.js +0 -333
  181. package/bin/runners/lib/polish/autofix/async-handlers.js +0 -273
  182. package/bin/runners/lib/polish/autofix/dead-code.js +0 -280
  183. package/bin/runners/lib/polish/autofix/imports-optimizer.js +0 -344
  184. package/bin/runners/lib/polish/autofix/index.js +0 -200
  185. package/bin/runners/lib/polish/autofix/remove-consoles.js +0 -209
  186. package/bin/runners/lib/polish/autofix/strengthen-types.js +0 -245
  187. package/bin/runners/lib/polish/backend-checks.js +0 -148
  188. package/bin/runners/lib/polish/documentation-checks.js +0 -111
  189. package/bin/runners/lib/polish/frontend-checks.js +0 -168
  190. package/bin/runners/lib/polish/index.js +0 -71
  191. package/bin/runners/lib/polish/infrastructure-checks.js +0 -131
  192. package/bin/runners/lib/polish/library-detection.js +0 -175
  193. package/bin/runners/lib/polish/performance-checks.js +0 -100
  194. package/bin/runners/lib/polish/security-checks.js +0 -148
  195. package/bin/runners/lib/polish/utils.js +0 -203
  196. package/bin/runners/lib/prompt-builder.js +0 -540
  197. package/bin/runners/lib/proof-certificate.js +0 -634
  198. package/bin/runners/lib/reality/accessibility-audit.js +0 -946
  199. package/bin/runners/lib/reality/api-contract-validator.js +0 -1012
  200. package/bin/runners/lib/reality/chaos-engineering.js +0 -1084
  201. package/bin/runners/lib/reality/performance-tracker.js +0 -1077
  202. package/bin/runners/lib/reality/scenario-generator.js +0 -1404
  203. package/bin/runners/lib/reality/visual-regression.js +0 -852
  204. package/bin/runners/lib/reality-profiler.js +0 -717
  205. package/bin/runners/lib/replay/flight-recorder-viewer.js +0 -1160
  206. package/bin/runners/lib/review/ai-code-review.js +0 -832
  207. package/bin/runners/lib/rules/custom-rule-engine.js +0 -985
  208. package/bin/runners/lib/sbom-generator.js +0 -641
  209. package/bin/runners/lib/scan-output-enhanced.js +0 -512
  210. package/bin/runners/lib/security/owasp-scanner.js +0 -939
  211. package/bin/runners/lib/validators/contract-validator.js +0 -283
  212. package/bin/runners/lib/validators/dead-export-detector.js +0 -279
  213. package/bin/runners/lib/validators/dep-audit.js +0 -245
  214. package/bin/runners/lib/validators/env-validator.js +0 -319
  215. package/bin/runners/lib/validators/index.js +0 -120
  216. package/bin/runners/lib/validators/license-checker.js +0 -252
  217. package/bin/runners/lib/validators/route-validator.js +0 -290
  218. package/bin/runners/runAuthority.js +0 -528
  219. package/bin/runners/runConductor.js +0 -772
  220. package/bin/runners/runContainer.js +0 -366
  221. package/bin/runners/runEasy.js +0 -410
  222. package/bin/runners/runIaC.js +0 -372
  223. package/bin/runners/runVibe.js +0 -791
  224. package/mcp-server/tools.js +0 -495
@@ -1,577 +0,0 @@
1
- /**
2
- * Smart Fix Suggestions Engine
3
- *
4
- * AI-powered fix recommendations with confidence scoring.
5
- * Generates actionable, context-aware fix suggestions for vibecheck findings.
6
- *
7
- * Features:
8
- * - Context-aware fix generation based on surrounding code
9
- * - Framework-specific fixes (React, Next.js, Express, etc.)
10
- * - Confidence scoring for each suggestion
11
- * - Auto-applicable fixes vs manual review required
12
- * - Code snippets for common patterns
13
- *
14
- * @module smart-fix-engine
15
- */
16
-
17
- "use strict";
18
-
19
- const path = require("path");
20
- const fs = require("fs");
21
-
22
- // ═══════════════════════════════════════════════════════════════════════════════
23
- // FIX TEMPLATES - Common fix patterns for different issue types
24
- // ═══════════════════════════════════════════════════════════════════════════════
25
-
26
- const FIX_TEMPLATES = {
27
- // ═══════════════════════════════════════════════════════════════════════════
28
- // FAKE SUCCESS FIXES
29
- // ═══════════════════════════════════════════════════════════════════════════
30
- "fake-success": {
31
- patterns: [
32
- {
33
- match: /return\s*{\s*success:\s*true\s*}/,
34
- replace: `// TODO: Implement actual logic before returning success
35
- const result = await performActualOperation();
36
- if (!result.ok) {
37
- return { success: false, error: result.error };
38
- }
39
- return { success: true, data: result.data };`,
40
- confidence: 0.85,
41
- autoApplicable: false,
42
- message: "Replace hardcoded success with actual operation result",
43
- },
44
- ],
45
- manualSteps: [
46
- "Identify what operation this function should perform",
47
- "Implement the actual business logic",
48
- "Add error handling for failure cases",
49
- "Return success only after verifying the operation completed",
50
- ],
51
- },
52
-
53
- // ═══════════════════════════════════════════════════════════════════════════
54
- // EMPTY CATCH FIXES
55
- // ═══════════════════════════════════════════════════════════════════════════
56
- "empty-catch": {
57
- patterns: [
58
- {
59
- match: /catch\s*\(\s*(?:e|err|error|_)?\s*\)\s*{\s*}/,
60
- replace: `catch (error) {
61
- console.error('Operation failed:', error);
62
- throw error; // Re-throw to let caller handle
63
- }`,
64
- confidence: 0.90,
65
- autoApplicable: true,
66
- message: "Add proper error handling - log and rethrow",
67
- },
68
- {
69
- // Catch with only console.log
70
- match: /catch\s*\(\s*(\w+)\s*\)\s*{\s*console\.log\([^)]+\)\s*;?\s*}/,
71
- replace: (match, varName) => `catch (${varName}) {
72
- console.error('Operation failed:', ${varName});
73
- // Choose one:
74
- // throw ${varName}; // Re-throw for caller to handle
75
- // return { success: false, error: ${varName}.message }; // Return error response
76
- }`,
77
- confidence: 0.85,
78
- autoApplicable: false,
79
- message: "Improve error handling beyond just logging",
80
- },
81
- ],
82
- manualSteps: [
83
- "Decide how this error should be handled in context",
84
- "Either: rethrow the error for upstream handling",
85
- "Or: return an error response to the caller",
86
- "Or: implement recovery/retry logic if appropriate",
87
- "Consider adding error reporting to a monitoring service",
88
- ],
89
- },
90
-
91
- // ═══════════════════════════════════════════════════════════════════════════
92
- // PLACEHOLDER DATA FIXES
93
- // ═══════════════════════════════════════════════════════════════════════════
94
- "placeholder-data": {
95
- patterns: [
96
- {
97
- // Placeholder UUID
98
- match: /["'](?:12345678-1234-1234-1234-123456789012|00000000-0000-0000-0000-000000000000)["']/,
99
- replace: `crypto.randomUUID() // Generate real UUID`,
100
- confidence: 0.95,
101
- autoApplicable: false,
102
- message: "Replace placeholder UUID with dynamically generated one",
103
- },
104
- {
105
- // Placeholder email
106
- match: /["'](?:test@test\.com|user@example\.com)["']/i,
107
- replace: `process.env.USER_EMAIL || throw new Error('USER_EMAIL not set')`,
108
- confidence: 0.75,
109
- autoApplicable: false,
110
- message: "Replace placeholder email with environment variable or actual user data",
111
- },
112
- ],
113
- manualSteps: [
114
- "Identify where this data should come from (database, user input, env var)",
115
- "Replace the hardcoded value with dynamic data",
116
- "Add validation for the data source",
117
- "Update tests to use proper test fixtures",
118
- ],
119
- },
120
-
121
- // ═══════════════════════════════════════════════════════════════════════════
122
- // PLACEHOLDER API URL FIXES
123
- // ═══════════════════════════════════════════════════════════════════════════
124
- "placeholder-api": {
125
- patterns: [
126
- {
127
- match: /fetch\s*\(\s*["']https?:\/\/(?:example\.com|api\.example|your-api|my-api)/i,
128
- replace: `fetch(process.env.API_URL + '/endpoint')`,
129
- confidence: 0.90,
130
- autoApplicable: false,
131
- message: "Use environment variable for API URL",
132
- },
133
- ],
134
- manualSteps: [
135
- "Add API_URL to your .env file with the real endpoint",
136
- "Update all fetch calls to use the environment variable",
137
- "Add API_URL to .env.example for documentation",
138
- "Verify the endpoint exists and is accessible",
139
- ],
140
- },
141
-
142
- // ═══════════════════════════════════════════════════════════════════════════
143
- // STUB IMPLEMENTATION FIXES
144
- // ═══════════════════════════════════════════════════════════════════════════
145
- "stub-implementation": {
146
- patterns: [
147
- {
148
- match: /{\s*throw\s+(?:new\s+Error\()?["'](?:not\s+implemented|TODO|NYI)/i,
149
- replace: `{
150
- // TODO: Implement this function
151
- // 1. Validate inputs
152
- // 2. Perform the operation
153
- // 3. Return the result
154
- throw new Error('Not implemented - remove this after implementing');
155
- }`,
156
- confidence: 0.80,
157
- autoApplicable: false,
158
- message: "Implement the function logic",
159
- },
160
- ],
161
- manualSteps: [
162
- "Review the function signature and docstring to understand what it should do",
163
- "Implement the actual business logic",
164
- "Add input validation",
165
- "Add proper error handling",
166
- "Write tests to verify the implementation",
167
- "Remove any 'not implemented' throws",
168
- ],
169
- },
170
-
171
- // ═══════════════════════════════════════════════════════════════════════════
172
- // HARDCODED SECRET FIXES
173
- // ═══════════════════════════════════════════════════════════════════════════
174
- "hardcoded-secret": {
175
- patterns: [
176
- {
177
- match: /(?:api[_-]?key|apiKey|API_KEY)\s*[=:]\s*["']([^"']+)["']/i,
178
- replace: `apiKey: process.env.API_KEY || throw new Error('API_KEY not configured')`,
179
- confidence: 0.95,
180
- autoApplicable: false,
181
- message: "Move secret to environment variable",
182
- },
183
- ],
184
- manualSteps: [
185
- "Add the secret to your .env file (never commit this)",
186
- "Add the variable name (without value) to .env.example",
187
- "Update code to read from process.env",
188
- "Add validation to ensure the env var is set",
189
- "Consider using a secrets manager in production",
190
- "IMPORTANT: If this was committed, rotate the secret immediately",
191
- ],
192
- },
193
-
194
- // ═══════════════════════════════════════════════════════════════════════════
195
- // ASYNC WITHOUT AWAIT FIXES
196
- // ═══════════════════════════════════════════════════════════════════════════
197
- "async-without-await": {
198
- patterns: [
199
- {
200
- match: /async\s+(?:function\s+)?(\w+)\s*\([^)]*\)\s*{/,
201
- replace: (match, funcName) => `// If this function doesn't need to be async, remove 'async':
202
- function ${funcName}(`,
203
- confidence: 0.60,
204
- autoApplicable: false,
205
- message: "Either add await calls or remove async keyword",
206
- },
207
- ],
208
- manualSteps: [
209
- "Check if this function actually needs to be async",
210
- "If yes: add await for async operations inside",
211
- "If no: remove the async keyword to avoid confusion",
212
- "Async functions always return Promises - make sure callers expect this",
213
- ],
214
- },
215
-
216
- // ═══════════════════════════════════════════════════════════════════════════
217
- // CONSOLE.LOG IN PRODUCTION FIXES
218
- // ═══════════════════════════════════════════════════════════════════════════
219
- "console-log": {
220
- patterns: [
221
- {
222
- match: /console\.log\s*\(/,
223
- replace: `// Use a proper logger instead:
224
- logger.debug(`,
225
- confidence: 0.70,
226
- autoApplicable: false,
227
- message: "Replace console.log with proper logger",
228
- },
229
- ],
230
- manualSteps: [
231
- "Set up a proper logging library (pino, winston, etc.)",
232
- "Replace console.log with logger.debug or logger.info",
233
- "Configure log levels for different environments",
234
- "Remove or downgrade debug logs before shipping",
235
- ],
236
- },
237
- };
238
-
239
- // ═══════════════════════════════════════════════════════════════════════════════
240
- // FRAMEWORK-SPECIFIC FIXES
241
- // ═══════════════════════════════════════════════════════════════════════════════
242
-
243
- const FRAMEWORK_FIXES = {
244
- nextjs: {
245
- "api-handler-error": {
246
- patterns: [
247
- {
248
- match: /export\s+(?:default\s+)?(?:async\s+)?function\s+handler/,
249
- fix: `export default async function handler(req, res) {
250
- try {
251
- // Your logic here
252
- return res.status(200).json({ success: true, data: result });
253
- } catch (error) {
254
- console.error('API Error:', error);
255
- return res.status(500).json({ success: false, error: error.message });
256
- }
257
- }`,
258
- message: "Next.js API handler should have try-catch",
259
- },
260
- ],
261
- },
262
- },
263
-
264
- react: {
265
- "missing-error-boundary": {
266
- patterns: [
267
- {
268
- message: "Wrap components with ErrorBoundary for better error handling",
269
- fix: `import { ErrorBoundary } from 'react-error-boundary';
270
-
271
- function ErrorFallback({error}) {
272
- return <div role="alert">Something went wrong: {error.message}</div>
273
- }
274
-
275
- // Wrap your component:
276
- <ErrorBoundary FallbackComponent={ErrorFallback}>
277
- <YourComponent />
278
- </ErrorBoundary>`,
279
- },
280
- ],
281
- },
282
- },
283
-
284
- express: {
285
- "missing-error-middleware": {
286
- patterns: [
287
- {
288
- message: "Add error handling middleware",
289
- fix: `// Add at the end of your routes:
290
- app.use((err, req, res, next) => {
291
- console.error('Server Error:', err);
292
- res.status(err.status || 500).json({
293
- success: false,
294
- error: process.env.NODE_ENV === 'production'
295
- ? 'Internal server error'
296
- : err.message
297
- });
298
- });`,
299
- },
300
- ],
301
- },
302
- },
303
- };
304
-
305
- // ═══════════════════════════════════════════════════════════════════════════════
306
- // SMART FIX GENERATOR
307
- // ═══════════════════════════════════════════════════════════════════════════════
308
-
309
- /**
310
- * Generate smart fix suggestions for a finding
311
- * @param {object} finding - The finding to generate fixes for
312
- * @param {object} context - Context about the file and project
313
- * @returns {object} Fix suggestions with confidence
314
- */
315
- function generateFixSuggestions(finding, context = {}) {
316
- const {
317
- fileContent = "",
318
- filePath = "",
319
- framework = null,
320
- projectType = null,
321
- } = context;
322
-
323
- const suggestions = [];
324
-
325
- // Get template for finding type
326
- const findingType = normalizeFindingType(finding.type || finding.category);
327
- const template = FIX_TEMPLATES[findingType];
328
-
329
- if (template) {
330
- // Generate pattern-based fixes
331
- for (const pattern of template.patterns) {
332
- const match = fileContent.match(pattern.match);
333
-
334
- if (match) {
335
- let replacement = pattern.replace;
336
-
337
- // If replace is a function, call it with match groups
338
- if (typeof replacement === "function") {
339
- replacement = replacement(match[0], ...match.slice(1));
340
- }
341
-
342
- suggestions.push({
343
- type: "code-fix",
344
- confidence: pattern.confidence,
345
- autoApplicable: pattern.autoApplicable,
346
- message: pattern.message,
347
- original: match[0],
348
- replacement,
349
- location: {
350
- file: filePath,
351
- line: finding.line,
352
- matchIndex: match.index,
353
- },
354
- });
355
- }
356
- }
357
-
358
- // Add manual steps
359
- if (template.manualSteps) {
360
- suggestions.push({
361
- type: "manual-steps",
362
- confidence: 0.95,
363
- autoApplicable: false,
364
- message: "Manual fix steps",
365
- steps: template.manualSteps,
366
- });
367
- }
368
- }
369
-
370
- // Add framework-specific fixes
371
- if (framework && FRAMEWORK_FIXES[framework]) {
372
- const frameworkFixes = FRAMEWORK_FIXES[framework];
373
-
374
- for (const [fixType, fixData] of Object.entries(frameworkFixes)) {
375
- // Check if this fix is relevant
376
- if (isFixRelevant(finding, fixType)) {
377
- for (const pattern of fixData.patterns) {
378
- suggestions.push({
379
- type: "framework-fix",
380
- framework,
381
- confidence: 0.75,
382
- autoApplicable: false,
383
- message: pattern.message,
384
- codeExample: pattern.fix,
385
- });
386
- }
387
- }
388
- }
389
- }
390
-
391
- // Add general best practice suggestions
392
- suggestions.push(...generateBestPracticeSuggestions(finding, context));
393
-
394
- // Sort by confidence
395
- suggestions.sort((a, b) => b.confidence - a.confidence);
396
-
397
- return {
398
- finding: finding.id || finding.type,
399
- fixCount: suggestions.length,
400
- hasAutoFix: suggestions.some(s => s.autoApplicable),
401
- suggestions: suggestions.slice(0, 5), // Top 5 suggestions
402
- priority: calculateFixPriority(finding, suggestions),
403
- };
404
- }
405
-
406
- /**
407
- * Normalize finding type to match template keys
408
- */
409
- function normalizeFindingType(type) {
410
- const typeMap = {
411
- "hardcoded-success-object": "fake-success",
412
- "async-fake-success": "fake-success",
413
- "api-fake-success": "fake-success",
414
- "catch-returns-success": "empty-catch",
415
- "catch-log-only": "empty-catch",
416
- "catch-todo-comment": "empty-catch",
417
- "empty-catch": "empty-catch",
418
- "swallowed-errors": "empty-catch",
419
- "placeholder-uuid": "placeholder-data",
420
- "placeholder-email": "placeholder-data",
421
- "fetch-example-url": "placeholder-api",
422
- "placeholder-api-url": "placeholder-api",
423
- "throws-not-implemented": "stub-implementation",
424
- "comment-only-function": "stub-implementation",
425
- "placeholder-api-key": "hardcoded-secret",
426
- "HardcodedSecret": "hardcoded-secret",
427
- "async-without-await": "async-without-await",
428
- "ConsoleLog": "console-log",
429
- };
430
-
431
- return typeMap[type] || type?.toLowerCase().replace(/_/g, "-");
432
- }
433
-
434
- /**
435
- * Check if a framework fix is relevant for a finding
436
- */
437
- function isFixRelevant(finding, fixType) {
438
- const relevanceMap = {
439
- "api-handler-error": ["fake-success", "empty-catch", "FakeSuccess"],
440
- "missing-error-boundary": ["empty-catch", "swallowed-errors"],
441
- "missing-error-middleware": ["empty-catch", "silent-failure"],
442
- };
443
-
444
- const relevantTypes = relevanceMap[fixType] || [];
445
- return relevantTypes.some(t =>
446
- finding.type?.includes(t) || finding.category?.includes(t)
447
- );
448
- }
449
-
450
- /**
451
- * Generate best practice suggestions
452
- */
453
- function generateBestPracticeSuggestions(finding, context) {
454
- const suggestions = [];
455
-
456
- // Error handling best practices
457
- if (finding.category?.includes("Error") || finding.type?.includes("catch")) {
458
- suggestions.push({
459
- type: "best-practice",
460
- confidence: 0.80,
461
- autoApplicable: false,
462
- message: "Error Handling Best Practices",
463
- tips: [
464
- "Always handle or rethrow errors - never swallow them",
465
- "Use typed error classes for different error types",
466
- "Log errors with context (user ID, request ID, etc.)",
467
- "Consider using a centralized error handler",
468
- "In production, never expose internal error details to users",
469
- ],
470
- });
471
- }
472
-
473
- // API best practices
474
- if (finding.type?.includes("api") || finding.category?.includes("API")) {
475
- suggestions.push({
476
- type: "best-practice",
477
- confidence: 0.80,
478
- autoApplicable: false,
479
- message: "API Best Practices",
480
- tips: [
481
- "Always use environment variables for API URLs",
482
- "Add timeout and retry logic for external API calls",
483
- "Validate API responses before using the data",
484
- "Use TypeScript interfaces for API response types",
485
- "Add error handling for network failures",
486
- ],
487
- });
488
- }
489
-
490
- return suggestions;
491
- }
492
-
493
- /**
494
- * Calculate fix priority
495
- */
496
- function calculateFixPriority(finding, suggestions) {
497
- let priority = 0;
498
-
499
- // Higher priority for blockers
500
- if (finding.severity === "BLOCK" || finding.severity === "critical") {
501
- priority += 30;
502
- } else if (finding.severity === "WARN") {
503
- priority += 15;
504
- }
505
-
506
- // Higher priority for auto-fixable issues
507
- if (suggestions.some(s => s.autoApplicable)) {
508
- priority += 20;
509
- }
510
-
511
- // Higher priority for high-confidence fixes
512
- const maxConfidence = Math.max(...suggestions.map(s => s.confidence || 0));
513
- priority += maxConfidence * 10;
514
-
515
- // Higher priority for security issues
516
- if (finding.category?.includes("Security") || finding.type?.includes("secret")) {
517
- priority += 25;
518
- }
519
-
520
- return Math.min(100, priority);
521
- }
522
-
523
- /**
524
- * Generate fix plan for multiple findings
525
- * @param {Array} findings - Array of findings
526
- * @param {object} context - Project context
527
- * @returns {object} Comprehensive fix plan
528
- */
529
- function generateFixPlan(findings, context = {}) {
530
- const fixes = findings.map(f => generateFixSuggestions(f, context));
531
-
532
- // Sort by priority
533
- fixes.sort((a, b) => b.priority - a.priority);
534
-
535
- // Group by fix type
536
- const autoFixable = fixes.filter(f => f.hasAutoFix);
537
- const manualRequired = fixes.filter(f => !f.hasAutoFix);
538
-
539
- // Calculate estimated effort
540
- const autoFixTime = autoFixable.length * 2; // ~2 min per auto-fix
541
- const manualFixTime = manualRequired.reduce((sum, f) => {
542
- const severity = findings.find(finding => finding.id === f.finding)?.severity;
543
- return sum + (severity === "BLOCK" ? 30 : 15); // 30 min for blockers, 15 for warnings
544
- }, 0);
545
-
546
- return {
547
- summary: {
548
- totalFindings: findings.length,
549
- autoFixable: autoFixable.length,
550
- manualRequired: manualRequired.length,
551
- estimatedTimeMinutes: autoFixTime + manualFixTime,
552
- },
553
- prioritized: fixes,
554
- autoFixes: autoFixable,
555
- manualFixes: manualRequired,
556
- recommendations: [
557
- autoFixable.length > 0 ?
558
- `Run 'vibecheck fix --auto' to apply ${autoFixable.length} automatic fixes` : null,
559
- manualRequired.length > 0 ?
560
- `${manualRequired.length} issues require manual review and fixes` : null,
561
- fixes.some(f => f.priority > 50) ?
562
- "Start with high-priority fixes marked with priority > 50" : null,
563
- ].filter(Boolean),
564
- };
565
- }
566
-
567
- // ═══════════════════════════════════════════════════════════════════════════════
568
- // EXPORTS
569
- // ═══════════════════════════════════════════════════════════════════════════════
570
-
571
- module.exports = {
572
- generateFixSuggestions,
573
- generateFixPlan,
574
- FIX_TEMPLATES,
575
- FRAMEWORK_FIXES,
576
- normalizeFindingType,
577
- };