How would I extract a single file (or changes to a file) from a git stash?

I’d like to know if it is possible to extract a single file or diff of a file from a git stash without popping the stash changeset off.

Might anyone be able to provide some suggestions/ideas about this?

  • How to best manage a Git repository for a website in 3 stages?
  • How can I re-merge commits that were reverted in github?
  • Using git-svn to merge a svn branch back into trunk and trunk back into the branch
  • Using git to Track changes to dropbox?
  • Multiple Git Branches in Multiple Eclipse Projects
  • Source control in Visual Studio 2010?
  • Class 'ZendSearch\Lucene\Lucene' not found ZendFramework2
  • How can I extract Git commit hash from VS/msbuild?
  • Does any Version Control System like SVN, Git, or Mercurial let you “keep latest version” but not the revisions? (such as for binary files)
  • Deleting remote branches?
  • Using github to host public git repositories whilst ensuring that sensitive data files remain untracked
  • How can I completely remove a file from a git repository?
  • 6 Solutions collect form web for “How would I extract a single file (or changes to a file) from a git stash?”

    In git stash manpage you can read that (in “Discussion” section, just after “Options” description):

    A stash is represented as a commit whose tree records the state of the
    working directory, and its first parent is the commit at HEAD when the
    stash was created.

    So you can treat stash (e.g. stash@{0} is first / topmost stash) as a merge commit, and use:

    $ git diff stash@{0}^1 stash@{0} -- <filename>

    Explanation: stash@{0}^1 shortcut means first parent of given stash, which as stated in explanation above is commit at which changes were stashed away. We use this form of “git diff” (with two commits) because stash@{0} / refs/stash is a merge commit, and we have to tell git which parent we want to diff against. More cryptic:

    $ git diff stash@{0}^! -- <filename>

    should also work (see git rev-parse manpage for explanation of rev^! syntax, in “Specifying ranges” section).

    Likewise, you can use git checkout to check a single file out of the stash:

    $ git checkout stash@{0} -- <filename>

    or to save it under another filename:

    $ git show stash@{0}:<full filename>  >  <newfile>


    $ git show stash@{0}:./<relative filename> > <newfile>

    (note that here <full filename> is full pathname of a file relative to top directory of a project (think: relative to stash@{0})).

    You might need to protect stash@{0} from shell expansion, i.e. use "stash@{0}" or 'stash@{0}'.

    If you use git stash apply rather than git stash pop, it will apply the stash to your working tree but still keep the stash.

    With this done, you can add/commit the file that you want and then reset the remaining changes.

    You can get the diff for a stash with “git show stash@{0}” (or whatever the number of the stash is; see “git stash list”). It’s easy to extract the section of the diff for a single file.

    Short answer

    To see the whole file: git show stash@{0}:<filename>

    To see the diff: git diff stash@{0}^1 stash@{0} -- <filename>

    The simplest concept to understand, although maybe not the best, is you have three files changed and you want to stash one file.

    If you do git stash to stash them all, git stash apply to bring them back again and then git checkout f.c on the file in question to effectively reset it.

    When you want to unstash that file run do a git reset --hard and then run git stash apply again, taking advantage ofthe fact that git stash apply doesn’t clear the diff from the stash stack.

    There is an easy way to get changes from any branch, including stashes:

    $ git checkout --patch stash@{0} path/to/file

    You may omit the file spec if you want to patch in many parts. Or omit patch (but not the path) to get all changes to a single file. Replace 0 with the stash number from git stash list, if you have more than one. Note that this is like diff, and offers to apply all differences between the branches. To get changes from only a single commit/stash, have a look at git cherry-pick --no-commit.

    Git Baby is a git and github fan, let's start git clone.