claude-git-hooks 2.14.4 → 2.15.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 (40) hide show
  1. package/CHANGELOG.md +94 -5
  2. package/LICENSE +20 -20
  3. package/bin/claude-hooks +84 -84
  4. package/lib/commands/analyze-diff.js +0 -1
  5. package/lib/commands/create-pr.js +1 -1
  6. package/lib/commands/debug.js +1 -1
  7. package/lib/commands/helpers.js +11 -6
  8. package/lib/commands/install.js +7 -8
  9. package/lib/commands/migrate-config.js +24 -2
  10. package/lib/commands/setup-github.js +1 -1
  11. package/lib/commands/update.js +1 -1
  12. package/lib/config.js +0 -4
  13. package/lib/hooks/prepare-commit-msg.js +2 -2
  14. package/lib/utils/changelog-generator.js +6 -8
  15. package/lib/utils/claude-client.js +7 -6
  16. package/lib/utils/claude-diagnostics.js +14 -21
  17. package/lib/utils/file-operations.js +1 -1
  18. package/lib/utils/file-utils.js +0 -1
  19. package/lib/utils/git-operations.js +0 -1
  20. package/lib/utils/github-api.js +3 -3
  21. package/lib/utils/github-client.js +2 -2
  22. package/lib/utils/installation-diagnostics.js +1 -1
  23. package/lib/utils/prompt-builder.js +4 -6
  24. package/lib/utils/sanitize.js +13 -14
  25. package/lib/utils/task-id.js +18 -20
  26. package/lib/utils/telemetry.js +5 -7
  27. package/package.json +68 -60
  28. package/templates/config.advanced.example.json +113 -113
  29. package/templates/pre-commit +7 -0
  30. package/templates/presets/ai/config.json +5 -5
  31. package/templates/presets/backend/config.json +5 -5
  32. package/templates/presets/backend/preset.json +49 -49
  33. package/templates/presets/database/config.json +5 -5
  34. package/templates/presets/database/preset.json +38 -38
  35. package/templates/presets/default/config.json +5 -5
  36. package/templates/presets/default/preset.json +53 -53
  37. package/templates/presets/frontend/config.json +5 -5
  38. package/templates/presets/frontend/preset.json +50 -50
  39. package/templates/presets/fullstack/config.json +5 -5
  40. package/templates/presets/fullstack/preset.json +55 -55
package/CHANGELOG.md CHANGED
@@ -5,84 +5,173 @@ Todos los cambios notables en este proyecto se documentarán en este archivo.
5
5
  El formato está basado en [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
6
6
  y este proyecto adhiere a [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
7
 
8
- ## [2.14.4] - 2026-02-06
8
+ ## [2.15.5] - 2026-02-12
9
+
10
+ ### ✨ Added
11
+ - Added comprehensive CI-safe integration test suite that runs without Claude CLI dependency
12
+ - Added new test scripts: `test:integration:ci` for CI environments and `test:changed` for testing only modified files
13
+
14
+ ### 🔧 Changed
15
+ - Optimized CI matrix to run full OS/Node.js combinations only on push events, reducing PR build times
16
+ - Refactored integration tests to verify installation workflow, hook lifecycle, config persistence, and CLI routing
17
+ - Improved timeout handling in Claude CLI client by clearing timeouts consistently on all exit paths
18
+ - Simplified template variable replacement in prompt-builder with cleaner regex handling
19
+ - Reduced Jest verbosity and coverage reporters for cleaner CI output
20
+
21
+ ### 🐛 Fixed
22
+ - Fixed potential timeout leak in claude-client.js where timeouts were not cleared on error or stdin failures
23
+
24
+ ### 🗑️ Removed
25
+ - Removed unused variables and parameters across multiple modules (analyze-diff, create-pr, install, config, changelog-generator, claude-client, claude-diagnostics, file-utils, git-operations, prompt-builder)
26
+
27
+
28
+ ## [2.15.4] - 2026-02-11
29
+
30
+ ### ✨ Added
31
+ - Added comprehensive unit tests for claude-diagnostics.js covering error detection, formatting, and recovery classification
32
+ - Added unit tests for file-utils.js covering directory creation and file writing operations
33
+
34
+
35
+ ## [2.15.3] - 2026-02-10
36
+
37
+ ### ✨ Added
38
+ - Unit tests for `generate-changelog.js` command covering CHANGELOG generation, version detection, and error handling
39
+ - Unit tests for `github-client.js` covering CODEOWNERS parsing, reviewer detection, and GitHub repo parsing
40
+ - Unit tests for `hooks.js` command covering enable, disable, status, and uninstall operations
41
+
42
+
43
+ ## [2.15.2] - 2026-02-10
9
44
 
10
45
  ### 🔧 Changed
11
46
  - The bump-version command now uses the configured default branch (from github.pr.defaultBase) in the 'Next steps' output instead of hardcoded 'main'
12
47
 
48
+ ### 🐛 Fixed
49
+ - Fixed cross-platform path assertions in unit tests to use partial matching instead of exact paths, improving Windows compatibility
50
+
51
+
52
+ ## [2.15.1] - 2026-02-10
53
+
54
+ ### 🐛 Fixed
55
+
56
+ - Fixed cross-platform test compatibility for Windows environments by updating path assertions to use partial matching instead of exact Unix paths
57
+ - Fixed CI workflow to properly skip integration tests that require Claude CLI, with clear documentation about manual testing requirements
58
+ - Fixed Unix-specific tests to be skipped on Windows platform
59
+ - Fixed executable file permissions for bin/claude-hooks and hook templates (pre-commit, prepare-commit-msg)
60
+
61
+ ## [2.15.0] - 2026-02-10
62
+
63
+ ### ✨ Added
64
+
65
+ - Comprehensive testing suite with GitHub Actions CI workflow including lint, smoke tests, unit tests, integration tests, and dogfooding checks
66
+ - Cross-platform unit tests running on Ubuntu, Windows, and macOS with Node.js 18, 20, and 22
67
+ - Codecov integration for coverage reporting on unit and integration tests
68
+ - Per-module coverage thresholds for critical modules (config.js, helpers.js, git-operations.js, preset-loader.js, analysis-engine.js)
69
+
70
+ ### 🔧 Changed
71
+
72
+ - Updated ESLint configuration from ECMAScript 2021 to 2022
73
+ - Improved Jest configuration with separate coverage reporters (text, text-summary, lcov, html) and adjusted global coverage thresholds
74
+ - Updated .gitignore to track test files (\*.test.js) while ignoring coverage directory
75
+
76
+ ### 🐛 Fixed
77
+
78
+ - Fixed ESLint linting issues across utility and command modules including string concatenation, switch case indentation, and arrow function formatting (#68)
79
+
80
+ ## [2.14.4] - 2026-02-09
81
+
82
+ ### 🔧 Changed
83
+
84
+ - The migrate-config command now detects and fixes incorrectly placed preset fields in config overrides
85
+
86
+ ### 🐛 Fixed
87
+
88
+ - Fixed preset field being incorrectly placed inside overrides when using --set-preset command (#66)
13
89
 
14
90
  ## [2.14.3] - 2026-02-06
15
91
 
92
+ ### 🔧 Changed
93
+
94
+ - The bump-version command now uses the configured default branch (from github.pr.defaultBase) in the 'Next steps' output instead of hardcoded 'main'
16
95
 
17
96
  ## [2.14.2] - 2026-02-06
18
97
 
19
98
  ### ✨ Added
99
+
20
100
  - New `--push` flag for `bump-version` command to explicitly push tags to remote when desired
21
101
 
22
102
  ### 🔧 Changed
103
+
23
104
  - Changed `bump-version` default behavior to keep tags local instead of automatically pushing to remote (#65)
24
105
  - Tags are now pushed by `create-pr` command or manually with `--push` flag, providing better control over the release workflow
25
106
  - Updated documentation in README.md, README-NPM.md, and CLAUDE.md to reflect new tag push behavior
26
107
 
27
108
  ### ⚠️ Deprecated
109
+
28
110
  - The `--no-push` flag for `bump-version` is no longer needed as tags now stay local by default
29
111
 
30
112
  ### 🗑️ Removed
31
- - Removed RFC-001 documentation file (pr-metadata-engine-refactor.md) as the refactor has been completed
32
113
 
114
+ - Removed RFC-001 documentation file (pr-metadata-engine-refactor.md) as the refactor has been completed
33
115
 
34
116
  ## [2.14.1] - 2026-02-06
35
117
 
36
118
  ### 🔧 Changed
119
+
37
120
  - Improved `bump-version` command workflow - now automatically stages and commits version changes with conventional commit format before tag creation
38
121
  - Enhanced `bump-version` command flexibility - added `--no-commit` flag for manual workflows where users prefer to commit changes themselves
39
122
  - Improved error handling in `bump-version` - provides clearer guidance when staging or committing fails, with manual fallback instructions
40
123
  - Enhanced next-steps guidance in `bump-version` output - adapts instructions based on flags used (--no-commit, --no-push, --no-tag)
41
124
 
42
125
  ### 🐛 Fixed
126
+
43
127
  - Fixed `bump-version` workflow inconsistency - prevented tag creation when using `--no-commit` flag, as tags should only be created after changes are committed
44
128
  - Fixed potential git history issues - version bump commits now use `--no-verify` flag to bypass pre-commit hooks and prevent circular execution
45
129
 
46
130
  ### 🗑️ Removed
47
- - Removed redundant fallback warnings from `analyze-diff` and `create-pr` commands - warnings were unnecessary as base branch resolution now throws clear errors with suggestions instead
48
131
 
132
+ - Removed redundant fallback warnings from `analyze-diff` and `create-pr` commands - warnings were unnecessary as base branch resolution now throws clear errors with suggestions instead
49
133
 
50
134
  ## [2.14.0] - 2026-02-06
51
135
 
52
136
  ### ✨ Added
137
+
53
138
  - PR metadata engine (`pr-metadata-engine.js`) - centralized module for generating PR titles, descriptions, and test plans from branch diffs with timeout resilience (#63)
54
139
  - Tiered diff reduction system - automatically truncates large diffs using context reduction, proportional budgets, and stat-only summaries to prevent timeouts
55
140
  - Extended git operations - added `fetchRemote()`, `branchExists()`, `resolveBaseBranch()`, `getChangedFilesBetweenRefs()`, `getDiffBetweenRefs()`, and `getCommitsBetweenRefs()` to `git-operations.js`
56
141
  - RFC-001 documentation - comprehensive design specification for PR metadata engine refactor with timeout resilience strategy
57
142
 
58
143
  ### 🔧 Changed
144
+
59
145
  - Refactored `analyze-diff` command to use shared PR metadata engine - reduced from 262 to ~80 lines by eliminating duplicate git logic
60
146
  - Refactored `create-pr` command to use shared PR metadata engine - eliminated duplicate diff extraction logic (lines 340-420)
61
147
  - Improved timeout error handling - timeout errors now include `errorInfo` and are classified as recoverable for automatic retry with exponential backoff
62
148
  - Updated CLAUDE.md with PR metadata engine architecture, new git operations exports, and tiered diff reduction strategy
63
149
 
64
150
  ### 🐛 Fixed
151
+
65
152
  - Fixed timeout failures in `analyze-diff` for large diffs - now uses tiered reduction instead of monolithic diff processing
66
153
  - Fixed inconsistent behavior between `analyze-diff` and `create-pr` commands - both now share identical analysis logic via unified engine
67
154
 
68
155
  ### 🗑️ Removed
69
- - Removed unreliable `SUBAGENT_INSTRUCTION` text hint - replaced with deterministic tiered diff reduction for parallel processing
70
156
 
157
+ - Removed unreliable `SUBAGENT_INSTRUCTION` text hint - replaced with deterministic tiered diff reduction for parallel processing
71
158
 
72
159
  ## [2.13.0] - 2026-02-05
73
160
 
74
161
  ### ✨ Added
162
+
75
163
  - Interactive analysis command `claude-hooks analyze` - review all issues (INFO to BLOCKER) interactively before committing with auto-commit option
76
164
  - Shared analysis engine module (`analysis-engine.js`) - centralized file data building, analysis orchestration, and results display for both pre-commit hooks and interactive analysis
77
165
  - Support for version files in subdirectories - automatically searches parent directories when version files not found in repo root
78
166
  - Auto-commit functionality after interactive analysis - creates commit with auto-generated message when user confirms
79
167
 
80
168
  ### 🔧 Changed
169
+
81
170
  - Improved version detection logic for pom.xml files - enhanced reliability of version extraction in Maven projects
82
171
 
83
172
  ### 🐛 Fixed
84
- - Fixed version search logic for pom.xml files - corrected parsing issues in Maven version detection
85
173
 
174
+ - Fixed version search logic for pom.xml files - corrected parsing issues in Maven version detection
86
175
 
87
176
  ## [2.12.0] - 2026-02-03
88
177
 
package/LICENSE CHANGED
@@ -1,21 +1,21 @@
1
- MIT License
2
-
3
- Copyright (c) 2024 Pablo Rovito
4
-
5
- Permission is hereby granted, free of charge, to any person obtaining a copy
6
- of this software and associated documentation files (the "Software"), to deal
7
- in the Software without restriction, including without limitation the rights
8
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
- copies of the Software, and to permit persons to whom the Software is
10
- furnished to do so, subject to the following conditions:
11
-
12
- The above copyright notice and this permission notice shall be included in all
13
- copies or substantial portions of the Software.
14
-
15
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
1
+ MIT License
2
+
3
+ Copyright (c) 2024 Pablo Rovito
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
21
  SOFTWARE.
package/bin/claude-hooks CHANGED
@@ -34,90 +34,90 @@ async function main() {
34
34
  const command = args[0];
35
35
 
36
36
  switch (command) {
37
- case 'install':
38
- await runInstall(args.slice(1));
39
- break;
40
- case 'update':
41
- await runUpdate();
42
- break;
43
- case 'uninstall':
44
- runUninstall();
45
- break;
46
- case 'enable':
47
- runEnable(args[1]);
48
- break;
49
- case 'disable':
50
- runDisable(args[1]);
51
- break;
52
- case 'status':
53
- runStatus();
54
- break;
55
- case 'analyze':
56
- await runAnalyze({
57
- staged: !args.includes('--unstaged') && !args.includes('--all'),
58
- unstaged: args.includes('--unstaged'),
59
- all: args.includes('--all')
60
- });
61
- break;
62
- case 'analyze-diff':
63
- await runAnalyzeDiff(args.slice(1));
64
- break;
65
- case 'create-pr':
66
- await runCreatePr(args.slice(1));
67
- break;
68
- case 'setup-github':
69
- await runSetupGitHub();
70
- break;
71
- case 'presets':
72
- await runShowPresets();
73
- break;
74
- case '--set-preset':
75
- await runSetPreset(args[1]);
76
- break;
77
- case 'preset':
78
- // Handle subcommands: preset current
79
- if (args[1] === 'current') {
80
- await runCurrentPreset();
81
- } else {
82
- error(`Unknown preset subcommand: ${args[1]}`);
83
- }
84
- break;
85
- case 'migrate-config':
86
- await runMigrateConfig();
87
- break;
88
- case 'bump-version':
89
- await runBumpVersion(args.slice(1));
90
- break;
91
- case 'generate-changelog':
92
- await runGenerateChangelog(args.slice(1));
93
- break;
94
- case 'telemetry':
95
- // Handle subcommands: telemetry show, telemetry clear
96
- if (args[1] === 'show' || args[1] === undefined) {
97
- await runShowTelemetry();
98
- } else if (args[1] === 'clear') {
99
- await runClearTelemetry();
100
- } else {
101
- error(`Unknown telemetry subcommand: ${args[1]}`);
102
- }
103
- break;
104
- case '--debug':
105
- await runSetDebug(args[1]);
106
- break;
107
- case '--version':
108
- case '-v':
109
- case 'version':
110
- runShowVersion();
111
- break;
112
- case 'help':
113
- case '--help':
114
- case '-h':
115
- case undefined:
116
- runShowHelp();
117
- break;
118
- default:
119
- error(`Unknown command: ${command}`);
120
- runShowHelp();
37
+ case 'install':
38
+ await runInstall(args.slice(1));
39
+ break;
40
+ case 'update':
41
+ await runUpdate();
42
+ break;
43
+ case 'uninstall':
44
+ runUninstall();
45
+ break;
46
+ case 'enable':
47
+ runEnable(args[1]);
48
+ break;
49
+ case 'disable':
50
+ runDisable(args[1]);
51
+ break;
52
+ case 'status':
53
+ runStatus();
54
+ break;
55
+ case 'analyze':
56
+ await runAnalyze({
57
+ staged: !args.includes('--unstaged') && !args.includes('--all'),
58
+ unstaged: args.includes('--unstaged'),
59
+ all: args.includes('--all')
60
+ });
61
+ break;
62
+ case 'analyze-diff':
63
+ await runAnalyzeDiff(args.slice(1));
64
+ break;
65
+ case 'create-pr':
66
+ await runCreatePr(args.slice(1));
67
+ break;
68
+ case 'setup-github':
69
+ await runSetupGitHub();
70
+ break;
71
+ case 'presets':
72
+ await runShowPresets();
73
+ break;
74
+ case '--set-preset':
75
+ await runSetPreset(args[1]);
76
+ break;
77
+ case 'preset':
78
+ // Handle subcommands: preset current
79
+ if (args[1] === 'current') {
80
+ await runCurrentPreset();
81
+ } else {
82
+ error(`Unknown preset subcommand: ${args[1]}`);
83
+ }
84
+ break;
85
+ case 'migrate-config':
86
+ await runMigrateConfig();
87
+ break;
88
+ case 'bump-version':
89
+ await runBumpVersion(args.slice(1));
90
+ break;
91
+ case 'generate-changelog':
92
+ await runGenerateChangelog(args.slice(1));
93
+ break;
94
+ case 'telemetry':
95
+ // Handle subcommands: telemetry show, telemetry clear
96
+ if (args[1] === 'show' || args[1] === undefined) {
97
+ await runShowTelemetry();
98
+ } else if (args[1] === 'clear') {
99
+ await runClearTelemetry();
100
+ } else {
101
+ error(`Unknown telemetry subcommand: ${args[1]}`);
102
+ }
103
+ break;
104
+ case '--debug':
105
+ await runSetDebug(args[1]);
106
+ break;
107
+ case '--version':
108
+ case '-v':
109
+ case 'version':
110
+ runShowVersion();
111
+ break;
112
+ case 'help':
113
+ case '--help':
114
+ case '-h':
115
+ case undefined:
116
+ runShowHelp();
117
+ break;
118
+ default:
119
+ error(`Unknown command: ${command}`);
120
+ runShowHelp();
121
121
  }
122
122
  }
123
123
 
@@ -11,7 +11,6 @@ import {
11
11
  colors,
12
12
  error,
13
13
  info,
14
- warning,
15
14
  checkGitRepo
16
15
  } from './helpers.js';
17
16
 
@@ -43,7 +43,7 @@ export async function runCreatePr(args) {
43
43
 
44
44
  // Import GitHub API module
45
45
  logger.debug('create-pr', 'Importing GitHub API modules');
46
- const { createPullRequest, GitHubAPIError, validateToken, findExistingPR } = await import('../utils/github-api.js');
46
+ const { createPullRequest, validateToken, findExistingPR } = await import('../utils/github-api.js');
47
47
  const { parseGitHubRepo } = await import('../utils/github-client.js');
48
48
 
49
49
  showInfo('🚀 Creating Pull Request...');
@@ -30,7 +30,7 @@ export async function runSetDebug(value) {
30
30
  const config = await getConfig();
31
31
  const isEnabled = config.system.debug || false;
32
32
  console.log('');
33
- info(`Debug mode: ${isEnabled ? colors.green + 'enabled' + colors.reset : colors.red + 'disabled' + colors.reset}`);
33
+ info(`Debug mode: ${isEnabled ? `${colors.green }enabled${ colors.reset}` : `${colors.red }disabled${ colors.reset}`}`);
34
34
  console.log('');
35
35
  } catch (err) {
36
36
  error(`Failed to check debug status: ${err.message}`);
@@ -193,10 +193,15 @@ export async function updateConfig(propertyPath, value, options = {}) {
193
193
  }
194
194
 
195
195
  // Set value at propertyPath (support dot notation like 'system.debug')
196
- // For v2.8.0 format, write inside 'overrides' so loadUserConfig picks it up
196
+ // For v2.8.0 format, write inside 'overrides' EXCEPT for top-level fields
197
197
  const pathParts = propertyPath.split('.');
198
198
  let current = config;
199
- if (config.version === '2.8.0') {
199
+
200
+ // Top-level fields that should NOT go into overrides
201
+ const topLevelFields = ['preset', 'version'];
202
+ const isTopLevelField = pathParts.length === 1 && topLevelFields.includes(pathParts[0]);
203
+
204
+ if (config.version === '2.8.0' && !isTopLevelField) {
200
205
  if (!config.overrides || typeof config.overrides !== 'object') {
201
206
  config.overrides = {};
202
207
  }
@@ -263,12 +268,12 @@ export function getLatestVersion(packageName) {
263
268
  */
264
269
  export class Entertainment {
265
270
  static jokes = [
266
- "Why do programmers prefer dark mode? Because light attracts bugs!",
267
- "A QA engineer walks into a bar. Orders 1 beer. Orders 0 beers. Orders -1 beers.",
271
+ 'Why do programmers prefer dark mode? Because light attracts bugs!',
272
+ 'A QA engineer walks into a bar. Orders 1 beer. Orders 0 beers. Orders -1 beers.',
268
273
  "What's a pirate's favorite programming language? R!",
269
274
  "There are 10 types of people: those who understand binary and those who don't.",
270
- "Why do programmers confuse Halloween with Christmas? Because Oct 31 = Dec 25",
271
- "What does one bit say to another? See you on the bus!",
275
+ 'Why do programmers confuse Halloween with Christmas? Because Oct 31 = Dec 25',
276
+ 'What does one bit say to another? See you on the bus!',
272
277
  "Why don't Java and C++ get along? Because they have different views on pointers.",
273
278
  "My code doesn't have bugs, just undocumented features."
274
279
  ];
@@ -63,7 +63,7 @@ async function checkVersionAndPromptUpdate() {
63
63
  success('Update completed. Please run your command again.');
64
64
  process.exit(0); // Exit so user restarts the process
65
65
  } catch (e) {
66
- error('Error updating: ' + e.message);
66
+ error(`Error updating: ${ e.message}`);
67
67
  resolve(false);
68
68
  }
69
69
  } else {
@@ -158,10 +158,9 @@ async function checkClaudeAuth() {
158
158
 
159
159
  /**
160
160
  * Check complete dependencies (like setup-wsl.sh)
161
- * @param {string|null} sudoPassword - Not used in v2.0.0+
162
161
  * @param {boolean} skipAuth - Skip Claude verification
163
162
  */
164
- async function checkAndInstallDependencies(sudoPassword = null, skipAuth = false) {
163
+ async function checkAndInstallDependencies(skipAuth = false) {
165
164
  info('Checking system dependencies...');
166
165
 
167
166
  // Check Node.js
@@ -252,7 +251,7 @@ function updateGitignore() {
252
251
  }
253
252
 
254
253
  // Add the missing entries
255
- gitignoreContent += missingEntries.join('\n') + '\n';
254
+ gitignoreContent += `${missingEntries.join('\n') }\n`;
256
255
 
257
256
  // Write the updated file
258
257
  fs.writeFileSync(gitignorePath, gitignoreContent);
@@ -294,7 +293,7 @@ function configureGit() {
294
293
  }
295
294
 
296
295
  } catch (e) {
297
- warning('Error configuring Git: ' + e.message);
296
+ warning(`Error configuring Git: ${ e.message}`);
298
297
  }
299
298
  }
300
299
 
@@ -399,7 +398,7 @@ export async function runInstall(args) {
399
398
 
400
399
  // v2.0.0+: No sudo needed (pure Node.js, no system packages required)
401
400
  // Check dependencies
402
- await checkAndInstallDependencies(null, skipAuth);
401
+ await checkAndInstallDependencies(skipAuth);
403
402
 
404
403
  const templatesPath = getTemplatesPath();
405
404
  const hooksPath = '.git/hooks';
@@ -641,8 +640,8 @@ export async function runInstall(args) {
641
640
  const settingsLocalPath = path.join(claudeDir, 'settings.local.json');
642
641
  if (!fs.existsSync(settingsLocalPath)) {
643
642
  const settingsLocalContent = {
644
- "_comment": "Local settings - DO NOT COMMIT. This file is gitignored.",
645
- "githubToken": ""
643
+ '_comment': 'Local settings - DO NOT COMMIT. This file is gitignored.',
644
+ 'githubToken': ''
646
645
  };
647
646
  fs.writeFileSync(settingsLocalPath, JSON.stringify(settingsLocalContent, null, 2));
648
647
  info('settings.local.json created (add your GitHub token here)');
@@ -36,7 +36,29 @@ export async function runMigrateConfig() {
36
36
 
37
37
  // Check if already in v2.8.0 format
38
38
  if (rawConfig.version === '2.8.0') {
39
- success('✅ Config is already in v2.8.0 format.');
39
+ // Bug fix: Check if preset was incorrectly placed in overrides
40
+ let fixed = false;
41
+ if (rawConfig.overrides?.preset) {
42
+ info('🔧 Fixing incorrectly placed preset field...');
43
+
44
+ // If top-level preset doesn't exist or differs, use the one from overrides
45
+ if (!rawConfig.preset || rawConfig.preset !== rawConfig.overrides.preset) {
46
+ info(` Moving preset '${rawConfig.overrides.preset}' from overrides to top level`);
47
+ rawConfig.preset = rawConfig.overrides.preset;
48
+ }
49
+
50
+ // Remove from overrides
51
+ delete rawConfig.overrides.preset;
52
+
53
+ // Write back
54
+ fs.writeFileSync(configPath, JSON.stringify(rawConfig, null, 4));
55
+ fixed = true;
56
+ success('✅ Config fixed: preset moved to correct location.');
57
+ }
58
+
59
+ if (!fixed) {
60
+ success('✅ Config is already in v2.8.0 format.');
61
+ }
40
62
  return;
41
63
  }
42
64
 
@@ -87,7 +109,7 @@ export async function runMigrateConfig() {
87
109
  info('📖 See .claude/config.advanced.example.json for documentation');
88
110
  }
89
111
 
90
- console.log(`\n✨ New config:`);
112
+ console.log('\n✨ New config:');
91
113
  console.log(JSON.stringify(newConfig, null, 2));
92
114
  console.log(`\n💾 Old config backed up to: ${backupPath}`);
93
115
  console.log('\n💡 Many parameters are now hardcoded with sensible defaults');
@@ -71,7 +71,7 @@ export async function runSetupGitHub() {
71
71
  // Save token
72
72
  const saveResult = saveGitHubToken(trimmedToken);
73
73
  if (!saveResult.success) {
74
- showError('Failed to save token: ' + saveResult.error);
74
+ showError(`Failed to save token: ${ saveResult.error}`);
75
75
  return;
76
76
  }
77
77
  showSuccess(`Token saved to ${saveResult.path}`);
@@ -61,7 +61,7 @@ export async function runUpdate() {
61
61
  success('Update completed');
62
62
  await runInstall(['--force']);
63
63
  } catch (updateError) {
64
- error('Error updating: ' + updateError.message);
64
+ error(`Error updating: ${ updateError.message}`);
65
65
  }
66
66
  }
67
67
  }
package/lib/config.js CHANGED
@@ -26,12 +26,8 @@
26
26
 
27
27
  import fs from 'fs';
28
28
  import path from 'path';
29
- import { fileURLToPath } from 'url';
30
29
  import logger from './utils/logger.js';
31
30
 
32
- const __filename = fileURLToPath(import.meta.url);
33
- const __dirname = path.dirname(__filename);
34
-
35
31
  /**
36
32
  * Hardcoded defaults (v3.0.0)
37
33
  * These are NOT user-configurable - sensible defaults that work for everyone
@@ -184,7 +184,7 @@ const main = async () => {
184
184
  const taskId = await getOrPromptTaskId({
185
185
  prompt: false, // Don't prompt - just detect from branch
186
186
  required: false,
187
- config: config // Pass config for custom pattern
187
+ config // Pass config for custom pattern
188
188
  });
189
189
 
190
190
  // Note: getOrPromptTaskId() already logs the task ID if found
@@ -302,7 +302,7 @@ const main = async () => {
302
302
  }
303
303
 
304
304
  // Write to commit message file
305
- await fs.writeFile(commitMsgFile, message + '\n', 'utf8');
305
+ await fs.writeFile(commitMsgFile, `${message }\n`, 'utf8');
306
306
 
307
307
  const duration = ((Date.now() - startTime) / 1000).toFixed(2);
308
308
  console.error(`⏱️ Message generation completed in ${duration}s`);