Worktree: $CLAUDE_PROJECT_DIR hooks can't find .claude/helpers/ files
Summary
When Claude Code spawns a git worktree (via the EnterWorktree tool or isolation: "worktree" agents), hooks defined in settings.json that reference $CLAUDE_PROJECT_DIR/.claude/helpers/ fail with MODULE_NOT_FOUND because the .claude/ directory is not copied or symlinked into the worktree.
Reproduction
- Have a project with hooks in
.claude/settings.jsonthat reference helper scripts:
``json``
{
"hooks": {
"Stop": [{
"hooks": [{
"type": "command",
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/auto-memory-hook.mjs\" sync"
}]
}]
}
}
- Place helper scripts in
.claude/helpers/(e.g.auto-memory-hook.mjs,hook-handler.cjs) - Start a session in a worktree (e.g.
/.claude/worktrees/bubbly-questing-hopper/) - Trigger any hook — it fails:
Error: Cannot find module '/Users/paul/code/universeos/.claude/worktrees/bubbly-questing-hopper/.claude/helpers/auto-memory-hook.mjs'
at Function._resolveFilename (node:internal/modules/cjs/loader:1383:15)
...
code: 'MODULE_NOT_FOUND'
Expected behavior
Hooks using $CLAUDE_PROJECT_DIR/.claude/helpers/ should work identically in worktrees and the main repo. Either:
- Symlink
.claude/helpers/from the main repo into the worktree's.claude/directory when creating the worktree, or - Set
$CLAUDE_PROJECT_DIRto point to the original repo root (not the worktree) so hooks resolve against the canonical.claude/directory, or - Provide a separate env var (e.g.
$CLAUDE_MAIN_PROJECT_DIR) that always points to the original repo root for hook resolution
Workaround
Manually copy the helpers directory into the worktree:
mkdir -p <worktree>/.claude/helpers
cp <main-repo>/.claude/helpers/* <worktree>/.claude/helpers/
Environment
- Claude Code: latest (Claude Opus 4.6)
- Node.js: v22.22.0
- Platform: macOS (darwin arm64)
This issue has 3 comments on GitHub. Read the full discussion on GitHub ↗