Discarding Local Changes
Sometimes you just want your working directory to look like it did at the last commit — edits gone, staged changes gone, scratch files swept away. Git treats each of those three things a little differently, so the trick is knowing which category your unwanted change falls into.
Three kinds of “local changes”
Unstaged edits — you modified a tracked file but did not
git addit.Staged edits — you ran
git addbut did not commit yet.Untracked files — brand-new files Git has never seen. They will not be touched by
restoreorreset.
Discard unstaged edits
Throw away working-tree edits
# A single file git restore src/util.js # Multiple files git restore src/util.js src/helpers.js # Everything in the current directory and below git restore . # Legacy spelling (still works) git checkout -- src/util.js
Discard staged + unstaged edits
Reset a file all the way to HEAD
git restore --staged --worktree src/util.js # Equivalent to a per-file hard reset # All files git restore --staged --worktree . # Or the nuclear option (for tracked files only) git reset --hard HEAD
Remove untracked files
Untracked files are invisible to restore and reset. To delete them you need git clean, which is intentionally a little awkward to type because it is so destructive.
git clean flags
git clean -n # dry run — lists what WOULD be deleted (recommended first!) git clean -nd # dry run, include untracked directories git clean -f # actually delete untracked files git clean -fd # delete untracked files AND directories git clean -fdx # also delete files ignored by .gitignore git clean -fdX # ONLY delete files ignored by .gitignore (e.g. build output)
The “start over” combo
Full reset of the working directory
# Dry run first git status git clean -nd # Then the real thing git reset --hard HEAD git clean -fd # Even more nuclear: also wipe ignored build output, node_modules, etc. git clean -fdx # (You will need to reinstall dependencies, regenerate caches, etc.)
Dry-run everything
Command | Dry-run flag | What it shows |
|---|---|---|
|
| Files that would be deleted |
| Interactive | You confirm each hunk before discarding |
|
| What would change in the index |
| (use stash itself) | Save your work first; verify by |
Safer alternative: stash, do not discard
If you are even a little unsure, stash instead of discard. Stashed work is recoverable for 30+ days and costs you nothing.
Park your work in case you change your mind
git stash push -m "Maybe-bad experiment" git status # clean — same effect as discarding # Later, if you want it back git stash list # find the right stash git stash pop # put it back into the working tree
What can be recovered after a discard?
Discarded unstaged edits — gone. Not in the reflog, not in the object database.
Discarded staged edits — gone, with the same caveat.
Deleted untracked files (via
git clean) — gone. Not in Git at all.Hard-reset commits — recoverable via the reflog for ~90 days, since the commits themselves are objects in
.git/objects.