Introduction à Git

Author

Ludovic Deneuville

Introduction

  • Outil indispensable
  • Pas d’évaluation immédiate
    • mais utilisé toute la scolarité et vie pro
  • Présentation perso en 1min
  • Évalué en Compléments d’info 2A
  • Suivi d’un TP
  • ⚠️ valable pour tous les TP
    • n’allez pas trop vite
    • suivez précisément les consignes

Introduction

Vous faites parti d’une équipe de 5 personnes qui doit coder une application de jeux de cartes.

😕 Comment mettre en commun votre code ?

  • Vous développez chacun de votre coté et à la fin, vous mettez tout en commun
  • Vous envoyez vos programmes par mail
  • Vous créez un dossier commun

😅 En cas d’erreur, comment revenir en arrière ?

Au programme

  • 📌 Versionner son code
  • 💾 Historique des modifications
  • 👷 Travail en équipe

Pourquoi versionner ?

  • Quelle est la bonne version ?
  • Comment faire pour revenir en arrière ?
  • Qui a écrit ce code ? Quand ?
  • les questions que l’on peut se poser en projet
  • Mais qui a écrit cette merde ???
    • ah ben c’est moi…

Pour connaitre la véritable dernière version

  • imaginons que vous partagiez un dossier commun
  • ou encore que ce fichier soit dans des mails
  • version v0, v1, v2
    • même si vous êtes bien intentionné
    • ça finira par déraper

Ancien code commenté

Vous souhaitez passer de R-base à ggplot2 pour votre graphique.

Mais vous vous dites que c’est mieux de garder l’ancien code au cas où…

La solution

La solution, tous en choeur, c’est …

Git

  • git : connard en argot britannique

Historique

  • Créé par Linus Torvalds en 2005
  • Pour gérer le développement du noyau Linux
  • Le standard incontournable de la gestion de versions
  • Anciens outils : CVS, SVN
  • Standard : produit qui s’est imposé par l’usage (ex : Moteur de recherche Google, TCP/IP)
    • peu causer des problèmes de monopole…

Logiciel

  • Logiciel Libre, Open source
  • Gratuit
  • Décentralisé
Note

😨 Git s’utilise majoritairement en ligne de commande dans un terminal Git Bash.
😅 Pas de panique, quelques commandes suffisent pour travailler avec Git.

Il existe aussi des interfaces graphiques mais elles sont souvent imparfaites et sources d’erreur.

  • Logiciel libre
    • code source est ouvert et disponible
    • permettant à quiconque de l’utiliser, le modifier, et le distribuer librement
    • différent de gratuit
    • légérement différent de Open source
      • Open Source : avantages pratiques et collaboratifs
      • Libre : libertés et les droits éthiques des utilisateurs
  • Décentralisé
    • chaque utilisateur dispose d’une copie complète de l’historique de tout le projet

Késako

  • Git
    • Logiciel de gestion de versions
  • Git Bash
    • Terminal pour écrire des commandes git
  • GitHub / GitLab
    • Plateforme de développement collaboratif
    • Héberge des dépôts Git
    • Propose d’autres fonctionnalités (CI/CD, wiki, gestion des incidents…)
  • GitHub racheté par Microsoft en 2018
  • GitLab, Libre, possible d’avoir son propre GitLab interne

Git Bash

  • Terminal de commande
  • Plusieurs manières de lancer (Menu Windows, clic droit, inclus dans VSCode)

Conseil : lors de l’installation de Git, choisissez le terminal Unix

  • 1ere ligne : prompt (username, machine, répertoire actuel)
  • 2e ligne (commence par $) : commande
  • 3e ligne : résultat de la commande

Commandes Unix

  • ce qui est entre < … > est à remplacer
  • ll : ls -l
  • cd : change directory
  • pwd : print working directory
  • mkdir : make directory
  • pour éditer un fichier : vi, nano
  • man

Attention avec les commandes rm, kill

Commandes Unix - Exemples

Pour chaque commande, de nombreuses options sont disponibles

ls *.py              # liste tous les fichiers python du répertoire courant
ls *.py > a.txt      # crée un fichier a.txt contenant le résultat de la commande
cd ..                # se positionne dans le répertoire parent
cd ../projet/src     # remonter dans le dossier parent puis aller dans projet puis src
cp /p/image.jpg .    # copie le fichier image.jpg du disque P dans le dossier courant
./setup.sh           # lance le programme setup.sh du répertoire courant
Tip
  • . : représente le dossier courant
  • .. : représente le dossier parent
  • ~ : répertoire personnel de l’utilisateur (echo $HOME)

répertoire = dossier

La ligne de commande reste très utilisée :

  • rapide, efficace
  • automatisation
    • exemple : renommer 1000 fichiers d’un dossier

Copier-Coller

Warning
  • CTRL + C et CTRL + V ne fonctionnent pas !
  • CTRL + C : stopper un processus (très utile)

2 possibilités pour coller du texte :

  • Clic droit
  • MAJ + INSERT

Versionner son code

  • Au début j’ai parlé de versionner
  • Comment faire avec Git

Que versionne-t-on ?

  • des fichiers de type texte (légers)
  • du code source
  • fichiers de données
  • mots de passe
  • outputs : logs, .pdf, .doc
  • un dépôt doit rester mince
  • quelques Mo max
  • possible de mettre du doc ou pdf
    • mais git ne sait comparer que du txt, csv, md
    • tout ce qui peut s’ouvrir avec notepad

Workflow

sequenceDiagram
    Workspace ->> Staging index: add
    Staging index ->> Local repository: commit
    Local repository ->> Remote repository: push
    Remote repository ->> Workspace: pull

  • ça fait un peu peur, pas intuitif au début
  • c’est un peu plus complexe que d’avoir simplement local et remote
  • workspace : tous les fichiers de votre dossier
  • staging : fichier reconnus par git
  • local : sauvegardes du dépôt local

Créer un commit

2 étapes pour créer une nouvelle version :

  • git add <filename>
    • ajouter le fichier à l’index (i.e. dire à Git de suivre ce fichier)
    • git add . : pour ajouter tous les fichiers
  • git commit -m "<mon message>"
  • git utilise la sauvegarde incrémentale
  • il ne garde que les modifs apportées depuis le dernier commit

https://talks.freelancerepublik.com/git-commandes-indispensables-developpeurs/

Exemple

git checkout <commit_number> : les fichiers de votre dépôt sont alors dans l’état où ils étaient à ce commit

Message du commit

😔 Ce n’est pas toujours évident de trouver un message court et explicite.

Tip

Utilisez un préfixe à votre message selon le pattern <type>: <sujet>:

  • doc: mise à jour documentaire
  • feat: nouvelle fonctionnalité
  • fix: correction
  • refactor: mise au propre du code
  • revert: retour arrière
  • test: Modification des tests

Suffixe WIP

Retour arrière

Si finalement, vous n’avez pas envie de « commiter » vos modifications ?

Commande Description
git restore <file> Annuler les modifications locales non indexées du fichier
git reset <file> Desindexer un fichier
git reset --hard Revenir à l’état du dernier commit,
perdant toutes les modifications locales
git stash Sauvegarder et remettre le working directory à l’état du dernier commit
Caution

Attention avec les commandes contenant les mots force, hard

Ignorer des fichiers

Le fichier .gitignore

.gitignore est un fichier présent à la racine du dépôt permettant de dire à Git quels fichiers il doit ignorer. Par exemple, s’il contient :

  • *.csv ➡️ tous les fichiers csv seront ignorés par Git
  • data/ ➡️ le dossier data et son contenu sera ignoré

Cela est utile, pour exclure par exemple du dépôt Git :

  • des fichiers contenant des mots de passe, des jetons d’accès…
  • des fichiers volumineux de données qui n’ont pas vocation à être versionnés
  • des fichiers de log
  • En info, il y a souvent plein de fichiers de config
  • ⚠️ Mots de passe ➡️ git garde tout l’historique
  • Next
    • c’était pour la partie “gestion du dépôt local”
    • ensuite regardons comment communiquer avec le dépôt distant

Travailler en équipe

Dépôt local et dépôt distant

  • 1 dépôt distant
    • appelé aussi remote
    • hébergé sur une forge (GitHub, GitLab, Bitbucket…)
  • n dépôts locaux
    • clone sur votre machine
    • git permet la synchronisation des dépôts
Remarque

Il est tout à fait possible d’avoir plusieurs clones du même dépôt sur son poste.

  • avoir un accès internet / réseau local pour communiquer avec remote
  • c’était pas nécessaire pour faire des add / commit

Commencer dessin avec :

  • un remote v0
  • 2 clones de Bob et Alice en v0

Dépôt local et dépôt distant

Important

Chaque dépôt est une copie intégrale du projet.

flowchart LR
    github[(Dépôt distant)]
    dev1[(Dépôt local 1)]
    dev2[(Dépôt local 2)]
    dev3[(Dépôt local 3)]
    dev4[(Dépôt local 4)]
    
    github <--> dev1
    github <--> dev2
    dev3 <--> github
    dev4 <--> github

  • Si vous perdez un dépôt, il suffit de repartir d’un autre

Communiquer avec le dépôt distant

  • git pull : mettre à jour son dépôt local à partir du dépôt distant
  • git push : envoyer ses commits locaux sur le dépôt distant
Important

Il est important de pousser et puller réguliérement son code pour garder son dépôt à jour.

  • sinon vos versions vont diverger

IMPORTANT :

  • Vous faites toujours vos actions sur un dépôt local
  • Vous ne modifiez jamais le dépôt distant

git push

Dépôt local ➡️ Dépôt distant

Pour pouvoir pousser son code, il est nécessaire :

  • d’avoir au préalable créé au minimum un commit
  • que votre dépôt local soit à jour
    • pas de retard de version par rapport au dépôt distant
    • si ce n’est pas le cas, il faut commencer par git pull

Vous pouvez push plusieurs commits

git push - si votre dépôt local n’est pas à jour

! [rejected]        main -> main (fetch first)
error: failed to push some refs
hint: Updates were rejected because the remote contains work that you do not
hint: have locally. This is usually caused by another repository pushing to
hint: the same ref. If you want to integrate the remote changes, use
hint: 'git pull' before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.

Le message est assez explicite.

git push - fichier disparu

  • Vous venez de faire un git push
  • Mais votre fichier n’apparait pas sur le dépôt distant…
  • Probablement parce que vous avez oublié de l’ajouter à l’index avec git add <mon_fichier>

Autre possibilité : votre fichier est ignoré par git car il fait parti du .gitignore

ça arrive quand vous voulez aller trop vite

git pull

Dépôt local ⬅️ Dépôt distant

  • Mise à jour de votre dépôt local
  • S’il y a eu des modifications sur le dépôt distant

Un pull se fait généralement après un commit.

git pull - conflit

Que se passe-t-il si :

  • Alice a modifié un fichier et poussé sa modification sur le dépôt distant
  • Vous avez également modifié le même fichier et vous faites un git pull pour mettre à jour votre dépôt à partir du dépôt distant

😨 Un conflit ! Git ne sait pas choisir quelle est la bonne version entre la votre et celle d’Alice.

git pull - conflit

😅 Pas de panique ! Pour résoudre le conflit, il faut simplement :

  • modifier le fichier en question pour garder la bonne version
  • git add puis git commit pour valider la résolution du conflit
  • conflit ≠ erreur
  • ça arrive

2 versions s’opposent

  • c’est un exemple, il peut y avoir d’autres types
  • git est assez bon pour merge (même si 2 modifs sur même fichier)
  • mais en cas de doute, il ne peut pas choisir

Résoudre un conflit

  • Contexte
    • Permier arrivé, premier servi
    • Le conflit (après votre pull)
  • Conflit
    • Git n’est pas un juge
    • VSCode : accept incoming/current/both change
  • Résolution
    • supprimez les <<<<<<< et ======= ➡️ pas du python
    • si vous relancez votre programme comme ça, il va pas aimer

Le conflit se résoud sur son dépôt local !

Etat du dépôt local

Est-ce qu’il y a des fichiers :

  • non suivis ? Untracked files
  • prêts à être commités ? Changes to be committed
  • modifiés non ajoutés à l’index ? Changes not staged for commit
Important

La commande git status permet de répondre à ces questions.

Elle peut être utilisée n’importe quand, sans modération !

git status

Est-ce que votre dépôt local est en avance de n commit par rapport au dépôt distant ?

Cloner un dépôt

git clone

  • Allez sur la page du dépôt distant (GitHub, GitLab…)
  • Cliquez sur le bouton Code
  • Copiez l’adresse https ou ssh du dépôt distant
  • git clone <adresse_depot>
  • exemples :
    • git clone https://github.com/ludo2ne/Git-tuto.git (https)
    • git clone git@github.com:ludo2ne/Git-tuto.git (ssh)

Créer sans cloner

Remarque

Il est possible de créer un dépôt local sans cloner un dépôt distant (git init).

Et éventuellement ensuite de le brancher à un dépôt distant.

Cependant ce cas d’utilisation est assez marginal.

https ou ssh ?

2 protocoles différents pour communiquer avec le dépôt distant.

  • ssh :
    • clé publique / clé privée -> config machine
    • push and pull
  • https :
    • token donné par github
    • pull only

Commandes principales

Commande Description
git clone <adr> Créer un dépôt local sur son poste
git status Voir où l’on en est
git add <file> Ajouter pour le prochain commit
git commit -m "<msg>" Créer un point de sauvegarde
git pull dépôt local ➡️ dépôt distant
git push dépôt local ⬅️ dépôt distant

clone : bouton vert code sur GitHub, GitLab

Autres commandes

  • git diff : différence avec le dernier commit
    • git diff <filename>
  • git checkout <commit_number> : passer à un commit spécifique
  • git log : historique des commits
    • git log --all --decorate --oneline --graph

La routine Git

  • pull : des fois qu’un camarade ait codé la nuit

Démo

  • aller sur GitHub, cloner
  • créer un fichier, status
  • reset, status
  • modifier un fichier, status
  • commit
  • modifier sur github
  • push

Travailler dans le cloud

  • Autre manière de travailler
  • Services non perennes
  • Sauvegarder votre code
  • vous ne travaillerez pas toujours en local
  • mais parfois sur des services à la demande
  • ex : besoin de puissance de calcul

Les branches

Imaginez que vous souhaitez ajouter une nouvelle fonctionnalité à votre code.

Seulement vous n’êtes pas encore sûr que :

  • cette fonctionnalité sera vraiment utile 😐
  • qu’elle ne va pas tout casser 😰
Note
  • si c’est tout petit, vous pouvez dev en local en faire un reset au cas où
  • sinon utilisez une branche

Les branches

Vous aimeriez pouvoir :

  • tester votre nouveau code
  • de manière isolée
  • sans polluer le dépôt
Note

La branche principale se nomme généralement main ou master.

La solution

  • Créez une branche
  • Développez sur cette branche (add, commit, push…)
  • Selon vos conclusions
    • fusionnez votre branche avec le tronc
    • supprimez votre branche

ça vous permet de coder de manière isolée

Commandes liées aux branches

Commande Description
git branch -a Lister toutes les branches
git switch <branch> Changer de branche
git switch -c <branch> Créer et changer de branche
git merge <branch> Fusionner <branch> dans la branche actuelle
git branch -d <branch> Supprimer la branche
git push origin <branch> Pousser la branche vers le dépôt distant

Bibliographie