Comment annuler les derniers commits locaux dans Git?

21067

J'ai accidentellement validé les mauvais fichiers dans Git , mais je n'ai pas encore poussé la validation sur le serveur.

Comment annuler ces validations à partir du référentiel local?

Peter Mortensen
la source
138
Avant de publier une nouvelle réponse, considérez qu'il existe déjà plus de 65 réponses à cette question. Assurez-vous que votre réponse contribue à ce qui ne figure pas parmi les réponses existantes.
Sazzad Hissain Khan
91
Vous savez de quoi a besoin git? git undo, c'est ça. Ensuite, le git de réputation a pour gérer les erreurs commises par nous simples mortels disparaît. Implémentez en poussant l'état actuel sur une pile git avant d'exécuter une gitcommande. Cela affecterait les performances, il serait donc préférable d'ajouter un indicateur de configuration pour l'activer.
Yimin Rong
11
@YiminRong Cela peut être fait avec la aliasfonctionnalité de Git : git-scm.com/book/en/v2/Git-Basics-Git-Aliases
Edric
3
@RomainValeri - De la même manière, l'annulation fonctionne partout ailleurs.
Yimin Rong
1
@YiminRong Ne pas l'acheter. Les gens échappaient encore et défaisaient des choses à ne pas défaire. Mais plus important encore, git reflogest déjà proche de ce que vous décrivez, mais donne à l'utilisateur plus de contrôle sur ce qui doit (ne) pas être fait. Mais s'il vous plaît, non, "annuler" ne fonctionne pas de la même manière partout, et les gens s'attendraient à beaucoup de choses différentes pour la fonctionnalité. Annuler le dernier commit? Annuler la dernière action? Si la dernière action a été une poussée, annuler comment exactement (réinitialiser et pousser) ou (revenir en arrière et pousser)?
RomainValeri

Réponses:

22866

Annuler un commit et refaire

$ git commit -m "Something terribly misguided"             # (1)
$ git reset HEAD~                                          # (2)
<< edit files as necessary >>                              # (3)
$ git add ...                                              # (4)
$ git commit -c ORIG_HEAD                                  # (5)
  1. C'est ce que vous voulez annuler.
  2. Cela ne fait rien à votre arborescence de travail (l'état de vos fichiers sur le disque), mais annule la validation et laisse les modifications que vous avez validées non mises en scène (elles apparaîtront donc comme "Modifications non mises en scène pour la validation" dans git status, vous devrez donc ajoutez-les à nouveau avant de valider). Si vous souhaitez uniquement ajouter d' autres modifications à la validation précédente ou modifier le message de validation 1 , vous pouvez utiliser à la git reset --soft HEAD~place, ce qui est comme git reset HEAD~2 mais laisse vos modifications existantes par étapes.
  3. Apportez des corrections aux fichiers d'arborescence de travail.
  4. git add tout ce que vous souhaitez inclure dans votre nouveau commit.
  5. Validez les modifications en réutilisant l'ancien message de validation. resetcopié la vieille tête .git/ORIG_HEAD; commitavec -c ORIG_HEADouvrira un éditeur, qui contient initialement le message du journal de l'ancien commit et vous permet de le modifier. Si vous n'avez pas besoin de modifier le message, vous pouvez utiliser l' -Coption.

Attention, cependant, si vous avez ajouté de nouvelles modifications à l'index, l'utilisation commit --amendles ajoutera à votre commit précédent.

Si le code est déjà envoyé à votre serveur et que vous avez les autorisations pour écraser l'historique (rebase), alors:

git push origin master --force

Vous pouvez également consulter cette réponse:

Comment puis-je déplacer HEAD vers un emplacement précédent? (Tête détachée) & Annuler les validations

La réponse ci-dessus vous montrera ce git reflog,qui est utilisé pour savoir quel est le SHA-1, que vous souhaitez annuler. Une fois que vous avez trouvé le point auquel vous souhaitez annuler l'utilisation de la séquence de commandes comme expliqué ci-dessus.


1 Notez, cependant, que vous n'avez pas besoin de rétablir une validation antérieure si vous venez de faire une erreur dans votre message de validation . L'option la plus simple consiste à git reset(pour annuler toute modification que vous avez apportée depuis), puis à git commit --amendouvrir votre éditeur de message de validation par défaut prérempli avec le dernier message de validation.

2 HEAD~ est le même que HEAD~1. Voir aussi Qu'est - ce que la tête dans git? . Il est utile si vous souhaitez annuler plusieurs validations.

Mark Amery
la source
472
Et si le commit était dans la mauvaise branche, vous pouvez git checkout theRightBranchavec toutes les étapes de changement. Comme je venais de le faire.
Frank Shearar
491
Si vous travaillez sous DOS, au lieu de git reset --soft HEAD^vous devrez utiliser git reset --soft HEAD~1. Le ^ est un caractère de continuation sous DOS donc il ne fonctionnera pas correctement. En outre, --softc'est la valeur par défaut, vous pouvez donc l'omettre si vous le souhaitez et le dire git reset HEAD~1.
Ryan Lundy
119
Les utilisateurs de zsh peuvent obtenir: zsh: no matches found: HEAD^- vous devez vous échapper ^ iegit reset --soft HEAD\^
tnajdek
7
La réponse n'est pas correcte si, par exemple, par accident, elle a git commit -aété émise alors qu'elle -aaurait dû être omise. Dans ce cas, il est préférable de ne pas laisser de côté --soft(ce qui entraînera --mixedla valeur par défaut) et vous pourrez alors reformater les modifications que vous vouliez valider.
dmansfield
6
@IcyBrk git add est une commande. git add [--verbose | -v] [--dry-run | -n] [--force | -f] [--interactive | -i] [--patch | -p] [--edit | -e] [--[no-]all | --[no-]ignore-removal | [--update | -u]] [--intent-to-add | -N] [--refresh] [--ignore-errors] [--ignore-missing] [--chmod=(+|-)x] [--] [<pathspec>…​]
Ashraf.Shk786
10734

Annuler une validation est un peu effrayant si vous ne savez pas comment cela fonctionne. Mais c'est en fait incroyablement facile si vous comprenez.

Supposons que vous ayez ceci, où C est votre HEAD et (F) est l'état de vos fichiers.

   (F)
A-B-C
    ↑
  master

Vous voulez nuke commit C et ne plus jamais le voir et perdre toutes les modifications dans les fichiers modifiés localement . Tu fais cela:

git reset --hard HEAD~1

Le résultat est:

 (F)
A-B
  ↑
master

Maintenant, B est la TÊTE. Parce que vous l'avez utilisé --hard, vos fichiers sont réinitialisés à leur état lors de la validation B.

Ah, mais supposons que le commit C n'était pas un désastre, mais juste un peu décalé. Vous souhaitez annuler la validation mais conserver vos modifications pour un peu de modification avant de faire une meilleure validation. À partir d'ici, avec C comme TÊTE:

   (F)
A-B-C
    ↑
  master

Vous pouvez le faire en laissant de côté --hard:

git reset HEAD~1

Dans ce cas, le résultat est:

   (F)
A-B-C
  ↑
master

Dans les deux cas, HEAD n'est qu'un pointeur vers le dernier commit. Lorsque vous effectuez un git reset HEAD~1, vous dites à Git de reculer le pointeur HEAD d'un commit. Mais (sauf si vous l'utilisez --hard), vous laissez vos fichiers tels qu'ils étaient. Affiche maintenant git statusles modifications que vous avez enregistrées dans C. Vous n'avez rien perdu!

Pour le toucher le plus léger, vous pouvez même annuler votre commit mais laisser vos fichiers et votre index :

git reset --soft HEAD~1

Cela laisse non seulement vos fichiers seuls, mais laisse également votre index seul. Lorsque vous le ferez git status, vous verrez que les mêmes fichiers sont dans l'index que précédemment. En fait, juste après cette commande, vous pourriez le faire git commitet vous referiez le même commit que vous venez d'avoir.

Encore une chose: supposons que vous détruisiez un commit comme dans le premier exemple, mais que vous découvriez ensuite que vous en aviez besoin après tout ? Pas de chance, non?

Non, il y a encore un moyen de le récupérer. Tapez git refloget vous verrez une liste de shas de validation (partiels) (c'est-à-dire des hachages) dans lesquels vous vous êtes déplacé. Trouvez le commit que vous avez détruit, et procédez comme suit :

git checkout -b someNewBranchName shaYouDestroyed

Vous avez maintenant ressuscité ce commit. Les commits ne sont pas réellement détruits dans Git pendant environ 90 jours, vous pouvez donc généralement revenir en arrière et en sauver un dont vous ne vouliez pas vous débarrasser.

Ryan Lundy
la source
15
IL FAUT SE MÉFIER! Cela pourrait ne pas faire ce que vous attendez si votre commit erroné était une fusion (avance rapide)! Si votre tête est sur un commit de fusion (ex: fonction de branche fusionnée dans master), git reset --hard~1pointera la branche master vers le dernier commit à l'intérieur de la branche de fonctionnalité. Dans ce cas, l'ID de validation spécifique doit être utilisé à la place de la commande relative.
Chris Kerekes
90
Il manque un point crucial: si ledit commit a été précédemment `` poussé '' vers la télécommande, toute opération de `` défaire '', aussi simple soit-elle, causera d'énormes souffrances et souffrances aux autres utilisateurs qui ont ce commit dans leur copie locale, quand ils font un «git pull» à l'avenir. Donc, si le commit a déjà été «poussé», faites-le à la place: git revert <bad-commit-sha1-id> git push origin:
FractalSpace
12
@FractalSpace, cela ne causera pas "d'énormes douleurs et souffrances". J'ai fait quelques poussées de force lors de l'utilisation de Git avec une équipe. Il suffit de communication.
Ryan Lundy
14
@ Kyralessa Sur mon lieu de travail, gâcher le flux de travail de toute l'équipe, puis leur dire comment réparer sh * t ne s'appelle pas «communication». La réécriture de l'historique git est une opération destructrice qui entraîne la mise à la corbeille de parties du référentiel. Insister sur son utilisation, alors qu'il existe des alternatives claires et sûres, est tout simplement irresponsable.
FractalSpace
14
Je voulais nuke un commit et ne plus jamais le revoir. J'ai utilisé votre exemple avec --hardmais ce que je ne savais pas, c'est que tous mes changements non mis en scène dans mon arbre de travail sont également supprimés! J'allais valider ces fichiers dans le cadre d'une validation ultérieure. Maintenant, il semble impossible de récupérer ces fichiers - j'ai même essayé la solution que vous avez publiée, reflogmais cela n'a pas restauré les modifications précédemment non mises en scène.
Adam Burley
2130

Il existe deux façons d'annuler votre dernier commit, selon que vous avez déjà rendu votre commit public (poussé vers votre référentiel distant):

Comment annuler un commit local

Disons que je me suis engagé localement, mais maintenant je veux supprimer ce commit.

git log
    commit 101: bad commit    # Latest commit. This would be called 'HEAD'.
    commit 100: good commit   # Second to last commit. This is the one we want.

Pour restaurer tout ce qu'il était avant le dernier commit, nous devons resetle faire avant HEAD:

git reset --soft HEAD^     # Use --soft if you want to keep your changes
git reset --hard HEAD^     # Use --hard if you don't care about keeping the changes you made

Maintenant git log, montrera que notre dernier commit a été supprimé.

Comment annuler un commit public

Si vous avez déjà rendu vos commits publics, vous souhaiterez créer un nouveau commit qui "reviendra" sur les modifications que vous avez apportées dans votre commit précédent (HEAD actuel).

git revert HEAD

Vos modifications seront désormais annulées et prêtes à être validées:

git commit -m 'restoring the file I removed by accident'
git log
    commit 102: restoring the file I removed by accident
    commit 101: removing a file we don't need
    commit 100: adding a file that we need

Pour plus d'informations, consultez Git Basics - Undoing Things .

Andrew
la source
101
J'ai trouvé cette réponse la plus claire. git revert HEAD^n'est pas le précédent, est le précédent du précédent. Je l'ai fait: git revert HEADpuis j'ai poussé à nouveau et cela a fonctionné :)
nacho4d
Si Git vous demande "Plus?" lorsque vous essayez ces commandes, utilisez la syntaxe alternative sur cette réponse: stackoverflow.com/a/14204318/823470
tar
1745

Ajoutez / supprimez des fichiers pour obtenir les choses comme vous le souhaitez:

git rm classdir
git add sourcedir

Modifiez ensuite le commit:

git commit --amend

Le commit erroné précédent sera modifié pour refléter le nouvel état d'index - en d'autres termes, ce sera comme si vous n'aviez jamais fait l'erreur en premier lieu.

Notez que vous ne devez le faire que si vous n'avez pas encore poussé. Si vous avez poussé, vous n'aurez qu'à valider un correctif normalement.

bdonlan
la source
2
FYI: Cela supprime tous mes fichiers et j'ai perdu les modifications.
egorlitvinenko
UPD: Cependant, je l'ai restauré en utilisant reflog. Mais la réception n'a pas fonctionné pour le commit initial.
egorlitvinenko
1
Utilisez git rm --cachedpour conserver les fichiers dans le système de fichiers et ne les supprimez que de l'index git!
xuiqzy
1017
git rm yourfiles/*.class
git commit -a -m "deleted all class files in folder 'yourfiles'"

ou

git reset --hard HEAD~1

Avertissement: La commande ci-dessus supprimera définitivement les modifications des .javafichiers (et de tout autre fichier) que vous vouliez valider.

Le hard resetto HEAD-1mettra votre copie de travail à l'état de la validation avant votre mauvaise validation.

Lennart Koopmann
la source
19
git commit -a -m ""ou git commit -am ""naturellement! :]
trejder
Une autre utilisation «raccourcie» de la cachette; si vous voulez tout mettre en scène (annuler l'ajout de git) git stash, alors, alorsgit stash pop
seanriordan08
778

Pour modifier le dernier commit

Remplacez les fichiers dans l'index:

git rm --cached *.class
git add *.java

Ensuite, s'il s'agit d'une branche privée, modifiez le commit:

git commit --amend

Ou, si c'est une branche partagée, faites un nouveau commit:

git commit -m 'Replace .class files with .java files'


( Pour modifier une validation précédente , utilisez la redéfinition interactive impressionnante .)


ProTip ™: Ajoutez *.classà un gitignore pour arrêter que cela se reproduise.


Pour annuler un commit

La modification d'un commit est la solution idéale si vous devez modifier le dernier commit, mais une solution plus générale l'est reset.

Vous pouvez réinitialiser Git à n'importe quel commit avec:

git reset @~N

Nest le nombre de validations avant HEADet @~revient à la validation précédente.

Ainsi, au lieu de modifier le commit, vous pouvez utiliser:

git reset @~
git add *.java
git commit -m "Add .java files"

Consultez git help reset, en particulier les sections sur --soft --mixedet --hard, pour une meilleure compréhension de ce que cela fait.

Reflog

Si vous vous trompez, vous pouvez toujours utiliser le reflog pour trouver les commits supprimés:

$ git reset @~
$ git reflog
c4f708b HEAD@{0}: reset: moving to @~
2c52489 HEAD@{1}: commit: added some .class files
$ git reset 2c52489
... and you're back where you started


Zaz
la source
2
Pour ceux qui liront à l'avenir - veuillez noter qu'il git reverts'agit d'une commande distincte - qui "réinitialise" essentiellement un commimt unique.
BKSpurgeon
682

Utilisez git revert <commit-id>.

Pour obtenir l'ID de validation, utilisez simplement git log.

Jaco Pretorius
la source
15
Qu'est-ce que cela signifie, choisir le commit? Dans mon cas, j'étais sur la mauvaise branche lorsque j'ai édité un fichier. Je l'ai commis puis j'ai réalisé que j'étais dans la mauvaise branche. L'utilisation de "git reset --soft HEAD ~ 1" m'a permis de revenir juste avant le commit, mais maintenant, si je récupère la bonne branche, comment annuler les modifications apportées au fichier dans la mauvaise branche mais les faire à la place (dans le même nom fichier) dans la bonne branche?
astronomerdave
J'ai juste utilisé git revert commit-idtravaillé comme un charme. Bien sûr, vous devrez alors pousser vos modifications.
Casey Robinson
8
Je pense que ce serait git cherry-pick <<erroneous-commit-sha>>@astronomerdave. De, M. Presque 2 ans de retard au parti.
Tom Howard
@Kris: Au lieu de choisir à la cerise, rebaser. Parce qu'il s'agit d'une sélection avancée des cerises
Eugen Konkov
J'utiliserais Revert uniquement si j'ai déjà poussé mon commit. Sinon, la réinitialisation est une meilleure option. N'oubliez pas que le retour crée un nouveau commit, et ce n'est généralement pas le but.
Hola Soy Edu Feliz Navidad
532

Si vous prévoyez d'annuler entièrement une validation locale, quelle que soit la modification que vous avez apportée à la validation, et si vous ne vous inquiétez de rien à ce sujet, exécutez simplement la commande suivante.

git reset --hard HEAD^1

(Cette commande ignorera l'intégralité de votre commit et vos modifications seront complètement perdues de votre arborescence de travail locale). Si vous souhaitez annuler votre validation, mais que vous souhaitez apporter vos modifications dans la zone de transfert (avant la validation comme après git add), exécutez la commande suivante.

git reset --soft HEAD^1

Vos fichiers validés arrivent maintenant dans la zone de transfert. Supposons que si vous souhaitez mettre à niveau les fichiers, car vous devez modifier un contenu incorrect, exécutez la commande suivante

git reset HEAD

Maintenant, les fichiers validés doivent provenir de la zone intermédiaire dans la zone non intermédiaire. Les fichiers sont maintenant prêts à être modifiés, donc quoi que vous changiez, vous voulez aller le modifier et l'ajouter et faire un nouveau / nouveau commit.

Plus

Madhan Ayyasamy
la source
13
@SMR, Dans votre exemple, tous pointent uniquement vers HEAD actuel. TETE ^ = TETE ^ 1. Ainsi que HEAD ^ 1 = HEAD ~ 1. Lorsque vous utilisez HEAD ~ 2, il existe une différence entre les symboles ~ et ^. Si vous utilisez ~ 2 signifie «le premier parent du premier parent» ou «le grand-parent».
Madhan Ayyasamy
501

Si Git Extras est installé, vous pouvez exécuter git undopour annuler la dernière validation. git undo 3annulera les trois derniers commits.

nickf
la source
470

Je voulais annuler les cinq derniers commits dans notre référentiel partagé. J'ai recherché l'ID de révision vers lequel je voulais revenir. Ensuite, j'ai tapé ce qui suit.

prompt> git reset --hard 5a7404742c85
HEAD is now at 5a74047 Added one more page to catalogue
prompt> git push origin master --force
Total 0 (delta 0), reused 0 (delta 0)
remote: bb/acl: neoneye is allowed. accepted payload.
To [email protected]:thecompany/prometheus.git
 + 09a6480...5a74047 master -> master (forced update)
prompt>
neoneye
la source
25
Réécrire l'historique sur un référentiel partagé est généralement une très mauvaise idée. Je suppose que vous savez ce que vous faites, j'espère juste que les futurs lecteurs le feront aussi.
Brad Koch
Oui, le retour en arrière est dangereux. Assurez-vous que votre copie de travail est dans l'état souhaité avant de pousser. Lorsque vous poussez, les validations indésirables sont supprimées définitivement.
neoneye
6
"Tout comme dans le monde réel, si vous voulez réécrire l'histoire, vous avez besoin d'une conspiration: tout le monde doit être" impliqué "dans la conspiration (au moins tous ceux qui connaissent l'histoire, c'est-à-dire tous ceux qui se sont déjà retirés de la branche) . " Source: stackoverflow.com/a/2046748/334451
Mikko Rantalainen
440

Je préfère utiliser git rebase -ipour ce travail, car une belle liste apparaît où je peux choisir les commits à supprimer. Ce n'est peut-être pas aussi direct que d'autres réponses ici, mais cela semble juste .

Choisissez le nombre de validations que vous souhaitez lister, puis invoquez comme ceci (pour enrôler les trois derniers)

git rebase -i HEAD~3

Exemple de liste

pick aa28ba7 Sanity check for RtmpSrv port
pick c26c541 RtmpSrv version option
pick 58d6909 Better URL decoding support

Ensuite, Git supprimera les validations pour toute ligne que vous supprimez.

Steven Penny
la source
422

Comment corriger le commit local précédent

Utilisez git-gui (ou similaire) pour effectuer a git commit --amend. Depuis l'interface graphique, vous pouvez ajouter ou supprimer des fichiers individuels de la validation. Vous pouvez également modifier le message de validation.

Comment annuler le commit local précédent

Réinitialisez simplement votre succursale à l'emplacement précédent (par exemple, en utilisant gitkou git rebase). Réappliquez ensuite vos modifications à partir d'une copie enregistrée. Après le garbage collection dans votre référentiel local, ce sera comme si la validation indésirable ne s'était jamais produite. Pour faire tout cela en une seule commande, utilisez git reset HEAD~1.

Avertissement : l' utilisation imprudente de git resetest un bon moyen de mettre votre copie de travail dans un état déroutant. Je recommande aux novices Git d'éviter cela s'ils le peuvent.

Comment annuler un commit public

Effectuez une sélection inversée ( git-revert ) pour annuler les modifications.

Si vous n'avez pas encore apporté d'autres modifications à votre branche, vous pouvez simplement le faire ...

git revert --no-edit HEAD

Poussez ensuite votre branche mise à jour vers le référentiel partagé.

L'historique des validations affichera les deux validations séparément .


Avancé: correction de la branche privée dans le référentiel public

Cela peut être dangereux - assurez-vous d'avoir une copie locale de la branche à repousser.

Notez également: vous ne voulez pas faire cela si quelqu'un d'autre travaille sur la branche.

git push --delete (branch_name) ## remove public version of branch

Nettoyez votre succursale localement puis repoussez ...

git push origin (branch_name)

Dans le cas normal, vous n'avez probablement pas à vous soucier de l'historique de validation de votre branche privée. Poussez simplement un commit de suivi (voir 'Comment annuler un commit public' ci-dessus), et plus tard, faites un squash-merge pour masquer l'historique.

nobar
la source
8
gitk --all $(git reflog | cut -c1-7)&peut être utile pour trouver la révision précédente si vous souhaitez annuler un commit '--amend'.
nobar
4
Il convient de noter que si vous essayez de supprimer des informations secrètes avant de passer à un référentiel partagé, effectuer une restauration ne vous aidera pas, car les informations seront toujours dans l'historique lors de la validation précédente. Si vous voulez vous assurer que le changement n'est jamais visible pour les autres, vous devez utilisergit reset
Jherico
Je pense que «privé» / «public» serait plus correctement «local» / «distant».
2018
La correction d'une branche privée dans un référentiel distant peut également être effectuée simplementgit push origin (branch_name) --force
nobar
336

Si vous souhaitez l'annuler définitivement et que vous avez cloné un référentiel

L'ID de validation peut être vu par

git log 

Ensuite, vous pouvez faire -

git reset --hard <commit_id>

git push origin <branch_name> -f
pauvresva
la source
Que faire si vous n'utilisez pas "<commit_id>" et utilisez simplement "git reset --hard"? Je veux généralement me débarrasser de mes dernières mises à jour que je n'ai pas encore validées et revenir à la dernière validation que j'ai faite, et j'utilise toujours "git reset --hard".
Jaime Montoya
3
@JaimeMontoya Pour annuler les dernières modifications que vous pouvez utiliser git reset --hard, mais si vous devez supprimer durement les derniers "n" commits, vous spécifiez un SHA
poorva
334

Si vous avez commis des pourriels mais pas poussé,

git reset --soft HEAD~1

HEAD ~ 1 est un raccourci pour la validation avant la tête. Alternativement, vous pouvez vous référer au SHA-1 du hachage si vous souhaitez réinitialiser. L' option --soft supprimera le commit mais laissera tous vos fichiers modifiés "Les changements à valider", comme le dirait git status.

Si vous souhaitez vous débarrasser des modifications apportées aux fichiers suivis dans l'arborescence de travail depuis la validation avant la tête, utilisez plutôt " --hard ".

OU

Si vous avez déjà poussé et que quelqu'un a tiré, ce qui est généralement mon cas, vous ne pouvez pas utiliser git reset . Vous pouvez cependant faire un git revert ,

git revert HEAD

Cela va créer un nouveau commit qui inverse tout ce qui a été introduit par le commit accidentel.

santos_mgr
la source
Je suis dans le 2ème cas, mais quand je fais "git revert HEAD" il dit "erreur: Commit [ID] est une fusion mais aucune option -m n'a été donnée. Fatal: échec du retour". Aucune suggestion?
metaforge
2
Il vaut probablement la peine de mentionner qu'au lieu de HEAD~1vous, vous pouvez utiliser le hachage réel comme affiché par git log --statou par git reflog- utile lorsque vous devez «annuler» plus d'un commit.
ccpizza
284

Sur SourceTree (GUI pour GitHub), vous pouvez cliquer avec le bouton droit sur le commit et faire un «Reverse Commit». Cela devrait annuler vos modifications.

Sur le terminal:

Vous pouvez également utiliser:

git revert

Ou:

git reset --soft HEAD^ # Use --soft if you want to keep your changes.
git reset --hard HEAD^ # Use --hard if you don't care about keeping your changes.
Varun Parakh
la source
263

Une seule commande:

git reset --soft 'HEAD^' 

Cela fonctionne très bien pour annuler le dernier commit local!

Manish Shrivastava
la source
11
J'avais besoin d'écrire git reset --soft "HEAD ^" avec des guillemets doubles, car je l'écris à partir de l'invite de commande Windows.
Ena
253

Réinitialisez-le simplement en faisant la commande ci-dessous en utilisant git:

git reset --soft HEAD~1

Expliquez: qu'est git reset- ce que c'est, c'est essentiellement resetà n'importe quel commit que vous souhaitez revenir, puis si vous le combinez avec la --softclé, il reviendra, mais gardez les modifications dans vos fichiers, donc vous revenez à l'étape auquel le fichier vient d'être ajouté, HEADest le chef de la branche et si vous combinez avec ~1(dans ce cas, vous utilisez également HEAD^), il ne retournera qu'un seul commit ce que vous voulez ...

Je crée les étapes dans l'image ci-dessous plus en détail pour vous, y compris toutes les étapes qui peuvent se produire dans des situations réelles et en validant le code:

Comment annuler les derniers commits dans Git?

Alireza
la source
239

Comment annuler le dernier commit Git?

Pour restaurer tout ce qu'il était avant le dernier commit, nous devons réinitialiser le commit avant HEAD.

  1. Si vous ne souhaitez pas conserver les modifications que vous avez apportées:

    git reset --hard HEAD^
    
  2. Si vous souhaitez conserver vos modifications:

    git reset --soft HEAD^
    

Maintenant, vérifiez votre journal git. Cela montrera que notre dernier commit a été supprimé.

Ranjithkumar Ravi
la source
193

"Réinitialiser l'arborescence de travail au dernier commit"

git reset --hard HEAD^ 

"Nettoyer les fichiers inconnus de l'arborescence de travail"

git clean    

voir - Git Quick Reference

REMARQUE: cette commande supprimera votre commit précédent, utilisez-la donc avec prudence! git reset --hardest plus sûr.

Ravi_Parmar
la source
190

Utilisez reflog pour trouver un état correct

git reflog

reflog avant REFLOG AVANT RÉINITIALISATION

Sélectionnez le reflog correct (f3cb6e2 dans mon cas) et tapez

git reset --hard f3cb6e2

Après cela, le repo HEAD sera réinitialisé à ce HEADid LOG AFTER réinitialiser l'effet RESET

Enfin le reflog ressemble à l'image ci-dessous

reflogger après REFLOG FINAL

Shubham Chaudhary
la source
164

Première exécution:

git reflog

Il vous montrera toutes les actions possibles que vous avez effectuées sur votre référentiel, par exemple, valider, fusionner, extraire, etc.

Alors fais:

git reset --hard ActionIdFromRefLog
U. Ali
la source
155

Annuler le dernier commit:

git reset --soft HEAD^ ou git reset --soft HEAD~

Cela annulera le dernier commit.

Ici --softsignifie réinitialiser la mise en scène.

HEAD~ou HEAD^signifie se déplacer pour s'engager avant HEAD.


Remplacer le dernier commit par un nouveau commit:

git commit --amend -m "message"

Il remplacera le dernier commit par le nouveau commit.

akshay_rahar
la source
153

Autrement:

Extrayez la branche que vous souhaitez rétablir, puis réinitialisez votre copie de travail locale sur le commit que vous souhaitez être la dernière sur le serveur distant (tout ce qui se passera ensuite au revoir). Pour ce faire, dans SourceTree, j'ai fait un clic droit sur le et sélectionné "Réinitialiser BRANCHNAME à ce commit".

Ensuite, accédez au répertoire local de votre référentiel et exécutez cette commande:

git -c diff.mnemonicprefix=false -c core.quotepath=false push -v -f --tags REPOSITORY_NAME BRANCHNAME:BRANCHNAME

Cela effacera toutes les validations après celle en cours dans votre référentiel local, mais uniquement pour cette branche.

CommaToast
la source
144

Tapez git loget recherchez le dernier code de hachage de validation, puis entrez:

git reset <the previous co>
Peter Mortensen
la source
139

Dans mon cas, j'ai accidentellement commis des fichiers que je ne voulais pas. J'ai donc fait ce qui suit et cela a fonctionné:

git reset --soft HEAD^
git rm --cached [files you do not need]
git add [files you need]
git commit -c ORIG_HEAD

Vérifiez les résultats avec gitk ou git log --stat

egridasov
la source
133

Simple, exécutez ceci dans votre ligne de commande:

git reset --soft HEAD~ 
ihue
la source
126

Il y a plusieurs façons de procéder:

Commande Git pour annuler la dernière validation / les validations précédentes:

Avertissement: n'utilisez pas --hard si vous ne savez pas ce que vous faites. --hard est trop dangereux , et il pourrait supprimer vos fichiers.

La commande de base pour annuler le commit dans Git est:

$ git reset --hard <COMMIT -ID>

ou

$ git reset --hard HEAD~<n>

COMMIT-ID : ID du commit

n: est le nombre de dernières validations que vous souhaitez annuler

Vous pouvez obtenir l'ID de validation comme indiqué ci-dessous:

$ **git log --oneline**

d81d3f1 function to subtract two numbers

be20eb8 function to add two numbers

bedgfgg function to mulitply two numbers

d81d3f1 et be20eb8 sont l'ID de validation.

Voyons maintenant quelques cas:

Supposons que vous souhaitiez annuler le dernier commit 'd81d3f1'. Voici deux options:

$ git reset --hard d81d3f1

ou

$ git reset --hard HEAD~1

Supposons que vous souhaitiez annuler la validation 'be20eb8':

$ git reset --hard be20eb8

Pour des informations plus détaillées, vous pouvez également consulter et essayer d'autres commandes pour réinitialiser la tête à un état spécifié:

$ git reset --help
utilisateur3799762
la source
5
git reset --hard HEAD~1est trop dangereux ! Cela n'annulera pas seulement le dernier commit, mais ramènera complètement le repo au commit précédent. Vous perdrez donc toutes les modifications validées lors du dernier commit!
Arnis Juraga
Vous avez raison, pour annuler cela, vous pouvez utilisergit push -f <remote> HEAD@{1}:<branch>
Benny
Malheureusement, j'utilise --hard, et mes fichiers sont supprimés! Je n'ai pas vérifié le commentaire en premier car il s'est effondré. N'utilisez pas --hard si vous ne savez pas ce que vous faites!
anonyme
125

Pour un commit local

git reset --soft HEAD~1

ou si vous ne vous souvenez pas exactement dans quel commit il se trouve, vous pouvez utiliser

git rm --cached <file>

Pour un commit poussé

La bonne façon de supprimer des fichiers de l'historique du référentiel est d'utiliser git filter-branch. C'est,

git filter-branch --index-filter 'git rm --cached <file>' HEAD

Mais je vous recommande d'utiliser cette commande avec soin. Pour en savoir plus, consultez la page de manuel git-filter-branch (1) .

geoom
la source
125

Il existe deux scénarios principaux

Vous n'avez pas encore poussé le commit

Si le problème était des fichiers supplémentaires que vous avez validés (et que vous ne voulez pas qu'ils soient dans le référentiel), vous pouvez les supprimer en utilisant git rmpuis en validant avec--amend

git rm <pathToFile>

Vous pouvez également supprimer des répertoires entiers avec -r, ou même combiner avec d'autres commandes Bash

git rm -r <pathToDirectory>
git rm $(find -name '*.class')

Après avoir supprimé les fichiers, vous pouvez valider, avec l' option --amend

git commit --amend -C HEAD # the -C option is to use the same commit message

Cela réécrira votre commit local récent en supprimant les fichiers supplémentaires, donc, ces fichiers ne seront jamais envoyés en push et seront également supprimés de votre dépôt local .git par GC.

Vous avez déjà poussé le commit

Vous pouvez appliquer la même solution de l'autre scénario et ensuite faire git pushavec l' -foption, mais ce n'est pas recommandé car il écrase l'historique distant avec une modification divergente (cela peut gâcher votre référentiel).

Au lieu de cela, vous devez effectuer la validation sans --amend(rappelez-vous ceci à propos de -amend`: cette option réécrit l'historique sur la dernière validation).

dseminara
la source
125

Pour rétablir la révision précédente, supprimer définitivement toutes les modifications non validées:

git reset --hard HEAD~1
étoile
la source
23
Peut-être pourriez-vous à une note / un avertissement que sa commande supprimera le commit et les modifications dans le répertoire de travail sans demander plus loin.
cr7pt0gr4ph7
6
S'il vous arrive de le faire par accident, tout n'est cependant pas perdu. Voir stackoverflow.com/questions/10099258/… , stackoverflow.com/questions/15479501/… et stackoverflow.com/questions/7374069/undo-git-reset-hard/7376959 .
cr7pt0gr4ph7
13
Utilisez --softpour conserver vos modifications uncommitted changes, --hardpour neutraliser complètement le commit et revenir en arrière par un. N'oubliez pas de faire de telles opérations uniquement sur des modifications qui ne sont pas encore poussées.
Yunus Nedim Mehel
@Zaz: Vous avez raison; j'aurais peut-être dû clarifier cela. Seuls les fichiers / modifications qui ont été ajoutés à l'index (/ staged) ou qui ont été validés peuvent éventuellement être récupérés. Les changements non engagés et non planifiés sont , comme vous l'avez dit, complètement rejetés git reset --hard.
cr7pt0gr4ph7
1
En tant que sidenote: chaque fois qu'un fichier est mis en scène, gitstocke son contenu dans sa base de données d'objets. Le contenu stocké n'est supprimé que lorsque le garbage collection est exécuté. Il est donc possible de récupérer la dernière version intermédiaire d'un fichier qui n'était pas actuellement en cours d' git reset --hardexécution lors de son exécution (voir les articles liés ci-dessus pour plus d'informations).
cr7pt0gr4ph7