Geekflare est soutenu par son public. Nous pouvons percevoir des commissions d'affiliation sur les liens d'achat présents sur ce site.
En Développement Dernière mise à jour : 25 septembre 2023
Partager sur :
Invicti Web Application Security Scanner - la seule solution qui offre une vérification automatique des vulnérabilités avec Proof-Based Scanning™.

Dans cet article, vous découvrirez différentes façons de jouer avec les commits dans Git

En tant que développeur, vous avez dû rencontrer de nombreuses fois des situations où vous vouliez revenir à l'un de vos commits précédents, mais vous n'étiez pas sûr de savoir comment le faire. Et même si vous connaissez les commandes Git comme reset, revert, rebase, vous n'êtes pas conscient des différences entre elles. Commençons donc par comprendre ce que sont les commandes git reset, revert et rebase

Réinitialisation de Git

Git reset est une commande complexe, utilisée pour annuler les modifications

Vous pouvez considérer git reset comme une fonction de retour en arrière. Avec git reset, vous pouvez passer d'un commit à l'autre. Il existe trois modes d'exécution de la commande git reset : -soft, -mixed et -hard. Par défaut, la commande git reset utilise le mode mixte. Lors d'une réinitialisation de git, trois mécanismes de gestion interne de git entrent en jeu : TÊTE, la zone de transit (index) et le répertoire de travail

git reset - geekflare

Le répertoire de travail est l'endroit où vous travaillez actuellement, c'est l'endroit où vos fichiers sont présents. En utilisant la commande git status, vous pouvez voir quels sont les fichiers/dossiers présents dans le répertoire de travail

La Staging Area (Index) est l'endroit où git suit et enregistre toutes les modifications apportées aux fichiers. Les modifications enregistrées sont reflétées dans le répertoire .git. Vous utilisez git add "nom de fichier" pour ajouter le fichier à la staging area. Et comme précédemment, lorsque vous exécutez git status, vous verrez quels fichiers sont présents dans la zone de transit

La branche courante dans Git est appelée HEAD. Elle pointe vers la dernière livraison, qui s'est produite dans la branche d'extraction actuelle. Elle est traitée comme un pointeur pour toute référence. Lorsque vous passez à une autre branche, le HEAD est également déplacé vers la nouvelle branche

Laissez-moi vous expliquer comment fonctionne git reset en mode hard, soft et mixte. Le mode hard est utilisé pour aller au commit pointé, le répertoire de travail est rempli avec les fichiers de ce commit, et la zone de transit est réinitialisée. Dans la réinitialisation douce, seul le pointeur est changé pour le commit spécifié. Les fichiers de toutes les livraisons restent dans le répertoire de travail et la zone de stockage avant la réinitialisation. En mode mixte (par défaut), le pointeur et la zone de stockage sont tous deux réinitialisés

Git Reset Hard

Le but de git hard reset est de déplacer le HEAD au commit spécifié. Elle supprimera tous les commits qui se sont produits après le commit spécifié. Cette commande modifiera l'historique des livraisons et pointera vers la livraison spécifiée

Dans cet exemple, je vais ajouter trois nouveaux fichiers, les livrer et ensuite effectuer un hard reset

Comme vous pouvez le voir dans la commande ci-dessous, il n'y a rien à livrer pour l'instant

$ git status
Sur la branche master
Votre branche est en avance sur 'origin/master' de 2 commits.

(utilisez "git push" pour publier vos commits locaux)

rien à commiter, arbre de travail propre

Maintenant, je vais créer 3 fichiers et y ajouter du contenu

$ vi file1.txt

$

 vi file2.txt

$

 vi file3.txt

Ajoutez ces fichiers au dépôt existant

$ git add file*

Lorsque vous réexécuterez la commande status, elle reflétera les nouveaux fichiers que je viens de créer

$ git status
Sur la branche master
Votre branche est en avance sur 'origin/master' de 2 commits.

(utilisez "git push" pour publier vos commits locaux)

Changements à livrer :

(utilisez "git restore --staged <file>..." pour déstager)

nouveau fichier :
file1.txt

nouveau fichier :
file2.txt

nouveau fichier :
file3.txt

Avant de commiter, laissez-moi vous montrer, j'ai actuellement un journal de 3 commits dans Git

$ git log --oneline

0db602e

(HEAD -> master) one more commit
59c86c9 new commit

e2f44fc

(origin/master, origin/HEAD) test

Maintenant, je vais faire un commit dans le dépôt

$ git commit -m 'ajouté 3 fichiers'
[master d69950b] ajouté 3 fichiers

3

 fichiers modifiés, 3 insertions( )
créer le mode 100644 fichier1.txt
créer le mode 100644 fichier2.txt
créer le mode 100644 fichier3.txt

Si je fais ls-files, vous verrez que les nouveaux fichiers ont été ajoutés

$ git ls-files
demo
dummyfile
newfile
file1.txt
file2.txt
file3.txt

Lorsque je lance la commande log dans git, j'ai 4 commits, et le HEAD pointe vers le dernier commit

$ git log --oneline

d69950b

(HEAD -> master) a ajouté 3 fichiers

0db602e

 un nouveau commit
59c86c9 nouveau commit

e2f44fc

(origin/master, origin/HEAD) test

Si je supprime manuellement le fichier 1.txt et que j'effectue un git status, le message suivant apparaîtra : les modifications ne sont pas mises à disposition pour le commit

$ git status
Sur la branche master
Votre branche est en avance sur 'origin/master' de 3 commits.

(utilisez "git push" pour publier vos commits locaux)

Changements non mis à disposition pour commit :

(utilisez "git add/rm <file>....
"pour mettre à jour ce qui sera livré)

(utilisez "git restore <file>..." pour supprimer les modifications dans le répertoire de travail)

supprimé :
file1.txt

pas de modifications ajoutées à la livraison (utilisez "git add" et/ou "git commit -a")

Maintenant, je vais lancer la commande hard reset

$ git reset --hard
HEAD est maintenant à d69950b a ajouté 3 fichiers

Si je vérifie à nouveau le statut, je constate qu'il n'y a rien à livrer, et que le fichier que j'ai supprimé est revenu dans le dépôt. Le retour en arrière s'est produit parce qu'après avoir supprimé le fichier, je n'ai pas fait de livraison, donc après une réinitialisation, le dépôt est revenu à l'état précédent

$ git status
Sur la branche master
Votre branche est en avance sur 'origin/master' de 3 commits.

(utilisez "git push" pour publier vos commits locaux)

rien à commiter, arbre de travail propre

Si je vérifie le journal de git, voici à quoi il ressemblera

$ git log
commit d69950b7ea406a97499e07f9b28082db9db0b387 (HEAD -> master)
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 19:53 :31 2020 0530

a ajouté 3 fichiers

commit 0db602e085a4d59cfa9393abac41ff5fd7afcb14
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 01:04 :13 2020 0530

un autre commit

commit 59c86c96a82589bad5ecba7668ad38aa684ab323
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 00:54 :53 2020 0530

nouveau commit

commit e2f44fca2f8afad8e4d73df6b72111f2fd71ad (origin/master, origin/HEAD)
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 00:16:33 2020 0530

test

Le but de la réinitialisation est de pointer vers le commit spécifié et de mettre à jour le répertoire de travail et la zone de transit. Laissez-moi vous montrer un autre exemple. Actuellement, la visualisation de mes commits ressemble à ce qui suit

git hard

Ici, je vais exécuter la commande avec HEAD^, ce qui signifie que je veux revenir au commit précédent (un commit en arrière)

$ git reset --hard HEAD^
HEAD est maintenant à 0db602e un commit de plus

Vous pouvez voir que le pointeur de tête est passé de d69950b à 0db602e

$ git log --oneline

0db602e

(HEAD -> master) one more commit
59c86c9 new commit

e2f44fc

(origin/master, origin/HEAD) test

git hard 1

Si vous vérifiez le journal, le commit de d69950b a disparu, et le head pointe maintenant vers 0db602e SHA

$ git log
commit 0db602e085a4d59cfa9393abac41ff5fd7afcb14 (HEAD -> master)
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 01:04:13 2020 0530

one more commit

commit 59c86c96a82589bad5ecba7668ad38aa684ab323
Author :

mrgeek

<mrgeek@gmail.com>
Date :
Mon May 17 00:54:53 2020 0530

nouveau commit

commit e2f44fca2f8afad8e4d73df6b72111f2f2fd71ad (origin/master, origin/HEAD)
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 00:16:33 2020 0530

Test

Si vous lancez ls-files, vous pouvez voir que file1.txt, file2.txt, et files3.txt ne sont plus dans le dépôt parce que ce commit et son fichier ont été supprimés après la réinitialisation

$ git ls-files
demo
dummyfile
newfile

Réinitialisation douce de Git

De la même manière, je vais maintenant vous montrer un exemple de réinitialisation douce. Considérez que j'ai ajouté les 3 fichiers comme mentionné ci-dessus et que je les ai validés. Le journal git apparaîtra comme ci-dessous. Vous pouvez voir que 'soft reset' est mon dernier commit, et que HEAD pointe également vers lui

$ git log --oneline

aa40085

(HEAD -> master) soft reset

0db602e

 one more commit
59c86c9 new commit

e2f44fc

(origin/master, origin/HEAD) test

Les détails du commit dans le journal peuvent être consultés à l'aide de la commande suivante

$ git log
commit aa400858aab3927e79116941c715749780a59fc9 (HEAD -> master)
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 21 :01:36 2020 0530

soft reset

commit 0db602e085a4d59cfa9393abac41ff5fd7afcb14
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 01:04 :13 2020 0530

un autre commit

commit 59c86c96a82589bad5ecba7668ad38aa684ab323
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 00:54 :53 2020 0530

nouveau commit

commit e2f44fca2f8afad8e4d73df6b72111f2fd71ad (origin/master, origin/HEAD)
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 00:16:33 2020 0530

test

Maintenant, en utilisant la réinitialisation douce, je veux passer à l'un des anciens commits avec SHA 0db602e085a4d59cfa9393abac41ff5fd7afcb14

Pour ce faire, je vais exécuter la commande ci-dessous. Vous devez passer plus de 6 caractères de début de SHA, le SHA complet n'est pas nécessaire

git reset --soft 0db602e085a4

Maintenant, lorsque je lance le journal git, je peux voir que le HEAD a été réinitialisé au commit que j'ai spécifié

$ git log
commit 0db602e085a4d59cfa9393abac41ff5fd7afcb14 (HEAD -> master)
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 01:04:13 2020 0530

one more commit

commit 59c86c96a82589bad5ecba7668ad38aa684ab323
Author :

mrgeek

<mrgeek@gmail.com>
Date :
Mon May 17 00:54:53 2020 0530

nouveau commit

commit e2f44fca2f8afad8e4d73df6b72111f2fd71ad (origin/master, origin/HEAD)
Author : mrgeek <mrgeek@gmail.com>
Date :
Mon May 17 00:16:33 2020 0530

test

Mais la différence ici est que les fichiers du commit (aa400858aab3927e79116941c715749780a59fc9) où j'avais ajouté 3 fichiers sont toujours dans mon répertoire de travail. Ils n'ont pas été supprimés. C'est pourquoi vous devriez utiliser une réinitialisation douce plutôt qu'une réinitialisation dure. Il n'y a pas de risque de perdre les fichiers en mode doux

$ git ls-files
demo
dummyfile
file1.txt
file2.txt
file3.txt
newfile

Git Revert

Dans Git, la commande revert est utilisée pour effectuer une opération de revert, c'est-à-dire pour annuler certaines modifications. Elle est similaire à la commande reset, mais la seule différence est que vous effectuez un nouveau commit pour revenir à un commit particulier. En résumé, on peut dire que la commande git revert est un commit

La commande Git revert ne supprime aucune donnée lors de l'exécution de l'opération de revert

Supposons que j'ajoute 3 fichiers et que j'exécute une opération git commit pour l'exemple revert

$ git commit -m 'add 3 files again'
[master 812335d] add 3 files again

3

 files changed, 3 insertions( )
create mode 100644 file1.txt
create mode 100644 file2.txt
create mode 100644 file3.txt

Le journal montrera le nouveau commit

$ git log --oneline

812335d

(HEAD -> master) add 3 files again

0db602e

 one more commit
59c86c9 new commit

e2f44fc

(origin/master, origin/HEAD) test

Maintenant, j'aimerais revenir à l'un de mes commits précédents, disons "59c86c9 new commit". J'exécute la commande suivante

$ git revert 59c86c9

Cela ouvrira un fichier dans lequel vous trouverez les détails du commit sur lequel vous essayez de revenir, et vous pouvez donner un nom à votre nouveau commit ici, puis sauvegarder et fermer le fichier

Revert "new commit"

Ceci annule le commit 59c86c96a82589bad5ecba7668ad38aa684ab323.

#

Veuillez entrer le message de commit pour vos changements.

Les

lignes commençant

#

par '#' seront ignorées, et un message vide annule la livraison.
#

#Sur la branche master

#

Votre branche est en avance sur 'origin/master' de 4 commits.

#

(utilisez "git push" pour publier vos commits locaux)

#


#Changements à livrer :

#

modifié : dummyfile

Après avoir sauvegardé et fermé le fichier, voici le résultat que vous obtiendrez

$ git revert 59c86c9
[master af72b7a] Revert "new commit"

1

 fichier modifié, 1 insertion( ), 1 suppression(-

)
Maintenant, pour effectuer les changements nécessaires, contrairement à la réinitialisation, revert a effectué un nouveau commit. Si vous vérifiez à nouveau le journal, vous trouverez un nouveau commit à cause de l'opération revert

$ git log --oneline
af72b7a (HEAD -> master) Revert "new commit"

812335d

 add 3 files again

0db602e

 one more commit
59c86c9 new commit

e2f44fc

(origin/master, origin/HEAD) test

git revert

Le journal Git contient tout l'historique des livraisons. Si vous souhaitez supprimer les commits de l'historique, revert n'est pas un bon choix, mais si vous souhaitez conserver les modifications des commits dans l'historique, revert est la commande appropriée au lieu de reset

Git Rebase

Dans Git, rebase est la façon de déplacer ou de combiner les commits d'une branche sur une autre branche. En tant que développeur, je ne créerais pas mes fonctionnalités sur la branche principale dans un scénario réel. Je travaillerais sur ma propre branche (une "branche de fonctionnalités"), et lorsque j'aurais quelques commits dans ma branche de fonctionnalités avec la fonctionnalité ajoutée, je voudrais alors la déplacer vers la branche principale

Le rebasement peut parfois être un peu difficile à comprendre, car il est très similaire à la fusion. Le but de la fusion et du rebasage est de prendre les commits de ma branche de fonctionnalités et de les placer sur la branche master ou toute autre branche. Prenons l'exemple d'un graphique qui ressemble à ceci

git rebase

Supposons que vous travailliez dans une équipe avec d'autres développeurs. Dans ce cas, vous pouvez imaginer que cela peut devenir très complexe lorsque vous avez un tas d'autres développeurs travaillant sur différentes branches de fonctionnalités, et qu'ils ont fusionné de multiples changements. La traçabilité devient alors difficile

C'est donc là que rebase va vous aider. Cette fois, au lieu de faire un git merge, je vais faire un rebase, où je veux prendre mes deux commits de la branche fonctionnalité et les déplacer sur la branche master. Un rebase va prendre tous les commits de la branche fonctionnalité et les déplacer au dessus des commits de la branche master. Ainsi, en coulisse, git duplique les commits de la feature branch sur la branche master

git rebase 1

Cette approche vous permet d'obtenir un graphique en ligne droite avec tous les commits en ligne

git revert 2

Il est ainsi plus facile de savoir quels commits sont allés où. Vous pouvez imaginer que si vous faites partie d'une équipe avec de nombreux développeurs, tous les commentaires sont toujours alignés. C'est donc très facile à suivre, même si plusieurs personnes travaillent en même temps sur le même projet

Laissez-moi vous montrer cela en pratique

Voici à quoi ressemble ma branche master actuellement. Elle a 4 commits

$ git log --oneline

812335d

(HEAD -> master) add 3 files again

0db602e

 one more commit
59c86c9 new commit

e2f44fc

(origin/master, origin/HEAD) test

Je vais exécuter la commande suivante pour créer et basculer vers une nouvelle branche appelée feature, et cette branche sera créée à partir du 2ème commit, c'est à dire 59c86c9

(master)

$

 git checkout -b feature 59c86c9
Passage à une nouvelle branche 'feature'

Si vous vérifiez le journal de la branche 'feature', il n'y a que 2 commits provenant du master (mainline)

(feature)

$

 git log --oneline
59c86c9 (HEAD -> feature) new commit

e2f44fc

(origin/master, origin/HEAD) test

Je vais créer la fonctionnalité 1 et la livrer sur la branche des fonctionnalités
(fonctionnalité

)

$

 vi feature1.txt

(fonctionnalité)

$

 git add .
Le fichier aura sa fin de ligne originale dans votre répertoire de travail

(fonctionnalité)

$

 git commit -m 'fonctionnalité 1'
[fonctionnalité c639e1b] fonctionnalité 1

1

 fichier modifié, 1 insertion( )
create mode 100644 fonctionnalité1.txt

Je vais créer une fonctionnalité supplémentaire, c'est-à-dire la fonctionnalité 2, dans la branche des fonctionnalités et la valider
(fonctionnalité)


$
 vi feature2.txt

(fonctionnalité)

$

 git add .
Le fichier aura sa fin de ligne originale dans votre répertoire de travail

(fonctionnalité)

$

 git commit -m 'feature 2'
[feature 0f4db49] feature 2

1

 file changed, 1 insertion( )
create mode 100644 feature2.txt

Maintenant, si vous vérifiez le journal de la branche feature, il y a deux nouveaux commits, que j'ai exécutés ci-dessus

(fonctionnalité)

$

 git log --oneline

0f4db49

(HEAD -> fonctionnalité) fonctionnalité 2

c639e1b

 fonctionnalité 1
59c86c9 nouveau commit

e2f44fc

(origin/master, origin/HEAD) test

Maintenant, je veux ajouter ces deux nouvelles fonctionnalités à la branche master. Pour cela, je vais utiliser la commande rebase. A partir de la branche des fonctionnalités, je vais rebaser sur la branche master. Cela aura pour effet de ré-ancrer ma branche de fonctionnalités avec les derniers changements

(feature)

$

 git rebase master
Rebase et met à jour refs/heads/feature avec succès

Maintenant, je vais aller de l'avant et extraire la branche master

(feature)

$

 git checkout master
Switched to branch 'master'
Votre branche est en avance sur 'origin/master' de 3 commits.

(utilisez "git push" pour publier vos commits locaux)

Et enfin, rebasez la branche master sur ma branche de fonctionnalités. Cela va prendre les deux nouveaux commits sur ma branche de fonctionnalités et les rejouer au dessus de ma branche master

(master)

$

 git rebase feature
Rebase et met à jour refs/heads/master avec succès

Maintenant, si je vérifie le journal de la branche master, je peux voir que les deux commits de ma branche features ont été ajoutés à ma branche master avec succès

(master)

$

 git log --oneline
766c996 (HEAD -> master, feature) feature 2

c036a11

 feature 1

812335d

 add 3 files again

0db602e

 one more commit
59c86c9 new commit

e2f44fc

(origin/master, origin/HEAD) test

Voilà pour les commandes reset, revert et rebase dans Git

Conclusion

Tout était dit sur les commandes reset, revert et rebase dans Git. J'espère que ce guide pas à pas vous a été utile. Maintenant, vous savez comment jouer avec vos commits selon vos besoins en utilisant les commandes mentionnées dans l'article.

  • Avi
    Auteur
    Avi est un passionné de technologie avec une expertise dans les technologies en vogue telles que DevOps, Cloud Computing, Big Data et bien d'autres. Il est passionné par l'apprentissage des technologies de pointe et le partage de ses connaissances avec d'autres... en savoir plus
Merci à nos sponsors
D'autres lectures intéressantes sur le développement
Alimentez votre entreprise
Quelques outils et services pour aider votre entreprise à se développer.
  • Invicti utilise le Proof-Based Scanning™ pour vérifier automatiquement les vulnérabilités identifiées et générer des résultats exploitables en quelques heures seulement.
    Essayez Invicti
  • Web scraping, proxy résidentiel, proxy manager, web unlocker, search engine crawler, et tout ce dont vous avez besoin pour collecter des données web.
    Essayez Brightdata
  • Monday.com est un système d'exploitation tout-en-un qui vous aide à gérer vos projets, vos tâches, votre travail, vos ventes, votre CRM, vos opérations, vos flux de travail et bien plus encore.
    Essayez le lundi
  • Intruder est un scanner de vulnérabilité en ligne qui détecte les faiblesses de votre infrastructure en matière de cybersécurité, afin d'éviter des violations de données coûteuses.
    Essayer l'intrus