git worktree: how to work on multiple branches at once
git worktree lets you attach several working directories to one repository, each with its own branch checked out. git worktree add ../hotfix main creates a folder with the main branch next to your project; history and objects are shared, so nothing needs to be cloned again.
What git worktree does
git worktree attaches several working directories to a single repository. Your main folder has a feature branch checked out, while a sibling folder has main for an urgent hotfix — and both exist at the same time. Objects, commits and branches are shared: a commit made in one folder is immediately visible from the other, no push or fetch needed.
Without worktree, a context switch looks like this: git stash, git switch main, fix, git switch back, git stash pop. If the project has a slow build or a heavy node_modules, every branch switch also invalidates caches. The other option is to clone the repository again, but then you get two independent copies of the history that have to be synced through the remote.
Worktree gives you the best of both: separate folders, but a single .git database. This works because a branch in Git is just a pointer to a commit, not a copy of the files, and nothing stops different working copies from looking at different pointers.
How to create an additional working tree
The basic form is git worktree add <path> [<branch>]. Let's go through the main variants.
Check out an existing branch
cd ~/projects/shop
git worktree add ../shop-main main
Preparing worktree (checking out 'main')
HEAD is now at 3f2c1ab Update README
A shop-main folder with the main branch appears next to your project. Just cd into it and work as in any repository.
Create a new branch together with the working tree
git worktree add -b hotfix/payment-timeout ../shop-hotfix main
The -b flag creates the hotfix/payment-timeout branch from main and checks it out in the new folder. -B does the same, but if the branch already exists it resets it to the given commit — use it carefully.
Short form
git worktree add ../experiment
If you don't specify a branch, Git creates a new branch named after the last path component (here, experiment) from the current HEAD. If a branch with that name already exists, it checks that one out.
A working tree without a branch
git worktree add --detach ../shop-v1.4 v1.4.0
Detached HEAD mode is handy for building or checking an old release by tag without creating extra branches.
A branch from the remote
git fetch origin
git worktree add ../review-auth feature/auth
If there's no local feature/auth branch but exactly one remote origin/feature/auth, Git creates a local tracking branch — just like git switch feature/auth. It's a convenient way to review someone else's pull request without touching your own work.
How to list and remove working trees
git worktree list
/home/anna/projects/shop a1b2c3d [feature/cart]
/home/anna/projects/shop-hotfix 7e8f9a0 [hotfix/payment-timeout]
/home/anna/projects/shop-v1.4 5d6e7f8 (detached HEAD)
The first line is the main worktree; the rest are linked worktrees. For scripts there's machine-readable output: git worktree list --porcelain.
Once the hotfix is merged, remove the working tree:
git worktree remove ../shop-hotfix
git branch -d hotfix/payment-timeout
git worktree remove deletes the folder and its administrative entries. If the copy has uncommitted changes or untracked files, the command refuses; add --force only if you're sure you don't need them. Note that the branch itself isn't deleted — you remove it separately.
If the folder was deleted manually
Deleting the folder in a file manager or with rm -rf leaves an orphaned entry in .git/worktrees, and the branch is still considered checked out. Clean up such entries:
git worktree prune --verbose
Git also does this periodically during garbage collection, but there's no need to wait.
How it works under the hood
A linked working tree has a .git file instead of a .git folder, containing a single line:
gitdir: /home/anna/projects/shop/.git/worktrees/shop-hotfix
That administrative folder holds data unique to the working tree: its own HEAD, its own index (staging area), its own merge and rebase state. Everything else is shared: objects, branches, tags, remotes, config and hooks.
| Per working tree | Shared by all |
|---|---|
| HEAD (current branch or commit) | Objects and the entire history |
| Index (git add) | Local and remote branches, tags |
| In-progress merge, rebase, cherry-pick | Stash (refs/stash is shared) |
| Files in the working directory | .git/config and hooks |
The table reveals a non-obvious detail: git stash list shows the same entries in every working tree. That's actually useful — you can stash changes in one folder and pop them in another.
The main limitation: one branch, one working tree
You can't check out the same branch in two working trees. If you try, Git responds with an error along these lines:
git worktree add ../shop-copy feature/cart
fatal: 'feature/cart' is already used by worktree at '/home/anna/projects/shop'
(in older Git versions the message reads "is already checked out at"). The restriction protects you from a commit in one folder silently moving the branch out from under another. Workarounds: create a new branch from the same commit (-b), open the copy with --detach, or, if you really must, use --force and accept the consequences.
For the same reason, you can't run git switch main in your main folder while main is checked out in a sibling working tree.
Practical scenarios
An urgent hotfix in the middle of a feature
git worktree add -b hotfix/null-price ../shop-hotfix main
cd ../shop-hotfix
# fix and test
git commit -am "Fix crash on empty price"
git push -u origin hotfix/null-price
cd ../shop
git worktree remove ../shop-hotfix
Your unfinished feature stays exactly as it was, nothing had to be stashed, and the IDE with the project open didn't even notice a switch.
Reviewing a pull request by running the code
A separate working tree for reviews lets you build and run someone else's branch and run the tests while continuing your own work in another editor window.
Comparing the behavior of two versions
Two working trees on different tags can run side by side on different ports, so you can compare, say, API response times before and after an optimization.
Long test runs and builds
Start the full test suite in one working tree and keep writing code in another — the build won't break because you're changing files.
Running several AI agents in parallel
If several agents or processes work on tasks at once, give each its own working tree on its own branch: they don't get in each other's way, and their results land straight in the shared repository.
How to organize folders if you use worktrees daily
If you need working trees every day, settle on a structure, or the sibling directories will quickly turn into a mess. A popular layout is one parent project folder containing a bare repository and one folder per branch:
git clone --bare git@example.com:team/shop.git ~/projects/shop/.bare
cd ~/projects/shop
echo "gitdir: ./.bare" > .git
git config remote.origin.fetch "+refs/heads/*:refs/remotes/origin/*"
git fetch origin
git worktree add main
git worktree add -b feature/cart feature-cart main
The remote.origin.fetch line is needed because a bare clone doesn't set up remote-tracking branches by default. You end up with main and feature-cart folders in ~/projects/shop, each on its own branch, and neither one is more "primary" than the other.
Another good habit is naming the folder after the branch (replacing the slash with a hyphen). Then git worktree list and the path in your terminal always tell you where you are. And finally, remove a working tree as soon as its branch is merged: stale working trees take up space and keep branches "checked out."
Common mistakes and gotchas
- Dependencies and builds aren't shared. Each working tree is a separate folder, so
node_modules, Python virtual environments,.envand build artifacts have to be recreated. Untracked files aren't copied to the new working tree. - A working tree inside the main folder.
git worktree add ./hotfixcreates a folder inside the project, and the main working tree sees it as untracked files. Keep working trees next to it (../) or in a separate directory, or add the path to.gitignore. - Moving the folder manually. That breaks the link. Move it with
git worktree move ../old ../new, and if you've already moved it, rungit worktree repairin the new folder. - A working tree on a removable drive disappears. To stop prune from removing the entry for a working tree on a disconnected drive, lock it:
git worktree lock --reason "external drive" ../shop-usb. - Submodules. Submodule support in working trees is limited; after creating one, run
git submodule update --initand check the result.
git worktree cheat sheet
| Task | Command |
|---|---|
| Check out an existing branch in a new folder | git worktree add ../dir branch |
| Create a branch and a working tree | git worktree add -b new-branch ../dir main |
| Working tree without a branch (tag, commit) | git worktree add --detach ../dir v1.0 |
| List working trees | git worktree list |
| Remove a working tree | git worktree remove ../dir |
| Clean up entries for deleted folders | git worktree prune |
| Move a working tree | git worktree move ../dir ../new-dir |
| Repair links after moving | git worktree repair |
| Protect from prune | git worktree lock ../dir |
git worktree vs. stash vs. a second clone
| Criterion | stash | worktree | second clone |
|---|---|---|---|
| Switching speed | Fast, but requires switching branches | Instant — just another folder | Instant |
| Disk space | Minimal | Working files only | A full copy of the history |
| Syncing | Not needed | Not needed, history is shared | Via push/fetch |
| Working in parallel | No | Yes | Yes |
Stash is still the best choice for quick interruptions of a couple of minutes. For anything longer, or when you need two versions open at once, worktree is more convenient.
Summary
git worktree is a simple way to work on several branches at once: add creates a folder, list shows them, and remove and prune clean up. History is shared, while each working tree has its own HEAD, index and files; one branch can't be checked out in two working trees. How branches work and why switching between them is so cheap is covered in detail, hands-on, in the Git course.
FAQ
Which Git version introduced git worktree?
The command appeared in Git 2.5 and has been improved considerably since — remove and move, for example, were added later. Every command described here is available in any modern Git version.
Can I commit in one working tree and see it in another?
Yes, the history is shared. The commit shows up immediately in git log in any working tree, and you can merge it with git merge without push or fetch.
Does my IDE see multiple working trees?
To an IDE, each working tree is just a project folder that you open in a separate window. Many editors also list working trees in their built-in Git UI.
Does git worktree remove delete the branch?
No, only the folder and the administrative entry are removed. Delete the branch separately with git branch -d.
Does git worktree work with a bare repository?
Yes, a popular setup is to keep a bare clone and create a working tree from it for each branch, so there's no "main" folder with files at all.
This topic is covered in depth with practice in the course “Git from Scratch to Confident Developer”.
Go to course