Worktree setup
Skill mickzijdel/dev-hooks/plugins/dev-hooks/skills/worktree-setup
Hooks and skills for Claude to write better code and verify its work, and an easy start to using Claude Code
npx -y skills add mickzijdel/dev-hooks --skill worktree-setupAssembled from the repository path, not quoted from the project. Check it against their README if it does not work.
One thing to look at
- 0 stars0 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.
What its author says it does
Copied from the file, not written here
Provision a freshly-created git worktree so it's actually ready to work in — trust its mise.toml, copy gitignored-but-needed files (Rails config/master.key, .env, …) from the main checkout, and re-mark shebang scripts executable. Use right after creating a worktree (native EnterWorktree or `git worktree add`), or when a new worktree errors with "mise.toml not trusted", is missing secrets/.env, can't load the app, or has non-executable scripts. Also when parallel worktrees collide on the same dev-server port or database — opt into per-worktree ports + databases via a `.worktree-isolate.conf`. Pairs with using-git-worktrees (which creates the worktree; this provisions it).
SKILL.md
5.8 KB, ~1.3k tokens by cl100k_base, as published. Nobody here has run it
worktree-setup
A fresh worktree is a clean git checkout — and that's the problem. The committed files are
there, but everything the working tree needs that git doesn't track is not: the mise.toml
is untrusted, gitignored secrets/config (config/master.key, .env, service-account JSON) are
absent, and core.fileMode=false checkouts can land shebang scripts without +x. So the app
won't boot and the tooling errors until you fix each by hand — every single time.
This skill closes those gaps in one step. It provisions a worktree; it does not create one (only the harness can switch the session into a worktree). Use it with [[using-git-worktrees]], not instead of it.
Workflow
-
Ensure
.worktrees/is ignored. Before creating any project-local worktree, confirm the directory is gitignored so its contents never get tracked:git check-ignore -q .worktrees || printf '.worktrees/\n' >>.gitignore # then commit it(The native
EnterWorktreetool uses.claude/worktrees/, which is already kept out of status; only the manualgit worktree addfallback needs this.) -
Branch from local HEAD, not origin. Your local
mainoften leads or lagsorigin; a worktree branched from origin silently drops local commits.git config worktree.baseref head(
setup-worktree.shalso sets this, idempotently, for next time.) -
Create the worktree. Prefer the native tool so the session switches into it:
- Native:
EnterWorktree(withworktree.baseref headset, it branches from local HEAD). - Fallback:
git worktree add .worktrees/<name> -b <branch> HEAD && cd .worktrees/<name>
- Native:
-
Provision it — run from inside the new worktree:
bash "$CLAUDE_PLUGIN_ROOT/skills/worktree-setup/scripts/setup-worktree.sh"It trusts the worktree's
mise.toml(safe — it's a worktree of a repo you already trust, so this does not contradict [[dev-env-setup]]'s "never auto-trust unknown configs" rule), copies the gitignored files, and re-marks shebang scripts executable. It reportscopied,skipped_heavy,mise_trusted,exec_fixed, andisolated. Pass--source DIRto override the copy origin, or a positional worktree path to provision one you're not currently inside. If the repo carries a.worktree-isolate.conf, this step also allocates the worktree its own port + database (see Per-worktree isolation below). -
Verify, then work. Confirm the toolchain loads (
mise exec -- <tool> --version) and the baseline tests pass, then proceed with the worktree-per-agent workflow (incremental commits → merge to main → clean up via [[finishing-a-development-branch]]).
What gets copied
Everything gitignored and present in the main checkout is copied into the worktree, with one
exclusion list: known-heavy build/dependency dirs (node_modules, .venv, venv,
vendor/bundle, tmp, dist, build, .next, .nuxt, target, __pycache__,
.pytest_cache, .ruff_cache, .mypy_cache, coverage, .git) and the worktree dirs
themselves (.worktrees, .claude/worktrees). The script uses git ls-files --others --ignored --directory, so a fully-ignored node_modules/ is one entry to skip, not 40k files to walk.
These are copies, not commits — the secrets land in the worktree's working tree (itself gitignored there too) so the app runs; they're never staged. If a repo carries a gitignored dir you do want (uploads, fixtures) it comes along automatically unless its name is on the heavy list; if it's huge and unwanted, delete it from the worktree after.
Per-worktree isolation
Copying .env verbatim means every worktree points at the same port and the same
database — so two dev servers fight over :3000 and parallel migrations stomp one shared DB.
Opt in by committing a .worktree-isolate.conf at the repo root; setup-worktree.sh then hands
off to isolate-worktree.sh, which allocates each worktree a stable, collision-free offset and
writes the derived values into a gitignored mise.local.toml overlay (layering over the
committed mise.toml — the copied .env is never touched).
# .worktree-isolate.conf — committed; declares what to isolate (ports/hostnames aren't secrets)
WT_BASE_PORT=3000 # PORT = base + per-worktree offset (offset 0 = main checkout)
WT_DB_SUFFIX_VAR=WORKTREE_DB_SUFFIX # export "_<slug>" for database.yml to read
WT_REDIS_URL_VAR=REDIS_URL # redis://localhost:6379/<offset>
WT_COMPOSE_NAME=myapp # emit COMPOSE_PROJECT_NAME=<name>_<slug> for compose/devcontainers
The offset is stable across re-runs and self-heals: a shared registry in the git common dir
tracks slug→offset, and removing a worktree frees its offset for the next one. Host-native runs
read PORT + the DB suffix; a per-worktree devcontainer reads COMPOSE_PROJECT_NAME. See
references/isolation.md for the full Rails recipe (database.yml
suffix + bin/rails db:prepare), the devcontainer notes, and the dotenv alternative.
What ships with it: 3 files
18.5 KB alongside SKILL.md, 2 of them executable
references/
- isolation.md4.0 KB
scripts/
- isolate-worktree.shruns7.7 KB
- setup-worktree.shruns6.8 KB
Gives 0 of the 12 instructions most project setup skills give in ~1.3k tokens
Counted across 999 of the 1,637 authors here whose files we hold, read 2026-08-07
- Ask one question at a timein 29 of 999, across 28 files
- Detect the package manager from lockfilesin 28 of 999, across 9 files
- Present findings to the userin 26 of 999, across 5 files
- Explore current repo statein 24 of 999, across 3 files
- Update the agent skills block in place if it existsin 24 of 999, across 3 files
- Install husky lint-staged and prettierin 23 of 999, across 4 files
- Create the lintstagedrc filein 22 of 999, across 3 files
- Commit all changed filesin 22 of 999, across 3 files
- Run lint-staged to verify it worksin 22 of 999, across 3 files
- Create the husky pre-commit filein 21 of 999, across 2 files
- Create a prettierrc file if missingin 21 of 999, across 2 files
- Initialize huskyin 21 of 999, across 2 files
Said here and by no other author read
- set the worktree base reference to local head
- create the worktree via the native tool
- trust the worktree mise.toml
- copy needed gitignored files
- re-mark shebang scripts executable
- verify the toolchain loads
Grouped from the skills themselves: near-identical wordings counted once, and counted by distinct author, so one author publishing three of these counts once. Length counted with cl100k_base; the agent that loads this file may tokenize it differently.