What is Git Worktree?
Git worktree lets you check out multiple branches from the same repository into separate directories simultaneously. Each worktree is an independent working copy with its own branch, staging area, and working files.
Why Use It?
- Work on a bugfix while keeping your feature branch intact
- Review someone else’s PR without stashing your changes
- Run two branches side-by-side for comparison
- Build/test different branches in parallel
- No need to stash or commit incomplete work to switch branches
How It Works
.git/ ← Single shared repository (objects, refs, config)
├── worktrees/ ← Metadata for each linked worktree
│ ├── branch-a/
│ └── branch-b/
├── HEAD ← Points to the MAIN worktree's branch
├── refs/
└── config
../project-main/ ← Main worktree (on branch: main)
../project-feature/ ← Linked worktree (on branch: feature-x)
../project-hotfix/ ← Linked worktree (on branch: hotfix-y)
All worktrees share the same .git/objects database - no duplication of history.
Commands
1. Create a Worktree
# Create and check out a new branch
git worktree add <path> <branch>
# Create and check out an existing branch
git worktree add <path> <existing-branch>
# Create a new branch and check it out
git worktree add -b <new-branch> <path>
# Create with detached HEAD
git worktree add --detach <path>
# Create with specific commit
git worktree add <path> <commit-hash>
Examples:
# New branch "feature/auth" at ../project-feature
git worktree add ../project-feature -b feature/auth
# Check out existing branch "main" at ../project-main-review
git worktree add ../project-main-review main
# Detached HEAD at a specific commit
git worktree add --detach ../project-review abc1234
2. List Worktrees
git worktree list
Output:
/path/to/project-main a1b2c3d [main]
/path/to/project-feature e4f5g6h [feature/auth]
/path/to/project-hotfix i7j8k9l [hotfix/login]
3. Remove a Worktree
# Remove (must be clean — no uncommitted changes)
git worktree remove <path>
# Force remove (discards uncommitted changes)
git worktree remove --force <path>
# Prune stale worktree entries (if directory was deleted manually)
git worktree prune
Examples:
git worktree remove ../project-feature
git worktree remove -f ../project-hotfix
4. Lock / Unlock a Worktree
Locking prevents a worktree from being pruned or accidentally removed.
# Lock a worktree
git worktree lock <path>
# Lock with a reason
git worktree lock --reason "In use for production debugging" <path>
# Unlock a worktree
git worktree unlock <path>
5. Move a Worktree
# Move to a new location
git worktree move <path> <new-path>
Example:
git worktree move ../project-feature ../new-location/project-feature
6. Repair a Worktree
If the link between a worktree and the main .git directory is broken:
git worktree repair
7. Clean Up Stale Entries
If you deleted a worktree directory manually (without git worktree remove):
git worktree prune
Common Workflows
Workflow 1: Quick Bugfix While Working on a Feature
# You're on feature/auth, need to fix a production bug
git worktree add ../project-hotfix main
cd ../project-hotfix
git checkout -b hotfix/critical-bug
# ... make fix, commit, push ...
cd ../project-main
git worktree remove ../project-hotfix
Workflow 2: Review a Pull Request
# Fetch the PR branch
git fetch origin pull/123/head:pr-123
# Create a worktree to review it
git worktree add ../project-pr-review pr-123
cd ../project-pr-review
# Review, test, etc.
cd ../project-main
git worktree remove ../project-pr-review
git branch -D pr-123
Workflow 3: Parallel Builds / Tests
# Main worktree on main branch
git worktree add ../project-bench -b benchmark/experiment
cd ../project-bench
# Run benchmarks while continuing development in main worktree
Workflow 4: Bisect Without Losing Your Place
# Start bisect in a separate worktree
git worktree add ../project-bisect
cd ../project-bisect
git bisect start
git bisect bad <commit>
git bisect good <commit>
# ... test commits ...
git bisect reset
cd ../project-main
git worktree remove ../project-bisect
Rules and Limitations
- Same branch cannot be checked out in multiple worktrees (unless using
--force) - Bare repositories are recommended as the main repo when using many worktrees
- Git submodules have limited support in worktrees
- Ignored files: Each worktree has its own
.git/info/excludebut shares.gitignore - Hooks: All worktrees share the same hooks from the main
.git/hooks/ - Config: Shared across all worktrees (use
git worktree configfor per-worktree settings)
Per-Worktree Configuration
# Set a config value for a specific worktree
git worktree config set <key> <value>
# Example: different user.email per worktree
git worktree config set user.email "review@company.com"
Bare Repository Pattern (Recommended for Heavy Use)
If you use worktrees frequently, convert your repo to bare:
# Clone as bare
git clone --bare git@github.com:user/repo.git ~/projects/repo.git
# Create worktrees from bare repo
cd ~/projects/repo.git
git worktree add ../main main
git worktree add ../feature -b feature/new-ui
# Structure:
# ~/projects/repo.git/ ← bare repo (no working files)
# ~/projects/main/ ← worktree on main
# ~/projects/feature/ ← worktree on feature/new-ui
Troubleshooting
“branch is already checked out”
Another worktree has this branch. Use a different branch or:
git worktree add --force <path> <branch>
Stale worktree entries after manual deletion
git worktree prune
Broken worktree links
git worktree repair
Cannot remove worktree with uncommitted changes
Commit or stash first, or force remove:
git worktree remove --force <path>
Quick Reference Card
| Command | Description |
|---|---|
git worktree add |
Create a new worktree |
git worktree add -b |
Create + new branch |
git worktree add --detach |
Create with detached HEAD |
git worktree list |
Show all worktrees |
git worktree remove |
Delete a worktree |
git worktree remove -f |
Force delete a worktree |
git worktree lock |
Lock a worktree |
git worktree unlock |
Unlock a worktree |
git worktree move |
Move a worktree |
git worktree prune |
Clean stale entries |
git worktree repair |
Fix broken links |
Tips
- Use absolute paths or paths outside the main repo directory
- Name worktree directories clearly (e.g.,
../project-hotfix, not../wt1) - Combine with
git stashif you need to share uncommitted changes between worktrees - IDE support: most IDEs (VS Code, WebStorm) handle worktrees well - just open the worktree directory as a separate window
Source: Original article on HackMD. Local review copy retrieved September 10, 2026.