如何从 git push -force 中恢复?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/12568628/
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 to recover from a git push -force?
提问by Brian
Here is what happened:
这是发生的事情:
I have two remote git branches: master
and feature1
. For some reason I have to use git push --force
for the feature1
branch, but I didn't know when I use git push --force
it will also push the master
branch. Then, a disaster happened, as I pushed my local master
branch to the remote repository.
我有两个远程 git 分支:master
和feature1
. 出于某种原因,我必须使用git push --force
的feature1
分支,但我不知道,当我使用git push --force
它也将推动master
分支。然后,当我将本地master
分支推送到远程存储库时,发生了灾难。
Luckily, my local branch is not too far away from the remote. Basically, my remote master
has two pull requests merged ahead of my local master
.
幸运的是,我的本地分支离远程不太远。基本上,我的遥控器master
在我的本地之前合并了两个拉取请求master
。
So my problem is: can I reopen the pull request and remerge? I noticed that there is commit version for merge request, so I am worried if I simply make new pull request it will mess up something? Ideally I just want to redo the merging of the two requests.
所以我的问题是:我可以重新打开拉取请求并重新合并吗?我注意到合并请求有提交版本,所以我担心如果我只是提出新的拉取请求,它会搞砸什么?理想情况下,我只想重做两个请求的合并。
Is there some other way to recover from this disaster? I learned the --force
is a really, really bad choice. :(
有没有其他方法可以从这场灾难中恢复过来?我了解到这--force
是一个非常非常糟糕的选择。:(
Update, example of what happened:
更新,发生的事情的例子:
I have following branches:
我有以下分支机构:
master
feature1
origin/master
origin/feature1
I integrate two pull requests by using the GitHub's Auto merge pull requests
. Then, I didn't fetch the master
branch on my local machine. Thus, I think my origin/master
is two versions behind the remote master.
我使用 GitHub 的Auto merge pull requests
. 然后,我没有master
在本地机器上获取分支。因此,我认为 myorigin/master
是远程 master 后面的两个版本。
Then I accidentally used git -f push
, which overwrote the remote branch and now I lost the commits from the pull requests on remote repository.
然后我不小心使用了git -f push
,它覆盖了远程分支,现在我丢失了远程存储库上拉取请求的提交。
How can I recover from it without messing up other contributors' history?
如何在不弄乱其他贡献者的历史记录的情况下从中恢复?
回答by user4815162342
You can always restore the previously observed state of master
, by resetting to the old commit and issuing another push -f
. The steps involved typically look like this:
您始终可以master
通过重置为旧提交并发出另一个push -f
. 涉及的步骤通常如下所示:
# work on local master
git checkout master
# reset to the previous state of origin/master, as recorded by reflog
git reset --hard origin/master@{1}
# at this point verify that this is indeed the desired commit.
# (if necessary, use git reflog to find the right one, and
# git reset --hard to that one)
# finally, push the master branch (and only the master branch) to the server
git push -f origin master
Note, however, that this restores remote master
to the state most recently retrieved by git fetch
or equivalent. Any commits pushed by others after the last time you fetched will be lost. However, those commits will still be available in theirreflogs, so they can restore them using steps like the above.
但是请注意,这会将 remote 恢复master
到最近由git fetch
或等效物检索到的状态。在您上次获取之后由其他人推送的任何提交都将丢失。但是,这些提交仍将在其reflog 中可用,因此他们可以使用上述步骤恢复它们。
回答by GHugo
Note that, with Github, you can use the API to recover a forced push even if you do not have the repository cloned locally (i.e., when you do not have a reflog), or the commit sha.
请注意,使用Github,即使您没有在本地克隆存储库(即,当您没有 reflog 时)或提交 sha,您也可以使用 API 来恢复强制推送。
First, you must get the previous commit sha, the one before the forced push:
首先,您必须获得之前的提交 sha,即强制推送之前的那个:
curl -u <username> https://api.github.com/repos/:owner/:repo/events
Then you can create a branch from this sha:
然后你可以从这个 sha 创建一个分支:
curl -u <github-username> -X POST -d '{"ref":"refs/heads/<new-branch-name>", "sha":"<sha-from-step-1>"}' https://api.github.com/repos/:owner/:repo/git/refs
Finally, you can clone the repository locally, and force push again to master:
最后,您可以在本地克隆存储库,并再次强制推送到 master:
git clone repo@github
git checkout master
git reset --hard origin/<new-branch-name>
git push -f origin master
Note that with two-factor authentication, you need to provide a token (see herefor more information).
请注意,使用双因素身份验证时,您需要提供令牌(有关更多信息,请参见此处)。
Credit: Sankara Rameswaran
图片来源:Sankara Rameswaran