如何在 Git 中恢复丢失的提交?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/10099258/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How can I recover a lost commit in Git?
提问by Elias7
First, got "your branch is ahead of origin/master by 3 commits" then my app has reverted to an earlier time with earlier changes.
首先,得到“您的分支领先于 origin/master 3 次提交”,然后我的应用程序已恢复到较早的时间,并进行了较早的更改。
How can I get what I spent the last 11 hours doing back?
我怎样才能收回我过去 11 个小时所做的事情?
回答by Amber
git reflog
is your friend. Find the commit that you want to be on in that list and you can reset to it (for example:git reset --hard e870e41
).
git reflog
是你的朋友。在该列表中找到您想要的提交,您可以重置它(例如:)git reset --hard e870e41
。
(If you didn't commit your changes... you might be in trouble - commit early, and commit often!)
(如果您没有提交更改……您可能会遇到麻烦 - 尽早提交,并经常提交!)
回答by CodeWizard
Before answering, let's add some background, explaining what this HEAD
is.
在回答之前,让我们添加一些背景,解释这HEAD
是什么。
First of all what is HEAD?
First of all what is HEAD?
HEAD
is simply a reference to the current commit (latest) on the current branch.
There can only be a single HEAD
at any given time (excluding git worktree
).
HEAD
只是对当前分支上的当前提交(最新)的引用。在任何给定时间
只能有一个HEAD
(不包括git worktree
)。
The content of HEAD
is stored inside .git/HEAD
and it contains the 40 bytes SHA-1 of the current commit.
的内容HEAD
存储在里面.git/HEAD
,它包含当前提交的 40 字节 SHA-1。
detached HEAD
detached HEAD
If you are not on the latest commit - meaning that HEAD
is pointing to a prior commit in history it's called detached HEAD
.
如果您不在最新的提交上——这意味着它HEAD
指向历史中的先前提交,则称为detached HEAD
.
On the command line, it will look like this - SHA-1 instead of the branch name since the HEAD
is not pointing to the tip of the current branch:
在命令行上,它看起来像这样 - SHA-1 而不是分支名称,因为HEAD
它没有指向当前分支的尖端:
A few options on how to recover from a detached HEAD:
关于如何从分离的 HEAD 中恢复的一些选项:
git checkout
git checkout
git checkout <commit_id>
git checkout -b <new branch> <commit_id>
git checkout HEAD~X // x is the number of commits t go back
This will checkout new branch pointing to the desired commit.
This command will checkout to a given commit.
At this point, you can create a branch and start to work from this point on.
这将签出指向所需提交的新分支。
此命令将检出给定的提交。
此时,您可以创建一个分支并从这一点开始工作。
# Checkout a given commit.
# Doing so will result in a `detached HEAD` which mean that the `HEAD`
# is not pointing to the latest so you will need to checkout branch
# in order to be able to update the code.
git checkout <commit-id>
# Create a new branch forked to the given commit
git checkout -b <branch name>
git reflog
git reflog
You can always use the reflog
as well. git reflog
will display any change which updated the HEAD
and checking out the desired reflog entry will set the HEAD
back to this commit.
您也可以随时使用reflog
。git reflog
将显示更新HEAD
并检出所需引用日志条目的任何更改将设置HEAD
回此提交。
Every time the HEAD is modified there will be a new entry in the reflog
每次修改 HEAD 时都会有一个新条目 reflog
git reflog
git checkout HEAD@{...}
This will get you back to your desired commit
这会让你回到你想要的提交
git reset --hard <commit_id>
git reset --hard <commit_id>
"Move" your HEAD back to the desired commit.
“移动”你的 HEAD 回到所需的提交。
# This will destroy any local modifications.
# Don't do it if you have uncommitted work you want to keep.
git reset --hard 0d1d7fc32
# Alternatively, if there's work to keep:
git stash
git reset --hard 0d1d7fc32
git stash pop
# This saves the modifications, then reapplies that patch after resetting.
# You could get merge conflicts if you've modified things which were
# changed since the commit you reset to.
- Note: (Since Git 2.7) you can also use the
git rebase --no-autostash
as well.
- 注意:(从 Git 2.7 开始)您也可以使用
git rebase --no-autostash
。
git revert <sha-1>
git revert <sha-1>
"Undo" the given commit or commit range.
The reset command will "undo" any changes made in the given commit.
A new commit with the undo patch will be committed while the original commit will remain in the history as well.
“撤消”给定的提交或提交范围。
reset 命令将“撤消”在给定提交中所做的任何更改。
带有撤消补丁的新提交将被提交,而原始提交也将保留在历史记录中。
# Add a new commit with the undo of the original one.
# The <sha-1> can be any commit(s) or commit range
git revert <sha-1>
This schema illustrates which command does what.
As you can see there, reset && checkout
modify the HEAD
.
这个模式说明了哪个命令做什么。
如您所见,reset && checkout
修改HEAD
.
回答by Atri
Another way to get to the deleted commit is with the git fsck
command.
获取已删除提交的另一种方法是使用git fsck
命令。
git fsck --lost-found
This will output something like at the last line:
这将输出类似于最后一行的内容:
dangling commit xyz
We can check that it is the same commit using reflog
as suggested in other answers. Now we can do a git merge
我们可以检查它是否与reflog
其他答案中建议的提交相同。现在我们可以做一个git merge
git merge xyz
Note:
We cannot get the commit back with fsck
if we have already run a git gc
command which will remove the reference to the dangling commit.
注意:如果我们已经运行了一个命令来删除对悬空提交的引用,
我们将无法恢复提交。fsck
git gc