sexta-feira, 23 de outubro de 2015

Git - GitHub - Controle de Versão - Desfazendo e Refazendo

Este é o quinto artigo sobre o Git.
Para ler o primeiro artigo, com comandos essenciais. Clique aqui.
Para ler o segundo artigo, com comandos para servidores remotos. Clique aqui.
Para ler o terceiro artigo, com comandos para fazer Tags/Releases. Clique aqui.
Para ler o quarto artigo, com comandos para Branchs. Clique Aqui.

Estudando sobre como voltar versões de arquivos e commits, senti dificuldade em diferenciar os comandos checkout, reset e revert.
A diferença entre esses comandos são interessantes, vamos começar com exemplos práticos, para identificar a diferença entre eles e saber quando usar.
O Git tem três componentes principais:
1 - Diretório de Trabalho
2 - Snapshot
3 - Histórico de Commits
Lembre-se destes componentes para saber a diferença do que estamos fazendo.

Checkout.
O comando checkout já é conhecido para entrar em branch, contudo podemos utilizar ele para verificar revisões antigas do nosso sistema.
Imagina que queira verificar como era o seu sistema na versão v.2.0, simular algumas funções nesta versão antiga.
O comando checkout altera o seu diretório de trabalho com a versão informada, por isso, antes de realizar o comando é necessário fazer commit das alterações que você realizou.
Eu vi na Internet algumas pessoas usando o checkout de uma forma de desfazer os commits realizados, o checkout não deve ser usado desta forma, somente para verificar versões antigas, uma forma de consulta.
Vou verificar a versão do meu sistema de exemplo na versão v.2.0.
Primeiramente criei um branch, não economizem na criação de branch é rápido e utiliza poucos recursos. Como o git trabalha com apontamentos, criar um branch é bem economico e te ajuda muito no trabalho.
Depois verifiquei as tags que criei e utilizei o comando git checkout v.2.0, com este comando nosso diretório de trabalho já foi substituído para a versão 2.0 e podemos fazer as verificações necessárias.
Verifique os comandos abaixo.
$ git branch testeCheckout  
$ git checkout testeCheckout  
 Switched to branch 'testeCheckout'  
 MacMiniRomero:TesteStoryBoard douglasromero$ git branch  
  Teste_2  
  master  
 * testeCheckout  
$ git tag  
 v.1.0  
 v.2.0  
 v.3.0  
$ git checkout v.2.0  
 Note: checking out 'v.2.0'.  
 You are in 'detached HEAD' state. You can look around, make experimental  
 changes and commit them, and you can discard any commits you make in this  
 state without impacting any branches by performing another checkout.  
 If you want to create a new branch to retain commits you create, you may  
 do so (now or later) by using -b with the checkout command again. Example:  
  git checkout -b <new-branch-name>  
 HEAD is now at 2128d14... Segunda Parte do Tutorial  
O git somente faz um apontamento para a versão 2.0. Os snapshots e o histórico de commits continuam existindo.
No exemplo abaixo, mandei exibir os commits da versão 2.0 e depois fiz um checkout em um versão mais recente, 3.0, depois executei o git log para exibir os commits, verificamos que tudo isso continua existindo no branch, histórico de commits e shapshot
$ git log --oneline  
 2128d14 Segunda Parte do Tutorial  
 7eda703 Initial Commit  
$ git checkout v.3.0  
 Previous HEAD position was 2128d14... Segunda Parte do Tutorial  
 HEAD is now at 02215fd... Inserindo arquivo de ignore.#  
$ git log --oneline  
 02215fd Inserindo arquivo de ignore.#  
 d28226b Update TesteStoryBoardTests.m  
 81c3aa1 Merge branch 'master' of https://github.com/dsromerobr/TesteStoryBoard  
 55f8e2a Deletando arquivos de configuração de usuário. Ok.  
 aa3945a Commit com alterações do exemplo de GIT. Inclusão de uma property na primeira tela.  
 afb0c3e Create README.md  
 2128d14 Segunda Parte do Tutorial  
 7eda703 Initial Commit  

O checkout também aceita passar um arquivo, caso queremos restaurar somente o histórico de um arquivo.
$ cat arquivo.txt   
 primeiro commit.  
 segundo commit.  
 terceiro commit.  
 quarto commit.  
$ git log --oneline  
 9d1e52e quarto commit  
 44bd001 terceiro commit  
 ce62788 segundo commit  
 7cc5847 arquivo de teste 1  
 02215fd Inserindo arquivo de ignore.#  
 d28226b Update TesteStoryBoardTests.m  
 81c3aa1 Merge branch 'master' of https://github.com/dsromerobr/TesteStoryBoard  
 55f8e2a Deletando arquivos de configuração de usuário. Ok.  
 aa3945a Commit com alterações do exemplo de GIT. Inclusão de uma property na primeira tela.  
 afb0c3e Create README.md  
 2128d14 Segunda Parte do Tutorial  
 7eda703 Initial Commit  
$ git checkout ce62788 arquivo.txt   
$ cat arquivo.txt   
 primeiro commit.  
 segundo commit.  

Lembrando que o checkout mexe somente com o diretório de trabalho. Se executarmos o git status, mostrará que tem um arquivo modificado para entrar em staged.
 $ git status  
 On branch testeCheckOutArquivo  
 Changes to be committed:  
  (use "git reset HEAD <file>..." to unstage)  
      modified:  arquivo.txt  

Reset.
O comando reset é um modo de voltar o snapshot para um ponto específico.
Imagina que você fez 3 commits e queira voltar para um ponto específico, assim removendo os commits, este comando consegue fazer isso.
O reset é o comando mais complicado e deve ser usado com cautela.
Este comando tem 3 flags.
--soft -> O diretório de trabalho e o snapshot não são alterados.
--mixed -> O snapshot é alterado mas o diretório de trabalho não altera. Default.
--hard -> Altera tudo para o ponto específico.

Vamos utilizar o parâmetro --soft, onde foram feitos diversos commits com somente o arquivo.txt, gostaria de realizar somente um commit dele. Executando o comando reset com o parâmetro --soft, gostaria de fazer somente 1 commit. Escolhi o commit de hash 7cc5847, assim o snapshot e o diretório de trabalho serão mantidos e farei somente um commit.
$ git log --oneline  
 9d1e52e quarto commit  
 44bd001 terceiro commit  
 ce62788 segundo commit  
 7cc5847 arquivo de teste 1  
 02215fd Inserindo arquivo de ignore.#  
 d28226b Update TesteStoryBoardTests.m  
 81c3aa1 Merge branch 'master' of https://github.com/dsromerobr/TesteStoryBoard  
 55f8e2a Deletando arquivos de configuração de usuário. Ok.  
 aa3945a Commit com alterações do exemplo de GIT. Inclusão de uma property na primeira tela.  
 afb0c3e Create README.md  
 2128d14 Segunda Parte do Tutorial  
 7eda703 Initial Commit  
$ git branch  
  master  
  testeCheckOutArquivo  
 * testeReset  
$ git reset --soft 7cc5847  
$ git log --oneline  
 7cc5847 arquivo de teste 1  
 02215fd Inserindo arquivo de ignore.#  
 d28226b Update TesteStoryBoardTests.m  
 81c3aa1 Merge branch 'master' of https://github.com/dsromerobr/TesteStoryBoard  
 55f8e2a Deletando arquivos de configuração de usuário. Ok.  
 aa3945a Commit com alterações do exemplo de GIT. Inclusão de uma property na primeira tela.  
 afb0c3e Create README.md  
 2128d14 Segunda Parte do Tutorial  
 7eda703 Initial Commit  
$ git status  
 On branch testeReset  
 Changes to be committed:  
  (use "git reset HEAD <file>..." to unstage)  
      modified:  arquivo.txt  

O git reset aceita um arquivo como parâmetro, diferente do checkout, que trás a versão antiga do arquivo para o snapshot atual, o reset manda a versão do arquivo atual para um determinado snapshot.
Veja o exemplo abaixo:
$ git reset Head~1 arquivo.txt   
 Unstaged changes after reset:  
 M     arquivo.txt  
 MacMiniRomero:TesteStoryBoard douglasromero$ cat arquivo.txt   
 primeiro commit.  
 segundo commit.  
 terceiro commit.  
 quarto commit.  
 quinto commit.  
 sexto commit.  
$ git log --oneline  
 cff27cc nova version  
 a22627f Commit de teste !!!  
 6584065 Merge branch 'teste2' into testeCheckOutArquivo Teste de Mergeeeeee  
 611c47d teste de commit do branch  
 9d1e52e quarto commit  
 44bd001 terceiro commit  
 ce62788 segundo commit  
 7cc5847 arquivo de teste 1  
 02215fd Inserindo arquivo de ignore.#  
 d28226b Update TesteStoryBoardTests.m  
 81c3aa1 Merge branch 'master' of https://github.com/dsromerobr/TesteStoryBoard  
 55f8e2a Deletando arquivos de configuração de usuário. Ok.  
 aa3945a Commit com alterações do exemplo de GIT. Inclusão de uma property na primeira tela.  
 afb0c3e Create README.md  
 2128d14 Segunda Parte do Tutorial  
 7eda703 Initial Commit  
$ git checkout a22627f  
 M     arquivo.txt  
 Note: checking out 'a22627f'.  
 You are in 'detached HEAD' state. You can look around, make experimental  
 changes and commit them, and you can discard any commits you make in this  
 state without impacting any branches by performing another checkout.  
 If you want to create a new branch to retain commits you create, you may  
 do so (now or later) by using -b with the checkout command again. Example:  
  git checkout -b <new-branch-name>  
 HEAD is now at a22627f... Commit de teste !!!  
$ cat arquivo.txt  
 primeiro commit.  
 segundo commit.  
 terceiro commit.  
 quarto commit.  
 quinto commit.  
 sexto commit.  

Revert.
Este é o comando seguro para desfazer coisas, os outros comandos são interessantes para branchs privados, contudo em branchs públicos, como o GitHub, utilizar o revert é a melhor opção para evitar problemas.
Execute o comando abaixo:
 $ git revert 2128d14  
Ele irá fazer um merge e poderá ocorrer conflitos.
Assim, tem os parâmetros para dar sequencia em caso de conflitos.
git revert --continue
git revert --abort
git revert --quit


Nenhum comentário:

Postar um comentário

 

Cadastrar Email

Sobre o Blog

Neste blog irei compartilhar as minhas experiências e observações. Os temas serão variados, mas com ênfase em tecnologia. Inscreva-se nos nossos canais para receber atualizações.