Como reverto todas as alterações locais no projeto gerenciado pelo Git para o estado anterior?


1914

Eu tenho um projeto no qual corri git init. Após várias confirmações, fiz o git statusque me dizia que tudo estava atualizado e que não havia alterações locais.

Depois, fiz várias alterações consecutivas e percebi que queria jogar tudo fora e voltar ao meu estado original. Esse comando fará isso por mim?

git reset --hard HEAD

Respostas:


3390

Se você deseja reverter as alterações feitas na sua cópia de trabalho, faça o seguinte:

git checkout .

Se você deseja reverter as alterações feitas no índice (ou seja, que você adicionou), faça isso. Aviso, isso redefinirá todas as suas confirmações não enviadas para o master! :

git reset

Se você deseja reverter uma alteração que você comprometeu, faça o seguinte:

git revert <commit 1> <commit 2>

Se você deseja remover arquivos não rastreados (por exemplo, novos arquivos, arquivos gerados):

git clean -f

Ou diretórios não rastreados (por exemplo, diretórios novos ou gerados automaticamente):

git clean -fd

133
fwiw depois de um longo tempo, git checkout path/to/filesó irá reverter as alterações locaispath/to/file
Matijs

29
+1 nas respostas abaixo mencionando também -f limpo git (para remover as alterações untracked) e -fd (também para remover diretórios untracked)
ptdev

3
e se você também deseja limpar seus arquivos não
rastreados

9
git checkout .e git reset [--hard HEAD]não funcionou, tive que fazer um git clean -fdpara reverter minhas alterações.
BrainSlugs83

7
git resetnão redefine suas alterações, git reset --hardfaz isso.
Cerin

388

Nota: Você também pode querer executar

git clean -fd

Como

git reset --hard

irá não remover arquivos untracked, onde, como git-clean irá remover todos os arquivos do diretório raiz tracked que não estão sob monitoramento git. AVISO - TENHA CUIDADO COM ISTO! É útil executar um teste a seco com o git-clean primeiro, para ver o que ele excluirá.

Isso também é especialmente útil quando você recebe a mensagem de erro

~"performing this command will cause an un-tracked file to be overwritten"

O que pode ocorrer ao fazer várias coisas, sendo uma atualização de uma cópia de trabalho quando você e seu amigo adicionaram um novo arquivo com o mesmo nome, mas ele o colocou no controle de origem primeiro e você não se preocupa em excluir sua cópia não rastreada .

Nessa situação, fazer uma execução a seco também ajudará a mostrar uma lista de arquivos que seriam substituídos.


13
O comando clean do arquivo é "git clean -f". Diretórios untracked são removidos com "-d limpo git"
Jonathan Mitchell

35
git -fd limpo (força é necessária para -d)
electblake

14
-n ou --dry-run são os sinalizadores para dry-run.
22414 stephenbez

2
git clean -ffd se você tiver outro repositório git no seu repositório git. Sem o dobro f, não seria removido.
Trismegistos #

149

Re-clonar

GIT=$(git rev-parse --show-toplevel)
cd $GIT/..
rm -rf $GIT
git clone ...
  • ✅ Exclui confirmações locais não enviadas
  • ✅ Reverte as alterações feitas nos arquivos rastreados
  • ✅ Restaura os arquivos rastreados que você excluiu
  • ✅ Exclui arquivos / diretórios listados em .gitignore(como arquivos de compilação)
  • ✅ Exclui arquivos / diretórios que não são rastreados e não estão .gitignore
  • 😀 Você não esquecerá esta abordagem
  • Astes Desperdiça largura de banda

A seguir estão outros comandos que esqueço diariamente.

Limpar e redefinir

git clean --force -d -x
git reset --hard
  • ❌ Exclui confirmações locais não enviadas
  • ✅ Reverte as alterações feitas nos arquivos rastreados
  • ✅ Restaura os arquivos rastreados que você excluiu
  • ✅ Exclui arquivos / diretórios listados em .gitignore(como arquivos de compilação)
  • ✅ Exclui arquivos / diretórios que não são rastreados e não estão .gitignore

Limpar \ limpo

git clean --force -d -x
  • ❌ Exclui confirmações locais não enviadas
  • ❌ Reverte as alterações feitas nos arquivos rastreados
  • ❌ Restaura os arquivos rastreados que você excluiu
  • ✅ Exclui arquivos / diretórios listados em .gitignore(como arquivos de compilação)
  • ✅ Exclui arquivos / diretórios que não são rastreados e não estão .gitignore

Redefinir

git reset --hard
  • ❌ Exclui confirmações locais não enviadas
  • ✅ Reverte as alterações feitas nos arquivos rastreados
  • ✅ Restaura os arquivos rastreados que você excluiu
  • ❌ Exclui arquivos / diretórios listados em .gitignore(como arquivos de compilação)
  • ❌ Exclui arquivos / diretórios que não são rastreados e não estão .gitignore

Notas

Caso de teste para confirmar todas as opções acima (use bash ou sh):

mkdir project
cd project
git init
echo '*.built' > .gitignore
echo 'CODE' > a.sourceCode
mkdir b
echo 'CODE' > b/b.sourceCode
cp -r b c
git add .
git commit -m 'Initial checkin'
echo 'NEW FEATURE' >> a.sourceCode
cp a.sourceCode a.built
rm -rf c
echo 'CODE' > 'd.sourceCode'

Veja também

  • git revert para fazer novas confirmações que desfazem confirmações anteriores
  • git checkout voltar no tempo para confirmações anteriores (pode ser necessário executar os comandos acima primeiro)
  • git stashigual ao git resetanterior, mas você pode desfazê-lo

Desculpe por roubar as respostas acima. Eu uso essa referência constantemente, postando principalmente para mim.
William Entriken

1
Tenho certeza, que a primeira opção ( Re-clone ) realmente faz "delete commits locais, não-empurrado" :)
Marandil

1
@styfle ✅ é algo que faz, ❌ é algo que não faz
William Entriken

3
@ FullDecent É meio confuso ler. "NOT NÃO apaga confirmações locais não enviadas". Isso significa que NÃO é excluído. O duplo negativo significa que ele exclui?
Styfle 25/05

1
Sinalizador About -x in git clean -f -d -x: se a opção -x for especificada, os arquivos ignorados também serão removidos. Isto pode, por exemplo, ser útil para remover todos products.- construção de docs GIT
Alex

82

Se você deseja reverter todas as alterações E estar atualizado com o mestre remoto atual (por exemplo, você acha que o HEAD mestre avançou desde que você o ramificou e seu push está sendo 'rejeitado'), você pode usar

git fetch  # will fetch the latest changes on the remote
git reset --hard origin/master # will set your local branch to match the representation of the remote just pulled down.

Parece importante especificar originem git reset --hard origin/master(que funciona) - sem ele (ie git reset --hard) nada parece ser alterado.
Jake

Eu tive algumas mudanças locais e não são capazes de se livrar deles por qualquer comando eu fiz git redefinir --hard origem / master e foi capaz de mudanças de mestrado puxar bem
ringsia abhishek

50

Olhe para o git-reflog. Ele listará todos os estados de que se lembra (o padrão é 30 dias) e você pode simplesmente fazer o checkout do que deseja. Por exemplo:

$ git init > /dev/null
$ touch a
$ git add .
$ git commit -m"Add file a" > /dev/null
$ echo 'foo' >> a
$ git commit -a -m"Append foo to a" > /dev/null
$ for i in b c d e; do echo $i >>a; git commit -a -m"Append $i to a" ;done > /dev/null
$ git reset --hard HEAD^^ > /dev/null
$ cat a
foo
b
c
$ git reflog
145c322 HEAD@{0}: HEAD^^: updating HEAD
ae7c2b3 HEAD@{1}: commit: Append e to a
fdf2c5e HEAD@{2}: commit: Append d to a
145c322 HEAD@{3}: commit: Append c to a
363e22a HEAD@{4}: commit: Append b to a
fa26c43 HEAD@{5}: commit: Append foo to a
0a392a5 HEAD@{6}: commit (initial): Add file a
$ git reset --hard HEAD@{2}
HEAD is now at fdf2c5e Append d to a
$ cat a
foo
b
c
d

obrigado uma tonelada William, por git reflog. Redefino minha árvore para a versão antiga e não sei como recuperar para recente. seu git reflog me salvou. Obrigado mais uma vez.
23411 Palaniraja

1
me salvou também! No meu caso, minha aventura git rebase -ideu errado (acabando com alguns commits devido a um erro de edição). Graças a esta dica, estou de volta em bom estado!
Paneer_tikka

O que você quer dizer com 30 dias padrão!?
Mohe TheDreamy

@MoheTheDreamy Quero dizer que há um limite de tempo. Eventualmente, o coletor de lixo excluirá referências inacessíveis quando a idade ultrapassar esse limite. O padrão costumava ser (e talvez ainda seja) 30 dias. Portanto, referências mais antigas podem não estar disponíveis.
William Pursell #

36

PERIGO À FRENTE: (leia os comentários. A execução do comando proposto na minha resposta pode excluir mais do que você deseja)

remover completamente todos os arquivos, incluindo diretórios que tive que executar

git clean -f -d

13
Para salvar qualquer um da dor que acabei de passar: isso também excluirá arquivos .gitignore-d!
landons

desculpe se eu lhe causei algum problema. Naquela época, eu apenas tentei reverter e excluir tudo nessa pasta. Não me lembro das circunstâncias exatas, mas o "-d" era a única coisa que funcionava para mim. Eu espero que eu não lhe causar muita dor :-)
Tobias Gassmann

1
Sem danos causados. Eu tinha backups, mas isso provavelmente merece um aviso;)
landons

35

Depois de ler várias respostas e experimentá-las, encontrei vários casos extremos que significam que às vezes eles não limpam completamente a cópia de trabalho.

Aqui está o meu script bash atual para fazê-lo, que funciona o tempo todo.

#!/bin/sh
git reset --hard
git clean -f -d
git checkout -- HEAD

Execute a partir do diretório raiz da cópia de trabalho.


10
Último comando me dáerror: pathspec 'HEAD' did not match any file(s) known to git.
0xC0000022L

1
Funcionou para mim quando tirei o "-". git checkout HEAD
Jester

4
git reset --hardreverte arquivos rastreados (em etapas ou não), git clean -f -dremove arquivos não rastreados , git checkout -- HEADpor que precisamos disso?
v.shashenko

Não precisamos do hífen duplo. Deve ser um erro de digitação.
Farax

35

simplesmente execute -

git stash

removerá todas as suas alterações locais. e você também pode usá-lo mais tarde executando -

git stash apply 

3
o uso git stash popremoveria automaticamente a alteração armazenada no topo da lista para você #
Arrow Cen

8
git stash droppara remover o último estado oculto sem aplicar à cópia de trabalho.
deerchao

O git stash apply não adicionará arquivos recém-criados
Ravistm 09/09/19

27

Eu encontrei um problema semelhante. A solução é usar git logpara procurar qual versão do commit local é diferente do remoto. (Por exemplo, a versão é3c74a11530697214cbcc4b7b98bf7a65952a34ec ).

Em seguida, use git reset --hard 3c74a11530697214cbcc4b7b98bf7a65952a34ecpara reverter a alteração.


16

Eu procurei por um problema semelhante,

Queria jogar fora os commits locais:

  1. clonou o repositório (git clone)
  2. mudou para o ramo dev (git checkout dev)
  3. fez poucos commits (git commit -m "commit 1")
  4. mas decidiu jogar fora esses commits locais para voltar ao controle remoto (origin / dev)

O mesmo aconteceu abaixo:

git reset --hard origin/dev

Verifica:

git status  

        On branch dev  
        Your branch is up-to-date with 'origin/dev'.  
        nothing to commit, working tree clean  

agora as confirmações locais são perdidas, de volta ao estado inicial clonado, ponto 1 acima.


1
Obrigado, isso é a única coisa que funcionou para mim - "git reset origem --hard"
Nisim Naim

feliz em saber que ajudou.
Manohar Reddy Poreddy 10/11/19

7

Você pode não necessariamente querer / precisar esconder seus arquivos / trabalho em seu diretório de trabalho, mas simplesmente se livrar deles completamente. O comandogit clean fará isso por você.

Alguns casos de uso comuns para isso seriam remover cruft gerado por mesclagens ou ferramentas externas ou remover outros arquivos para que você possa executar uma construção limpa.

Lembre-se de que você deve ter muito cuidado com esse comando, pois ele foi projetado para remover arquivos do diretório de trabalho local que NÃO SÃO TRACKED. se você mudar de idéia repentinamente após executar este comando, não há como voltar atrás para ver o conteúdo dos arquivos que foram removidos. Uma alternativa mais segura é executar

git stash --all

que removerá tudo, mas salvará tudo em um esconderijo. Esse estoque pode ser usado posteriormente.

No entanto, se você realmente deseja remover todos os arquivos e limpar seu diretório de trabalho, execute

git clean -f -d

Isso removerá todos os arquivos e subdiretórios que não possuem itens como resultado do comando. Uma coisa inteligente a se fazer antes de executar o git clean -f -dcomando é executar

git clean -f -d -n

que mostrará uma prévia do que será removido após a execução git clean -f -d

Então, aqui está um resumo de suas opções, da mais agressiva à menos agressiva


Opção 1 : remova todos os arquivos localmente (mais agressivo)

git clean -f -d

Opção 2 : visualizar o impacto acima (visualização mais agressiva)

git clean -f -d -n

Opção 3 : Esconder todos os arquivos (menos agressivo)

`git stash --all` 

6

Tente isso para reverter todas as alterações não confirmadas na ramificação local

$ git reset --hard HEAD

Mas se você vir um erro como este:

fatal: Unable to create '/directory/for/your/project/.git/index.lock': File exists.

Você pode navegar para a pasta '.git' e excluir o arquivo index.lock:

$ cd /directory/for/your/project/.git/
$ rm index.lock

Por fim, execute novamente o comando:

$ git reset --hard HEAD

0

Esta pergunta é mais sobre redefinição / reversão mais ampla do repositório, mas, se você estiver interessado em reverter alterações individuais - adicionei resposta semelhante aqui:

https://stackoverflow.com/a/60890371/2338477

Respostas às perguntas:

  • Como reverter alterações individuais com ou sem alterações preservadas no histórico do git

  • Como retornar à versão antiga para reiniciar do mesmo estado

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.