Comment modifier les messages de commit existants et non poussés?

7664

J'ai écrit la mauvaise chose dans un message de validation.

Comment puis-je changer le message? Le commit n'a pas encore été poussé.

Laurie Young
la source
868
Pour ceux qui sont un peu novices: le point de Laurie sur le fait de ne pas avoir encore poussé est important. Comme le rebasage, cela change l'histoire. Si quelqu'un a cloné / retiré de votre référentiel entre l'historique original et réécrit, il ne pourra pas tirer après la réécriture (pour cette branche).
Pat Notz

Réponses:

16132

Modification du message de validation le plus récent

git commit --amend

ouvrira votre éditeur, vous permettant de modifier le message de validation du commit le plus récent. De plus, vous pouvez définir le message de validation directement dans la ligne de commande avec:

git commit --amend -m "New commit message"

… Cependant, cela peut rendre les messages de validation sur plusieurs lignes ou les petites corrections plus difficiles à saisir.

Assurez - vous que vous ne disposez pas des modifications de la copie de travail mis en scène avant de le faire ou ils seront engagés aussi. ( Les modifications non planifiées ne seront pas validées.)

Modification du message d'un commit que vous avez déjà transmis à votre branche distante

Si vous avez déjà poussé votre commit vers votre branche distante, alors - après avoir modifié votre commit localement (comme décrit ci-dessus) - vous devrez également forcer le push avec:

git push <remote> <branch> --force
# Or
git push <remote> <branch> -f

Avertissement: la poussée forcée écrasera la branche distante avec l'état de votre branche locale . S'il y a des commits sur la branche à distance que vous n'avez pas dans votre branche locale, vous allez perdre ces commits.

Avertissement: soyez prudent lorsque vous modifiez des commits que vous avez déjà partagés avec d'autres personnes. La modification des validations les réécrit essentiellement pour avoir des ID SHA différents , ce qui pose un problème si d'autres personnes ont des copies de l'ancienne validation que vous avez réécrite. Quiconque possède une copie de l'ancien commit devra synchroniser son travail avec votre commit nouvellement réécrit, ce qui peut parfois être difficile, alors assurez-vous de vous coordonner avec les autres lorsque vous essayez de réécrire l'historique des commit partagés, ou évitez simplement de réécrire les commits partagés tout à fait.


Effectuer un rebase interactif

Une autre option consiste à utiliser un rebase interactif. Cela vous permet de modifier tout message que vous souhaitez mettre à jour même s'il ne s'agit pas du dernier message.

Afin de faire un squash Git, procédez comme suit:

// n is the number of commits up to the last commit you want to be able to edit
git rebase -i HEAD~n

Une fois que vous écrasez vos commits - choisissez le e/rpour éditer le message:

Entrez la description de l'image ici

Remarque importante sur le rebasage interactif

Lorsque vous utilisez, git rebase -i HEAD~nil peut y avoir plus de n validations. Git "collectera" toutes les validations dans les n dernières validations, et s'il y avait une fusion quelque part entre cette plage, vous verrez également toutes les validations, donc le résultat sera n +.

Bon conseil:

Si vous devez le faire pour plus d'une seule branche et que vous pouvez rencontrer des conflits lors de la modification du contenu, configurez git rerereet laissez Git résoudre ces conflits automatiquement pour vous.


Documentation

utilisateur456814
la source
257
Mais git commit --amendn'est pas aussi puissant que git rebase -i.
Jeffrey Jose
76
@jeffjose, ce n'est certainement pas nécessaire. En outre, git commit --amendpeut réparer le maître (un?) Commettre.
strager
116
Si vous avez déjà poussé, forcez à nouveau à pousser:git push -f origin branchname
Hughes
177
@hughes n'est pas git push -fun peu dangereux si d'autres personnes utilisent le même référentiel?
Armand
91
Si vous ne souhaitez pas réécrire l'intégralité du message de validation, optez pour git commit --amend -c HEAD. Cela ouvrira l'éditeur pré-rempli avec votre ancien message de validation, vous pourrez donc le modifier.
Sam
2506
git commit --amend -m "your new message"
lfx_cool
la source
7
J'ai fait git commit --amend -m "Nouveau message", mais pousser vers Github a généré le "Fusionner les changements distants avant de pousser à nouveau". Après avoir tiré, validé --amend et poussé à nouveau, le nouveau message n'apparaît pas. Au lieu de cela, j'ai "Merge branch 'master' of github.com:[myrepo]"
Dave Everitt
8
@DaveEveritt, vous avez probablement poussé votre commit en amont avant d'essayer de le corriger.
Thorbjørn Ravn Andersen
12
@ Kyralessa n'est pas vrai. Dans bash, vous pouvez facilement composer des messages de validation multiligne en ne fermant simplement pas le devis tant que vous n'avez pas terminé (en appuyant sur retour à la fin de chaque ligne dans les guillemets).
plaques de cuisson
32
Je ne comprends pas comment une réponse qui ressemble beaucoup à l'idée principale d'une réponse qui a été écrite il y a deux ans et aussi la réponse acceptée obtient autant de votes. Étrange. (rien de mal à la réponse cependant)
codeur heureux
7
@AmalMurali, eh bien. Mon point n'était pas tant la popularité de la question, ni l'utilité de la réponse. Mais cette réponse particulière n'est pas la réponse la plus ancienne, et elle n'offre aucun autre aperçu de la réponse acceptée. Il semble que ce soit une copie d'une section de la réponse acceptée. C'était mon point. À VOTRE SANTÉ!
codeur heureux
2376

Si le commit que vous souhaitez corriger n'est pas le plus récent:

  1. git rebase --interactive $parent_of_flawed_commit

    Si vous souhaitez corriger plusieurs validations défectueuses, passez le parent du plus ancien d'entre eux.

  2. Un éditeur apparaîtra, avec une liste de tous les commits depuis celui que vous avez donné.

    1. Passez pickà reword(ou sur les anciennes versions de Git, à edit) devant tous les commits que vous souhaitez corriger.
    2. Une fois que vous avez enregistré, Git rejouera les validations répertoriées.

  3. Pour chaque commit que vous souhaitez reformuler , Git vous renverra dans votre éditeur. Pour chaque commit que vous souhaitez modifier , Git vous dépose dans le shell. Si vous êtes dans le shell:

    1. Modifiez le commit comme vous le souhaitez.
    2. git commit --amend
    3. git rebase --continue

La plupart de cette séquence vous sera expliquée par la sortie des différentes commandes au fur et à mesure. C'est très facile; vous n'avez pas besoin de le mémoriser - rappelez-vous simplement que cela git rebase --interactivevous permet de corriger les commits, peu importe leur ancienneté.


Notez que vous ne voudrez pas modifier les commits que vous avez déjà poussés. Ou peut-être que vous le faites, mais dans ce cas, vous devrez prendre grand soin de communiquer avec tous ceux qui peuvent avoir tiré vos engagements et effectué un travail par-dessus eux. Comment récupérer / resynchroniser après que quelqu'un a poussé un rebase ou une réinitialisation dans une branche publiée?

Aristote Pagaltzis
la source
39
Peut-on changer le message du premier commit (qui n'a pas de parent)?
13ren
27
Cela est mentionné dans l'une des autres réponses, mais j'en mettrai une note ici. Depuis git 1.6.6, vous pouvez utiliser rewordà la place de pickpour modifier le message du journal.
MitMaro
89
Par ailleurs, $parent_of_flawed_commitest équivalent à $flawed_commit^.
Peeja
67
Ne JAMAIS faire cela (ou rebaser en général) si vous avez déjà poussé en amont!
Daniel Rinser
20
Utilisez -p( --preserve-merges) s'il y a eu une fusion après la validation défectueuse.
ahven
778

Pour modifier le commit précédent, effectuez les modifications souhaitées et effectuez ces modifications, puis exécutez

git commit --amend

Cela ouvrira un fichier dans votre éditeur de texte représentant votre nouveau message de validation. Il commence avec le texte de votre ancien message de validation. Modifiez le message de validation comme vous le souhaitez, puis enregistrez le fichier et quittez votre éditeur pour terminer.

Pour modifier le commit précédent et conserver le même message de journal, exécutez

git commit --amend -C HEAD

Pour corriger le commit précédent en le supprimant entièrement, exécutez

git reset --hard HEAD^

Si vous souhaitez modifier plusieurs messages de validation, exécutez

git rebase -i HEAD~commit_count

(Remplacez commit_count par le nombre de validations que vous souhaitez modifier.) Cette commande lance votre éditeur. Marquez le premier commit (celui que vous voulez changer) comme "edit" au lieu de "pick", puis enregistrez et quittez votre éditeur. Apportez la modification que vous souhaitez valider, puis exécutez

git commit --amend
git rebase --continue

Remarque: Vous pouvez également "Apporter la modification souhaitée" à partir de l'éditeur ouvert par git commit --amend

Fatih Acet
la source
18
git rebase -i HEAD~commit_countvous permettra également de modifier les messages de validation du nombre de validations que vous choisissez. Il suffit de marquer les commits choisis comme "reformuler" au lieu de "choisir".
Joe
2
Et si vous ne voulez pas rebaser? Vous voulez juste changer un ancien message?
SuperUberDuper
3
git reset --hardannule les modifications non validées. Veuillez remplacer --hardpar --soft.
eel ghEEz
1
D'accord, git reset --hardest une commande parfaitement légitime, mais elle est trompeuse compte tenu de la question. Vous utilisez --hardsi vous avez validé les modifications que vous souhaitez supprimer, pas si vous avez fait une faute de frappe dans le message de validation!
Soren Bjornstad du
398

Comme déjà mentionné, git commit --amendest le moyen d'écraser le dernier commit. Une remarque: si vous souhaitez également écraser les fichiers , la commande serait

git commit -a --amend -m "My new commit message"
John
la source
4
Et si vous ne voulez pas ajouter tout, vous pouvez d' abord faire git add file.extalors justegit commit --amend
MalcolmOcean
358

Vous pouvez également l'utiliser git filter-branchpour cela.

git filter-branch -f --msg-filter "sed 's/errror/error/'" $flawed_commit..HEAD

Ce n'est pas aussi facile qu'un trivial git commit --amend, mais c'est particulièrement utile, si vous avez déjà quelques fusions après votre message de validation erroné.

Notez que cela va essayer de réécrire chaque commit entre HEADet le commit défectueux, vous devez donc choisir votre msg-filtercommande très judicieusement ;-)

marque
la source
4
Existe-t-il une version de ceci qui ne change pas la validation si l'expression régulière ne trouve rien?
sjakubowski
3
AFAIK filter-branch --msg-filter générera de nouveaux commits dans tous les cas. Cependant, vous pouvez vérifier dans le msg-filter si le sed a réussi et utiliser ces informations lorsque l'opération de branchement du filtre se termine pour réinitialiser votre arborescence à refs / original.
Mark
4
@DavidHogue Cela n'est vrai que lors de l'utilisation de la méthode filter-branch. Les ID de validation après une validation modifiée ne changent pas si vous utilisez le rebase interactif.
Mark
6
@Mark Oui, ils le doivent. Les ID de validation dépendent des validations précédentes. S'ils ne changeaient pas, git serait inutile.
Miles Rout
2
Vous en avez besoin $flawed_commit^..HEAD, non $flawed_commit..HEAD. comme indiqué par la page de manuel: « La commande ne réécrira que les références positives mentionnées dans la ligne de commande (par exemple si vous passez a..b, seul b sera réécrit). »
Ángel
319

Je préfère cette façon:

git commit --amend -c <commit ID>

Sinon, il y aura une nouvelle validation avec un nouvel ID de validation.

krevedko
la source
7
Pour moi, l'utilisation de votre commande ci-dessus crée en fait un nouveau commit avec un nouvel ID de commit plus un commit supplémentaire disant "merge branch" comme message de commit par défaut.
janvier
46
La modification crée toujours un nouveau commit avec un nouvel ID de commit. L'ID de validation est le hachage SHA du contenu de la validation, y compris le message de validation et les horodatages créés / validés. C'est une fonctionnalité de Git qui, à l'exception des collisions de hachage, garantit que deux validations avec le même ID sont exactement la même validation, avec exactement le même contenu, l'historique, etc.
Emil Lundberg
7
D'accord avec Emil. De plus, en lisant la documentation - il semble que tout ce que "-c" fait est de dire à git quel message de commit utiliser comme défaut / modèle pour votre nouveau commit .. Vraiment, il va déjà faire "-c <ID de commit>" par défaut , donc pas besoin de le préciser.
Gal
2
Le -cfait quelques choses. Il utilise l'ancien message par défaut, mais il copie également les informations sur la paternité (personne et heure). -Cfait la même chose sauf qu'il ne vous demande pas de modifier le message.
Joseph K. Strauss
1
Comme @SantanuDey, cela n'a pas fonctionné pour moi. J'ai eufatal: Option -m cannot be combined with -c/-C/-F/--fixup.
Andrew Grimm
312

Si vous utilisez l'outil Git GUI, il existe un bouton nommé Modifier le dernier commit . Cliquez sur ce bouton, puis il affichera vos derniers fichiers de validation et message. Modifiez simplement ce message et vous pouvez le valider avec un nouveau message de validation.

Ou utilisez cette commande depuis une console / un terminal:

git commit -a --amend -m "My new commit message"
Akhilraj NS
la source
4
Cette réponse est littéralement identique à cette ancienne . Avez-vous vérifié les réponses existantes avant d'en fournir une autre?
Dan Dascalescu
284

Vous pouvez utiliser le rebasage Git . Par exemple, si vous souhaitez modifier à nouveau pour valider bbc643cd, exécutez

$ git rebase bbc643cd^ --interactive

Dans l'éditeur par défaut, modifiez «choisir» pour «modifier» dans la ligne dont vous souhaitez modifier la validation. Apportez vos modifications, puis mettez-les en scène avec

$ git add <filepattern>

Vous pouvez maintenant utiliser

$ git commit --amend

pour modifier le commit, et après cela

$ git rebase --continue

pour revenir au commit de tête précédent.

Shoaib Ud-Din
la source
1
Si vous voulez vous assurer que votre changement a git commit --amendpris effet, vous pouvez l'utiliser git showet il affichera le nouveau message.
Steve Tauber
279
  1. Si vous souhaitez uniquement modifier votre dernier message de validation, procédez comme suit:

    git commit --amend
    

Cela vous déposera dans votre éditeur de texte et vous permettra de modifier le dernier message de validation.

  1. Si vous souhaitez modifier les trois derniers messages de validation, ou l'un des messages de validation jusqu'à ce point, fournissez HEAD~3à la git rebase -icommande:

    git rebase -i HEAD~3
    
Heena Hussain
la source
6
Cette réponse plus tôt dit déjà que vous pouvez utiliser git commit --amend, et il dit aussi que vous pouvez utiliser git rebase -i HEAD~commit_count, tout ce que vous avez été prise en 3pour commit_count.
A également voté. Les gens ne prennent tout simplement pas la peine de lire les réponses existantes .
Dan Dascalescu
261

Si vous devez modifier un ancien message de validation sur plusieurs branches (c'est-à-dire que la validation avec le message erroné est présente dans plusieurs branches), vous pouvez utiliser:

git filter-branch -f --msg-filter \
'sed "s/<old message>/<new message>/g"' -- --all

Git créera un répertoire temporaire pour la réécriture et sauvegardera également les anciennes références dans refs/original/.

  • -fimposera l'exécution de l'opération. Cela est nécessaire si le répertoire temporaire est déjà présent ou s'il y a déjà des références stockées sous refs/original. Si ce n'est pas le cas, vous pouvez supprimer ce drapeau.

  • -- sépare les options de branche de filtre des options de révision.

  • --alls'assurera que toutes les branches et balises sont réécrites.

En raison de la sauvegarde de vos anciennes références, vous pouvez facilement revenir à l'état avant d'exécuter la commande.

Dites, vous voulez récupérer votre maître et y accéder en succursale old_master:

git checkout -b old_master refs/original/refs/heads/master
sebers
la source
3
Cette réponse ne répond pas à la question du PO, car ils sont purement intéressés à corriger un commit qu'ils viennent de faire. Je l' utilise régulièrement git commit --amendpour corriger des commentaires ou ajouter des fichiers que j'ai oublié à git add, mais jamais avant que je git pushn'Éd. J'utilise également git filter-branchquand je veux totalement gâcher l'historique des versions, mais l'OP ne le veut pas, donc cette réponse a besoin d'un gros avertissement de santé - n'essayez pas cela à la maison, peeps !!
kbro
226

Utilisation

git commit --amend

Pour le comprendre en détail, un excellent article est 4. Rewriting Git History . Il indique également quand ne pas l'utiliser git commit --amend .

peau
la source
2
Existe-t-il un bon moyen de corriger les messages de validation déjà poussés vers un référentiel public? Jusqu'à présent, je suis parvenu à la conclusion qu'une fois poussé, mes fautes de frappe et mes thinkos de message doivent vivre pour toujours.
stackunderflow
2
En un mot, NOPE! Il n'y a aucun BON moyen de rétracter quelque chose que vous avez poussé. Toutes les rétractations sont MAUVAIS à un degré plus ou moins élevé. Vous devez adopter la discipline de travailler dans une branche dans votre propre référentiel privé, en effectuant plusieurs validations lorsque vous ajoutez un peu, testez un peu, ajustez un peu. Ensuite, fusionnez votre branche entière en un seul commit, écrivez un nouveau message de commit décrivant le changement global, PROOFREAD et push.
kbro
1
Juste pour souligner l'évidence qu'il n'est pas nécessaire de faire un seul commit en revenant d'une branche de fonctionnalité. Ce que beaucoup de gens font est de rebaser sur la branche cible (pour que les choses paraissent propres) puis de fusionner avec l'option pour supprimer l'avance rapide. Soyez d'accord avec le point principal de la prudence avant de pousser.
ShawnFumo
1
La git commit --amendréponse avait déjà été donnée (plusieurs fois) avant que vous écriviez la vôtre. Pourquoi l'avez-vous posté à nouveau? Si vous vouliez ajouter un lien vers "Rewriting Git History", vous auriez pu modifier l'une des réponses existantes ou laisser un commentaire.
Dan Dascalescu
199

Modifier

Vous avez quelques options ici. Tu peux faire

git commit --amend

tant que c'est votre dernier commit.

Rebase interactive

Sinon, si ce n'est pas votre dernier commit, vous pouvez faire un rebase interactif,

git rebase -i [branched_from] [hash before commit]

Ensuite, à l'intérieur du rebase interactif, vous ajoutez simplement la modification à ce commit. Quand il apparaît, faites un git commit --amendet modifiez le message de validation. Si vous souhaitez annuler avant ce point de validation, vous pouvez également utiliser git refloget simplement supprimer cette validation. Ensuite, vous faites à git commitnouveau.

wallerjake
la source
191

Si c'est votre dernier commit, modifiez simplement le commit:

git commit --amend -o -m "New commit message"

(Utilisation de l' indicateur -o( --only) pour vous assurer de ne modifier que le message de validation)


S'il s'agit d'un commit enterré, utilisez la redéfinition interactive impressionnante :

git rebase -i @~9   # Show the last 9 commits in a text editor

Recherchez le commit que vous souhaitez, passez pickà r( reword), puis enregistrez et fermez le fichier. Terminé!



Tutoriel Miniature Vim (ou comment rebaser avec seulement 8 touches 3jcwrEscZZ):

  • Courez vimtutorsi vous avez le temps
  • hjkl correspondent aux touches de mouvement
  • Toutes les commandes peuvent être préfixées par une "plage", par exemple 3jdescend de trois lignes
  • i pour entrer en mode insertion - le texte que vous tapez apparaîtra dans le fichier
  • Escou Ctrlcpour quitter le mode insertion et revenir au mode "normal"
  • u défaire
  • Ctrlr refaire
  • dd, dw, dlSupprimer une ligne, un mot ou une lettre, respectivement
  • cc, cw, cl, Respectivement changer une ligne, un mot ou lettre (comme ddi)
  • yy, yw, ylCopier ( « Yank ») une ligne, un mot ou une lettre, respectivement
  • pou Ppour coller respectivement après ou avant la position actuelle
  • :wEnter enregistrer (écrire) un fichier
  • :q!Enter quitter sans enregistrer
  • :wqEnterou ZZpour enregistrer et quitter

Si vous modifiez beaucoup de texte, passez à la disposition du clavier Dvorak , apprenez à taper et apprenez Vim. Cela en vaut-il la peine? Oui.



ProTip ™: N'ayez pas peur d'expérimenter avec des commandes "dangereuses" qui réécrivent l'historique * - Git ne supprime pas vos validations pendant 90 jours par défaut; vous pouvez les trouver dans le reflog:

$ git reset @~3   # Go back three commits
$ git reflog
c4f708b HEAD@{0}: reset: moving to @~3
2c52489 HEAD@{1}: commit: more changes
4a5246d HEAD@{2}: commit: make important changes
e8571e4 HEAD@{3}: commit: make some changes
... earlier commits ...
$ git reset 2c52489
... and you're back where you started

* Méfiez-vous des options comme --hardet --forcebien - ils peuvent éliminer les données. * De plus, ne réécrivez pas l'historique sur les branches sur lesquelles vous collaborez.

Zaz
la source
3
La partie vim est complètement hors sujet, et au lieu d'encourager les utilisateurs à passer du temps à apprendre à utiliser un éditeur arcane, pourquoi ne pas leur enseigner quelque chose de plus sur le sujet, comme comment configurer l'éditeur git par défaut pour qu'il soit convivial, comme nano? Nous parlons de modifications insignifiantes qui doivent être apportées à un fichier texte, pas de codage hardcore qui générerait une guerre de flamme sur le "meilleur" éditeur de texte.
Dan Dascalescu
1
@DanDascalescu: Parce qu'il est plus rapide d'apprendre Vim en utilisant les instructions ci-dessus que d'effectuer plusieurs rebases en utilisant nano. La raison pour laquelle git ouvre un éditeur de texte et non sa propre interface pour le rebasage est parce que Vim existe: il est léger, installé par défaut sur la plupart des systèmes, et très facile à apprendre suffisamment pour effectuer facilement un rebase: par exemple, ddjjpZZdéplace un commit 2 vers le bas. La connaissance de base de Vim n'a rien d'arcane; il faut 10 minutes pour devenir plus à l'aise avec Vim qu'avec nano.
Zaz
185

Si vous utilisez l'interface graphique Git, vous pouvez modifier le dernier commit qui n'a pas été poussé avec:

Commit/Amend Last Commit
gulchrider
la source
168

J'utilise autant que possible l' interface graphique de Git , et cela vous donne la possibilité de modifier le dernier commit:

Cochez cette case

En outre, git rebase -i origin/masterc'est un joli mantra qui vous présentera toujours les commits que vous avez effectués sur Master, et vous donnera la possibilité de modifier, supprimer, réorganiser ou écraser. Pas besoin de mettre la main sur ce hachage en premier.

Havard Graff
la source
4
Comment accéder à cet écran que vous avez affiché dans votre exemple?
Marwan مروان
2
C'est la partie inférieure droite de Windows Git Gui. Sélectionnez simplement la bascule «Modifier la dernière validation» et elle s'affichera avec les informations de validation les plus récentes.
wbdarby
138

Wow, il y a donc beaucoup de façons de le faire.

Une autre façon de procéder consiste à supprimer le dernier commit, mais à conserver ses modifications afin de ne pas perdre votre travail. Vous pouvez ensuite faire un autre commit avec le message corrigé. Cela ressemblerait à quelque chose comme ceci:

git reset --soft HEAD~1
git commit -m 'New and corrected commit message'

Je fais toujours cela si j'oublie d'ajouter un fichier ou de faire un changement.

N'oubliez pas de spécifier --softau lieu de --hard, sinon vous perdez entièrement ce commit.

Radu Murzea
la source
5
Cela fait exactement la même chose que git commit --amendsauf qu'il s'agit d'un processus en 2 étapes.
Joseph K. Strauss,
3
@ JosephK.Strauss Je crois que la modification du commit conserve également les informations originales sur l'auteur et la date du commit, avec le nouveau commiter et les informations de date séparément. Je ne suis pas sûr que cette approche fasse cela.
everton
4
@EvertonAgner Vous avez raison. --amendconservera les informations sur l'auteur, mais la question ne demande que de modifier le message.
Joseph K. Strauss
131

Pour tous ceux qui recherchent une interface graphique Windows / Mac pour aider à modifier les messages plus anciens (c'est-à-dire pas seulement le dernier message), je recommanderais Sourcetree . Les étapes à suivre sont ci-dessous.

Rebase interactive Sourcetree

Pour les validations qui n'ont pas encore été transmises à une télécommande:

  1. Assurez-vous que vous avez validé ou caché toutes les modifications en cours (c'est-à-dire qu'il n'y a aucun fichier répertorié dans l'onglet "État du fichier") - cela ne fonctionnera pas autrement.
  2. Dans l'onglet "Journal / Historique", cliquez avec le bouton droit de la souris sur l'entrée avec une ligne adjacente dans le graphique situé sous le ou les commit (s) que vous souhaitez modifier et sélectionnez "Rebase des enfants de <commit ref> de manière interactive ..."
  3. Sélectionnez la ligne entière pour un message de validation que vous souhaitez modifier (cliquez sur la colonne "Message") .
  4. Cliquez sur le bouton "Modifier le message".
  5. Modifiez le message comme vous le souhaitez dans la boîte de dialogue qui s'affiche, puis cliquez sur OK.
  6. Répétez les étapes 3 à 4 s'il y a d'autres messages de validation à modifier.
  7. Cliquez sur OK: Le rebasage commencera. Si tout va bien, la sortie se terminera "Terminé avec succès". REMARQUE: j'ai parfois vu cela échouer Unable to create 'project_path/.git/index.lock': File exists.lors de la tentative de modification de plusieurs messages de validation en même temps. Je ne sais pas exactement quel est le problème, ni s'il sera résolu dans une future version de Sourcetree, mais si cela se produit, je recommanderais de les rebaser un par un (plus lent mais semble plus fiable).

... Ou ... pour les commits qui ont déjà été poussés:

Suivez les étapes de cette réponse , qui sont similaires à celles ci-dessus, mais nécessitent qu'une autre commande soit exécutée à partir de la ligne de commande ( git push origin <branch> -f) pour forcer le branchement. Je recommanderais de tout lire et d'appliquer la prudence nécessaire!

Steve Chambers
la source
de toutes les réponses - c'est la plus appropriée pour tous les débutants git ^^^ (utilisez un programme gratuit SourceTree et appliquez "Rebase children of" sur un commit avant celui que vous voulez éditer)
revelt
127

Si vous souhaitez simplement modifier le dernier commit, utilisez:

git commit --amend

ou

git commit --amend -m 'one line message'

Mais si vous souhaitez modifier plusieurs validations d'affilée, vous devriez plutôt utiliser le rebasage:

git rebase -i <hash of one commit before the wrong commit>

Édition de rebase Git

Dans un fichier, comme celui ci-dessus, écrivez edit/eou l'une des autres options, puis appuyez sur Enregistrer et quitter.

Vous serez maintenant au premier mauvais commit. Apportez des modifications dans les fichiers et ils seront automatiquement mis en scène pour vous. Type

git commit --amend

Enregistrez et quittez cela et tapez

git rebase --continue

pour passer à la sélection suivante jusqu'à ce que vous ayez terminé toutes vos sélections.

Notez que ces choses changent tous vos hachages SHA après ce commit particulier.

Shubham Chaudhary
la source
2
git rebase -i <hachage d'un commit avant le mauvais commit> fonctionne pour moi. Merci.
Viraths
127

Si vous souhaitez uniquement modifier votre dernier message, vous devez utiliser l' --onlyindicateur ou son raccourci -oavec commit --amend:

git commit --amend -o -m "New commit message"

Cela garantit que vous n'améliorez pas accidentellement votre validation avec des éléments mis en scène. Bien sûr, il est préférable d'avoir une $EDITORconfiguration appropriée . Ensuite, vous pouvez laisser l' -moption désactivée, et Git pré-remplira le message de validation avec l'ancien. De cette façon, il peut être facilement édité.

David Ongaro
la source
1
La réponse "top" ne répond pas à la question. Il donne juste une introduction générale à git commit --amend. La question était très précise, donc plus longue! = Mieux. La mention décisive du -odrapeau serait probablement enfouie dans le reste des informations. Je ne suis pas non plus à l'aise de modifier une réponse qui a déjà tant de votes.
David Ongaro
2
Cela étant dit, vous êtes libre de modifier la première réponse, car il y a un réel danger que les gens l'utilisent comme «bonne» réponse. Il peut facilement arriver de modifier votre commit avec des trucs mis en scène - cela m'est arrivé, et c'est vraiment ennuyeux quand il vous arrive de pousser cela. Mais encore, la quantité n'est pas une garantie d'exactitude. Ni en nombre de réponses ni en nombre de votes.
David Ongaro
1
Je n'irais pas si loin pour dire que la première réponse est "incorrecte" et qu'elle "ne répond pas à la question". Cela fonctionne certainement et répond à la question, il vous suffit de vous assurer que vous n'avez pas de changements par étapes lorsque vous essayez de modifier. Mais je vois votre point de vue sur la nécessité d'avertir les gens à ce sujet. Je le modifierai plus tard si j'ai le temps.
1
Pour être honnête: même si l' --onlyoption avec --amendest disponible depuis git 1.3.0, elle ne fonctionnait pas correctement jusqu'à ce qu'elle soit corrigée dans 1.7.11.3 ( ea2d4ed35902ce15959965ab86d80527731a177c ). Ainsi , le dos de bonne réponse en 2008 aurait probablement été quelque chose comme: git stash; git commit --amend; git stash pop.
David Ongaro
103

Mettez à jour votre dernier message de validation incorrect avec le nouveau message de validation sur une seule ligne:

git commit --amend -m "your new commit message"

Ou essayez Git reset comme ci-dessous:

# You can reset your head to n number of commit
# NOT a good idea for changing last commit message,
# but you can get an idea to split commit into multiple commits
git reset --soft HEAD^

# It will reset you last commit. Now, you
# can re-commit it with new commit message.

Utilisation de la réinitialisation pour diviser les commits en petits commits

git reset peut également vous aider à diviser un commit en plusieurs commit:

# Reset your head. I am resetting to last commits:
git reset --soft HEAD^
# (You can reset multiple commit by doing HEAD~2(no. of commits)

# Now, reset your head for splitting it to multiple commits
git reset HEAD

# Add and commit your files separately to make multiple commits: e.g
git add app/
git commit -m "add all files in app directory"

git add config/
git commit -m "add all files in config directory"

Ici, vous avez réussi à diviser votre dernier commit en deux commits.

przbadu
la source
3
Si tout ce que vous voulez faire est d'éditer le message de votre dernier commit, l'utilisation d'une réinitialisation logicielle à cet effet est une mise à mort excessive . Utilisez simplement git commit --amend, exactement comme il est dit dans la réponse la plus votée . En outre, git reset --soft HEAD^fonctionne de manière identique à la réinitialisation logicielle dans cette réponse précédente , car ils sont tous les deux réinitialisés au premier commit parent.
3
Je prends seulement la peine d'ajouter git resetla solution juste pour donner une idée de diviser un message de validation en plusieurs messages de validation. Parce que, j'ai rencontré ce problème quand, je commençais à utiliser git. Parfois, cela peut être très utile. :)
przbadu
87

Sur cette question, il existe de nombreuses réponses, mais aucune d'entre elles n'explique en détail comment modifier les anciens messages de validation à l'aide de Vim . J'étais coincé à essayer de le faire moi-même, alors ici, je vais écrire en détail comment j'ai fait cela, en particulier pour les personnes qui n'ont aucune expérience à Vim!

Je voulais modifier mes cinq derniers commits que j'ai déjà envoyés au serveur. C'est assez «dangereux» car si quelqu'un d'autre s'en est déjà tiré, vous pouvez gâcher les choses en modifiant les messages de validation. Cependant, lorsque vous travaillez sur votre propre petite branche et que vous êtes sûr que personne ne l'a tirée, vous pouvez la changer comme ceci:

Imaginons que vous souhaitiez modifier vos cinq derniers commits, puis saisissez ceci dans le terminal:

git rebase -i HEAD~5

* Où 5 est le nombre de messages de commit que vous voulez changer (donc si vous voulez changer le 10ème au dernier commit, vous tapez 10).

Cette commande vous amènera dans Vim où vous pourrez «modifier» votre historique de commit. Vous verrez vos cinq derniers commits en haut comme ceci:

pick <commit hash> commit message

Au lieu de pickvous devez écrire reword. Vous pouvez le faire dans Vim en tapant i. Cela vous fait passer en mode insertion . (Vous voyez que vous êtes en mode d'insertion par le mot INSERT en bas.) Pour les commits que vous souhaitez modifier, tapez à la rewordplace de pick.

Ensuite, vous devez enregistrer et quitter cet écran. Pour ce faire, Escpassez d'abord en «mode commande» en appuyant sur le bouton (vous pouvez vérifier que vous êtes en mode commande si le mot INSERT en bas a disparu). Ensuite, vous pouvez taper une commande en tapant :. La commande pour enregistrer et quitter est wq. Donc, si vous tapez, :wqvous êtes sur la bonne voie.

Ensuite, Vim examinera chaque message de validation que vous souhaitez reformuler, et ici vous pouvez réellement modifier les messages de validation. Pour ce faire, passez en mode insertion, modifiez le message de validation, passez en mode commande, puis enregistrez et quittez. Faites-le cinq fois et vous êtes hors de Vim!

Ensuite, si vous avez déjà poussé vos mauvais commits, vous devez les git push --forceécraser. N'oubliez pas que git push --forcec'est une chose assez dangereuse à faire, alors assurez-vous que personne ne s'est retiré du serveur puisque vous avez poussé vos mauvais commits!

Vous avez maintenant changé vos messages de validation!

(Comme vous le voyez, je ne suis pas très expérimenté à Vim, donc si j'ai utilisé le mauvais 'jargon' pour expliquer ce qui se passe, n'hésitez pas à me corriger!)

Marijn
la source
4
<nitpick>Il n'y a pas de "threads" sur Stack Overflow, car ce n'est pas un forum de discussion, il n'y a que des "questions", des "réponses" et des "publications". </nitpick>. De plus, toutes les versions de Vim ne sont pas identiques, toutes ne vous permettront pas de supprimer des caractères en mode d'insertion (cela a du sens en quelque sorte, non?). Si vous voulez toujours pouvoir supprimer des caractères dans Vim, Xet xque vous ferez cela (les petits xsupprime les caractères devant le curseur, Xseront supprimés derrière). Si vous faites des erreurs, vous pouvez utiliser à uplusieurs reprises pour annuler. Enfin, rest un raccourci pour reworddans l'éditeur de rebase interactif.
1
Changer un mot dans vim est cwtapé à son début (bien que la question ne concerne pas vim, je suis d'accord).
Yaroslav Nikitenko
Vous n'avez pas besoin d'utiliser cette abomination . Vous pouvez définir votre éditeur git sur quelque chose de sain et convivial, comme nanoou mcedit de Midnight Commander.
Dan Dascalescu
79

Vous pouvez utiliser git-rebase-reword

Il est conçu pour éditer n'importe quel commit (pas seulement le dernier) de la même manière que commit --amend

$ git rebase-reword <commit-or-refname>

Il est nommé d'après l'action sur rebase interactive pour modifier un commit: "reword". Voir cet article et man -section mode interactif-

Exemples:

$ git rebase-reword b68f560
$ git rebase-reword HEAD^
albfan
la source
6
Cela nécessite l'installation d'un programme externe. À mon avis, il serait préférable d'apprendre à utiliser plus efficacement les outils intégrés et les alias. Je voudrais taper: g c; g rb -i @~9(commit et rebase), déplacer le nouveau commit là où je le veux, changer commiten f( fixup) et sauvegarder. Si vous vouliez quelque chose de plus rapide que cela, vous pourriez alias git commit --fixup=<commit>; git rebase -i --autosquash <commit>^
Zaz
79

J'ai ajouté les alias reciet recmpour recommit (amend)cela. Maintenant je peux le faire avec git recmou git recm -m:

$ vim ~/.gitconfig

[alias]

    ......
    cm = commit
    reci = commit --amend
    recm = commit --amend
    ......
Chu-Siang Lai
la source
57

J'ai réalisé que j'avais poussé un commit avec une faute de frappe dedans. Pour annuler, j'ai fait ce qui suit:

git commit --amend -m "T-1000, advanced prototype"
git push --force

Avertissement: pousser de force vos modifications écrasera la branche distante avec votre branche locale. Assurez-vous que vous n'écraserez pas tout ce que vous souhaitez conserver. Soyez également prudent lorsque vous forcez à pousser un commit modifié (réécrit) si quelqu'un d'autre partage la branche avec vous, car il devra réécrire sa propre histoire s'il a l'ancienne copie du commit que vous venez de réécrire.

neoneye
la source
7
Rien n'est jamais "écrasé" dans git. Dans ce cas, le pointeur de branche sera défini sur votre nouveau commit et l'ancien commit deviendra périmé si aucune référence ne lui est laissée et il pourrait être nettoyé après quelques semaines. (Jusque-là, d'autres peuvent encore le trouver et le référencer, par exemple en regardant dans le reflog.)
David Ongaro
51

J'aime utiliser ce qui suit:

  1. git status
  2. git add --all
  3. git commit -am "message goes here about the change"
  4. git pull <origin master>
  5. git push <origin master>
Kedar Adhikari
la source
46

Si vous n'avez pas poussé le code vers votre branche distante ( GitHub / Bitbucket ), vous pouvez modifier le message de validation sur la ligne de commande comme ci-dessous.

 git commit --amend -m "Your new message"

Si vous travaillez sur une branche spécifique, procédez comme suit:

git commit --amend -m "BRANCH-NAME: new message"

Si vous avez déjà poussé le code avec le mauvais message et que vous devez être prudent lorsque vous modifiez le message. Autrement dit, après avoir modifié le message de validation et essayé de le pousser à nouveau, vous vous retrouvez avec des problèmes. Pour le rendre lisse, suivez ces étapes.

Veuillez lire l'intégralité de ma réponse avant de le faire.

git commit --amend -m "BRANCH-NAME : your new message"

git push -f origin BRANCH-NAME                # Not a best practice. Read below why?

Remarque importante: lorsque vous utilisez directement la poussée forcée, vous pouvez vous retrouver avec des problèmes de code que d'autres développeurs travaillent sur la même branche. Donc, pour éviter ces conflits, vous devez extraire le code de votre branche avant de faire le push de force :

 git commit --amend -m "BRANCH-NAME : your new message"
 git pull origin BRANCH-NAME
 git push -f origin BRANCH-NAME

Il s'agit de la meilleure pratique lors de la modification du message de validation, s'il a déjà été poussé.

Prabhakar Undurthi
la source