What I would do is create a branch from your current state as a feature branch so you don't lose any work.
git checkout -b new-features && git push origin new-features
Now that you've saved your current state to a branch (and pushed it to the remote), git checkout
your original branch and revert it back to a point before your current head.
The best way to do this is to use git revert
. A good explanation on why and how can be found on: Revert multiple git commits.
Once you reverted the changes, committed, and pushed, I'd recommend you create a branch to develop the bugfix on. This is good practice for the same reason people create feature branches. A good rule of thumb is to create a branch with the same or similar name / number as the issue you are working on. Do all of your changes on there and when it's all done, you can pull it in to whatever branch you are tagging your deployments from.
The best part about this is that it works whether or not any changes have been pushed to a remote, is simple and follows best practices.
Hope that helps.
EDIT: To answer question in comment.
"This also assumes that the changes you made are only local on your machine and not pushed to any remote branches."
That method will not work if you've already pushed. There are ways around it, but I wouldn't recommend it.
Basically, the only difference between the two methods at their core is that one does git reset --hard [commit]
and the other uses git revert
. Resetting actually tells git to go back to a particular commit, which is essentially the effect you want, but is frowned upon if you've already pushed. Since git will not allow a push to have non-fastforwarding changes and you have actually erased history, you'd have to do a git push origin [branch] --force
causing the remote to also lose the changes.
Revert actually creates a commit that adds history to git about the commits you are undoing. This is better because all reverted changes can be tracked and anyone who has pulled from that branch will not become out of sync. They will get the revert, or reverts, when they pull. A good side effect of this is that if you make a mistake in your reverted change, you can revert it later since it is just another commit.