Git diff contre une cachette

Réponses:

1873

Voir la cachette la plus récente:

git stash show -p

Voir une cachette arbitraire:

git stash show -p stash@{1}

Depuis les git stashpages de manuel:

Par défaut, la commande affiche le diffstat, mais elle accepte tout format connu pour git diff (par exemple, git stash show -p stash @ {1} pour afficher le deuxième stash le plus récent sous forme de patch).

ambre
la source
72
stash@{0}est la valeur par défaut; vous n'avez besoin d'un argument que si vous souhaitez consulter les masques précédents.
Cascabel
52
Droite. Je l'ai simplement fourni pour qu'il soit clair comment regarder les autres cachettes en plus {0}.
Amber
74
Cela ne montrera pas la différence entre la cachette et le répertoire de travail actuel, mais entre la cachette et son parent d'origine. Droite? À partir de la page de manuel: "Affichez les modifications enregistrées dans la cachette sous forme de différence entre l'état caché et son parent d'origine."
Magne
14
@Amber - Certes, bien que si votre arbre de travail actuel est sale, cela compte et le rend un peu plus compliqué. Je suis venu sous cet angle et j'ai trouvé une procédure que j'ai partagée dans ma réponse ci-dessous.
Magne
6
que signifie le -pstand?
Gerald
308

Pour voir la cachette la plus récente:

git stash show -p

Pour voir une cachette arbitraire:

git stash show -p stash@{1}

De plus, j'utilise git diff pour comparer le stash avec n'importe quelle branche.

Vous pouvez utiliser:

git diff stash@{0} master

Pour voir toutes les modifications par rapport au maître de branche.


Ou vous pouvez utiliser:

git diff --name-only stash@{0} master

Pour trouver facilement uniquement les noms de fichiers modifiés.

czerasz
la source
10
Cela ne répond pas à la question spécifique. Si vous avez créé la cachette du maître (pour enregistrer le travail pour plus tard), puis effectuez quelques validations pour d'autres travaux sur le maître, alors faites-le git diff stash@{0} master, vous obtenez un diff de votre cachette par rapport au maître actuel (qui inclut le travail effectué sur le maître après la cachette a été fait), pas les fichiers / lignes que la cachette changerait, c'est de cela qu'il s'agit.
Tom De Leu
52
Je suis content que vous ayez répondu à la question même si ce n'était pas une réponse à la question exacte. Cela a donné plus d'informations, et je pense que c'est génial de savoir comment faire une différence entre une branche et la branche à laquelle vous souhaitez comparer. J'ai aussi aimé apprendre le drapeau --name-only :)
Rebekah Waterbury
6
cela permet également de regarder les différences en utilisant un visualiseur de différences personnalisé, par exemplegit difftool --tool=... stash@{0} HEAD
Andre Holzner
9
@TomDeLeu Bonne observation et un point important. Pour comparer un article caché avec son parent, cela semble fonctionner:git diff stash@{0}^ stash@{0}
erikprice
1
De plus, vous pouvez ajouter le nom git diff stash@{0} master -- filenamede fichier pour obtenir les modifications dans un fichier spécifique.
David
104

Si la branche sur laquelle vos modifications cachées sont basées a changé entre-temps, cette commande peut être utile:

git diff stash@{0}^!

Cela compare la cachette à la validation sur laquelle elle est basée.

t.heintz
la source
tellement bon j'ai ajouté un alias à ~/.gitconfig:laststash = diff stash@{0}^!
sbeam
5
Paire parfaite: git difftool stash^!pour le diff du dernier stash contre la validation sur laquelle il était basé, git difftool stash HEADpour le diff du dernier stash contre le commit actuel (stash @ {n} pour les stashes précédents)
ChrisV
17
Pour ceux qui étaient comme moi et qui n'ont jamais vu le ^! avant: commit ^! est un spécificateur de plage qui signifie: ce commit, mais aucun de ses parents.
Jonathan Gawrych
"git diff stash @ {0} ^!" se résume à "git diff stash @ {0} ^ stash @ {0} ~ 1 ^ stash @ {0} ~ 2 ......." mais comme git diff ne prend que 2 commits, il montre le diff entre stash @ {0} et ^ stash @ {0} ~ 1 et regarde ^ au début du 2ème commit ne fait pas de différence et git l'ignore.
Naga Kiran
Je préfère cette version pour pouvoir utiliser mon outil de diff préféré (Beyond Compare bien sûr!). Cela montre également le changement dans cette cachette qui, je crois, est la question d'origine, par opposition à une alternative mentionnée dans les commentaires ci-dessus "git diff stash @ {X} ^ stash @ {X}" qui montre plus que la différence cachée.
user107172
44

Si votre arbre de travail est sale , vous pouvez le comparer à une stash en validant d'abord l'arbre de travail sale, puis en le comparant à la stash. Ensuite, vous pouvez annuler la validation avec l'arborescence de travail sale (car vous ne voudrez peut-être pas avoir cette validation sale dans votre journal de validation).

Vous pouvez également utiliser l'approche suivante pour comparer deux stashes l'un avec l'autre (dans ce cas, vous venez de sauter l'un des stashes au début).

  • Engagez votre arbre de travail sale:

    git add .
    git commit -m "Dirty commit"
    
  • Diff la cachette avec ce commit:

    git diff HEAD stash@{0}
    
  • Ensuite, après, vous pouvez annuler le commit et le remettre dans le répertoire de travail:

    git reset --soft HEAD~1
    git reset .
    

Maintenant, vous avez différencié l'arbre de travail sale avec votre cachette et vous êtes revenu à l'endroit où vous étiez au départ.

Magne
la source
Y a-t-il un moyen de le faire mais de ne voir qu'un diff des fichiers qui seraient modifiés par ce qui est dans la cachette?
lagweezle
En 2020, c'est beaucoup plus simple; consultez ma réponse mise à jour .
David Deprost
Intéressant, je ne savais pas git stash show -l . Est-ce que la dernière cachette diffère de la copie de travail (sale)? Comment l'utilisez-vous sans obtenir error: switch l requires a value?
Magne
Oui en effet, il diffère de la copie de travail (éventuellement sale). Vous l'utilisez simplement en entrant git stash show -l. Quant à savoir pourquoi cela ne fonctionne pas pour vous, je peux seulement deviner que vous pourriez être sur une ancienne version de git? Je suis sur git v2.20.1, et cela fonctionne parfaitement sans erreurs.
David Deprost
25

La réponse de @ Magne est la seule à date (très tardive) qui répond à l'interprétation la plus flexible / utile de la question, mais c'est un peu plus compliqué que nécessaire. Plutôt que de valider et de réinitialiser, stockez simplement votre copie de travail, comparez, puis décompressez.

git stash save "temp"
git diff stash@{0} stash@{1}
git stash pop

Cela vous montre les différences entre le haut de la pile de stash et votre dossier de travail en faisant temporairement les modifications de votre dossier de travail devenir le haut de la pile de stash (stash @ {0}), en déplaçant le haut d'origine vers le bas (stash @ {1} ) puis en comparant en utilisant le haut d'origine dans la position «nouveau jeu» afin de voir les changements qui résulteraient de son application au-dessus de votre travail actuel.

"Mais si je n'ai pas de travail en cours?" Ensuite, vous êtes dans le cas ennuyeux normal. Utilisez simplement la réponse de @ Amber

git stash show

ou la réponse de @ czerasz

git diff stash@{0}

ou admettez que le stockage et le désarchivage sont rapides et faciles de toute façon, il vous suffit de décompresser les modifications et de les inspecter. Si vous ne les voulez pas pour le moment, jetez-les (l'index / le dossier de travail actuel change). En entier c'est

git stash apply
git diff
git reset
git checkout
SensorSmith
la source
3
Cette approche simple (stash puis comparer à une autre stash) est sûre et facile à comprendre. Pour certains cas d'utilisation, vous souhaiterez peut-être également stocker des fichiers non suivis avecgit stash save -u
mleonard
19

Cela fonctionne pour moi sur la version 1.8.5.2 de git:

git diff stash HEAD
Rimian
la source
2
Trompeur! La question est la suivante: comment puis-je voir les modifications que le non-stockage apportera à l'arborescence de travail actuelle? Cela montre la différence entre le stash et le HEAD qui peut être TRÈS différent de ce qui sera appliqué avec git stash apply.
MikeJansen
Veuillez lire la question plus "Je voudrais savoir quelles modifications seront apportées avant de les appliquer!". Je donne une réponse rapide à cela.
yerlilbilgin
Vous pouvez également voir que toutes les autres réponses concernent la différence entre la tête actuelle (ou l'ensemble de travail) et la cachette. Pourquoi seule ma réponse est-elle trompeuse? Ce n'est pas juste.
yerlilbilgin
@yerlilbilgin Voir ma réponse sur votre réponse ci-dessous.
MikeJansen
On peut ommettre HEAD, c'est par défaut, non?
Al.G.
10

Au cas où, pour comparer un fichier dans l'arborescence de travail et dans la cachette, utilisez la commande ci-dessous

git diff stash@{0} -- fileName (with path)
Pramod BR
la source
9

Si vous avez des outils pour diff (comme au-delà de comparer)

git difftool stash HEAD
yerlilbilgin
la source
1
Trompeur! La question est la suivante: comment puis-je voir les modifications que le non-stockage apportera à l'arborescence de travail actuelle? Cela montre la différence entre le stash et le HEAD qui peut être TRÈS différent de ce qui sera appliqué avec git stash apply.
MikeJansen
1
Si vous pensez que cela est trompeur, veuillez cocher toutes les autres réponses. Ce n'est pas juste!
yerlilbilgin
1
Vous remarquerez que j'ai copié ce même commentaire dans l'autre réponse qui était tout aussi trompeuse (à peu près la même réponse). D'autres réponses qui avaient déjà un commentaire similaire, je les ai laissées seules. Si vous comprenez comment fonctionne git stash, alors vous vous rendrez compte que la différence entre stash et HEAD n'est pas ce qui est appliqué (c'est ce que l'OP demande). Le "stash" réel est la différence entre le commit de stash et ce qui l'a précédé. Ce patch est ensuite appliqué à la HEAD. Donc, si vous voulez savoir ce que l'OP a demandé, vous devez montrer la différence entre la cachette et le commit avant, ce que font les bonnes réponses.
MikeJansen
1
Cela répond à la question plus directement que toutes les autres réponses (inutilement) longues, et fait exactement ce que le PO a demandé, à moins de le supprimer HEAD. Je pourrais modifier la réponse de @ yerlilbilgin pour supprimer HEAD mais je pense que toute personne qui utilise git peut comprendre cette partie et moi allonger la réponse la rendrait moins lisible. Pas de blâme sur @yerlibilgin.
Sridhar Sarnobat
4

Une façon de le faire sans bouger quoi que ce soit est de profiter du fait que l' patchon peut lire les diff de git (diff unifiés en gros)

git stash show -p | patch -p1 --verbose --dry-run

Cela vous montrera un aperçu étape par étape de ce que le correctif ferait normalement. L'avantage supplémentaire est que le correctif ne s'empêchera pas non plus d'écrire le correctif dans l'arborescence de travail, si pour une raison quelconque vous avez vraiment besoin de git pour arrêter la validation avant de modifier, allez-y et supprimez --dry- exécutez et suivez les instructions détaillées.

xenithorb
la source
2

En combinant ce que j'ai appris dans ce fil et dans celui-ci , quand je veux voir "ce qui est à l'intérieur de la cachette", je lance d'abord:

git stash show stash@{0}

Cela montrera quels fichiers ont été modifiés. Ensuite, pour obtenir un joli diff visuel dans un difftool, je fais:

git difftool --dir-diff stash@{0} stash@{0}^

Cela affichera toutes les différences à la fois de la cachette donnée par rapport à son parent.

Vous pouvez configurer l'outil diff dans ~/.gitconfig, par exemple avec Meld :

...
[diff]
    tool = meld
Ferrard
la source
1

FWIW Cela peut être un peu redondant pour toutes les autres réponses et est très similaire à la réponse acceptée qui est parfaite; mais peut-être que cela aidera quelqu'un.

git stash show --helpvous donnera tout ce dont vous avez besoin; y compris les informations sur le spectacle caché.

afficher [<stash>]

Affichez les modifications enregistrées dans la sauvegarde sous forme de différence entre l'état stocké et son parent d'origine. Lorsque non est indiqué, affiche le dernier. Par défaut, la commande affiche le diffstat, mais elle accepte tout format connu pour git diff (par exemple, git stash show -p stash @ {1} pour afficher le deuxième stash le plus récent sous forme de patch). Vous pouvez utiliser les variables de configuration stash.showStat et / ou stash.showPatch pour modifier le comportement par défaut.

Rockin4Life33
la source
1

Elle la liste des cachettes

git stash list 
stash@{0}: WIP on feature/blabla: 830335224fa Name Commit
stash@{1}: WIP on feature/blabla2: 830335224fa Name Commit 2

Alors, obtenez le numéro de réserve et faites:

Tu peux faire:

 git stash show -p stash@{1}

Mais si vous voulez un diff (c'est différent pour montrer la cachette, c'est pourquoi j'écris cette réponse. DiffConsidérez le code actuel dans votre branche et showmontrez juste ce que vous appliquerez )

Vous pouvez utiliser:

git diff stash@{0}

ou

git diff stash@{0} <branch name>

Une autre chose intéressante à faire est:

git stash apply
git stash apply stash@{10}

Cela applique le stash sans le supprimer de la liste, vous pouvez git checkout .supprimer ces modifications ou si vous êtes heureux git stash drop stash@{10}de supprimer un stash de la liste.

De là, je ne recommande jamais d'utiliser git stash popet d'utiliser une combinaison de git stash applyet git stash dropSi vous appliquez une cachette dans la mauvaise branche ... eh bien, il est parfois difficile de récupérer votre code.

Raúl Martín
la source
1

Selon ce avec quoi vous voulez comparer la cachette (arbre de travail local / commit parent / commit head), il existe en fait plusieurs commandes disponibles, parmi lesquelles la bonne vieille git diffet la plus spécifique git stash show:

╔══════════════════════╦═══════════════════════════════╦═══════════════════╗
║ Compare stash with ↓ ║ git diff                      ║ git stash show    ║
╠══════════════════════╬═══════════════════════════════╬═══════════════════╣
║ Local working tree   ║ git diff stash@{0}            ║ git stash show -l ║
║----------------------║-------------------------------║-------------------║
║ Parent commit        ║ git diff stash@{0}^ stash@{0} ║ git stash show -p ║
║----------------------║-------------------------------║-------------------║
║ HEAD commit          ║ git diff stash@{0} HEAD       ║   /               ║
╚══════════════════════╩═══════════════════════════════╩═══════════════════╝

Bien qu'il git stash showsemble plus convivial à première vue, il git diffest en fait plus puissant en ce qu'il permet de spécifier des noms de fichiers pour une différence plus ciblée. J'ai personnellement configuré des alias pour toutes ces commandes dans mon plugin zsh git .

David Deprost
la source