Undo working copy modifications of one file in Git?

GitFileVersion ControlDvcsUndo

Git Problem Overview


After the last commit, I modified a bunch of files in my working copy, but I want to undo the changes to one of those files, as in reset it to the same state as the most recent commit.

However, I only want to undo the working copy changes of just that one file alone, nothing else with it.

How do I do that?

Git Solutions


Solution 1 - Git

You can use

git checkout -- file

You can do it without the -- (as suggested by nimrodm), but if the filename looks like a branch or tag (or other revision identifier), it may get confused, so using -- is best.

You can also check out a particular version of a file:

git checkout v1.2.3 -- file         # tag v1.2.3
git checkout stable -- file         # stable branch
git checkout origin/master -- file  # upstream master
git checkout HEAD -- file           # the version from the most recent commit
git checkout HEAD^ -- file          # the version before the most recent commit

Solution 2 - Git

Just use

git checkout filename

This will replace filename with the latest version from the current branch.

WARNING: your changes will be discarded — no backup is kept.

Solution 3 - Git

git checkout <commit> <filename>

I used this today because I realized that my favicon had been overwritten a few commits ago when I upgrated to drupal 6.10, so I had to get it back. Here is what I did:

git checkout 088ecd favicon.ico

Solution 4 - Git

If your file is already staged (happens when you do a git add etc after the file is edited) to unstage your changes.

Use

git reset HEAD <file>

Then

git checkout <file>

If not already staged, just use

git checkout <file>

Solution 5 - Git

I have Done through git bash:

(use "git checkout -- <file>..." to discard changes in working directory)

  1. Git status. [So we have seen one file wad modified.]

  2. git checkout -- index.html [i have changed in index.html file :

  3. git status [now those changes was removed]

enter image description here

Solution 6 - Git

If you want to just undo the previous commit's changes to that one file, you can try this:

git checkout branchname^ filename

This will checkout the file as it was before the last commit. If you want to go a few more commits back, use the branchname~n notation.

Solution 7 - Git

This answers is for command needed for undoing local changes which are in multiple specific files in same or multiple folders (or directories). This answers specifically addresses question where a user has more than one file but the user doesn't want to undo all local changes:

> if you have one or more files you could apply the same command (git checkout -- file ) to > each of those files by listing each of their location separated by > space as in:

git checkout -- name1/name2/fileOne.ext nameA/subFolder/fileTwo.ext

>mind the space above between name1/name2/fileOne.ext nameA/subFolder/fileTwo.ext

For multiple files in the same folder: >If you happen to need to discard changes for all of the files in a > certain directory, use the git checkout as follows:

git checkout -- name1/name2/*

The asterisk in the above does the trick of undoing all files at that location under name1/name2.

> And, similarly the following can undo changes in all files for > multiple folders:

git checkout -- name1/name2/* nameA/subFolder/*

> again mind the space between name1/name2/* nameA/subFolder/* in the > above.

Note: name1, name2, nameA, subFolder - all of these example folder names indicate the folder or package where the file(s) in question may be residing.

Solution 8 - Git

I always get confused with this, so here is a reminder test case; let's say we have this bash script to test git:

set -x
rm -rf test
mkdir test
cd test
git init
git config user.name test
git config user.email test@test.com
echo 1 > a.txt
echo 1 > b.txt
git add *
git commit -m "initial commit"
echo 2 >> b.txt
git add b.txt
git commit -m "second commit"
echo 3 >> b.txt

At this point, the change is not staged in the cache, so git status is:

$ git status
On branch master
Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git checkout -- <file>..." to discard changes in working directory)

	modified:   b.txt

no changes added to commit (use "git add" and/or "git commit -a")

If from this point, we do git checkout, the result is this:

$ git checkout HEAD -- b.txt
$ git status
On branch master
nothing to commit, working directory clean

If instead we do git reset, the result is:

$ git reset HEAD -- b.txt
Unstaged changes after reset:
M	b.txt
$ git status
On branch master
Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git checkout -- <file>..." to discard changes in working directory)

	modified:   b.txt

no changes added to commit (use "git add" and/or "git commit -a")

So, in this case - if the changes are not staged, git reset makes no difference, while git checkout overwrites the changes.


Now, let's say that the last change from the script above is staged/cached, that is to say we also did git add b.txt at the end.

In this case, git status at this point is:

$ git status
On branch master
Changes to be committed:
  (use "git reset HEAD <file>..." to unstage)

	modified:   b.txt

If from this point, we do git checkout, the result is this:

$ git checkout HEAD -- b.txt
$ git status
On branch master
nothing to commit, working directory clean

If instead we do git reset, the result is:

$ git reset HEAD -- b.txt
Unstaged changes after reset:
M	b.txt
$ git status
On branch master
Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git checkout -- <file>..." to discard changes in working directory)

	modified:   b.txt

no changes added to commit (use "git add" and/or "git commit -a")

So, in this case - if the changes are staged, git reset will basically make staged changes into unstaged changes - while git checkout will overwrite the changes completely.

Solution 9 - Git

Git 2.23 introduced a restore to do just that, in an attempt, I think, to make the answer to these kind of questions straightforward.

git restore [--] <pathspec>...

As always, the -- could be needed but when a file name starts with a dash. (The confusion with a branch name is not possible here, as restore's perimeter does not include branches, unlike the do-all checkout)

To be complete, restore can also restore staged files with --staged, and restore from a different commit than HEAD with --source=<tree>.

Solution 10 - Git

I restore my files using the SHA id, What i do is git checkout <sha hash id> <file name>

Solution 11 - Git

For me only this one worked

git checkout -p filename

enter image description here

Solution 12 - Git

If you have not yet pushed or otherwise shared your commit:

git diff --stat HEAD^...HEAD | \
fgrep filename_snippet_to_revert | cut -d' ' -f2 | xargs git checkout HEAD^ --
git commit -a --amend

Solution 13 - Git

If it is already committed, you can revert the change for the file and commit again, then squash new commit with last commit.

Solution 14 - Git

git checkout a3156ae4913a0226caa62d8627e0e9589b33d04c -p */SearchMaster.jsp

Breakdown: a3156ae4913a0226caa62d8627e0e9589b33d04c = This is the hash value of the commit. It's on my own personal branch (not master).

The -p flag is the path.

*/SearchMaster.jsp is the filename.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionhasenView Question on Stackoverflow
Solution 1 - GitBrian CampbellView Answer on Stackoverflow
Solution 2 - GitnimrodmView Answer on Stackoverflow
Solution 3 - GitneoneyeView Answer on Stackoverflow
Solution 4 - GitthanikkalView Answer on Stackoverflow
Solution 5 - GitShivanandamView Answer on Stackoverflow
Solution 6 - GitsykoraView Answer on Stackoverflow
Solution 7 - GitNirmalView Answer on Stackoverflow
Solution 8 - GitsdaauView Answer on Stackoverflow
Solution 9 - GitP-GnView Answer on Stackoverflow
Solution 10 - GitBetoView Answer on Stackoverflow
Solution 11 - GitRamesh BhupathiView Answer on Stackoverflow
Solution 12 - GitJesse GlickView Answer on Stackoverflow
Solution 13 - GitGinaView Answer on Stackoverflow
Solution 14 - GitGeneView Answer on Stackoverflow