Git reset cheatsheet


The reset command in git does quite a lot, but I always forget all its uses.
This is a cheatsheet based on this blog.

The reset command will:

  1. Move whatever branch HEAD points to (stop here unless --soft)
  2. THEN, make the Index look like that (stop here unless --hard)
  3. THEN, make the Working Directory look like that

Commit level

Updates Current Branch?Updates Index?Updates Working Dir?Working Dir Safe?
reset --soft [commit]YESNONOYES
reset (--mixed) [commit]YESYESNOYES
reset --hard [commit]YESYESYESNO
checkout [commit]NOYESYESYES

reset —soft [commit]
When given HEAD~, this undos the git commit
Will move the current branch back to the given commit, but not update the index or working directory
This provides similar functionality as git checkout --amend (but changing the whole commit, not just the message)

reset (—mixed) [commit] (default form)
When given HEAD~, this undos the git commit and the git add
Will move the current branch and update the index, but working directory will remain untouched

reset —hard [commit] (unsafe)
When given HEAD~, this undos the git commit, git add and also the changes in the working directory
Will update all three trees to match the given commit
This is useful to remove commits you don’t want
From a clean working tree, it is also useful to undo a conflicted (or not conflicted) git merge or a git pull
From a dirty working tree, use --merge instead, this will safely preserve your local changes
The --keep option is useful when removing some of the last commits while safely keeping your local changes

checkout [commit]
When given HEAD~, this will safely update the working directory and the index without moving the current branch
This will leave you in a detached HEAD state

File level

Updates Current Branch?Updates Index?Updates Working Dir?Working Dir safe?
reset (commit) [file]NOYESNOYES
checkout (commit) [file]NONOYESNO

reset (commit) [file]
When given a file path, the first step of updating the branch that HEAD points to is skipped
Will update the index only to match commit, leaving both working directory and current branch untouched
From here, you could use git checkout to make the working directory match the index, although git checkout can do that with one command (see below)
The commit parameter will default to HEAD which effectively un-stages files

checkout (commit) [file] (unsafe)
Updates the working directory only, without changing the index, current branch or even what HEAD is pointing to
This would effectively be git reset --hard [branch] file, but this command does not exist

More info and examples in git reset --help