321 lines
14 KiB
Markdown
321 lines
14 KiB
Markdown
## 🎯 Objetivo
|
|
Este repositório é um guia de referência para aprender Git e GitLab, desde os primeiros passos até tópicos avançados. Ideal para estudantes, desenvolvedores iniciantes ou quem deseja reforçar conceitos de versionamento de código em projetos individuais ou em equipe.
|
|
|
|
## Introdução ao git
|
|
---
|
|
O git é um sistema de controle de versão distribuído amplamente utilizado para rastrear mudanças em arquivos de código-fonte durante o desenvolvimento de software.
|
|
|
|
- O Git permite que múltiplos desenvolvedores trabalhem juntos em um projeto, fornecendo ferramentas para colaborar sem sobrescrever o trabalho uns dos outros.
|
|
- Ele armazena o histórico de versões em um repositório local, permitindo que os usuários revertam para versões anteriores dos arquivos.
|
|
- Os principais conceitos do git incluem 'commit', 'branch', 'merge', e 'pull request'.
|
|
|
|
## Configuração inicial do git
|
|
---
|
|
Antes de começar a usar o git, é necessário configurar seu ambiente de usuário.
|
|
|
|
- Instalação do git: Pode ser feita através de gerenciadores de pacotes ou baixando o instalador do site oficial.
|
|
- Configuração de usuário: Defina seu nome de usuário e endereço de email com os comandos `git config --global user.name "Seu Nome"` e `git config --global user.email "seuemail@exemplo.com"`.
|
|
- Geração de chave SSH: Para conexões seguras com repositórios remotos, é recomendável gerar uma chave SSH.
|
|
|
|
## Comandos básicos do git
|
|
---
|
|
O git possui uma série de comandos essenciais para gerenciar repositórios e controlar versões.
|
|
|
|
- `git init`: Inicializa um novo repositório Git local.
|
|
- `git clone [URL]`: Clona um repositório remoto para o local.
|
|
- `git add [arquivo]`: Adiciona arquivos à área de preparação (staging area).
|
|
- `git commit -m "mensagem"`: Grava as mudanças na área de preparação em um novo commit.
|
|
- `git status`: Mostra o status atual do repositório, incluindo arquivos modificados ou adicionados.
|
|
|
|
## Trabalhando com branches no git
|
|
---
|
|
Branches são fundamentais no Git para permitir o desenvolvimento paralelo de recursos ou correções.
|
|
|
|
- `git branch [nome]`: Cria uma nova branch.
|
|
- `git checkout [nome]`: Muda para a branch especificada.
|
|
- `git merge [nome]`: Mescla as mudanças da branch especificada na branch atual.
|
|
- Estratégia de branches: É comum usar uma branch 'master' ou 'main' para o código estável e criar branches separadas para desenvolvimento de recursos ou correções.
|
|
|
|
## Gerenciamento de conflitos no git
|
|
---
|
|
Durante o merge de branches, podem ocorrer conflitos quando as mesmas linhas de código são alteradas de maneiras diferentes.
|
|
|
|
- O Git sinaliza os arquivos com conflitos e o desenvolvedor precisa resolver manualmente.
|
|
- A resolução de conflitos envolve editar os arquivos para escolher as alterações desejadas e, em seguida, fazer um novo commit.
|
|
- Ferramentas de merge podem ajudar na visualização e resolução de conflitos.
|
|
|
|
## Git rebase para histórico linear
|
|
---
|
|
O comando `git rebase` é usado para reescrever o histórico de commits, criando um histórico linear mais limpo.
|
|
|
|
- O rebase move os commits de uma branch para o topo da outra, evitando merges desnecessários.
|
|
- É útil para atualizar uma branch de recurso com as últimas alterações da branch principal.
|
|
- Deve ser usado com cautela, pois altera o histórico de commits.
|
|
|
|
## Trabalhando com repositórios remotos
|
|
---
|
|
Repositórios remotos são versões de seu repositório hospedadas em um servidor, como GitHub ou GitLab.
|
|
|
|
- `git remote add [nome] [URL]`: Adiciona um novo repositório remoto.
|
|
- `git push [remoto] [branch]`: Envia commits da branch local para a remota.
|
|
- `git pull [remoto] [branch]`: Atualiza a branch local com as últimas alterações da remota.
|
|
- É importante manter o repositório local sincronizado com o remoto para evitar conflitos.
|
|
|
|
## Git stash para salvar mudanças temporárias
|
|
---
|
|
O comando `git stash` é usado para salvar temporariamente alterações não finalizadas, permitindo trocar de branch sem commitar.
|
|
|
|
- `git stash push`: Salva as mudanças atuais em uma pilha temporária.
|
|
- `git stash list`: Lista todas as entradas na pilha de stashes.
|
|
- `git stash pop`: Aplica a última entrada da pilha e a remove.
|
|
- Útil para interromper rapidamente o trabalho atual e mudar para outra tarefa.
|
|
|
|
## Estratégias de workflow no git
|
|
---
|
|
Existem várias estratégias de workflow no git, como git flow e forking forkflow, que organizam o processo de desenvolvimento.
|
|
|
|
- git flow: Define um modelo estrito com branches específicas para desenvolvimento, recursos, lançamentos e correções.
|
|
- forking workflow: Cada desenvolvedor tem seu próprio repositório, e as contribuições são feitas através de pull requests.
|
|
- Escolher uma estratégia de workflow depende das necessidades da equipe e do projeto.
|
|
|
|
## Git cherry-pick para aplicar commits específicos
|
|
---
|
|
O comando `git cherry-pick` permite aplicar as mudanças de commits específicos de uma branch para outra.
|
|
|
|
- Útil para trazer correções ou recursos específicos para outra branch sem fazer um merge completo.
|
|
- Use `git cherry-pick [commit]` para aplicar as mudanças do commit especificado.
|
|
- Pode causar conflitos se as mudanças não se aplicarem limpa na branch de destino.
|
|
|
|
## Reflog do git para recuperação de dados
|
|
---
|
|
O reflog do Git registra as atualizações feitas nas referências dos repositórios, como branches e tags, facilitando a recuperação de dados perdidos.
|
|
|
|
- Use `git reflog` para exibir o histórico de alterações nas referências.
|
|
- Cada entrada mostra a ação realizada (como um commit ou um checkout) e o hash do commit.
|
|
- Para recuperar um estado anterior, use `git reset --hard [reflog entry]`.
|
|
- O reflog é uma ferramenta de segurança, pois permite reverter ações acidentais, como redefinições ou rebase.
|
|
|
|
## Git clean para remover arquivos não rastreados
|
|
---
|
|
O comando `git clean` é usado para remover arquivos não rastreados do diretório de trabalho, ajudando a manter o repositório limpo.
|
|
|
|
- Use `git clean -n` para fazer uma simulação e mostrar quais arquivos seriam removidos.
|
|
- `git clean -f` remove os arquivos não rastreados.
|
|
- `git clean -fd` remove também os diretórios não rastreados.
|
|
- Use com cautela, pois essa ação é irreversível e pode resultar na perda de dados não rastreados.
|
|
|
|
## Tags no git para versões de lançamento
|
|
---
|
|
As tags no Git são usadas para marcar pontos específicos no histórico do repositório, como versões de lançamento.
|
|
|
|
- Use `git tag [nome]` para criar uma tag leve apontando para o commit atual.
|
|
- Para uma tag anotada, que inclui informações adicionais como autor e data, use `git tag -a [nome] -m "mensagem"`.
|
|
- As tags podem ser enviadas para repositórios remotos com `git push --tags`.
|
|
- Elas são úteis para marcar versões estáveis do software ou pontos de referência importantes no desenvolvimento.
|
|
|
|
## Git revert para desfazer commits
|
|
---
|
|
O comando `git revert` cria um novo commit que desfaz as mudanças de um commit anterior, preservando o histórico.
|
|
|
|
- Use `git revert [commit]` para gerar um commit que inverte as alterações do commit especificado.
|
|
- Diferente do `git reset`, o revert não altera o histórico existente, tornando-o seguro para repositórios compartilhados.
|
|
- Pode ser usado para desfazer alterações indesejadas ou erros sem reescrever o histórico de commits.
|
|
|
|
## Git ignore para excluir arquivos do controle de versão
|
|
---
|
|
O arquivo `.gitignore` é usado para especificar arquivos ou diretórios que devem ser ignorados pelo Git, evitando que sejam rastreados.
|
|
|
|
- Crie um arquivo chamado `.gitignore` no diretório raiz do repositório.
|
|
- Adicione padrões de arquivo ou diretório que devem ser ignorados (por exemplo, `*.log`, `build/`).
|
|
- Arquivos ignorados não aparecerão em `git status` e não serão adicionados ao repositório.
|
|
- Útil para excluir arquivos temporários, de compilação ou sensíveis do controle de versão.
|
|
|
|
# Entendendo a Relação entre Repositório Fonte e Cópia Sincronizada (fork)
|
|
|
|
Já imaginou como manter seu fork atualizado com as mudanças do projeto original? A chave está na configuração inteligente dos repositórios remotos!
|
|
|
|
![[2025-03-18_15h22_34.png]]
|
|
|
|
## 🔄 Os Três Pilares do Versionamento
|
|
|
|
## 1. Repositório Fonte (Primário)
|
|
- **Função**: Base oficial do projeto, geralmente mantido pelo autor original
|
|
- **Identificação no Git**: Nomeado como `upstream` (referência à origem do fluxo)
|
|
- **Característica**: Somente leitura para contribuidores externos
|
|
|
|
## 2. Cópia Pessoal (Derivado)
|
|
- **Origem**: Criado através do botão "Fork" na interface do GitLab/GitHub
|
|
- **Identificação no Git**: Chamado de `origin` após clonagem
|
|
- **Vantagem**: Seu espaço seguro para experimentações
|
|
|
|
## 3. Ambiente Local
|
|
- **Finalidade**: Máquina física onde o desenvolvimento acontece
|
|
- **Gestão**: Conexão simultânea com `origin` e `upstream`
|
|
|
|
## ⚙️ Configuração Estratégica de Remotos
|
|
|
|
1. **Clonagem do Derivado**
|
|
|
|
Obtenha sua cópia pessoal:
|
|
|
|
```bash
|
|
git clone git@gitlab.com:seu_usuario/cblc.git
|
|
cd cblc
|
|
```
|
|
|
|
2. **Vinculação com o fonte**
|
|
|
|
```bash
|
|
git remote add upstream https://gitlab.com/blau_araujo/cblc.git
|
|
```
|
|
|
|
3. **Verificação de Conexões**
|
|
|
|
```bash
|
|
git remote -v
|
|
# origin git@gitlab.com:seu_usuario/cblc.git (push/fetch)
|
|
# upstream https://gitlab.com/blau_araujo/cblc.git (push/fetch)
|
|
```
|
|
|
|
## 💡 Por Que Esta Estrutura?
|
|
|
|
- **Sincronização Simplificada**: Atualize seu fork com `git fetch upstream`
|
|
- **Controle de Versão**: Mantenha histórico limpo entre suas alterações e as oficiais
|
|
- **Colaboração Eficiente**: Envie alterações via `origin` sem afetar o projeto principal
|
|
|
|
> **Dica Pro**: Use `upstream` para puxar atualizações e `origin` para enviar suas contribuições!
|
|
|
|
## 🔍 Fluxo de Atualização Básico
|
|
|
|
```bash
|
|
# Obter mudanças do projeto original
|
|
git fetch upstream main
|
|
|
|
# Mesclar com sua cópia local
|
|
git merge upstream/main
|
|
|
|
# Atualizar fork remoto
|
|
git push origin main
|
|
```
|
|
|
|
Esta estrutura garante que seu ambiente sempre reflita as mudanças mais recentes do projeto, enquanto mantém suas contribuições isoladas e organizadas.
|
|
|
|
# **Workflow Recomendado para acompanhar o curso**
|
|
|
|
## 1. **Sincronize o `main` do seu fork com o repositório do professor**
|
|
|
|
Sempre que o professor atualizar o `upstream/main`, atualize seu fork:
|
|
|
|
```bash
|
|
git checkout main
|
|
git fetch upstream main # Puxa as atualizações do professor
|
|
git reset --hard upstream/main # Alinha seu main local com o upstream
|
|
git push origin main --force # Atualiza seu fork no GitHub (origin)
|
|
```
|
|
## 2. **Crie um branch para cada exercício**
|
|
|
|
Nunca trabalhe diretamente no `main`. Para cada novo exercício:
|
|
|
|
```bash
|
|
git checkout main
|
|
git checkout -b exercicio-1 # Cria um branch a partir do main atualizado
|
|
```
|
|
## 3. **Desenvolva no branch do exercício**
|
|
|
|
Faça commits normalmente:
|
|
|
|
```bash
|
|
git add .
|
|
git commit -m "Resolução do exercício 1"
|
|
```
|
|
## 4. **Atualize o branch do exercício com as mudanças do professor**
|
|
|
|
Se o professor atualizar o `upstream/main` enquanto você está trabalhando:
|
|
|
|
```bash
|
|
git checkout main
|
|
git fetch upstream main
|
|
git reset --hard upstream/main
|
|
git push origin main --force
|
|
|
|
git checkout exercicio-1
|
|
git rebase main # Atualiza seu branch com as mudanças do professor
|
|
```
|
|
|
|
- Se houver conflitos, resolva-os durante o rebase.
|
|
|
|
## **Por que o `git reset --hard upstream/main`?**
|
|
|
|
Quando você faz um fork de um projeto, seu repositório (`origin`) começa como uma cópia exata do projeto original (`upstream`). Com o tempo, o `upstream/main` (o branch principal do projeto original) pode ser atualizado com novos commits, enquanto seu fork (`origin/main`) pode ficar desatualizado ou acumular commits próprios.
|
|
|
|
O comando **`git reset --hard upstream/main`** serve para:
|
|
|
|
1. **Forçar seu branch local `main` a corresponder exatamente ao `upstream/main`**.
|
|
2. **Descartar quaisquer commits locais ou alterações que não existam no `upstream`**.
|
|
3. **Garantir que seu fork volte a ser um espelho perfeito do repositório original**.
|
|
|
|
---
|
|
### **Quando isso é útil?**
|
|
|
|
- Você fez commits acidentais no `main` do seu fork (em vez de usar branches).
|
|
- O `upstream/main` foi atualizado, e você quer sincronizar seu fork **descartando alterações locais**.
|
|
- Você quer "limpar" o histórico do seu fork para evitar conflitos futuros.
|
|
|
|
Em resumo: desde que seus branches não estejam diretamente ligados ao `main` (ou você tenha backups), o `git reset --hard` não os afeta! 😊
|
|
|
|
## 5. **Envie o branch para seu fork (GitHub)**
|
|
|
|
```bash
|
|
git push origin exercicio-1
|
|
```
|
|
|
|
---
|
|
### **Fluxo Visual**
|
|
```txt
|
|
main (origin/main) → sempre igual ao upstream/main (professor)
|
|
/
|
|
upstream/main
|
|
\
|
|
exercicio-1 → seu branch de trabalho
|
|
```
|
|
---
|
|
## **Por que essa recomendação?**
|
|
|
|
- **`main` limpo**: Sempre reflete o estado oficial do professor.
|
|
- **Branches isolados**: Cada exercício tem seu próprio histórico, sem interferir no `main`.
|
|
- **Atualizações seguras**: O `git rebase main` mantém seu branch atualizado com as mudanças do professor.
|
|
|
|
---
|
|
|
|
## **Quando NÃO usar `git reset --hard`?**
|
|
|
|
- Se você tem commits locais **que quer manter**.
|
|
- Se outros colaboradores dependem do histórico do seu fork.
|
|
- **Solução alternativa**: Crie um branch novo para seus commits e sincronize o `main` sem perder trabalho
|
|
## **Dicas Importantes**
|
|
|
|
1. **Nunca commite no `main`**: Isso evitará divergências com o `upstream`.
|
|
2. **Use `git fetch` antes de trabalhar**: Verifique se há atualizações do professor.
|
|
3. **Nomeie branches claramente**: Ex: `exercicio-1`, `projeto-final`, etc.
|
|
4. **Apague branches antigos** após a correção:
|
|
|
|
```bash
|
|
git branch -D exercicio-1 # Local
|
|
git push origin --delete exercicio-1 # Remoto
|
|
```
|
|
|
|
---
|
|
|
|
## **Se o Professor Pedir para Entregar o Exercício**
|
|
|
|
1. Envie o branch para seu fork (`git push origin exercicio-1`).
|
|
2. Abra um **Pull Request** no repositório do professor (se for o processo definido por ele).
|
|
3. Ou compartilhe o link do branch no seu fork (ex: `https://github.com/seu-user/seu-fork/tree/exercicio-1`).
|
|
|
|
### **Benefícios**
|
|
|
|
- Você mantém um histórico organizado.
|
|
- O `main` do seu fork sempre estará pronto para receber novas atualizações do professor.
|
|
- Seus exercícios ficam isolados e fáceis de gerenciar.
|
|
|
|
Esse workflow é amplamente usado em projetos open source e ambientes educacionais! 🚀
|