Plugin cache strips execute permission from hook scripts
Bug
The plugin cache mechanism strips the execute bit from hook handler scripts when downloading/caching plugins. This causes SessionStart:startup hook error on every session start for affected plugins.
Affected Plugins
explanatory-output-style—hooks-handlers/session-start.shlearning-output-style—hooks-handlers/session-start.sh
Details
Both files are committed upstream with mode 100755 (executable):
plugins/explanatory-output-style/hooks-handlers/session-start.sh mode=100755
plugins/learning-output-style/hooks-handlers/session-start.sh mode=100755
But after plugin cache download, the local copies have 644 (not executable):
-rw-r--r-- 1 bosco bosco 1468 Mar 25 08:20 session-start.sh
-rw-r--r-- 1 bosco bosco 3564 Mar 25 08:20 session-start.sh
Since the hooks.json command references the script directly (${CLAUDE_PLUGIN_ROOT}/hooks-handlers/session-start.sh), Claude Code fails to execute it.
Why superpowers is unaffected
The superpowers plugin works around this by using a polyglot .cmd wrapper (run-hook.cmd) which retains its execute bit. The wrapper explicitly calls bash on the target script, bypassing the permission issue.
Workaround
chmod +x ~/.claude/plugins/cache/claude-plugins-official/explanatory-output-style/unknown/hooks-handlers/session-start.sh
chmod +x ~/.claude/plugins/cache/claude-plugins-official/learning-output-style/unknown/hooks-handlers/session-start.sh
This workaround is fragile — the next plugin cache refresh will likely restore the broken permissions.
Suggested Fix
Either:
- Preserve git file modes (
100755) when downloading plugin files to cache - Or auto-detect and
chmod +xany file referenced by acommandfield inhooks.json
Environment
- Claude Code 2.1.83
- Linux (CachyOS / Arch-based)
- bash 5.2
This issue has 1 comment on GitHub. Read the full discussion on GitHub ↗