Undoing Changes in Git: reset, checkout, restore
Summary:
Learn how to undo mistakes using different Git commands.
When working with Git, mistakes happen. You might commit changes you want to take back, modify the wrong file, or simply change your mind about a local edit. Fortunately, Git provides robust tools for "undoing" changes. In this article, we’ll dive into three fundamental commands for undoing work in Git: reset
, checkout
, and restore
.
Table of Contents
- Understanding the Git Three-Tree Architecture
git reset
git checkout
git restore
- When to Use Each Command
- Common Scenarios and Examples
- Summary Table
- Conclusion
Understanding the Git Three-Tree Architecture
Before undoing changes, it’s helpful to know where changes reside in Git's three main states:
- Working Directory: Your local files with changes (edited, new, deleted)
- Staging Area (Index): Files marked for inclusion on the next commit (
git add
) - Repository (HEAD/Commit History): All commits in the repository
Undoing changes can manipulate any of these three areas.
git reset
What it Does
git reset
moves the current branch pointer and, optionally, modifies the staging area and working directory to match a specified commit. It is mainly used to undo commits or unstage files.
Common Forms
- Soft Reset (
--soft
): Moves HEAD to the specified commit. Staging and working directory unchanged. - Mixed Reset (
--mixed
, default): Moves HEAD and updates the staging area. Working directory unchanged. - Hard Reset (
--hard
): Moves HEAD and updates both staging area and working directory to match the commit.
Examples
# Undo last commit (but keep changes staged)
git reset --soft HEAD~1
# Unstage files, keep changes in working directory
git reset HEAD <file>
# Completely discard all changes and commits after a certain commit
git reset --hard <commit>
Warning: --hard
deletes your changes permanently unless committed elsewhere.
git checkout
What it Does
Historically, the git checkout
command was used to switch branches and restore files. Since Git 2.23 (August 2019), its role has been split. However, you may still encounter it for the following actions:
- Switch between branches.
- Restore a file in your working directory from a commit.
Examples
# Switch to another branch
git checkout feature-branch
# Restore a file from the latest commit
git checkout HEAD -- README.md
# Restore a file from a specific commit
git checkout <commit> -- file.txt
Note: Today,
git switch
andgit restore
are recommended for these tasks (see below).
git restore
What it Does
Introduced in Git 2.23, git restore
provides a clearer, focused interface for restoring file contents. It directly affects the working directory and the staging area.
Common Usage
-
From Latest Commit to Working Directory:
# Discard local changes to a file git restore file.txt
-
Unstage File (Keep Changes in Working Directory):
git restore --staged file.txt
-
Restore From a Specific Commit:
git restore --source=<commit> file.txt
When to Use Each Command
Command | Use case | Caution |
---|---|---|
git reset |
Undo commits, unstage files | --hard deletes changes permanently |
git checkout |
Switch branches, restore files from commits | Use git switch or git restore in modern Git |
git restore |
Discard changes in files, unstage changes | Only affects working directory or staging area |
Common Scenarios and Examples
1. Revert Unstaged Local Changes
You edited a file but want the original content back.
git restore file.txt
2. Unstage a File
You ran git add
, but want to unstage:
git restore --staged file.txt
# or
git reset HEAD file.txt
3. Undo Last Commit (Keep Changes in Working Directory)
You made a commit but realized you need to edit it:
git reset --soft HEAD~1
4. Undo Last Commit (Lose Changes)
Danger! This removes the commit and the changes themselves:
git reset --hard HEAD~1
5. Switch Branches
git switch develop
# or
git checkout develop
Summary Table
Task | Command |
---|---|
Discard local file changes | git restore file.txt |
Unstage file (keep local changes) | git restore --staged file.txt |
Undo last commit, keep changes staged | git reset --soft HEAD~1 |
Undo last commit, move changes to WD | git reset --mixed HEAD~1 |
Undo last commit, remove all changes | git reset --hard HEAD~1 |
Switch branches | git switch <branch> / git checkout <branch> |
Restore file from previous commit | git restore --source=<commit> file.txt |
Conclusion
Making mistakes in Git isn’t tragic—with the right commands, you can recover almost effortlessly. git reset
, git checkout
, and git restore
are powerful tools for reverting unwanted changes. Just be cautious with commands that destroy data (reset --hard
). With practice, you’ll master the art of undoing mistakes and keeping your project history tidy.
Further Resources: