diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 000000000..7387a83b3 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,17 @@ +# Ensure shell scripts always have LF line endings +*.sh text eol=lf + +# Ensure the polyglot wrapper keeps LF (it's parsed by both cmd and bash) +*.cmd text eol=lf + +# Common text files +*.md text eol=lf +*.json text eol=lf +*.js text eol=lf +*.mjs text eol=lf +*.ts text eol=lf + +# Explicitly mark binary files +*.png binary +*.jpg binary +*.gif binary diff --git a/RELEASE-NOTES.md b/RELEASE-NOTES.md index 52686110b..7bafbf26e 100644 --- a/RELEASE-NOTES.md +++ b/RELEASE-NOTES.md @@ -16,6 +16,14 @@ Components: The visual companion is opt-in and falls back gracefully to terminal-only operation. +### Bug Fixes + +**Fixed Windows hook execution for Claude Code 2.1.x** + +Claude Code 2.1.x changed how hooks execute on Windows: it now auto-detects `.sh` files in commands and prepends `bash `. This broke the polyglot wrapper pattern because `bash "run-hook.cmd" session-start.sh` tries to execute the .cmd file as a bash script. + +Fix: hooks.json now calls session-start.sh directly. Claude Code 2.1.x handles the bash invocation automatically. Also added .gitattributes to enforce LF line endings for shell scripts (fixes CRLF issues on Windows checkout). + ### Improvements **Instruction priority clarified in using-superpowers** diff --git a/hooks/hooks.json b/hooks/hooks.json index d1745650c..17e0ac87b 100644 --- a/hooks/hooks.json +++ b/hooks/hooks.json @@ -6,7 +6,7 @@ "hooks": [ { "type": "command", - "command": "\"${CLAUDE_PLUGIN_ROOT}/hooks/run-hook.cmd\" session-start.sh" + "command": "${CLAUDE_PLUGIN_ROOT}/hooks/session-start.sh" } ] } diff --git a/hooks/run-hook.cmd b/hooks/run-hook.cmd index 8d8458fcb..b2a8b3acc 100755 --- a/hooks/run-hook.cmd +++ b/hooks/run-hook.cmd @@ -1,6 +1,30 @@ : << 'CMDBLOCK' @echo off -REM Polyglot wrapper: runs .sh scripts cross-platform +REM ============================================================================ +REM DEPRECATED: This polyglot wrapper is no longer used as of Claude Code 2.1.x +REM ============================================================================ +REM +REM Claude Code 2.1.x changed the Windows execution model for hooks: +REM +REM Before (2.0.x): Hooks ran with shell:true, using the system default shell. +REM This wrapper provided cross-platform compatibility by +REM being both a valid .cmd file (Windows) and bash script. +REM +REM After (2.1.x): Claude Code now auto-detects .sh files in hook commands +REM and prepends "bash " on Windows. This broke the wrapper +REM because the command: +REM "run-hook.cmd" session-start.sh +REM became: +REM bash "run-hook.cmd" session-start.sh +REM ...and bash cannot execute a .cmd file. +REM +REM The fix: hooks.json now calls session-start.sh directly. Claude Code 2.1.x +REM handles the bash invocation automatically on Windows. +REM +REM This file is kept for reference and potential backward compatibility. +REM ============================================================================ +REM +REM Original purpose: Polyglot wrapper to run .sh scripts cross-platform REM Usage: run-hook.cmd [args...] REM The script should be in the same directory as this wrapper