Ich denke nicht, dass die akzeptierte Antwort von @ bukzor eine korrekte Antwort auf die Frage ist, wie sie gestellt wurde. git stash --keep-indexbehält zwar den Index bei, versteckt aber alles - sowohl im Index als auch außerhalb.
Raman
@Antonio Es scheint mir, dass Ihr Kopfgeld eigentlich eine separate Frage sein sollte, da die ursprüngliche Frage nichts speziell mit TortoiseGit zu tun hat.
JesusFreke
1
@JesusFreke Ja, angesichts des Ergebnisses hätte ich 50 Wiederholungen sparen können :) Es ist nur so, dass dies die Frage ist, auf die Sie umgeleitet werden, wenn Sie versuchen, nach "partiellem Stash Tortoisegit" zu suchen. Tortoisegit scheint hier kein beliebtes Thema zu sein stackoverflow.com/questions/tagged/tortoisegit
Antonio
7
>>>>>>>>> git diff -- *filename* > ~/patchdann git checkout -- *filename*und später können Sie den Patch mitgit apply ~/patch
neaumusic
36
Die meisten der unten aufgeführten Antworten sind veraltet. Seit Git 2.13 (Q2 2017) wird es mit unterstützt git stash push [--] [<pathspec>...].
Ohad Schneider
Antworten:
1372
Haftungsausschluss : Die folgende Antwort gilt für Git vor Git 2.13. Schauen Sie sich für Git 2.13 und höher eine weitere Antwort weiter unten an .
Warnung
Wie in den Kommentaren erwähnt, wird dadurch alles inszeniert, sowohl inszeniert als auch nicht inszeniert. Der --keep-Index lässt den Index nach Abschluss des Stashs einfach in Ruhe. Dies kann zu Zusammenführungskonflikten führen, wenn Sie den Stash später öffnen.
Dadurch wird alles gespeichert, was Sie zuvor noch nicht hinzugefügt haben. Nur git adddie Dinge, die Sie behalten möchten, und dann ausführen.
git stash --keep-index
Wenn Sie beispielsweise ein altes Commit in mehrere Änderungssätze aufteilen möchten, können Sie folgende Prozedur verwenden:
git rebase -i <last good commit>
Markieren Sie einige Änderungen als edit.
git reset HEAD^
git add <files you want to keep in this change>
git stash --keep-index
Repariere die Dinge nach Bedarf. Vergessen Sie git addkeine Änderungen.
Ich bin mir nicht sicher, warum dies positiv bewertet wird. Jeder muss eine andere Erwartung haben als ich. Der ursprüngliche Beitrag fragt: "Wie kann ich nur einen Teil der nicht festgeschriebenen Änderungen aufbewahren?" Wenn ich benutze git stash save -k, git statbleibt der Index (grün in ) ja erhalten, aber der gesamte Änderungssatz (sowohl grün als auch rot) geht in den Vorrat. Dies verstößt gegen die Anforderung des OP, "nur einige Änderungen zu speichern". Ich möchte nur einen Teil der roten (für die zukünftige Verwendung) verstauen.
@ Raman: Ausgezeichnet! git stash -pist genau das, wonach ich gesucht habe. Ich frage mich, ob dieser Schalter erst kürzlich hinzugefügt wurde.
Pistos
14
WARNUNG: git stash --keep-indexist defekt. Wenn Sie weitere Änderungen vornehmen, versuchen git stash popSie später, Zusammenführungskonflikte zu erhalten, da der Stash die geänderten Dateien enthält, die Sie gespeichert haben, und nicht nur die, die Sie nicht gespeichert haben. Zum Beispiel: Ich ändere die Dateien A und B und verstecke dann B, weil ich die Änderungen in A testen möchte. Ich finde ein Problem mit A, das ich dann behebe. Ich begebe A; Jetzt kann ich nicht mehr speichern, da sich eine alte Version von A ohne guten Grund im Speicher befindet und einen Zusammenführungskonflikt verursacht. In der Praxis können A und B viele Dateien sein, vielleicht sogar Binärbilder oder so, also muss ich im Grunde aufgeben und verlieren B.
rjmunro
3015
Sie können auch verwenden git stash save -p "my commit message" . Auf diese Weise können Sie auswählen, welche Hunks zum Stash hinzugefügt werden sollen. Es können auch ganze Dateien ausgewählt werden.
Sie werden mit ein paar Aktionen für jedes Stück aufgefordert:
y - stash this hunk
n - do not stash this hunk
q - quit; do not stash this hunk or any of the remaining ones
a - stash this hunk and all later hunks in the file
d - do not stash this hunk or any of the later hunks in the file
g - select a hunk to go to
/ - search for a hunk matching the given regex
j - leave this hunk undecided, see next undecided hunk
J - leave this hunk undecided, see next hunk
k - leave this hunk undecided, see previous undecided hunk
K - leave this hunk undecided, see previous hunk
s - split the current hunk into smaller hunks
e - manually edit the current hunk
? - print help
Es war nicht. Es wurde etwa 7 Jahre später von Darcs ausgeliehen.
Nomen
6
Ich bin ein TortoiseGit-Süchtiger. TortoiseGit unterstützt dies jedoch nicht stash -p. Ich vergebe diese Antwort, weil sie am interaktivsten / benutzerfreundlichsten bleibt.
Antonio
27
Vielleicht möchten Sie hinzufügen : git stash save -p my stash message; da die Reihenfolge der Argumente nicht sehr intuitiv ist ...
Chris Maes
15
Zwischen diesem und git log -p, denke ich, -pmuss die Flagge bedeuten "Mach das Coole, was ich will, aber ich weiß nicht, wie ich es ausdrücken soll."
Kyle Strand
2
Warum um alles in der Welt ist diese großartige Antwort auf Platz 12? nach all diesen 0, +1, +2 Antworten ??????
DenisFLASH
548
Da es bei git im Wesentlichen um die Verwaltung des gesamten Repository- Inhalts und -Index (und nicht einer oder mehrerer Dateien) geht, git stashhandelt es sich nicht überraschend ummit dem gesamten Arbeitsverzeichnis.
Seit Git 2.13 (Q2 2017) können Sie einzelne Dateien mit git stash pushfolgenden Elementen speichern :
git stash push [--] [<pathspec>...]
Wenn pathspec' git stash push' angegeben wird, zeichnet der neue Stash die geänderten Zustände nur für die Dateien auf, die der Pfadspezifikation entsprechen. Weitere Informationen finden Sie unter " Stash-Änderungen an bestimmten Dateien ".
Vereinfachtes Beispiel:
git stash push path/to/file
Der Testfall für diese Funktion zeigt einige weitere Optionen:
test_expect_success 'stash with multiple pathspec arguments' '
>foo &&
>bar &&
>extra &&
git add foo bar extra &&
git stash push -- foo bar &&
test_path_is_missing bar &&
test_path_is_missing foo &&
test_path_is_file extra &&
git stash pop &&
test_path_is_file foo &&
test_path_is_file bar &&
test_path_is_file extra
Bei der ursprünglichen Antwort (unten, Juni 2010) ging es darum, manuell auszuwählen, was Sie verstauen möchten.
Dies (die stash --patchursprüngliche Lösung) ist nett, aber oft habe ich viele Dateien geändert, so dass die Verwendung von Patches ärgerlich ist
bukzor ‚s Antwort (upvoted November 2011) schlägt vor , eine praktischere Lösung, basierend auf git add+git stash --keep-index .
Gehen Sie und sehen Sie seine Antwort, die die offizielle sein sollte (anstelle meiner).
Zu dieser Option weist chhh in den Kommentaren auf einen alternativen Workflow hin:
Sie sollten git reset --softnach einem solchen Vorrat " " " " tun, um Ihre klare Inszenierung wiederherzustellen:
Um zum ursprünglichen Zustand zurückzukehren - der ein klarer Staging-Bereich ist und nur einige ausgewählte nicht inszenierte Modifikationen enthält, können Sie den Index sanft zurücksetzen, um ihn zu erhalten (ohne) etwas wie Sie zu begehen - bukzor - tat).
(Ursprüngliche Antwort Juni 2010: manuelle Aufbewahrung)
Dennoch git stash save --patchkonnte ermöglicht es Ihnen , die teilweise stashing erreichen Sie nach:
Mit --patchkönnen Sie interaktiv Hunks aus dem Diff zwischen HEAD und dem zu verstauenden Arbeitsbaum auswählen.
Der Stash-Eintrag ist so aufgebaut, dass sein Indexstatus mit dem Indexstatus Ihres Repositorys übereinstimmt und sein Arbeitsbaum nur die Änderungen enthält, die Sie interaktiv ausgewählt haben. Die ausgewählten Änderungen werden dann von Ihrem Arbeitsbaum zurückgesetzt.
Dadurch werden jedoch der vollständige Index (der möglicherweise nicht Ihren Wünschen entspricht, da er möglicherweise andere bereits indizierte Dateien enthält) und ein Teilarbeitsbaum (der möglicherweise so aussieht wie der, den Sie speichern möchten) gespeichert.
git stash --patch --no-keep-index
könnte besser passen.
Wenn --patchdies nicht funktioniert, kann ein manueller Vorgang Folgendes bewirken:
Für eine oder mehrere Dateien wäre eine Zwischenlösung:
Das ist schön, aber oft habe ich viele Dateien geändert, so dass die Verwendung von Patch ärgerlich ist
Casebash
6
@VonC: Es ist ein guter Stil, nur eine Antwort pro Antwort zu haben. Das Kopieren und Einfügen der Antworten anderer in Ihre eigenen ist ebenfalls schlecht.
Bukzor
3
@bukzor: Es tut mir leid, wenn meine bearbeitete Antwort unangemessen schien. Meine einzige Absicht war es, Ihre Antwort sichtbarer zu machen. Ich habe meinen Beitrag erneut bearbeitet, um diese Absicht klarer zu machen.
git is fundamentally about managing a all repository content and index and not one or several files- Diese Implementierung überschattet das zu lösende Problem. Es ist eine Erklärung, aber keine Rechtfertigung. Bei jedem Versionsverwaltungssystem geht es darum, "mehrere Dateien zu verwalten". Schauen Sie sich nur an, welche Kommentare am meisten positiv bewertet werden.
Victor Sergienko
90
Wenn git stash -p(oder git add -pmit stash --keep-index) zu umständlich wäre, fand ich es einfacher zu bedienen diff, checkoutund apply:
So "verstauen" Sie nur eine bestimmte Datei / ein bestimmtes Verzeichnis:
Interessante Alternative zu der, die git add -pich oben in meiner eigenen Antwort erwähnt habe. +1.
VonC
11
Beachten Sie, dass Binärdateien (wie PNGs) nicht in die Diff-Datei ausgegeben werden. Das ist also keine 100% ige Lösung.
void.pointer
1
@ RobertDailey: Das ist ein interessanter Punkt für mich, ebenso git diff > file.diffwie git applymeine üblichen Teilversteck-Tools. Ich muss möglicherweise in Betracht ziehen, git stash -pfür größere Änderungssätze zu wechseln.
thekingoftruth
1
@thekingoftruth Hier ist der Alias, den ich zum Erstellen von Patch-Dateien verwende und der Binärdateien unterstützt : patch = log --pretty=email --patch-with-stat --reverse --full-index --binary. Beachten Sie jedoch, dass Ihre Änderungen erforderlich sind, damit der Patch festgeschrieben wird.
void.pointer
2
Dies funktionierte für mich nicht sauber, wenn die zu verstauende Datei so etwas wie war ../../foo/bar.txt. Der Patch generiert OK, aber ich muss dann zum Repository-Stammverzeichnis wechseln, damit der Patch angewendet wird. Wenn Sie also Probleme damit haben, stellen Sie einfach sicher, dass Sie dies aus dem Repository-Stammverzeichnis tun.
Michael Anderson
86
Verwenden Sie git stash pushwie folgt:
git stash push [--] [<pathspec>...]
Zum Beispiel:
git stash push -- my/file.sh
Dies ist seit Git 2.13 verfügbar, das im Frühjahr 2017 veröffentlicht wurde.
Ich bin froh, dass Git so schnell voranschreitet, dass dies lange Zeit nicht möglich war und dann 2.13 veröffentlicht wird und plötzlich eine einfache Lösung verfügbar ist!
Sandstrom
1
@VonC Sie haben Recht, Sie erwähnen auch die richtige Antwort. Zwischen den beiden Antworten ist diese jedoch leichter zu lesen (kein verwirrender Text und es gibt auch ein Beispiel). Vielleicht hätten sie stattdessen Ihre Antwort bearbeiten sollen
Utopik
@Utopik Du hattest mich bei "du hast recht" ... aber ja, ich habe meine Antwort so bearbeitet, dass sie ein Beispiel enthält.
VonC
Verwendet man dann git stash apply, um die versteckten Änderungen wiederherzustellen?
Tschad
49
Angenommen, Sie haben 3 Dateien
a.rb
b.rb
c.rb
und du willst nur b.rb und c.rb verstauen, aber nicht a.rb.
Sie können so etwas tun
# commit the files temporarily you don't want to stash
git add a.rb
git commit -m "temp"
# then stash the other files
git stash save "stash message"
# then undo the previous temp commit
git reset --soft HEAD^
git reset
# Save everything
git stash
# Re-apply everything, but keep the stash
git stash apply
git checkout <"files you don't want in your stash"># Save only the things you wanted saved
git stash
# Re-apply the original state and drop it from your stash
git stash apply stash@{1}
git stash drop stash@{1}
git checkout <"files you put in your stash">
Ich habe mir das ausgedacht, nachdem ich (noch einmal) auf diese Seite gekommen bin und die ersten beiden Antworten nicht gemocht habe (die erste Antwort beantwortet die Frage einfach nicht und ich habe es nicht ganz gemocht, mit dem -pinteraktiven Modus zu arbeiten).
Die Idee entspricht der von @VonC vorgeschlagenen Verwendung von Dateien außerhalb des Repositorys. Sie speichern die gewünschten Änderungen irgendwo, entfernen die nicht gewünschten Änderungen in Ihrem Vorrat und wenden die Änderungen, die Sie aus dem Weg geräumt haben, erneut an. Ich habe jedoch den Git-Stash als "irgendwo" verwendet (und als Ergebnis gibt es am Ende einen zusätzlichen Schritt: Entfernen der Cahnges, die Sie in den Stash gelegt haben, weil Sie diese ebenfalls aus dem Weg geräumt haben).
Ich bevorzuge diesen Ansatz am meisten. Es bietet einen einfachen Workflow in Tortoisegit, bei dem nur Stash- und Revert-Befehle verwendet werden.
Mark Ch
Es ist nicht ratsam, auf Antworten zu SO unter Verwendung von Positionen zu verweisen. Die Positionen ändern sich, wenn sich die Bewertungen ändern.
Bryan Ash
2
@BryanAsh Nun, es ist nicht so, dass es hier wichtig ist. Ich gebe eine Anekdote, anstatt mich wirklich auf die anderen Antworten zu beziehen. Die Nachricht ist, dass mir die Antworten, die der Community gefallen haben, nicht gefallen haben und nicht, was diese Antworten tatsächlich enthalten. Außerdem macht es die 900-Stimmen-Lücke zwischen der zweiten und dritten Antwort unwahrscheinlich, dass sich dies in naher Zukunft ändert, und sollte sich dies jemals ändern, kann ich es jederzeit so bearbeiten, dass es "die Spitze der Antworten zu der Zeit" sagt. Wirklich, ich sehe nicht, wie das in dieser Situation irgendein Problem ist.
Jasper
23
Update (14.02.2015) - Ich habe das Skript ein wenig umgeschrieben, um den Fall von Konflikten besser zu behandeln, die jetzt als nicht zusammengeführte Konflikte und nicht als .rej-Dateien dargestellt werden sollten.
Ich finde es oft intuitiver, das Gegenteil von @ bukzors Ansatz zu tun. Das heißt, einige Änderungen zu inszenieren und dann nur diese inszenierten Änderungen zu speichern.
Leider bietet git keinen Git-Stash - nur Index oder ähnliches, deshalb habe ich ein Skript erstellt, um dies zu tun.
#!/bin/sh
# first, go to the root of the git repo
cd `git rev-parse --show-toplevel`
# create a commit with only the stuff in staging
INDEXTREE=`git write-tree`
INDEXCOMMIT=`echo "" | git commit-tree $INDEXTREE -p HEAD`
# create a child commit with the changes in the working tree
git add -A
WORKINGTREE=`git write-tree`
WORKINGCOMMIT=`echo "" | git commit-tree $WORKINGTREE -p $INDEXCOMMIT`
# get back to a clean state with no changes, staged or otherwise
git reset -q --hard
# Cherry-pick the index changes back to the index, and stash.
# This cherry-pick is guaranteed to succeed
git cherry-pick -n $INDEXCOMMIT
git stash
# Now cherry-pick the working tree changes. This cherry-pick may fail
# due to conflicts
git cherry-pick -n $WORKINGCOMMIT
CONFLICTS=`git ls-files -u`
if test -z "$CONFLICTS"; then
# If there are no conflicts, it's safe to reset, so that
# any previously unstaged changes remain unstaged
#
# However, if there are conflicts, then we don't want to reset the files
# and lose the merge/conflict info.
git reset -q
fi
Sie können das obige Skript als git-stash-indexirgendwo auf Ihrem Pfad speichern und es dann als Git-Stash-Index aufrufen
# <hack hack hack>
git add <files that you want to stash>
git stash-index
Jetzt enthält der Stash einen neuen Eintrag, der nur die Änderungen enthält, die Sie bereitgestellt haben, und Ihr Arbeitsbaum enthält weiterhin alle nicht bereitgestellten Änderungen.
In einigen Fällen können die Änderungen des Arbeitsbaums von den Indexänderungen abhängen. Wenn Sie also die Indexänderungen speichern, treten bei den Änderungen des Arbeitsbaums Konflikte auf. In diesem Fall erhalten Sie die üblichen nicht zusammengeführten Konflikte, die Sie mit git merge / git mergetool / etc. Lösen können.
Empfehlen Sie pushdanstelle cdund popdam Ende des Skripts. Wenn das Skript erfolgreich ist, befindet sich der Benutzer im selben Verzeichnis wie vor dem Ausführen.
Nate
1
@Nate: Soweit ich weiß, sollte das Verzeichnis für den Benutzer nur geändert werden, wenn er das Skript bezogen hat. Wenn Sie das Skript normal (~ / bin / git-stash-index) oder über git (git stash-index) ausführen, wird es in einer separaten Terminalsitzung ausgeführt, und Änderungen des Arbeitsverzeichnisses in dieser Sitzung wirken sich nicht auf das aus Arbeitsverzeichnis in der Terminalsitzung des Benutzers. Kennen Sie einen häufigen Anwendungsfall, wenn dies nicht der Fall ist? (außer das Skript zu beschaffen, das ich nicht als "gewöhnlich" betrachten würde)
JesusFreke
20
Wenn Sie keine Nachricht mit Ihren versteckten Änderungen angeben möchten, übergeben Sie den Dateinamen nach einem Doppelstrich.
$ git stash -- filename.ext
Wenn es sich um eine nicht verfolgte / neue Datei handelt, müssen Sie sie zuerst bereitstellen.
Diese Antwort ist ausführlich, dies ist prägnant. Wenn es jemandem hilft, werde ich es verlassen. Niemand auf dieser Seite erwähnt diese Syntax und das Ergebnis - sie erwähnen stattdessen "git stash push".
Sealocal
Dies ist die Antwort, nach der ich gesucht habe. Vielen Dank! +1
nicodp
19
Da das Erstellen von Zweigen in Git trivial ist, können Sie einfach einen temporären Zweig erstellen und die einzelnen Dateien darin einchecken.
Sie können keinen Zweig mit nicht bereitgestellten Änderungen erstellen. Sie können alle Änderungen problemlos in einen neuen Zweig verschieben (Stash / Stash Pop), aber dann kehren Sie zum ersten Punkt zurück: Wie testen Sie Ihren Zweig mit nur einigen dieser Änderungen, ohne die anderen zu verlieren?
Bukzor
7
Sie können keine Zweige wechseln, wenn Sie lokale Änderungen haben. Sie können jedoch einen neuen Zweig erstellen und Dateien selektiv hinzufügen / festschreiben, dann einen weiteren Zweig erstellen und das Gleiche rekursiv tun ... dann den ursprünglichen Zweig auschecken und selektiv wieder zusammenführen. Ich habe es gerade getan. Es scheint tatsächlich die natürliche Art zu sein, Dinge zu tun, da Sie im Wesentlichen Feature-Zweige erstellen.
iain
3
@iain können Sie Zweige wechseln, wenn Sie lokale Änderungen haben, solange diese keine Zusammenführung erfordern. Siehe Beispiel Gist . Dies gilt mindestens ab Git v2.7.0.
Dies fügt nichts Neues hinzu. Git Stash Push wird bereits in mehreren Antworten erwähnt
JesusFreke
12
Speichern Sie den folgenden Code in einer Datei mit dem Namen stash. Verwendung ist stash <filename_regex>. Das Argument ist der reguläre Ausdruck für den vollständigen Pfad der Datei. Zum Beispiel, um a / b / c.txt stash a/b/c.txtoder stash .*/c.txtusw. zu verstauen .
Tolle Methode. Ich hätte dies als Antwort gewählt. Tipp für zukünftige Leser: Sie müssen auf dem vollen Weg übereinstimmen. zB stash subdir / foo.c
er0
12
Nur für den Fall, dass Sie tatsächlich Änderungen verwerfen möchten, wann immer Sie sie verwenden git stash(und Git Stash nicht wirklich verwenden, um sie vorübergehend zu speichern), können Sie sie in diesem Fall verwenden
git checkout -- <file>
[ HINWEIS ]
Das git stashist nur eine schnellere und einfachere Alternative zum Verzweigen und Ausführen.
Das Problem bei VonCs "Zwischen" -Lösung zum Kopieren von Dateien außerhalb des Git-Repos besteht darin, dass Sie Pfadinformationen verlieren, was das spätere Zurückkopieren einer Reihe von Dateien etwas mühsam macht.
Es ist einfacher, tar zu verwenden (ähnliche Tools werden es wahrscheinlich tun) als zu kopieren:
tar cvf /tmp/stash.tar Pfad / zu / einigen / Dateipfad / zu / einigen / anderen / Dateien (... usw.)
Git Checkout-Pfad / zu / einigen / Dateipfad / zu / einigen / anderen / Dateien
checkout -fwird nicht benötigt, checkout(ohne -f) ist genug, ich habe die Antwort aktualisiert.
Eleotlecram
8
Manchmal habe ich eine nicht verwandte Änderung an meinem Zweig vorgenommen, bevor ich sie festgeschrieben habe, und ich möchte sie in einen anderen Zweig verschieben und separat festschreiben (wie Master). Ich mache das:
git stash
git checkout master
git stash pop
git add <files that you want to commit>
git commit -m 'Minor feature'
git stash
git checkout topic1
git stash pop
...<resume work>...
Beachten Sie, dass das erste stash& stash popbeseitigt werden kann. Sie können alle Ihre Änderungen auf das übertragenmaster beim Auschecken Filiale übertragen, jedoch nur, wenn keine Konflikte vorliegen. Auch wenn Sie einen neuen Zweig für die Teiländerungen erstellen, benötigen Sie den Stash.
Sie können es vereinfachen, indem Sie keine Konflikte und keinen neuen Zweig annehmen:
git checkout master
git add <files that you want to commit>
git commit -m 'Minor feature'
git checkout topic1
...<resume work>...
Dies kann mit SourceTree in 3 Schritten einfach durchgeführt werden.
Legen Sie vorübergehend alles fest, was Sie nicht verstauen möchten.
Git alles andere hinzufügen, dann verstauen.
Pop Ihr temporäres Commit, indem Sie git reset ausführen und das Commit vor Ihrem temporären festsetzen.
Dies alles kann in SourceTree in Sekundenschnelle erledigt werden, wo Sie einfach auf die Dateien (oder sogar einzelne Zeilen) klicken können, die Sie hinzufügen möchten. Einmal hinzugefügt, verpflichten Sie sie einfach zu einem temporären Commit. Klicken Sie anschließend auf das Kontrollkästchen, um alle Änderungen hinzuzufügen, und klicken Sie dann auf Stash, um alles zu speichern. Wenn die versteckten Änderungen nicht im Weg sind, werfen Sie einen Blick auf Ihre Festschreibungsliste und notieren Sie sich den Hash für das Festschreiben vor Ihrem temporären Festschreiben. Führen Sie dann "git reset hash_b4_temp_commit" aus direkt davor begehen. Jetzt haben Sie nur noch das Zeug, das Sie nicht verstauen wollten.
Ich würde verwenden git stash save --patch. Ich finde die Interaktivität nicht ärgerlich, da es währenddessen Optionen gibt, um den gewünschten Vorgang auf ganze Dateien anzuwenden.
Ich habe es versucht, aber nichts passiert. Wenn ich git applykeinen Fehler habe, aber Änderungen auch nicht zurückgebracht werden
ClementWalter
Die in / tmp generierte Patch-Datei wurde wahrscheinlich gelöscht. Möglicherweise haben Sie zwischen dem Diff und dem Apply neu gestartet. Versuchen Sie es mit einem anderen dauerhafteren Ort. Es funktioniert. Überprüfen Sie auch den Inhalt der Patch-Datei.
Christophe Fondacci
4
Ich habe Antworten und Kommentare zu diesem und einer Reihe ähnlicher Themen überprüft. Beachten Sie, dass keiner der folgenden Befehle korrekt ist, um bestimmte verfolgte / nicht verfolgte Dateien speichern zu können :
git stash -p (--patch): Wählen Sie Hunks manuell aus, ausgenommen nicht verfolgte Dateien
git stash -k (--keep-index): Verstecke alle verfolgten / nicht verfolgten Dateien und behalte sie im Arbeitsverzeichnis
git stash -u (--include-untracked): Versteckt alle verfolgten / nicht verfolgten Dateien
Um eine einzelne Datei zu verstauen, verwenden Sie git stash --patch [file].
Dies wird dazu auffordern : Stash this hunk [y,n,q,a,d,j,J,g,/,e,?]? ?. aGeben Sie einfach ein (verstauen Sie dieses Stück und alle späteren Stücke in der Datei) und schon geht es Ihnen gut.
@FilipeEsperandio pushfunktioniert nur in neueren Versionen von Git save. In beiden Fällen pushoder saveimpliziert durch den Aufruf stash: "Das Aufrufen von git stash ohne Argumente entspricht git stash push", docs
patrick
2
Ähnliche Situation. Hat sich verpflichtet und festgestellt, dass es nicht in Ordnung ist.
git commit -a -m "message"
git log -p
Aufgrund der Antworten hat mir das geholfen.
# revert to previous state, keeping the files changed
git reset HEAD~
#make sure it's ok
git diff
git status
#revert the file we don't want to be within the commit
git checkout specs/nagios/nagios.spec
#make sure it's ok
git status
git diff
#now go ahead with commit
git commit -a -m "same|new message"
#eventually push tu remote
git push
Ich weiß nicht, wie ich es in der Kommandozeile machen soll, nur mit SourceTree. Nehmen wir an, Sie haben Datei A geändert und haben zwei Änderungsblöcke in Datei B. Wenn Sie nur den zweiten Teil in Datei B speichern und alles andere unberührt lassen möchten, gehen Sie folgendermaßen vor:
Alles inszenieren
Nehmen Sie Änderungen an Ihrer Arbeitskopie vor, die alle Änderungen in Datei A rückgängig machen (z. B. das externe Diff-Tool starten und die Dateien übereinstimmen lassen.)
Lassen Sie Datei B so aussehen, als würde nur eine zweite Änderung darauf angewendet. (z. B. externes Diff-Tool starten und erste Änderung rückgängig machen.)
Erstellen Sie einen Stash mit "Bereitgestellte Änderungen beibehalten".
git add . //stage all the files
git reset <pathToFileWillBeStashed> //unstage file which will be stashed
git stash //stash the file(s)
git reset . // unstage all staged files
git stash pop // unstash file(s)
Nun, das solltest du nicht tun. Die Antwort sollte eine Lösung für die Frage bieten. Sie könnten einfach Ihre eigene Frage stellen.
L_J
Diese Lösung ist eine der einfachsten Antworten auf diese Frage. Lesen Sie die Frage, vergleichen Sie alle Antworten und meine. Wenn Sie Zweifel haben, dass diese Antwort weder eine zutreffende Lösung noch unzureichende Informationen zu der Frage enthält, können wir erneut sprechen.
Celikz
Dies funktioniert nicht, da der dritte Befehl "git stash" keine bereitgestellten Dateien berücksichtigt. Sowohl bereitgestellte als auch nicht bereitgestellte Dateien werden in den Stash verschoben. Die Fragen fragen speziell, wie man nur eine Datei
versteckt
0
Ein komplizierter Weg wäre, zuerst alles zu begehen:
git add -u
git commit // creates commit with sha-1 A
Zurück zum ursprünglichen Commit zurücksetzen, aber die_one_file aus dem neuen Commit auschecken:
git reset --hard HEAD^
git checkout A path/to/the_one_file
Jetzt können Sie die_one_file verstauen:
git stash
Bereinigen Sie, indem Sie den festgeschriebenen Inhalt in Ihrem Dateisystem speichern und auf das ursprüngliche Festschreiben zurücksetzen:
git stash --keep-index
behält zwar den Index bei, versteckt aber alles - sowohl im Index als auch außerhalb.git diff -- *filename* > ~/patch
danngit checkout -- *filename*
und später können Sie den Patch mitgit apply ~/patch
git stash push [--] [<pathspec>...]
.Antworten:
Haftungsausschluss : Die folgende Antwort gilt für Git vor Git 2.13. Schauen Sie sich für Git 2.13 und höher eine weitere Antwort weiter unten an .
Warnung
Wie in den Kommentaren erwähnt, wird dadurch alles inszeniert, sowohl inszeniert als auch nicht inszeniert. Der --keep-Index lässt den Index nach Abschluss des Stashs einfach in Ruhe. Dies kann zu Zusammenführungskonflikten führen, wenn Sie den Stash später öffnen.
Dadurch wird alles gespeichert, was Sie zuvor noch nicht hinzugefügt haben. Nur
git add
die Dinge, die Sie behalten möchten, und dann ausführen.Wenn Sie beispielsweise ein altes Commit in mehrere Änderungssätze aufteilen möchten, können Sie folgende Prozedur verwenden:
git rebase -i <last good commit>
edit
.git reset HEAD^
git add <files you want to keep in this change>
git stash --keep-index
git add
keine Änderungen.git commit
git stash pop
git rebase --continue
quelle
git stash save -k
,git stat
bleibt der Index (grün in ) ja erhalten, aber der gesamte Änderungssatz (sowohl grün als auch rot) geht in den Vorrat. Dies verstößt gegen die Anforderung des OP, "nur einige Änderungen zu speichern". Ich möchte nur einen Teil der roten (für die zukünftige Verwendung) verstauen.git stash -p
ist genau das, wonach ich gesucht habe. Ich frage mich, ob dieser Schalter erst kürzlich hinzugefügt wurde.git stash --keep-index
ist defekt. Wenn Sie weitere Änderungen vornehmen, versuchengit stash pop
Sie später, Zusammenführungskonflikte zu erhalten, da der Stash die geänderten Dateien enthält, die Sie gespeichert haben, und nicht nur die, die Sie nicht gespeichert haben. Zum Beispiel: Ich ändere die Dateien A und B und verstecke dann B, weil ich die Änderungen in A testen möchte. Ich finde ein Problem mit A, das ich dann behebe. Ich begebe A; Jetzt kann ich nicht mehr speichern, da sich eine alte Version von A ohne guten Grund im Speicher befindet und einen Zusammenführungskonflikt verursacht. In der Praxis können A und B viele Dateien sein, vielleicht sogar Binärbilder oder so, also muss ich im Grunde aufgeben und verlieren B.Sie können auch verwenden
git stash save -p "my commit message"
. Auf diese Weise können Sie auswählen, welche Hunks zum Stash hinzugefügt werden sollen. Es können auch ganze Dateien ausgewählt werden.Sie werden mit ein paar Aktionen für jedes Stück aufgefordert:
quelle
stash -p
. Ich vergebe diese Antwort, weil sie am interaktivsten / benutzerfreundlichsten bleibt.git stash save -p my stash message
; da die Reihenfolge der Argumente nicht sehr intuitiv ist ...git log -p
, denke ich,-p
muss die Flagge bedeuten "Mach das Coole, was ich will, aber ich weiß nicht, wie ich es ausdrücken soll."Da es bei git im Wesentlichen um die Verwaltung des gesamten Repository- Inhalts und -Index (und nicht einer oder mehrerer Dateien) geht,
git stash
handelt es sich nicht überraschend ummit dem gesamten Arbeitsverzeichnis.Seit Git 2.13 (Q2 2017) können Sie einzelne Dateien mit
git stash push
folgenden Elementen speichern :Vereinfachtes Beispiel:
Der Testfall für diese Funktion zeigt einige weitere Optionen:
Bei der ursprünglichen Antwort (unten, Juni 2010) ging es darum, manuell auszuwählen, was Sie verstauen möchten.
Casebash- Kommentare:
bukzor ‚s Antwort (upvoted November 2011) schlägt vor , eine praktischere Lösung, basierend auf
git add
+git stash --keep-index
.Gehen Sie und sehen Sie seine Antwort, die die offizielle sein sollte (anstelle meiner).
Zu dieser Option weist chhh in den Kommentaren auf einen alternativen Workflow hin:
(Ursprüngliche Antwort Juni 2010: manuelle Aufbewahrung)
Dennoch
git stash save --patch
konnte ermöglicht es Ihnen , die teilweise stashing erreichen Sie nach:Dadurch werden jedoch der vollständige Index (der möglicherweise nicht Ihren Wünschen entspricht, da er möglicherweise andere bereits indizierte Dateien enthält) und ein Teilarbeitsbaum (der möglicherweise so aussieht wie der, den Sie speichern möchten) gespeichert.
könnte besser passen.
Wenn
--patch
dies nicht funktioniert, kann ein manueller Vorgang Folgendes bewirken:Für eine oder mehrere Dateien wäre eine Zwischenlösung:
(Eigentlich schlägt eleotlecram eine interessante Alternative vor )
git stash
git stash
# Dieses Mal werden nur die gewünschten Dateien gespeichertgit stash pop stash@{1}
# Wenden Sie alle Änderungen an Ihren Dateien erneut angit checkout -- afile
# Setzen Sie die Datei vor lokalen Änderungen auf den HEAD-Inhalt zurückAm Ende dieses ziemlich umständlichen Prozesses werden nur eine oder mehrere Dateien gespeichert.
quelle
git reset
(gemischte)git is fundamentally about managing a all repository content and index and not one or several files
- Diese Implementierung überschattet das zu lösende Problem. Es ist eine Erklärung, aber keine Rechtfertigung. Bei jedem Versionsverwaltungssystem geht es darum, "mehrere Dateien zu verwalten". Schauen Sie sich nur an, welche Kommentare am meisten positiv bewertet werden.Wenn
git stash -p
(odergit add -p
mitstash --keep-index
) zu umständlich wäre, fand ich es einfacher zu bedienendiff
,checkout
undapply
:So "verstauen" Sie nur eine bestimmte Datei / ein bestimmtes Verzeichnis:
Dann danach
quelle
git add -p
ich oben in meiner eigenen Antwort erwähnt habe. +1.git diff > file.diff
wiegit apply
meine üblichen Teilversteck-Tools. Ich muss möglicherweise in Betracht ziehen,git stash -p
für größere Änderungssätze zu wechseln.patch = log --pretty=email --patch-with-stat --reverse --full-index --binary
. Beachten Sie jedoch, dass Ihre Änderungen erforderlich sind, damit der Patch festgeschrieben wird.../../foo/bar.txt
. Der Patch generiert OK, aber ich muss dann zum Repository-Stammverzeichnis wechseln, damit der Patch angewendet wird. Wenn Sie also Probleme damit haben, stellen Sie einfach sicher, dass Sie dies aus dem Repository-Stammverzeichnis tun.Verwenden Sie
git stash push
wie folgt:Zum Beispiel:
Dies ist seit Git 2.13 verfügbar, das im Frühjahr 2017 veröffentlicht wurde.
quelle
git stash push
bereits in meiner obigen Antwort vom letzten März vor 5 Monaten. Und ich habe diesen neuen Git 2.13-Befehl hier detailliert beschrieben: stackoverflow.com/a/42963606/6309 .git stash apply
, um die versteckten Änderungen wiederherzustellen?Angenommen, Sie haben 3 Dateien
und du willst nur b.rb und c.rb verstauen, aber nicht a.rb.
Sie können so etwas tun
Und du bist fertig! HTH.
quelle
Ein anderer Weg, dies zu tun:
Ich habe mir das ausgedacht, nachdem ich (noch einmal) auf diese Seite gekommen bin und die ersten beiden Antworten nicht gemocht habe (die erste Antwort beantwortet die Frage einfach nicht und ich habe es nicht ganz gemocht, mit dem
-p
interaktiven Modus zu arbeiten).Die Idee entspricht der von @VonC vorgeschlagenen Verwendung von Dateien außerhalb des Repositorys. Sie speichern die gewünschten Änderungen irgendwo, entfernen die nicht gewünschten Änderungen in Ihrem Vorrat und wenden die Änderungen, die Sie aus dem Weg geräumt haben, erneut an. Ich habe jedoch den Git-Stash als "irgendwo" verwendet (und als Ergebnis gibt es am Ende einen zusätzlichen Schritt: Entfernen der Cahnges, die Sie in den Stash gelegt haben, weil Sie diese ebenfalls aus dem Weg geräumt haben).
quelle
Update (14.02.2015) - Ich habe das Skript ein wenig umgeschrieben, um den Fall von Konflikten besser zu behandeln, die jetzt als nicht zusammengeführte Konflikte und nicht als .rej-Dateien dargestellt werden sollten.
Ich finde es oft intuitiver, das Gegenteil von @ bukzors Ansatz zu tun. Das heißt, einige Änderungen zu inszenieren und dann nur diese inszenierten Änderungen zu speichern.
Leider bietet git keinen Git-Stash - nur Index oder ähnliches, deshalb habe ich ein Skript erstellt, um dies zu tun.
Sie können das obige Skript als
git-stash-index
irgendwo auf Ihrem Pfad speichern und es dann als Git-Stash-Index aufrufenJetzt enthält der Stash einen neuen Eintrag, der nur die Änderungen enthält, die Sie bereitgestellt haben, und Ihr Arbeitsbaum enthält weiterhin alle nicht bereitgestellten Änderungen.
In einigen Fällen können die Änderungen des Arbeitsbaums von den Indexänderungen abhängen. Wenn Sie also die Indexänderungen speichern, treten bei den Änderungen des Arbeitsbaums Konflikte auf. In diesem Fall erhalten Sie die üblichen nicht zusammengeführten Konflikte, die Sie mit git merge / git mergetool / etc. Lösen können.
quelle
pushd
anstellecd
undpopd
am Ende des Skripts. Wenn das Skript erfolgreich ist, befindet sich der Benutzer im selben Verzeichnis wie vor dem Ausführen.Wenn Sie keine Nachricht mit Ihren versteckten Änderungen angeben möchten, übergeben Sie den Dateinamen nach einem Doppelstrich.
Wenn es sich um eine nicht verfolgte / neue Datei handelt, müssen Sie sie zuerst bereitstellen.
Diese Methode funktioniert in Git-Versionen 2.13+
quelle
Da das Erstellen von Zweigen in Git trivial ist, können Sie einfach einen temporären Zweig erstellen und die einzelnen Dateien darin einchecken.
quelle
Sie können dies einfach tun:
oder mit einer optionalen Nachricht
quelle
Speichern Sie den folgenden Code in einer Datei mit dem Namen
stash
. Verwendung iststash <filename_regex>
. Das Argument ist der reguläre Ausdruck für den vollständigen Pfad der Datei. Zum Beispiel, um a / b / c.txtstash a/b/c.txt
oderstash .*/c.txt
usw. zu verstauen .Code zum Kopieren in die Datei:
quelle
Nur für den Fall, dass Sie tatsächlich Änderungen verwerfen möchten, wann immer Sie sie verwenden
git stash
(und Git Stash nicht wirklich verwenden, um sie vorübergehend zu speichern), können Sie sie in diesem Fall verwenden[ HINWEIS ]
Das
git stash
ist nur eine schnellere und einfachere Alternative zum Verzweigen und Ausführen.quelle
Das Problem bei VonCs "Zwischen" -Lösung zum Kopieren von Dateien außerhalb des Git-Repos besteht darin, dass Sie Pfadinformationen verlieren, was das spätere Zurückkopieren einer Reihe von Dateien etwas mühsam macht.
Es ist einfacher, tar zu verwenden (ähnliche Tools werden es wahrscheinlich tun) als zu kopieren:
quelle
checkout -f
wird nicht benötigt,checkout
(ohne-f
) ist genug, ich habe die Antwort aktualisiert.Manchmal habe ich eine nicht verwandte Änderung an meinem Zweig vorgenommen, bevor ich sie festgeschrieben habe, und ich möchte sie in einen anderen Zweig verschieben und separat festschreiben (wie Master). Ich mache das:
Beachten Sie, dass das erste
stash
&stash pop
beseitigt werden kann. Sie können alle Ihre Änderungen auf das übertragenmaster
beim Auschecken Filiale übertragen, jedoch nur, wenn keine Konflikte vorliegen. Auch wenn Sie einen neuen Zweig für die Teiländerungen erstellen, benötigen Sie den Stash.Sie können es vereinfachen, indem Sie keine Konflikte und keinen neuen Zweig annehmen:
Versteck nicht einmal benötigt ...
quelle
Dies kann mit SourceTree in 3 Schritten einfach durchgeführt werden.
Dies alles kann in SourceTree in Sekundenschnelle erledigt werden, wo Sie einfach auf die Dateien (oder sogar einzelne Zeilen) klicken können, die Sie hinzufügen möchten. Einmal hinzugefügt, verpflichten Sie sie einfach zu einem temporären Commit. Klicken Sie anschließend auf das Kontrollkästchen, um alle Änderungen hinzuzufügen, und klicken Sie dann auf Stash, um alles zu speichern. Wenn die versteckten Änderungen nicht im Weg sind, werfen Sie einen Blick auf Ihre Festschreibungsliste und notieren Sie sich den Hash für das Festschreiben vor Ihrem temporären Festschreiben. Führen Sie dann "git reset hash_b4_temp_commit" aus direkt davor begehen. Jetzt haben Sie nur noch das Zeug, das Sie nicht verstauen wollten.
quelle
Ich würde verwenden
git stash save --patch
. Ich finde die Interaktivität nicht ärgerlich, da es währenddessen Optionen gibt, um den gewünschten Vorgang auf ganze Dateien anzuwenden.quelle
git stash -p
ermöglicht es Ihnen, eine ganze Datei schnell zu verstauen und danach zu beenden.Jede Antwort hier ist so kompliziert ...
Was ist damit zu "verstauen":
Dies, um die Dateiänderung zurückzusetzen:
Genau das gleiche Verhalten wie beim Verstauen einer Datei und beim erneuten Einlegen.
quelle
git apply
keinen Fehler habe, aber Änderungen auch nicht zurückgebracht werdenIch habe Antworten und Kommentare zu diesem und einer Reihe ähnlicher Themen überprüft. Beachten Sie, dass keiner der folgenden Befehle korrekt ist, um bestimmte verfolgte / nicht verfolgte Dateien speichern zu können :
git stash -p (--patch)
: Wählen Sie Hunks manuell aus, ausgenommen nicht verfolgte Dateiengit stash -k (--keep-index)
: Verstecke alle verfolgten / nicht verfolgten Dateien und behalte sie im Arbeitsverzeichnisgit stash -u (--include-untracked)
: Versteckt alle verfolgten / nicht verfolgten Dateiengit stash -p (--patch) -u (--include-untracked)
: ungültiger BefehlDerzeit ist die vernünftigste Methode, um bestimmte verfolgte / nicht verfolgte Dateien zu speichern, folgende:
Ich habe ein einfaches Skript für diese Prozedur in einer Antwort auf eine andere Frage geschrieben , und hier finden Sie Schritte zum Ausführen der Prozedur in SourceTree .
quelle
Lösung
Lokale Änderungen:
So erstellen Sie einen Stash "my_stash" mit nur den Änderungen in file_C :
Erledigt.
Erläuterung
Sie können den Git-Status zwischen den Schritten verwenden, um zu sehen, was los ist.
quelle
Wenn Sie versuchen, zwischen zwei Zweigen zu wechseln, tritt diese Situation auf.
Versuchen Sie, die Dateien mit "
git add filepath
" hinzuzufügen .Führen Sie diese Zeile später aus
quelle
Um eine einzelne Datei zu verstauen, verwenden Sie
git stash --patch [file]
.Dies wird dazu auffordern :
Stash this hunk [y,n,q,a,d,j,J,g,/,e,?]? ?
.a
Geben Sie einfach ein (verstauen Sie dieses Stück und alle späteren Stücke in der Datei) und schon geht es Ihnen gut.quelle
push
wie ingit stash push --patch [file]
push
funktioniert nur in neueren Versionen von Gitsave
. In beiden Fällenpush
odersave
impliziert durch den Aufrufstash
: "Das Aufrufen von git stash ohne Argumente entspricht git stash push", docsÄhnliche Situation. Hat sich verpflichtet und festgestellt, dass es nicht in Ordnung ist.
Aufgrund der Antworten hat mir das geholfen.
quelle
In dieser Situation habe ich
git add -p
(interaktiv)git commit -m blah
und dann bei Bedarf verstaut, was noch übrig ist.quelle
Ich weiß nicht, wie ich es in der Kommandozeile machen soll, nur mit SourceTree. Nehmen wir an, Sie haben Datei A geändert und haben zwei Änderungsblöcke in Datei B. Wenn Sie nur den zweiten Teil in Datei B speichern und alles andere unberührt lassen möchten, gehen Sie folgendermaßen vor:
quelle
quelle
Ein komplizierter Weg wäre, zuerst alles zu begehen:
Zurück zum ursprünglichen Commit zurücksetzen, aber die_one_file aus dem neuen Commit auschecken:
Jetzt können Sie die_one_file verstauen:
Bereinigen Sie, indem Sie den festgeschriebenen Inhalt in Ihrem Dateisystem speichern und auf das ursprüngliche Festschreiben zurücksetzen:
Ja, etwas umständlich ...
quelle
Ich fand keine Antwort als das, was ich brauchte und das ist so einfach wie:
Dadurch wird genau eine Datei gespeichert.
quelle
Schnelle Antwort
Um eine bestimmte geänderte Datei in git zurückzusetzen, können Sie die folgende Zeile ausführen:
Hier ist ein aktuelles Beispiel:
quelle
Wenn Sie einige geänderte Dateien speichern möchten, einfach nur
Es werden alle nicht bereitgestellten geänderten Dateien gespeichert
quelle