问题
I had done five commits and I wanted to make them all into one commit before pushing them. For some reason I decided to try doing this by a different means than I usually use.
FWIW: I was attempting to follow the instructions here http://gitready.com/advanced/2009/02/10/squashing-commits-with-rebase.html .
I'll put a lot of detail below but you might want to skip down to the bottom of the question where I put the output of git reflog
because I suspect that's what's significant here.
So here's what I did - with all my changes committed I did :
git rebase -i HEAD~5
and I was presented with the text editor which showed the commits and I, wrongly I now realise, changed all the first column values of 'pick' to 'squash'.
I then saw an error message. To my shame I can't remember what the error message said but I think it said something like "You have no commit to use".
At that point I was back to the prompt and when I try to repeat the :
git rebase -i HEAD~5
I get the message :
It seems that there is already a rebase-merge directory, and
I wonder if you are in the middle of another rebase. If that is the
case, please try
git rebase (--continue | --abort | --skip)
If that is not the case, please
rm -fr /home/foo/dev/bar/.git/rebase-merge
and run me again. I am stopping in case you still have something
valuable there.
Then I read this answer https://stackoverflow.com/a/12163247/364088 which suggests doing :
git reset --soft HEAD^
I did that (I wish I had not). After I'd done it.
git status
showed a number of files with uncommitted changes although
git diff
showed no changes . Anyway I then did a
git commit
And now I have lost all my chnages in the last five commits !
git reflog
shows (this is just the top of it):
3f80e4b HEAD@{0}: commit: Decorator demo added
1888dd9 HEAD@{1}: reset: moving to HEAD^
7d6228e HEAD@{2}: checkout: moving from master to 7d6228eb9b03d0c45acf7c66e662220213cf4fb9
705736f HEAD@{3}: commit: Snapshot commit - squash later
75db0c3 HEAD@{4}: commit: Snapshot commit - squash later
b70b50f HEAD@{5}: commit: Snapshot commit - squash later
d970a62 HEAD@{6}: commit: Snapshot commit - squash later
0f24e88 HEAD@{7}: commit: Snapshot commit - squash later
7d6228e HEAD@{8}: commit: Move some standard code into its own module and tidy up .
1888dd9 HEAD@{9}: commit: Early version of the decorators demo
So the thing is the commits labelled "Snapshot commit - squash later" are the ones I wanted to merge into a single commit.
The commits HEAD@{2} and HEAD@{1} are stuff I've done in the process of trying to merge those "Snapshot commit - squash later". The commit HEAD@{0} is the commit I did after the rebase and the reset.
In case it matters the last commit pushed was HEAD@{8}.
So what I'd like is to get back to the '705736f' commit and then, ideally do the merging of commits again only this time make it work !
I'd be quite happy if I could recover the work in the "Snapshot commit - squash later" changes.
Would be grateful for advice.
回答1:
My preferred method is to stick a label on the thing you want to get back, like a branch:
git branch recover 705736f
At this point you can check it out (it's a new local branch) and make sure you've recovered what you wanted:
git checkout recover
git log # or gitk, or whatever
This is a new branch label, pointing at the old (pre-rebase-attempt) commits.
Your new commit (Decorator demo added
) will be on the other branch, which (in a graph log viewer, like gitk --branches
or git log
with --graph
) forks off after the Early version of the decorators demo
commit.
If you're willing to "lose" (except for in the reflog) the new commit, you can force-reset your current branch back to the old commit in the reflog:
git reset --hard 705736f
(instead of creating a new branch to point to 705736f
). Again, run git log
to see if that's where you want (you can even git log 705736f
first!).
回答2:
Just do:
$ git reset --hard HEAD@{3}
and you'll get back to the point where you did your last commit. From then you can act accordingly.
来源:https://stackoverflow.com/questions/22191901/git-rebase-ate-my-commits-translate-git-reflog-output-for-me