Categories
git git-stash

How can I git stash a specific file?

2059

How can I stash a specific file leaving the others currently modified out of the stash I am about to save?

For example, if git status gives me this:

younker % gst      
# On branch master
# Your branch is ahead of 'origin/master' by 1 commit.
#
# 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:   app/controllers/cart_controller.php
#   modified:   app/views/cart/welcome.thtml
#
no changes added to commit (use "git add" and/or "git commit -a")

and I only want to stash app/views/cart/welcome.thtml, how would I do that? Something like (but of course this does not work):

git stash save welcome_cart app/views/cart/welcome.thtml

5

  • 66

    The “possible duplicate” question currently has an incorrect answer marked as accepted.

    Mar 22, 2017 at 5:08

  • 8

    you can use git checkout -- filename and revert it to the original state.

    – visualex

    Aug 30, 2017 at 9:57

  • 10

    @visualex it will indeed revert it, but not stash it

    – Jesper

    Jul 10, 2018 at 14:54

  • 2

    Re Penguin Brian’s comment: Yes, the accepted answer to the “possible duplicate” question links to this question for recent versions of git.

    – Mars

    Mar 23, 2019 at 18:29

  • 3

    $ git stash — filename.ext

    – Lini

    Dec 24, 2019 at 12:32

2966

EDIT: Since git 2.13, there is a command to save a specific path to the stash: git stash push <path>. For example:

git stash push -m welcome_cart app/views/cart/welcome.thtml

OLD ANSWER:

You can do that using git stash --patch (or git stash -p) — you’ll enter interactive mode where you’ll be presented with each hunk that was changed. Use n to skip the files that you don’t want to stash, y when you encounter the one that you want to stash, and q to quit and leave the remaining hunks unstashed. a will stash the shown hunk and the rest of the hunks in that file.

Not the most user-friendly approach, but it gets the work done if you really need it.

26

  • 39

    Cumbersome, but works. I wish there was a quick way to stash only staged changes, and then have the changes go into the unstaged working tree when it’s later popped.

    Sep 26, 2012 at 14:42

  • 67

    @JamesJohnston git stash --keep-index will allow you to stash all the unstaged changes (the opposite of what you’re looking for). stackoverflow.com/a/8333163/378253

    – nimser

    Oct 16, 2013 at 11:23


  • 126

    If you say a instead of y it will stash that hunk + the remainder of the file, which is much faster.

    – i_am_jorf

    Nov 21, 2013 at 21:39

  • 53

    @jeffamaphone great! also d will do the opposite, i.e. not stash any further hunks in the current file. and indeed ? will show all possible options.

    – omnikron

    Dec 5, 2013 at 11:15


  • 15

    @Vencovsky It stands for “message” and is used to specify optional description of the stash. If you don’t need that, you can leave the -m welcome_cart part out.

    – svick

    Aug 5, 2019 at 16:22

366

I usually add to index changes I don’t want to stash and then stash with --keep-index option.

git add app/controllers/cart_controller.php
git stash --keep-index
git reset

The last step is optional, but usually, you want it. It removes changes from the index.


Warning
As noted in the comments, git stash --keep-index pushes everything onto the stash, both staged and unstaged. The --keep-index just leaves the index alone after the stash is done. This can cause merge conflicts when you later pop the stash.

6

  • 5

    This is much better than the accepted answer if you have a lot changes you don’t want to wade through with the –patch option.

    – quux00

    Dec 21, 2012 at 15:36

  • 197

    No, this puts everything into the stash, both staged and unstaged. The --keep-index just leaves the index alone after the stash is done. So this isn’t a valid answer to the question, AFAICT.

    – Raman

    Mar 17, 2013 at 19:22

  • 3

    See my answer on @Rachel’s question for a solution to doing the inverse of this (stashing the staged changes, instead of the unstaged changes) – stackoverflow.com/questions/3040833/…

    Jun 16, 2013 at 21:06


  • 3

    After, if you want to get back the files you stashed without committing the files you added, you can run git stash; git stash pop [email protected]{1}.

    – yndolok

    Nov 20, 2013 at 21:07


  • 8

    WARNING: Take note of @Raman’s point. This doesn’t do what it should. This will put the same changes in the stash and leave them in the working tree. When you later try to pop the stash, you are likely to get merge conflicts, and they are often really confusing and hard to fix.

    – rjmunro

    Apr 8, 2014 at 10:23

123

To add to svick’s answer, the -m option simply adds a message to your stash, and is entirely optional. Thus, the command

git stash push [paths you wish to stash]

is perfectly valid. So for instance, if I want to only stash changes in the src/ directory, I can just run

git stash push src/

1

  • 3

    NB: Popping is done without the path, just git stash pop.

    Apr 28, 2021 at 15:58