"git stash" pendant un conflit de fusion

Nous avons fait quelque chose de mauvais.

Nous avons couru git stash save lors d'un conflit de fusion, et maintenant nous ne pouvons pas restaurer notre travail.

choses que nous avons essayées:

git pull -Xours origin master
git stash apply --index

Et:

 git pull origin master
 git stash save --keep-index "merge conflicts"
 git stash apply stash@{1}

s'il vous Plaît aider!

23
demandé sur bukzor 2012-01-25 23:56:17

5 réponses

Le problème semble être que git stash n'enregistre pas une référence à la branche dans laquelle vous essayiez de fusionner. Lors d'une fusion, ceci est stocké dans un ref nommé MERGE_HEAD.

pour le corriger et revenir à votre état précédent, vous devez trouver la révision (faisons comme si c'était d7a9884a380f81b2fbf002442ee9c9eaf34ff68d) dans laquelle vous essayiez de fusionner, et définir MERGE_HEAD après avoir appliqué la stash.

alors vous pouvez appliquer la cachette (avec -- index pour re-mettre en scène tout ce qui était mis en scène avant), et mettre votre MERGE_HEAD:

git stash apply --index
git update-ref MERGE_HEAD d7a9884a380f81b2fbf002442ee9c9eaf34ff68d
25
répondu Evan Krall 2012-09-20 20:21:58

j'ai fait la même chose aujourd'hui, et j'ai pris une approche différente (après des essais et des erreurs) pour revenir à l'état juste avant de planquer afin que je puisse continuer à résoudre les conflits et compléter la fusion.

tout d'abord, après avoir dégrafé la fusion partielle dans la branche de destination, j'ai capturé une liste des fichiers avec les conflits restants (fichier texte ou onglet Editeur). Il s'agit simplement de la liste des fichiers non-marqués après un décollement, car les fichiers avec des conflits déjà résolus auraient été mis en scène avant d'accrocher.

$ git status
# Changes not staged for commit:
#   (use "git add <file>..." to update what will be committed)
#   (use "git checkout -- <file>..." to discard changes in working directory)
#
#   modified:   myproject/src/main/java/com/acme/package3/Class3.java
#   modified:   myproject/src/main/java/com/acme/package3/Class4.java
#

ensuite, j'ai créé un patch et réinitialisé la branche à l'état de pré-fusion:

$ git diff HEAD > ~/merge-with-resolved-conflicts.patch
$ git reset --hard HEAD

puis j'ai créé une branche temporaire (dérivée de la branche destination de la fusion), et j'ai appliqué le patch:

$ git checkout -b my-temp-branch
$ git apply ~/merge-with-resolved-conflicts.patch
$ git commit -a -m "Merge with resolved conflicts"

ainsi le chef de ma branche temporaire contient maintenant tout ce qui a été fusionné, y compris les fichiers avec les conflits résolus, et les fichiers avec les conflits restants.

puis je suis revenu à la branche d'origine, j'ai fusionné à nouveau, et regardé le statut git

$ git checkout my-branch
$ git merge other-branch
$ git status

Le statut de montre la liste complète des fichiers avec des conflits:

# Unmerged paths:
#   (use "git add <file>..." to mark resolution)
#
#   both modified:      myproject/src/main/java/com/acme/package1/Class1.java
#   both modified:      myproject/src/main/java/com/acme/package2/Class2.java
#   both modified:      myproject/src/main/java/com/acme/package3/Class3.java
#   both modified:      myproject/src/main/java/com/acme/package3/Class4.java
#

maintenant je devais comparer ces deux listes de fichiers. Tous les fichiers de la deuxième liste, mais pas le premier, avaient déjà été résolus (dans cet exemple, classe1.java et Class2.Java.) Donc pour chacun de ces fichiers, j'ai tiré dans la version avec des conflits résolus à partir de la branche temporaire (comme cherry-pick, mais pour les fichiers individuels plutôt qu'un entier commit):

$ git checkout my-temp-branch myproject/src/main/java/com/acme/package1/Class1.java
$ git checkout my-temp-branch myproject/src/main/java/com/acme/package2/Class2.java

ayant fait cela, j'étais de retour à l'état avant la cachette, pour que je puisse reprendre la résolution des conflits restants et engager la fusion.

1
répondu mmindenhall 2013-08-10 00:19:34

lorsque vous êtes dans un État de conflit (index et répertoire de travail), vous ne pourrez pas faire git stash - il donnera une erreur de pointage des entrées non fusionnées.

assurez-vous que vous avez vraiment fait une cachette. Voir la sortie de git stauts et git stash show

0
répondu manojlds 2012-01-26 01:44:28

vu votre dernier commentaire: vous pouvez utiliser

git stash megre --no-commit <branch>

placer l'index dans une "fusion" de l'état sans valider les modifications

puis le modifier avec ce que vous voulez :

si vous avez déjà travaillé votre fusion dans le coffre :

git reset #to remove the "conflicts" flags
git checkout <initial commit> -- ./ #to revert everything to the previous working state,
git stash apply   #apply your changes

et une fois que tout est dans l'état souhaité, git commit


bukzorcommentaire : il y a effectivement une grande différence entre git checkout <tree-ish> et git checkout <tree-ish> -- <files>.

référencegit checkout:

  • git checkout <branch>: ce formulaire change les branches en mettant à jour l'index, l'arbre de travail et la tête pour refléter la branche spécifiée ou la propagation.

  • git checkout [-p|--patch] <tree-ish> -- <pathspec>: quand ou -- patch sont donnés, git checkout ne change pas de branches. Il met à jour les chemins nommés dans l'arbre de travail à partir du fichier index ou d'un nom (le plus souvent un engager.)

git checkout <initial commit> rejetterait en effet les informations de fusion.

git checkout <initial commit> -- ./ (notez le supplément -- ./), d'un autre côté, conservera les informations de fusion, et ramènera chaque fichier traqué à son état dans <initial commit>.

0
répondu LeGEC 2017-05-23 12:02:36

ma solution pour m'en sortir (git stash pop pendant un conflit de fusion) était:

  • créer et de commander une nouvelle branche (locale) mytemporarybranch

    git branch mytemporarybranch & & git checkout mytemporarybranch

  • s'engager dans ce mytemporarybranch

    git commit -m "mon désordre de fusion et la courge"

  • caisse myoriginalbranch

    git checkout myoriginalbranch

  • fusionner correctement (pas de squash pop/appliquer cette fois!)

  • squash fusionner les mytemporarybranch sur le myoriginal branche

    git merge --squash mytemporarybranch

0
répondu mmathieum 2013-11-20 20:50:52