When we make a mistake and already pushed to the remote repo, we can either fix our mistake and push it again or revert and delete the history. Here’s how to achieve both.
History remains
Alternative 1: Fix and commit again
No need to explain this. Simply fix and push again in a new commit.
Alternative 2: Revert the commit
This will achieve more or less the same as fixing and committing again, but it’s done automatically and erases all the changes from the bad commit. If your mistakes is only a small part of a big commit, scenario 1 should be the best bet. This is useful if the commit is let’s say 5 commits behind and you wish to erase those changes. I say erase because the history will still show all commits, but the bad ones won’t affect the code anymore.
git revert acfcaf7b
History is removed
Reverting and removing history should be done with care. Best to do on private repo or when other people haven’t pull yet or are not working on the project at the moment of your commit. It’s best to remove a bad commit from history right away after a push. If your push is a few days old or not the immediate last one, this can become tricky because rewriting history affects every other people or cloned repo out there. Meaning that deleting a commit will affect the ability of other to pull
back the changes, especially if they have already worked on other parts of the code.
So in those cases, a revert without affecting history is the best choice.
Case 1: Delete last commit
- Remote repo name:
projectX
- Branch:
master
- Last commit :
acfcaf7b
We need to tell git to force projectX
of branch master
to the parent commit of acfcaf7b
git push projectX +acfcaf7b^:master
Where git
interprets x^
as the parent of x
and +
as a forced non-fastforward push.
If you have the master branch locally checked out you can simply reset the current commit to it’s parent and force push it to the remote repo
git reset HEAD^ --hard
git push projectX -f
The remote branch needs to be not protected to accept these forced commits.
Case 2: Delete the second last commit
If we want to delete an older commit but keep it’s children, then the easiest is to achieve this is to do an interactive rebase
down to the parent of the bad (offending) commit.
git rebase -i acfcaf7b^
This will open an editor and you can simply delete the offending commit and save the changes to the disk.
pick 01722073
pick acfcaf7b
pick dd89be5f
here just delete pick acfcaf7b
and save.
then force push the changes back to the remote repo
git push projectX -f
Case 3: Fix a typo in a commit
Here we do a rebase just like in Case 2
but instead of deleting the line, we change pick
for edit
. rebase
will stop at that commit, put the changes in the index and let you change it as you need. Commit the change and continue the rebase ( use git rebase --continue
if necessary to continue the process — git
will tell you how to keep the commit message and author if you want ). Then force push the changes as described above. You can use this to even split commit in smaller ones or merge commit in fewer ones.
original source: http://christoph.ruegg.name/blog/git-howto-revert-a-commit-already-pushed-to-a-remote-reposit.html rewrote here for me.
Leave a Reply