Git Reset
Last updated
git reset moves the current branch to a different commit and, depending on the mode, updates the staging area (index) and working tree to match. The three modes differ only in how far that update reaches: --soft moves the branch and stops, --mixed (the default) also resets the staging area, and --hard also overwrites your working files.
Because --hard discards uncommitted work, know which mode you want before you run it. Try these safely in the terminal playground - a real shell in your browser.
The three modes
| Mode | Moves branch | Resets staging | Resets working tree |
|---|---|---|---|
--soft | Yes | No | No |
--mixed (default) | Yes | Yes | No |
--hard | Yes | Yes | Yes |
Syntax
| Command | What it does |
|---|---|
git reset --soft HEAD~1 | Undo last commit, keep changes staged |
git reset HEAD~1 | Undo last commit, keep changes unstaged |
git reset --hard HEAD~1 | Undo last commit, discard changes |
git reset <file> | Unstage a file (keep its changes) |
git reset --hard origin/main | Force local branch to match the remote |
Common cases
| Goal | Command |
|---|---|
| Unstage everything | git reset |
| Unstage one file | git reset README.md |
| Move back 3 commits, keep the work | git reset --soft HEAD~3 |
| Throw away all local changes since a commit | git reset --hard <hash> |
Git reset FAQ
What is the difference between --soft, --mixed, and --hard?
All three move your branch pointer to the target commit; they differ in what else they touch.
--soft changes nothing else, so your changes stay staged. --mixed (the default) also clears the staging area, so changes become unstaged but stay in your files. --hard also overwrites your working tree to match the target commit, discarding uncommitted changes.How do I unstage a file with git reset?
Run
git reset <file> (for example git reset README.md), or git reset with no path to unstage everything. This removes the file from the staging area but keeps your edits in the working tree. In newer Git you can also use git restore --staged <file>, which does the same thing more explicitly.Is git reset --hard reversible?
Not from the working tree -
--hard discards uncommitted changes permanently. However, committed work you reset away can usually be recovered: run git reflog to find the commit's hash, then git reset --hard <hash> (or create a branch at it). Uncommitted changes that were never staged or committed can't be recovered, so use --hard carefully.What's the difference between git reset and git revert?
git reset rewrites history by moving the branch backward - fine for local commits, but dangerous on commits you've already pushed. git revert leaves history intact and adds a new commit that undoes an earlier one, which is the safe choice for shared branches.Can I practice this online?
Yes. Open the terminal playground to run
git reset in a real shell in your browser - nothing to install. Coddy's free interactive Git course also covers resetting and undoing changes step by step.