Como usar o Git Reverert

107

Como é git revertusado?

Isso pode soar como uma pergunta duplicada, mas quando as pessoas perguntam, a resposta é frequentemente, usar git resetcomo por Reverter para um commit por um hash SHA no Git?

Então, quando alguém pergunta como usar, as git resetpessoas respondem dizendo que você deve usar git revertconforme Git - como fazer rollback

Antes que você perceba, 8 pessoas diferentes apareceram com suas próprias maneiras únicas de salvar a bunda do OP, tudo isso passando por cima da sua cabeça.

Então, vamos tentar cumprir o briefing e escrever um guia para leigos git revert.

Um cenário: você se comprometeu duas vezes a dominar e é ruim. Você pressionou e outras pessoas tiveram suas mudanças ruins.

Você quer desfazer isso. Não é algo que você pode desfazer manualmente no código, digamos que algum assistente ou gerenciador de pacotes mudou toneladas de coisas por todo o lugar - você só quer colocar tudo de volta como antes.

É disso que trata o controle de origem. Tenho certeza que é fácil.

Ok, você vai usar, git revertmas como?

E depois de correr git revert, você tem que fazer outra coisa depois? Você tem que confirmar as alterações feitas ou reverter diretamente para o repo ou o quê ??

Obviamente, você precisará empurrar novamente e provavelmente anunciar sua coragem para o time.

Luke Puplett
fonte

Respostas:

119

git revert faz um novo commit

git revert simplesmente cria um novo commit que é o oposto de um commit existente.

Ele deixa os arquivos no mesmo estado como se o commit que foi revertido nunca existisse. Por exemplo, considere o seguinte exemplo simples:

$ cd /tmp/example
$ git init
Initialized empty Git repository in /tmp/example/.git/
$ echo "Initial text" > README.md
$ git add README.md
$ git commit -m "initial commit"
[master (root-commit) 3f7522e] initial commit
 1 file changed, 1 insertion(+)
 create mode 100644 README.md
$ echo "bad update" > README.md 
$ git commit -am "bad update"
[master a1b9870] bad update
 1 file changed, 1 insertion(+), 1 deletion(-)

Neste exemplo, o histórico de commits tem dois commits e o último é um erro. Usando git revert:

$ git revert HEAD
[master 1db4eeb] Revert "bad update"
 1 file changed, 1 insertion(+), 1 deletion(-)

Haverá 3 commits no log:

$ git log --oneline
1db4eeb Revert "bad update"
a1b9870 bad update
3f7522e initial commit

Portanto, há um histórico consistente do que aconteceu, mas os arquivos são como se a atualização ruim nunca tivesse ocorrido:

cat README.md 
Initial text

Não importa onde no histórico o commit a ser revertido está (no exemplo acima, o último commit é revertido - qualquer commit pode ser revertido).

Perguntas finais

você tem que fazer outra coisa depois?

A git reverté apenas outro commit, então, por exemplo, empurre para o remoto para que outros usuários possam puxar / buscar / mesclar as alterações e pronto.

Você tem que fazer commit das alterações feitas ou reverter confirma diretamente para o repo?

git revert é um commit - não há etapas extras assumindo que reverter um único commit é o que você deseja fazer.

Obviamente, você precisará pressionar novamente e provavelmente anunciar para a equipe.

Na verdade - se o controle remoto estiver em um estado instável - comunicar ao resto da equipe que eles precisam puxar para obter a correção (o commit de reversão) seria a coisa certa a fazer :).

AD7six
fonte
A título de confirmação, tanto para a primeira declaração aqui quanto para quem está se perguntando a mesma coisa que acabei de me perguntar sobre como funciona, você pode reverter uma reversão, onde há vários novos commits desde a reversão que você está revertendo. Portanto, reverter é apenas um commit do oposto do commit revertido. Você pode, é claro, ter conflitos ... mas essa é uma história diferente.
GG2
Sempre acho melhor evitar comprometer-se com isso, apenas para revisar as alterações primeiro e eu uso, git revert -n <commitToRevet> ou git revert --no-commit <commitToRevet>
Eklavyaa
2
Só queria dizer que, depois de anos de stackoverflow, acho que essa pode ser uma das melhores respostas que já encontrei. Ótimo exemplo e explicação. Obrigado.
user3344977
Entrei aqui esperando obter mais informações, algo como um TLDR deste raw.githubusercontent.com/git/git/master/Documentation/howto/…
wviana
1
@wviana Se as informações que você encontrou forem insuficientes, escreva uma resposta. Observe que o estouro de pilha não substitui a documentação oficial (para a qual você parece estar vinculando e cobre um escopo muito mais amplo do que esta questão).
AD7six
35

Use git revert assim:

git revert <insert bad commit hash here>

git revertcria um novo commit com as mudanças que são revertidas. git resetapaga seu histórico do git em vez de fazer um novo commit.

As etapas a seguir são as mesmas de qualquer outro commit.

Johnny Z
fonte
A diferença entre "reverter um commit" e "reverter para um commit" é sutil o suficiente para que lutei com esse comando por anos. Sua explicação resolveu para mim instantaneamente. Obrigado!
claviska
24

A razão resete reverttendem a aparecer muito nas mesmas conversas é porque diferentes sistemas de controle de versão os usam para significar coisas diferentes.

Em particular, as pessoas que estão acostumadas com SVN ou P4 e que desejam descartar alterações não confirmadas em um arquivo, muitas vezes revertprocuram antes de serem informadas do que realmente desejam reset.

Da mesma forma, o revertequivalente em outros VCSes é freqüentemente chamado rollbackou algo semelhante - mas "rollback" também pode significar "Eu quero descartar completamente os últimos commits", o que é apropriado, resetmas não revert. Portanto, há muita confusão em que as pessoas sabem o que querem fazer, mas não têm certeza de qual comando devem usar para isso.

Quanto às suas reais dúvidas sobre reverter ...

Ok, você vai usar git revert, mas como?

git revert first-bad-commit..last-bad-commit

E depois de executar git revert, você precisa fazer outra coisa depois? Você tem que confirmar as alterações feitas ou reverter diretamente para o repo ou o quê ??

Por padrão, git revertsolicita uma mensagem de confirmação e, em seguida, confirma os resultados. Isso pode ser substituído. Cito a página de manual :

--editar

Com esta opção, git revert permitirá que você edite a mensagem de confirmação antes de confirmar a reversão. Este é o padrão se você executar o comando de um terminal.

--no-commit

Normalmente, o comando cria automaticamente alguns commits com mensagens de log de commits informando quais commits foram revertidos. Este sinalizador aplica as mudanças necessárias para reverter os commits nomeados para sua árvore de trabalho e o índice, mas não faz os commits. Além disso, quando esta opção é usada, seu índice não precisa corresponder ao commit HEAD. A reversão é feita em relação ao estado inicial do seu índice.

Isso é útil ao reverter mais de um efeito de commits em seu índice em uma linha.

Em particular, por padrão, ele cria um novo commit para cada commit que você está revertendo. Você pode usar revert --no-commitpara criar mudanças revertendo todos eles sem comprometer essas mudanças como commits individuais, então comprometa-se em seu lazer.

ToxicFrog
fonte
git revert first-bad-commit..last-bad-commit: Eu acho que isso deveria ser git revert parent-of-first-bad-commit..last-bad-commit.
user1071847 de
9

A questão é bastante antiga, mas reverter ainda confunde as pessoas (como eu)

Como um iniciante, depois de algumas tentativas e erros (mais erros do que tentativas), tenho um ponto importante:

  • git revertrequer o id do commit que você deseja remover mantendo-o em seu histórico

  • git resetrequer o commit que você deseja manter e, consequentemente, removerá do histórico qualquer coisa depois disso.

Ou seja, se você usar revertcom o primeiro id de commit, você se encontrará em um diretório vazio e um commit adicional no histórico, enquanto com reset seu diretório será .. revertido para o commit inicial e seu histórico será como se os últimos commits nunca aconteceram.

Para ser ainda mais claro, com um log como este:

# git log --oneline

cb76ee4 wrong
01b56c6 test
2e407ce first commit

Usar git revert cb76ee4irá, por padrão, trazer seus arquivos de volta para 01b56c6 e irá adicionar mais um commit ao seu histórico:

8d4406b Revert "wrong"
cb76ee4 wrong
01b56c6 test
2e407ce first commit

git reset 01b56c6 em vez disso, trará seus arquivos de volta para 01b56c6 e limpará qualquer outro commit depois disso de seu histórico:

01b56c6 test
2e407ce first commit

Eu sei que estes são "a base", mas foi bastante confuso para mim, ao executar o revertprimeiro id ('primeiro commit') eu esperava encontrar meus arquivos iniciais, demorou um pouco para entender que se você precisar de seus arquivos de volta como 'primeiro commit' você precisa usar o próximo id.

senso
fonte
Eu observei o mesmo. é realmente confuso, mas muito importante saber. recentemente eu tive que ajudar um colega de trabalho e esqueci disso. Isso foi um pouco embaraçoso.
ExOfDe
1

Eu reverti alguns commits executando 'git revert commit id' como:

git revert b2cb7c248d416409f8eb42b561cbff91b0601712

Em seguida, fui solicitado a confirmar a reversão (assim como você faria ao executar 'git commit'). Meu programa de terminal padrão é o Vim, então executei:

:wq 

Finalmente, empurrei a mudança para o repositório com:

git push
jrc16
fonte