Stash Without the Staged Changes
The Problem with --keep-index
/ -k
Stashing just the working tree (unstaged changes) in Git is more difficult than it should be. The accepted answer, and quite a few other answers, stashes the unstaged changes and leaves the stage alone as requested via --keep-index
.
However what isn't obvious is that --keep-index
also stashes the staged changes. The staged changes end up in both the stage AND the stash. This is rarely what one wants because any interim changes to the stash are likely to result in conflicts when popping the stash later.
Alias Solution
This alias works well to stage just the working copy changes:
stash-working = "!f() { \
git commit --quiet --no-verify -m \"temp for stash-working\" && \
git stash push \"$@\" && \
git reset --quiet --soft HEAD~1; }; f"
It commits the staged changes temporarily, creates a stash from the remaining changes (and allows additional arguments such as --include-untracked
and --message
to be passed as alias arguments), and then resets the temporary commit to get back the staged changes.
It is similar to @Simon Knapp's answer, but with a few minor differences -- it uses --quiet
on the temporary actions taken, and it accepts any number of parameters for the stash push
, rather than hard-coding the -m
, and it does add --soft
to the final reset so that the index remains as it started. It also uses --no-verify
on the commit to avoid changes to the working copy from pre-commit hooks (HT: @Granfalloner).
For the opposite problem of stashing just the staged changes (alias stash-index
) see this answer.
man git stash
is much better. – Vetavetchgit push [-k|--keep-index]
time. Instead you can decide at apply time and usegit cherry-pick -m2 -n stash
to only pick the unstaged changes. See detailed answer. – Hatshepsutstash only unstaged
is here. – Ecchymosis