baseguard 1.0.3 → 1.0.5

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 (169) hide show
  1. package/.baseguardrc.example.json +63 -63
  2. package/.eslintrc.json +24 -24
  3. package/.prettierrc +7 -7
  4. package/CHANGELOG.md +195 -195
  5. package/DEPLOYMENT.md +624 -624
  6. package/DEPLOYMENT_CHECKLIST.md +239 -239
  7. package/DEPLOYMENT_SUMMARY_v1.0.2.md +202 -202
  8. package/QUICK_START.md +134 -134
  9. package/README.md +488 -488
  10. package/RELEASE_NOTES_v1.0.2.md +434 -434
  11. package/bin/base.js +627 -627
  12. package/dist/ai/fix-manager.d.ts.map +1 -1
  13. package/dist/ai/fix-manager.js +1 -1
  14. package/dist/ai/fix-manager.js.map +1 -1
  15. package/dist/ai/gemini-analyzer.d.ts.map +1 -1
  16. package/dist/ai/gemini-analyzer.js +29 -35
  17. package/dist/ai/gemini-analyzer.js.map +1 -1
  18. package/dist/ai/gemini-code-fixer.d.ts.map +1 -1
  19. package/dist/ai/gemini-code-fixer.js +58 -58
  20. package/dist/ai/gemini-code-fixer.js.map +1 -1
  21. package/dist/ai/jules-implementer.d.ts +3 -0
  22. package/dist/ai/jules-implementer.d.ts.map +1 -1
  23. package/dist/ai/jules-implementer.js +63 -32
  24. package/dist/ai/jules-implementer.js.map +1 -1
  25. package/dist/ai/unified-code-fixer.js.map +1 -1
  26. package/dist/commands/check.d.ts.map +1 -1
  27. package/dist/commands/check.js +1 -1
  28. package/dist/commands/check.js.map +1 -1
  29. package/dist/commands/config.js +2 -1
  30. package/dist/commands/config.js.map +1 -1
  31. package/dist/commands/fix.d.ts.map +1 -1
  32. package/dist/commands/fix.js +48 -15
  33. package/dist/commands/fix.js.map +1 -1
  34. package/dist/core/api-key-manager.js +2 -2
  35. package/dist/core/api-key-manager.js.map +1 -1
  36. package/dist/core/baseguard.d.ts +1 -0
  37. package/dist/core/baseguard.d.ts.map +1 -1
  38. package/dist/core/baseguard.js +13 -10
  39. package/dist/core/baseguard.js.map +1 -1
  40. package/dist/core/baseline-checker.d.ts.map +1 -1
  41. package/dist/core/baseline-checker.js +8 -5
  42. package/dist/core/baseline-checker.js.map +1 -1
  43. package/dist/core/configuration-recovery.d.ts.map +1 -1
  44. package/dist/core/configuration-recovery.js +1 -1
  45. package/dist/core/configuration-recovery.js.map +1 -1
  46. package/dist/core/debug-logger.d.ts.map +1 -1
  47. package/dist/core/debug-logger.js +1 -1
  48. package/dist/core/debug-logger.js.map +1 -1
  49. package/dist/core/error-handler.d.ts.map +1 -1
  50. package/dist/core/error-handler.js +2 -1
  51. package/dist/core/error-handler.js.map +1 -1
  52. package/dist/core/gitignore-manager.js +5 -5
  53. package/dist/core/graceful-degradation-manager.d.ts.map +1 -1
  54. package/dist/core/graceful-degradation-manager.js +16 -16
  55. package/dist/core/graceful-degradation-manager.js.map +1 -1
  56. package/dist/core/lazy-loader.d.ts.map +1 -1
  57. package/dist/core/lazy-loader.js +9 -2
  58. package/dist/core/lazy-loader.js.map +1 -1
  59. package/dist/core/memory-manager.d.ts +0 -3
  60. package/dist/core/memory-manager.d.ts.map +1 -1
  61. package/dist/core/memory-manager.js.map +1 -1
  62. package/dist/core/parser-worker.d.ts +2 -0
  63. package/dist/core/parser-worker.d.ts.map +1 -0
  64. package/dist/core/parser-worker.js +19 -0
  65. package/dist/core/parser-worker.js.map +1 -0
  66. package/dist/core/startup-optimizer.d.ts.map +1 -1
  67. package/dist/core/startup-optimizer.js +4 -8
  68. package/dist/core/startup-optimizer.js.map +1 -1
  69. package/dist/core/system-error-handler.d.ts.map +1 -1
  70. package/dist/core/system-error-handler.js.map +1 -1
  71. package/dist/git/automation-engine.d.ts.map +1 -1
  72. package/dist/git/automation-engine.js +5 -4
  73. package/dist/git/automation-engine.js.map +1 -1
  74. package/dist/git/github-manager.d.ts.map +1 -1
  75. package/dist/git/github-manager.js.map +1 -1
  76. package/dist/git/hook-manager.js +5 -5
  77. package/dist/git/hook-manager.js.map +1 -1
  78. package/dist/parsers/parser-manager.d.ts.map +1 -1
  79. package/dist/parsers/parser-manager.js +1 -1
  80. package/dist/parsers/parser-manager.js.map +1 -1
  81. package/dist/parsers/svelte-parser.js +1 -1
  82. package/dist/parsers/svelte-parser.js.map +1 -1
  83. package/dist/parsers/vanilla-parser.d.ts.map +1 -1
  84. package/dist/parsers/vanilla-parser.js.map +1 -1
  85. package/dist/parsers/vue-parser.d.ts.map +1 -1
  86. package/dist/parsers/vue-parser.js.map +1 -1
  87. package/dist/ui/components.d.ts +1 -1
  88. package/dist/ui/components.d.ts.map +1 -1
  89. package/dist/ui/components.js +11 -11
  90. package/dist/ui/components.js.map +1 -1
  91. package/dist/ui/terminal-header.js +14 -14
  92. package/package.json +105 -105
  93. package/src/ai/__tests__/gemini-analyzer.test.ts +180 -180
  94. package/src/ai/agentkit-orchestrator.ts +533 -533
  95. package/src/ai/fix-manager.ts +362 -362
  96. package/src/ai/gemini-analyzer.ts +665 -671
  97. package/src/ai/gemini-code-fixer.ts +539 -540
  98. package/src/ai/index.ts +3 -3
  99. package/src/ai/jules-implementer.ts +504 -460
  100. package/src/ai/unified-code-fixer.ts +347 -347
  101. package/src/commands/automation.ts +343 -343
  102. package/src/commands/check.ts +298 -299
  103. package/src/commands/config.ts +584 -583
  104. package/src/commands/fix.ts +269 -238
  105. package/src/commands/index.ts +6 -6
  106. package/src/commands/init.ts +155 -155
  107. package/src/commands/status.ts +306 -306
  108. package/src/core/api-key-manager.ts +298 -298
  109. package/src/core/baseguard.ts +757 -756
  110. package/src/core/baseline-checker.ts +566 -563
  111. package/src/core/cache-manager.ts +271 -271
  112. package/src/core/configuration-recovery.ts +672 -673
  113. package/src/core/configuration.ts +595 -595
  114. package/src/core/debug-logger.ts +590 -590
  115. package/src/core/directory-filter.ts +420 -420
  116. package/src/core/error-handler.ts +518 -517
  117. package/src/core/file-processor.ts +337 -337
  118. package/src/core/gitignore-manager.ts +168 -168
  119. package/src/core/graceful-degradation-manager.ts +596 -596
  120. package/src/core/index.ts +16 -16
  121. package/src/core/lazy-loader.ts +317 -307
  122. package/src/core/memory-manager.ts +290 -295
  123. package/src/core/parser-worker.ts +33 -0
  124. package/src/core/startup-optimizer.ts +246 -255
  125. package/src/core/system-error-handler.ts +755 -756
  126. package/src/git/automation-engine.ts +361 -361
  127. package/src/git/github-manager.ts +190 -192
  128. package/src/git/hook-manager.ts +210 -210
  129. package/src/git/index.ts +3 -3
  130. package/src/index.ts +7 -7
  131. package/src/parsers/feature-validator.ts +558 -558
  132. package/src/parsers/index.ts +7 -7
  133. package/src/parsers/parser-manager.ts +418 -419
  134. package/src/parsers/parser.ts +25 -25
  135. package/src/parsers/react-parser-optimized.ts +160 -160
  136. package/src/parsers/react-parser.ts +358 -358
  137. package/src/parsers/svelte-parser.ts +510 -510
  138. package/src/parsers/vanilla-parser.ts +685 -686
  139. package/src/parsers/vue-parser.ts +476 -478
  140. package/src/types/index.ts +95 -95
  141. package/src/ui/components.ts +567 -567
  142. package/src/ui/help.ts +192 -192
  143. package/src/ui/index.ts +3 -3
  144. package/src/ui/prompts.ts +680 -680
  145. package/src/ui/terminal-header.ts +58 -58
  146. package/test-build.js +40 -40
  147. package/test-config-commands.js +55 -55
  148. package/test-header-simple.js +32 -32
  149. package/test-terminal-header.js +11 -11
  150. package/test-ui.js +28 -28
  151. package/tests/e2e/baseguard.e2e.test.ts +515 -515
  152. package/tests/e2e/cross-platform.e2e.test.ts +419 -419
  153. package/tests/e2e/git-integration.e2e.test.ts +486 -486
  154. package/tests/fixtures/react-project/package.json +13 -13
  155. package/tests/fixtures/react-project/src/App.css +75 -75
  156. package/tests/fixtures/react-project/src/App.tsx +76 -76
  157. package/tests/fixtures/svelte-project/package.json +10 -10
  158. package/tests/fixtures/svelte-project/src/App.svelte +368 -368
  159. package/tests/fixtures/vanilla-project/index.html +75 -75
  160. package/tests/fixtures/vanilla-project/script.js +330 -330
  161. package/tests/fixtures/vanilla-project/styles.css +358 -358
  162. package/tests/fixtures/vue-project/package.json +11 -11
  163. package/tests/fixtures/vue-project/src/App.vue +215 -215
  164. package/tmp-smoke/.baseguard/backups/config-2026-02-19T12-04-11-067Z-auto.json +30 -0
  165. package/tmp-smoke/src/bad.css +3 -0
  166. package/tsconfig.json +34 -34
  167. package/vitest.config.ts +11 -11
  168. package/dist/terminal-header.d.ts +0 -12
  169. package/dist/terminal-header.js +0 -45
@@ -1,344 +1,344 @@
1
- import chalk from 'chalk';
2
- import inquirer from 'inquirer';
3
- import { UIComponents } from '../ui/index.js';
4
- import { ConfigurationManager } from '../core/configuration.js';
5
- import { ErrorHandler } from '../core/error-handler.js';
6
- import { GitHookManager } from '../git/hook-manager.js';
7
- import { AutomationEngine } from '../git/automation-engine.js';
8
- import type { AutomationOptions } from '../types/index.js';
9
-
10
- /**
11
- * Manage git automation and hooks
12
- */
13
- export async function automation(action: string, options?: any): Promise<void> {
14
- try {
15
- switch (action) {
16
- case 'enable':
17
- await enableAutomation(options);
18
- break;
19
- case 'disable':
20
- await disableAutomation();
21
- break;
22
- case 'status':
23
- await showAutomationStatus();
24
- break;
25
- case 'configure':
26
- await configureAutomation();
27
- break;
28
- case 'run':
29
- await runAutomation(options);
30
- break;
31
- default:
32
- await showAutomationHelp();
33
- }
34
- } catch (error) {
35
- const apiError = ErrorHandler.handleAPIError(error);
36
- ErrorHandler.displayError(apiError);
37
-
38
- // Provide specific help for automation command issues
39
- console.log('\nšŸ’” Automation troubleshooting:');
40
- if (action === 'enable') {
41
- UIComponents.showList([
42
- 'Ensure you\'re in a git repository (run "git init" if needed)',
43
- 'Check that you have a package.json file',
44
- 'Verify write permissions for .husky directory',
45
- 'Make sure Husky is installed (npm install husky)'
46
- ]);
47
- } else if (action === 'run') {
48
- UIComponents.showList([
49
- 'This command is typically called by git hooks automatically',
50
- 'Check that BaseGuard configuration exists (.baseguardrc.json)',
51
- 'Verify git hooks are properly installed',
52
- 'Run "base automation status" to check setup'
53
- ]);
54
- } else if (action === 'disable') {
55
- UIComponents.showList([
56
- 'Check file permissions for .husky directory',
57
- 'Verify git repository is properly initialized',
58
- 'Run "base automation status" to check current state'
59
- ]);
60
- } else {
61
- UIComponents.showList([
62
- 'Run "base automation status" to check current setup',
63
- 'Use "base automation --help" to see available commands',
64
- 'Ensure you\'re in a git repository with BaseGuard configured'
65
- ]);
66
- }
67
-
68
- process.exit(1);
69
- }
70
- }
71
-
72
- /**
73
- * Enable automation with optional configuration
74
- */
75
- async function enableAutomation(options?: { trigger?: string; autoFix?: boolean; autoAnalyze?: boolean }): Promise<void> {
76
- console.log(chalk.cyan('šŸ¤– Enabling BaseGuard automation...'));
77
-
78
- const config = await ConfigurationManager.load();
79
- const hookManager = new GitHookManager();
80
-
81
- // Configure automation settings
82
- let trigger: 'pre-commit' | 'pre-push' = config.automation.trigger;
83
- let autoFix = config.automation.autoFix;
84
- let autoAnalyze = config.automation.autoAnalyze;
85
-
86
- // Use provided options or prompt for configuration
87
- if (options?.trigger) {
88
- if (options.trigger === 'pre-commit' || options.trigger === 'pre-push') {
89
- trigger = options.trigger;
90
- } else {
91
- throw new Error('Invalid trigger. Must be "pre-commit" or "pre-push"');
92
- }
93
- } else if (!config.automation.enabled) {
94
- // First time setup - prompt for configuration
95
- const answers = await inquirer.prompt([
96
- {
97
- type: 'list',
98
- name: 'trigger',
99
- message: 'When should BaseGuard check for violations?',
100
- choices: [
101
- { name: 'Before each commit (pre-commit)', value: 'pre-commit' },
102
- { name: 'Before each push (pre-push)', value: 'pre-push' }
103
- ],
104
- default: trigger
105
- },
106
- {
107
- type: 'confirm',
108
- name: 'autoAnalyze',
109
- message: 'Enable automatic AI analysis of violations?',
110
- default: autoAnalyze,
111
- when: () => !!config.apiKeys.gemini
112
- },
113
- {
114
- type: 'confirm',
115
- name: 'autoFix',
116
- message: 'Enable automatic AI fixing of violations?',
117
- default: autoFix,
118
- when: () => !!config.apiKeys.jules && !!config.apiKeys.gemini
119
- }
120
- ]);
121
-
122
- trigger = answers.trigger;
123
- autoAnalyze = answers.autoAnalyze ?? autoAnalyze;
124
- autoFix = answers.autoFix ?? autoFix;
125
- }
126
-
127
- if (options?.autoFix !== undefined) {
128
- autoFix = options.autoFix;
129
- }
130
-
131
- if (options?.autoAnalyze !== undefined) {
132
- autoAnalyze = options.autoAnalyze;
133
- }
134
-
135
- // Update configuration
136
- config.automation.enabled = true;
137
- config.automation.trigger = trigger;
138
- config.automation.autoAnalyze = autoAnalyze;
139
- config.automation.autoFix = autoFix;
140
-
141
- await ConfigurationManager.save(config);
142
-
143
- // Install git hooks
144
- await hookManager.installHooks(trigger);
145
-
146
- UIComponents.showSuccessBox(`Automation enabled with ${trigger} trigger`);
147
-
148
- // Show configuration summary
149
- console.log(chalk.cyan('\nšŸ“‹ Automation Configuration:'));
150
- console.log(` Trigger: ${chalk.white(trigger)}`);
151
- console.log(` Auto-analyze: ${autoAnalyze ? chalk.green('enabled') : chalk.red('disabled')}`);
152
- console.log(` Auto-fix: ${autoFix ? chalk.green('enabled') : chalk.red('disabled')}`);
153
- console.log(` Block commits: ${config.automation.blockCommit ? chalk.green('enabled') : chalk.red('disabled')}`);
154
-
155
- if (!config.apiKeys.gemini) {
156
- console.log(chalk.yellow('\nāš ļø Gemini API key not configured. Run "base config" to set up AI features.'));
157
- }
158
-
159
- if (!config.apiKeys.jules) {
160
- console.log(chalk.yellow('āš ļø Jules API key not configured. Run "base config" to set up AI fixing.'));
161
- }
162
- }
163
-
164
- /**
165
- * Disable automation
166
- */
167
- async function disableAutomation(): Promise<void> {
168
- console.log(chalk.cyan('šŸ¤– Disabling BaseGuard automation...'));
169
-
170
- const config = await ConfigurationManager.load();
171
- const hookManager = new GitHookManager();
172
-
173
- // Update configuration
174
- config.automation.enabled = false;
175
- await ConfigurationManager.save(config);
176
-
177
- // Uninstall git hooks
178
- await hookManager.uninstallHooks();
179
-
180
- UIComponents.showSuccessBox('Automation disabled');
181
- }
182
-
183
- /**
184
- * Show automation status
185
- */
186
- async function showAutomationStatus(): Promise<void> {
187
- const config = await ConfigurationManager.load();
188
- const hookManager = new GitHookManager();
189
-
190
- console.log(chalk.cyan('šŸ¤– BaseGuard Automation Status\n'));
191
-
192
- // Configuration status
193
- console.log(chalk.white('Configuration:'));
194
- console.log(` Enabled: ${config.automation.enabled ? chalk.green('āœ“') : chalk.red('āœ—')}`);
195
- console.log(` Trigger: ${chalk.white(config.automation.trigger)}`);
196
- console.log(` Auto-analyze: ${config.automation.autoAnalyze ? chalk.green('āœ“') : chalk.red('āœ—')}`);
197
- console.log(` Auto-fix: ${config.automation.autoFix ? chalk.green('āœ“') : chalk.red('āœ—')}`);
198
- console.log(` Block commits: ${config.automation.blockCommit ? chalk.green('āœ“') : chalk.red('āœ—')}`);
199
-
200
- // Git hooks status
201
- const hooksInstalled = await hookManager.areHooksInstalled();
202
- const installedHooks = await hookManager.getInstalledHooks();
203
-
204
- console.log(chalk.white('\nGit Hooks:'));
205
- console.log(` Installed: ${hooksInstalled ? chalk.green('āœ“') : chalk.red('āœ—')}`);
206
- if (installedHooks.length > 0) {
207
- console.log(` Active hooks: ${chalk.white(installedHooks.join(', '))}`);
208
- }
209
-
210
- // API keys status
211
- console.log(chalk.white('\nAPI Keys:'));
212
- console.log(` Gemini: ${config.apiKeys.gemini ? chalk.green('āœ“ configured') : chalk.red('āœ— not configured')}`);
213
- console.log(` Jules: ${config.apiKeys.jules ? chalk.green('āœ“ configured') : chalk.red('āœ— not configured')}`);
214
-
215
- // Recommendations
216
- if (config.automation.enabled && !hooksInstalled) {
217
- console.log(chalk.yellow('\nāš ļø Automation is enabled but git hooks are not installed. Run "base automation enable" to fix this.'));
218
- }
219
-
220
- if (config.automation.autoAnalyze && !config.apiKeys.gemini) {
221
- console.log(chalk.yellow('āš ļø Auto-analyze is enabled but Gemini API key is not configured.'));
222
- }
223
-
224
- if (config.automation.autoFix && (!config.apiKeys.jules || !config.apiKeys.gemini)) {
225
- console.log(chalk.yellow('āš ļø Auto-fix is enabled but API keys are not configured.'));
226
- }
227
- }
228
-
229
- /**
230
- * Configure automation settings
231
- */
232
- async function configureAutomation(): Promise<void> {
233
- console.log(chalk.cyan('šŸ¤– Configuring BaseGuard automation...\n'));
234
-
235
- const config = await ConfigurationManager.load();
236
- const hookManager = new GitHookManager();
237
-
238
- const answers = await inquirer.prompt([
239
- {
240
- type: 'confirm',
241
- name: 'enabled',
242
- message: 'Enable automation?',
243
- default: config.automation.enabled
244
- },
245
- {
246
- type: 'list',
247
- name: 'trigger',
248
- message: 'When should BaseGuard check for violations?',
249
- choices: [
250
- { name: 'Before each commit (pre-commit)', value: 'pre-commit' },
251
- { name: 'Before each push (pre-push)', value: 'pre-push' }
252
- ],
253
- default: config.automation.trigger,
254
- when: (answers) => answers.enabled
255
- },
256
- {
257
- type: 'confirm',
258
- name: 'autoAnalyze',
259
- message: 'Enable automatic AI analysis of violations?',
260
- default: config.automation.autoAnalyze,
261
- when: (answers) => answers.enabled && !!config.apiKeys.gemini
262
- },
263
- {
264
- type: 'confirm',
265
- name: 'autoFix',
266
- message: 'Enable automatic AI fixing of violations?',
267
- default: config.automation.autoFix,
268
- when: (answers) => answers.enabled && !!config.apiKeys.jules && !!config.apiKeys.gemini
269
- },
270
- {
271
- type: 'confirm',
272
- name: 'blockCommit',
273
- message: 'Block commits when violations are found?',
274
- default: config.automation.blockCommit,
275
- when: (answers) => answers.enabled
276
- }
277
- ]);
278
-
279
- // Update configuration
280
- const oldTrigger = config.automation.trigger;
281
-
282
- config.automation.enabled = answers.enabled ?? config.automation.enabled;
283
- config.automation.trigger = answers.trigger ?? config.automation.trigger;
284
- config.automation.autoAnalyze = answers.autoAnalyze ?? config.automation.autoAnalyze;
285
- config.automation.autoFix = answers.autoFix ?? config.automation.autoFix;
286
- config.automation.blockCommit = answers.blockCommit ?? config.automation.blockCommit;
287
-
288
- await ConfigurationManager.save(config);
289
-
290
- // Update git hooks if needed
291
- if (config.automation.enabled) {
292
- if (oldTrigger !== config.automation.trigger) {
293
- await hookManager.updateHookConfiguration(oldTrigger, config.automation.trigger);
294
- } else {
295
- await hookManager.installHooks(config.automation.trigger);
296
- }
297
- } else {
298
- await hookManager.uninstallHooks();
299
- }
300
-
301
- UIComponents.showSuccessBox('Automation configuration updated');
302
-
303
- // Show updated status
304
- await showAutomationStatus();
305
- }
306
-
307
- /**
308
- * Run automation manually (used by git hooks)
309
- */
310
- async function runAutomation(options: { trigger?: string; strict?: boolean } = {}): Promise<void> {
311
- const trigger = options.trigger as 'pre-commit' | 'pre-push' || 'pre-commit';
312
-
313
- const automationOptions: AutomationOptions = {
314
- trigger,
315
- strict: options.strict
316
- };
317
-
318
- const engine = new AutomationEngine();
319
- await engine.run(automationOptions);
320
- }
321
-
322
- /**
323
- * Show automation help
324
- */
325
- async function showAutomationHelp(): Promise<void> {
326
- console.log(chalk.cyan('šŸ¤– BaseGuard Automation Commands\n'));
327
-
328
- console.log(chalk.white('Usage:'));
329
- console.log(' base automation <command> [options]\n');
330
-
331
- console.log(chalk.white('Commands:'));
332
- console.log(' enable Enable automation with git hooks');
333
- console.log(' disable Disable automation and remove git hooks');
334
- console.log(' status Show current automation status');
335
- console.log(' configure Interactive configuration of automation settings');
336
- console.log(' run Run automation manually (used by git hooks)\n');
337
-
338
- console.log(chalk.white('Examples:'));
339
- console.log(' base automation enable');
340
- console.log(' base automation enable --trigger pre-push');
341
- console.log(' base automation disable');
342
- console.log(' base automation status');
343
- console.log(' base automation configure');
1
+ import chalk from 'chalk';
2
+ import inquirer from 'inquirer';
3
+ import { UIComponents } from '../ui/index.js';
4
+ import { ConfigurationManager } from '../core/configuration.js';
5
+ import { ErrorHandler } from '../core/error-handler.js';
6
+ import { GitHookManager } from '../git/hook-manager.js';
7
+ import { AutomationEngine } from '../git/automation-engine.js';
8
+ import type { AutomationOptions } from '../types/index.js';
9
+
10
+ /**
11
+ * Manage git automation and hooks
12
+ */
13
+ export async function automation(action: string, options?: any): Promise<void> {
14
+ try {
15
+ switch (action) {
16
+ case 'enable':
17
+ await enableAutomation(options);
18
+ break;
19
+ case 'disable':
20
+ await disableAutomation();
21
+ break;
22
+ case 'status':
23
+ await showAutomationStatus();
24
+ break;
25
+ case 'configure':
26
+ await configureAutomation();
27
+ break;
28
+ case 'run':
29
+ await runAutomation(options);
30
+ break;
31
+ default:
32
+ await showAutomationHelp();
33
+ }
34
+ } catch (error) {
35
+ const apiError = ErrorHandler.handleAPIError(error);
36
+ ErrorHandler.displayError(apiError);
37
+
38
+ // Provide specific help for automation command issues
39
+ console.log('\nšŸ’” Automation troubleshooting:');
40
+ if (action === 'enable') {
41
+ UIComponents.showList([
42
+ 'Ensure you\'re in a git repository (run "git init" if needed)',
43
+ 'Check that you have a package.json file',
44
+ 'Verify write permissions for .husky directory',
45
+ 'Make sure Husky is installed (npm install husky)'
46
+ ]);
47
+ } else if (action === 'run') {
48
+ UIComponents.showList([
49
+ 'This command is typically called by git hooks automatically',
50
+ 'Check that BaseGuard configuration exists (.baseguardrc.json)',
51
+ 'Verify git hooks are properly installed',
52
+ 'Run "base automation status" to check setup'
53
+ ]);
54
+ } else if (action === 'disable') {
55
+ UIComponents.showList([
56
+ 'Check file permissions for .husky directory',
57
+ 'Verify git repository is properly initialized',
58
+ 'Run "base automation status" to check current state'
59
+ ]);
60
+ } else {
61
+ UIComponents.showList([
62
+ 'Run "base automation status" to check current setup',
63
+ 'Use "base automation --help" to see available commands',
64
+ 'Ensure you\'re in a git repository with BaseGuard configured'
65
+ ]);
66
+ }
67
+
68
+ process.exit(1);
69
+ }
70
+ }
71
+
72
+ /**
73
+ * Enable automation with optional configuration
74
+ */
75
+ async function enableAutomation(options?: { trigger?: string; autoFix?: boolean; autoAnalyze?: boolean }): Promise<void> {
76
+ console.log(chalk.cyan('šŸ¤– Enabling BaseGuard automation...'));
77
+
78
+ const config = await ConfigurationManager.load();
79
+ const hookManager = new GitHookManager();
80
+
81
+ // Configure automation settings
82
+ let trigger: 'pre-commit' | 'pre-push' = config.automation.trigger;
83
+ let autoFix = config.automation.autoFix;
84
+ let autoAnalyze = config.automation.autoAnalyze;
85
+
86
+ // Use provided options or prompt for configuration
87
+ if (options?.trigger) {
88
+ if (options.trigger === 'pre-commit' || options.trigger === 'pre-push') {
89
+ trigger = options.trigger;
90
+ } else {
91
+ throw new Error('Invalid trigger. Must be "pre-commit" or "pre-push"');
92
+ }
93
+ } else if (!config.automation.enabled) {
94
+ // First time setup - prompt for configuration
95
+ const answers = await inquirer.prompt([
96
+ {
97
+ type: 'list',
98
+ name: 'trigger',
99
+ message: 'When should BaseGuard check for violations?',
100
+ choices: [
101
+ { name: 'Before each commit (pre-commit)', value: 'pre-commit' },
102
+ { name: 'Before each push (pre-push)', value: 'pre-push' }
103
+ ],
104
+ default: trigger
105
+ },
106
+ {
107
+ type: 'confirm',
108
+ name: 'autoAnalyze',
109
+ message: 'Enable automatic AI analysis of violations?',
110
+ default: autoAnalyze,
111
+ when: () => !!config.apiKeys.gemini
112
+ },
113
+ {
114
+ type: 'confirm',
115
+ name: 'autoFix',
116
+ message: 'Enable automatic AI fixing of violations?',
117
+ default: autoFix,
118
+ when: () => !!config.apiKeys.jules && !!config.apiKeys.gemini
119
+ }
120
+ ]);
121
+
122
+ trigger = answers.trigger;
123
+ autoAnalyze = answers.autoAnalyze ?? autoAnalyze;
124
+ autoFix = answers.autoFix ?? autoFix;
125
+ }
126
+
127
+ if (options?.autoFix !== undefined) {
128
+ autoFix = options.autoFix;
129
+ }
130
+
131
+ if (options?.autoAnalyze !== undefined) {
132
+ autoAnalyze = options.autoAnalyze;
133
+ }
134
+
135
+ // Update configuration
136
+ config.automation.enabled = true;
137
+ config.automation.trigger = trigger;
138
+ config.automation.autoAnalyze = autoAnalyze;
139
+ config.automation.autoFix = autoFix;
140
+
141
+ await ConfigurationManager.save(config);
142
+
143
+ // Install git hooks
144
+ await hookManager.installHooks(trigger);
145
+
146
+ UIComponents.showSuccessBox(`Automation enabled with ${trigger} trigger`);
147
+
148
+ // Show configuration summary
149
+ console.log(chalk.cyan('\nšŸ“‹ Automation Configuration:'));
150
+ console.log(` Trigger: ${chalk.white(trigger)}`);
151
+ console.log(` Auto-analyze: ${autoAnalyze ? chalk.green('enabled') : chalk.red('disabled')}`);
152
+ console.log(` Auto-fix: ${autoFix ? chalk.green('enabled') : chalk.red('disabled')}`);
153
+ console.log(` Block commits: ${config.automation.blockCommit ? chalk.green('enabled') : chalk.red('disabled')}`);
154
+
155
+ if (!config.apiKeys.gemini) {
156
+ console.log(chalk.yellow('\nāš ļø Gemini API key not configured. Run "base config" to set up AI features.'));
157
+ }
158
+
159
+ if (!config.apiKeys.jules) {
160
+ console.log(chalk.yellow('āš ļø Jules API key not configured. Run "base config" to set up AI fixing.'));
161
+ }
162
+ }
163
+
164
+ /**
165
+ * Disable automation
166
+ */
167
+ async function disableAutomation(): Promise<void> {
168
+ console.log(chalk.cyan('šŸ¤– Disabling BaseGuard automation...'));
169
+
170
+ const config = await ConfigurationManager.load();
171
+ const hookManager = new GitHookManager();
172
+
173
+ // Update configuration
174
+ config.automation.enabled = false;
175
+ await ConfigurationManager.save(config);
176
+
177
+ // Uninstall git hooks
178
+ await hookManager.uninstallHooks();
179
+
180
+ UIComponents.showSuccessBox('Automation disabled');
181
+ }
182
+
183
+ /**
184
+ * Show automation status
185
+ */
186
+ async function showAutomationStatus(): Promise<void> {
187
+ const config = await ConfigurationManager.load();
188
+ const hookManager = new GitHookManager();
189
+
190
+ console.log(chalk.cyan('šŸ¤– BaseGuard Automation Status\n'));
191
+
192
+ // Configuration status
193
+ console.log(chalk.white('Configuration:'));
194
+ console.log(` Enabled: ${config.automation.enabled ? chalk.green('āœ“') : chalk.red('āœ—')}`);
195
+ console.log(` Trigger: ${chalk.white(config.automation.trigger)}`);
196
+ console.log(` Auto-analyze: ${config.automation.autoAnalyze ? chalk.green('āœ“') : chalk.red('āœ—')}`);
197
+ console.log(` Auto-fix: ${config.automation.autoFix ? chalk.green('āœ“') : chalk.red('āœ—')}`);
198
+ console.log(` Block commits: ${config.automation.blockCommit ? chalk.green('āœ“') : chalk.red('āœ—')}`);
199
+
200
+ // Git hooks status
201
+ const hooksInstalled = await hookManager.areHooksInstalled();
202
+ const installedHooks = await hookManager.getInstalledHooks();
203
+
204
+ console.log(chalk.white('\nGit Hooks:'));
205
+ console.log(` Installed: ${hooksInstalled ? chalk.green('āœ“') : chalk.red('āœ—')}`);
206
+ if (installedHooks.length > 0) {
207
+ console.log(` Active hooks: ${chalk.white(installedHooks.join(', '))}`);
208
+ }
209
+
210
+ // API keys status
211
+ console.log(chalk.white('\nAPI Keys:'));
212
+ console.log(` Gemini: ${config.apiKeys.gemini ? chalk.green('āœ“ configured') : chalk.red('āœ— not configured')}`);
213
+ console.log(` Jules: ${config.apiKeys.jules ? chalk.green('āœ“ configured') : chalk.red('āœ— not configured')}`);
214
+
215
+ // Recommendations
216
+ if (config.automation.enabled && !hooksInstalled) {
217
+ console.log(chalk.yellow('\nāš ļø Automation is enabled but git hooks are not installed. Run "base automation enable" to fix this.'));
218
+ }
219
+
220
+ if (config.automation.autoAnalyze && !config.apiKeys.gemini) {
221
+ console.log(chalk.yellow('āš ļø Auto-analyze is enabled but Gemini API key is not configured.'));
222
+ }
223
+
224
+ if (config.automation.autoFix && (!config.apiKeys.jules || !config.apiKeys.gemini)) {
225
+ console.log(chalk.yellow('āš ļø Auto-fix is enabled but API keys are not configured.'));
226
+ }
227
+ }
228
+
229
+ /**
230
+ * Configure automation settings
231
+ */
232
+ async function configureAutomation(): Promise<void> {
233
+ console.log(chalk.cyan('šŸ¤– Configuring BaseGuard automation...\n'));
234
+
235
+ const config = await ConfigurationManager.load();
236
+ const hookManager = new GitHookManager();
237
+
238
+ const answers = await inquirer.prompt([
239
+ {
240
+ type: 'confirm',
241
+ name: 'enabled',
242
+ message: 'Enable automation?',
243
+ default: config.automation.enabled
244
+ },
245
+ {
246
+ type: 'list',
247
+ name: 'trigger',
248
+ message: 'When should BaseGuard check for violations?',
249
+ choices: [
250
+ { name: 'Before each commit (pre-commit)', value: 'pre-commit' },
251
+ { name: 'Before each push (pre-push)', value: 'pre-push' }
252
+ ],
253
+ default: config.automation.trigger,
254
+ when: (answers) => answers.enabled
255
+ },
256
+ {
257
+ type: 'confirm',
258
+ name: 'autoAnalyze',
259
+ message: 'Enable automatic AI analysis of violations?',
260
+ default: config.automation.autoAnalyze,
261
+ when: (answers) => answers.enabled && !!config.apiKeys.gemini
262
+ },
263
+ {
264
+ type: 'confirm',
265
+ name: 'autoFix',
266
+ message: 'Enable automatic AI fixing of violations?',
267
+ default: config.automation.autoFix,
268
+ when: (answers) => answers.enabled && !!config.apiKeys.jules && !!config.apiKeys.gemini
269
+ },
270
+ {
271
+ type: 'confirm',
272
+ name: 'blockCommit',
273
+ message: 'Block commits when violations are found?',
274
+ default: config.automation.blockCommit,
275
+ when: (answers) => answers.enabled
276
+ }
277
+ ]);
278
+
279
+ // Update configuration
280
+ const oldTrigger = config.automation.trigger;
281
+
282
+ config.automation.enabled = answers.enabled ?? config.automation.enabled;
283
+ config.automation.trigger = answers.trigger ?? config.automation.trigger;
284
+ config.automation.autoAnalyze = answers.autoAnalyze ?? config.automation.autoAnalyze;
285
+ config.automation.autoFix = answers.autoFix ?? config.automation.autoFix;
286
+ config.automation.blockCommit = answers.blockCommit ?? config.automation.blockCommit;
287
+
288
+ await ConfigurationManager.save(config);
289
+
290
+ // Update git hooks if needed
291
+ if (config.automation.enabled) {
292
+ if (oldTrigger !== config.automation.trigger) {
293
+ await hookManager.updateHookConfiguration(oldTrigger, config.automation.trigger);
294
+ } else {
295
+ await hookManager.installHooks(config.automation.trigger);
296
+ }
297
+ } else {
298
+ await hookManager.uninstallHooks();
299
+ }
300
+
301
+ UIComponents.showSuccessBox('Automation configuration updated');
302
+
303
+ // Show updated status
304
+ await showAutomationStatus();
305
+ }
306
+
307
+ /**
308
+ * Run automation manually (used by git hooks)
309
+ */
310
+ async function runAutomation(options: { trigger?: string; strict?: boolean } = {}): Promise<void> {
311
+ const trigger = options.trigger as 'pre-commit' | 'pre-push' || 'pre-commit';
312
+
313
+ const automationOptions: AutomationOptions = {
314
+ trigger,
315
+ strict: options.strict
316
+ };
317
+
318
+ const engine = new AutomationEngine();
319
+ await engine.run(automationOptions);
320
+ }
321
+
322
+ /**
323
+ * Show automation help
324
+ */
325
+ async function showAutomationHelp(): Promise<void> {
326
+ console.log(chalk.cyan('šŸ¤– BaseGuard Automation Commands\n'));
327
+
328
+ console.log(chalk.white('Usage:'));
329
+ console.log(' base automation <command> [options]\n');
330
+
331
+ console.log(chalk.white('Commands:'));
332
+ console.log(' enable Enable automation with git hooks');
333
+ console.log(' disable Disable automation and remove git hooks');
334
+ console.log(' status Show current automation status');
335
+ console.log(' configure Interactive configuration of automation settings');
336
+ console.log(' run Run automation manually (used by git hooks)\n');
337
+
338
+ console.log(chalk.white('Examples:'));
339
+ console.log(' base automation enable');
340
+ console.log(' base automation enable --trigger pre-push');
341
+ console.log(' base automation disable');
342
+ console.log(' base automation status');
343
+ console.log(' base automation configure');
344
344
  }