git worktree
Aprenda o comando git worktree para verificar várias branches ao mesmo tempo de um único repositório, sem re-clonar. Inclui comandos e exemplos.
O que o git worktree faz
O comando git worktree permite que você faça checkout de mais de uma branch ao mesmo tempo a partir de um único repositório. Cada worktree é um diretório de trabalho separado com sua própria branch em checkout e seu próprio índice, mas todos compartilham o mesmo armazenamento de objetos .git, histórico, referências e configuração. É a forma limpa de trabalhar em duas branches em paralelo sem clonar o repositório duas vezes.
O diretório no qual você clonou é sua worktree principal; cada diretório que você cria com git worktree add é uma worktree vinculada. Worktrees vinculadas são leves: armazenam apenas um pequeno arquivo .git (não uma pasta) que aponta de volta para o repositório compartilhado, por isso custam quase nada em disco em comparação com um segundo clone.
Esta página aborda quando usar uma worktree, como adicionar, listar, mover e remover worktrees, as regras que o Git impõe e as armadilhas comuns.
O problema que ela resolve
Imagine que você está trabalhando em uma feature branch quando chega um relatório de bug urgente. Normalmente você teria que guardar seu trabalho, trocar de branch, corrigir o bug, voltar para a branch anterior e restaurar — algo perturbador e propenso a erros. Com worktrees, você simplesmente cria um segundo diretório de trabalho com checkout na branch do hotfix, corrige o bug lá e deixa seu trabalho de feature completamente intocado. Quando a build precisa dos dois estados lado a lado — por exemplo, para comparar comportamento ou executar dois longos conjuntos de testes ao mesmo tempo — as worktrees se destacam onde o stashing não consegue ajudar.
Adicionando uma worktree
Aponte git worktree add para um caminho e uma branch. Para fazer checkout de uma branch existente em um diretório irmão:
git worktree add ../hotfix hotfixIsso cria ../hotfix com a branch hotfix em checkout:
Preparing worktree (checking out 'hotfix')
HEAD is now at 1a2b3c4 Add login formPara criar uma branch completamente nova ao mesmo tempo, use -b. O último argumento é o ponto de partida no qual a nova branch é baseada:
git worktree add -b experiment ../experiment mainAgora você tem dois diretórios de trabalho independentes apoiados por um único repositório. Se você omitir a branch completamente, o Git cria uma branch com o nome do último componente do caminho:
git worktree add ../docs # creates and checks out a branch named "docs"Para inspecionar um commit sem colocar uma branch lá — útil para testar uma release antiga — adicione-o no estado detached HEAD:
git worktree add --detach ../v1-check v1.0.0Veja Detached HEAD para entender o que esse estado significa.
Listando worktrees
Veja todas as árvores de trabalho vinculadas ao repositório:
git worktree listA saída mostra cada caminho, o commit em que está e a branch (ou (detached HEAD)):
/home/dev/project 1a2b3c4 [main]
/home/dev/hotfix 9f8e7d6 [hotfix]
/home/dev/v1-check 0011223 (detached HEAD)Adicione --porcelain para um formato estável e compatível com scripts.
Movendo e removendo worktrees
Para realocar uma worktree vinculada, deixe o Git atualizar seu registro em vez de usar o mv do shell:
git worktree move ../hotfix ../urgent-fixQuando terminar com uma, remova-a (isso exclui seu diretório):
git worktree remove ../urgent-fixO Git recusa remover uma worktree que tem alterações não confirmadas ou arquivos não rastreados, para que você não perca trabalho acidentalmente. Quando tiver certeza, substitua essa verificação com --force:
git worktree remove --force ../urgent-fixSe você excluiu manualmente a pasta de uma worktree com rm -rf, o repositório ainda mantém um registro administrativo obsoleto. Limpe-o com:
git worktree pruneBloqueando uma worktree
Se uma worktree estiver em uma unidade removível ou compartilhamento de rede, bloqueie-a para que o prune nunca remova seu registro enquanto a unidade estiver desmontada:
git worktree lock ../usb-backup --reason "external disk"
git worktree unlock ../usb-backupResumo dos comandos
| Comando | Descrição |
|---|---|
git worktree add <path> <branch> | Cria uma worktree em <path> com checkout de uma <branch> existente. |
git worktree add -b <new> <path> <start> | Cria uma nova branch a partir de <start> e faz checkout em uma nova worktree. |
git worktree add --detach <path> <commit> | Adiciona uma worktree em detached HEAD no <commit>. |
git worktree list [--porcelain] | Lista todas as worktrees vinculadas ao repositório. |
git worktree move <from> <to> | Move uma worktree vinculada para um novo caminho. |
git worktree remove [--force] <path> | Remove uma worktree e seu diretório. |
git worktree lock / unlock | Impede ou permite a poda automática de uma worktree. |
git worktree prune | Limpa registros de worktrees cujas pastas foram excluídas. |
Regras e armadilhas
- Uma branch, uma worktree. Uma branch só pode ter checkout em uma worktree por vez. Se você tentar adicionar uma worktree para uma branch já em checkout em outro lugar, o Git recusa com
fatal: '<branch>' is already used by worktree at .... Isso garante que dois diretórios nunca possam disputar o mesmo ponteiro de branch. Use--detach, ou uma nova branch com-b, se precisar do mesmo commit em dois lugares. - Alterações locais não são compartilhadas. Cada worktree tem seus próprios arquivos de trabalho, índice e stash. Commits, branches, tags e remotos são compartilhados porque residem no armazenamento
.gitcomum. - Removendo a worktree principal. Você não pode usar
git worktree removena worktree original (principal) — apenas nas vinculadas. - Repositórios bare são ótimos hosts para worktrees: clone com
git clone --bare, depois adicione cada branch de trabalho como sua própria worktree, mantendo os dados do repositório separados de qualquer checkout.
Comandos relacionados
- git branch — crie e gerencie as branches que você faz checkout nas worktrees.
- git switch — mova entre branches dentro de um único diretório de trabalho.
- git stash — a alternativa mais antiga, de diretório único, a uma worktree rápida.