NeuroAgent

How to Recover Dropped Git Stash: Complete Guide

Learn how to recover dropped Git stashes using reflog, fsck, and other methods. Complete guide with step-by-step instructions to restore lost work in Git repositories.

Question

How can I recover a dropped stash in Git?

I frequently use git stash and git stash pop to save and restore changes in my working tree. Yesterday, I had some changes in my working tree that I had stashed and popped, and then I made more changes to my working tree. I’d like to go back and review yesterday’s stashed changes, but git stash pop appears to remove all references to the associated commit.

I know that if I use git stash then .git/refs/stash contains the reference of the commit used to create the stash. And .git/logs/refs/stash contains the whole stash. But those references are gone after git stash pop. I know that the commit is still in my repository somewhere, but I don’t know what it was.

Is there an easy way to recover yesterday’s stash commit reference?

NeuroAgent

Recovering a dropped Git stash is often possible using Git’s built-in history tracking tools. When you use git stash pop, the stash reference is removed from the stash list but the actual commit typically remains in your repository’s object database, making recovery feasible through several methods.


Contents


Understanding Git Stash Behavior

When you use git stash, Git creates a commit object that stores your changes and adds a reference to it in .git/refs/stash. This commit object contains:

  • The changes from your working directory
  • A reference to the commit you were on when you stashed
  • A parent commit that points to the previous stash

The key insight is that when you use git stash pop, Git only removes the reference from the stash list and applies the changes to your working directory. The actual commit object usually remains in the repository’s object database unless garbage collection has cleaned it up.

💡 Important: Garbage collection can permanently remove unreferenced commits. Run git gc less frequently and avoid git gc --aggressive to prevent accidental loss of dropped stashes.


Recovering Dropped Stashes Using Reflog

The reflog (reference log) is your most powerful tool for recovering dropped stashes. Git maintains a log of changes to branch tips, including stash references.

Step-by-Step Reflog Recovery:

  1. Check the reflog for stash entries:

    bash
    git reflog show stash
    
  2. Look for stash-related entries in the output. You’ll see entries like:

    6a4b2f3 stash@{0}: drop: WIP on feature-branch: abc1234 Add new functionality
    
  3. Recreate the stash reference from the commit hash:

    bash
    git update-ref refs/stash 6a4b2f3
    
  4. Verify the recovery:

    bash
    git stash list
    

If the reflog doesn’t show stash entries, try checking the main branch reflog:

bash
git reflog

Look for entries around the time you popped the stash. The commit hash in the reflog entry corresponds to the stash commit.


Finding Orphaned Stash Commits with fsck

When a stash is dropped, its commit becomes “dangling” - it exists but isn’t referenced by anything. Git’s fsck (file system check) can find these orphaned objects.

Using fsck to Recover Stashes:

  1. Find all dangling commits:

    bash
    git fsck --dangling
    
  2. Look for stash-related dangling commits. They’ll appear as:

    dangling commit 6a4b2f3 stash@{0}: WIP on feature-branch: abc1234 Add new functionality
    
  3. Create a new stash reference from the commit hash:

    bash
    git update-ref refs/stash 6a4b2f3
    
  4. Double-check with:

    bash
    git stash show stash@{0}
    

Note that git fsck --dangling may show many objects. You can filter for stash-related ones by looking for commit messages containing “WIP” (Work In Progress) or “stash”.


Using Git Log and Gitk for Recovery

Visual Recovery with Gitk

The gitk graphical tool can help visualize commit history and find dropped stashes:

bash
gitk --all

In gitk:

  1. Look for commits with “WIP” in the message
  2. Check the parent-child relationships
  3. Identify which commit represents your dropped stash
  4. Note the commit hash

Command-Line Log Search

You can also search through commit history:

bash
git log --grep="WIP" --oneline

Or more broadly search for stash-related commits:

bash
git log --all --grep="stash" --oneline

Once you identify the commit hash, recreate the stash reference:

bash
git update-ref refs/stash <commit-hash>

Prevention and Best Practices

Better Stash Management

Instead of relying on recovery, consider these preventive measures:

  1. Use descriptive stash names:

    bash
    git stash push -m "Feature X: Add user authentication"
    
  2. List stashes before popping:

    bash
    git stash list
    git stash pop stash@{2}
    
  3. Use git stash apply instead of pop when unsure:

    bash
    git stash apply stash@{0}
    
  4. Create branches for important work:

    bash
    git checkout -b temp-branch
    # work on changes
    # return to main branch when ready
    

Configure Git for Better Stash Handling

Add this to your .gitconfig:

[alias]
    stash-pop = !git stash list && echo "Which stash to pop? (stash@{n})" && read stash && git stash pop $stash

This forces you to see available stashes before popping one.


Alternative Recovery Methods

Using Bisect to Find the Stash Commit

If other methods fail, you can use git bisect to narrow down when the stash commit was created:

  1. Start a bisect session:

    bash
    git bisect start
    
  2. Mark a known good commit (before you created the stash):

    bash
    git bisect good abc1234
    
  3. Mark a known bad commit (after you popped the stash):

    bash
    git bisect bad def5678
    
  4. Git will guide you through commits to find the stash.

Manual Object Database Search

For advanced recovery, you can manually search the object database:

bash
find .git/objects -type f | while read obj; do
    git cat-file -p $(basename $obj | tr '[:lower:]' '[:upper:]') 2>/dev/null | grep -q "WIP" && echo "Found: $obj"
done

This searches through all Git objects for those containing “WIP” in their content.


Sources

  1. Official Git Documentation - Stash
  2. Pro Git Book - Stashing
  3. Git Reflog Documentation
  4. Git Fsck Documentation
  5. Stack Overflow - Recovering dropped git stash

Conclusion

Recovering a dropped Git stash is usually possible when you act quickly before garbage collection removes the orphaned commit. The reflog method is your most reliable approach, followed by fsck for finding dangling commits. Always use descriptive stash names and consider using git stash apply instead of pop to prevent accidental loss.

Key takeaways:

  • Check git reflog show stash first for dropped stash references
  • Use git fsck --dangling to find orphaned stash commits
  • Recreate stash references with git update-ref refs/stash <commit-hash>
  • Prevent future losses with descriptive stash names and careful stash management

If you frequently work with stashes, consider setting up alias commands or using GUI tools that provide better stash management interfaces to minimize the risk of accidental drops.