How to undo an unwarranted git pull
A few days back a colleague of mine approached me with a problem, that they inadvertently messed up a local feature branch by pulling the master branch into their feature branch instead of rebasing and resolving conflicts sequentially.
To paraphrase, “Is there any way to revert (or) undo git pull so that my source/repos will come to the old state that was before doing a git pull? I want to do this because it merged some files which I didn’t want to do so but only merge other remaining files. So, I want to get those files back, is that possible?”
My solution:
Since we all know that running git pull
performs the following tasks, in the following order:
git fetch
git merge
The merge step combines branches that have been set up to be merged in your config.
Assumption:
You want to undo the merge step, but probably not the fetch (doesn’t make a lot of sense and shouldn’t be necessary).
Approach 1:
To undo the merge:
git reset --hard <sha-1>
to reset the local repository to a previous state.- Use git-reflog to find the SHA-1 of the previous state and then reset to it.
Warning:
The commands listed above remove all uncommitted changes, potentially leading to a loss of work (be careful):
git reset --hard <sha-1>
Approach 2:
Alternatively, reset to a particular point in time, such as:
git reset --hard <branch-name>@{"10 minutes ago"}
In my opinion, the latter is an excellent way to pick the previous state. Instead of using git-reflog and copying hashes, use a shortcut like:
<branch-name>@{1}
, reverts to the previous state of<branch-name>
,<branch-name>@{"5 minutes ago"}
, reverts to the state 5 minutes ago or<branch-name>@{14:30}
, reverts to the specified timestamp
Full details on specifying revisions in this way can be found in:
man git-rev-parse
, under the section "specifying revisions".