【问题标题】:How do I reset the git master branch to the upstream branch in a forked repository?如何将 git master 分支重置为分叉存储库中的上游分支?
【发布时间】:2017-02-19 20:55:25
【问题描述】:

我已经完全搞砸了我的分叉 git repo 的 master 分支。

我想用上游主仓库的内容完全重置推送到我的分支的主分支。我没有兴趣保留任何主分支更改或历史记录。

最简单的方法是从上游项目中删除我的分叉 repo 和 refork。但是,我在其他推送的分支中有工作,我不想失去。

那么我如何用上游的 master 重置我推送的 master 分支?


git clone https://myrepo.git
cd myrepo
git remote add upstream https://upstream.git
git fetch upstream

从这里到哪里去重置我的本地和远程 master 分支与上游 master?

【问题讨论】:

    标签: git


    【解决方案1】:

    您可以将本地主分支重置为上游版本并将其推送到您的原始存储库。

    假设“upstream”是原始存储库,“origin”是您的 fork:

    # ensures current branch is master
    git checkout master
    
    # pulls all new commits made to upstream/master
    git pull upstream master
    
    # this will delete all your local changes to master
    git reset --hard upstream/master
    
    # take care, this will delete all your changes on your forked master
    git push origin master --force
    

    (您可以使用git remote add upstream /url/to/original/repo 将原始存储库定义为“上游”。)

    【讨论】:

    • 也应该是git reset --hard upstream/master 来重置工作目录。不过你的答案是正确的。
    • 不使用“--hard”在保持本地更改的同时也有效。我会分步进行硬重置,以检查差异。
    • 需要先致电git fetch upstream
    • 正如@HenryE 所指出的,如果无法首先使用git fetch upstream 获取上游更改,通常会产生以下非人类可读错误:"fatal: ambiguous argument 'upstream/master': unknown revision or path not in the working tree."
    • 请注意强制推送会自动关闭您为上游所做的所有打开的拉取请求。我没有意识到这一点,这有点令人惊讶。
    【解决方案2】:

    这会将您的 master 分支重置为上游 master,如果分支在您的分叉后已更新,它也会拉取这些更改。

    git checkout master 
    git reset upstream/master
    git pull --rebase upstream master
    git push origin master --force
    

    PS:假设 Upstream 是原始仓库,而 origin 是您的副本。

    【讨论】:

    • 看起来好像你是从不同的提交中创建了你的分支。变基的主要原因是保持线性项目历史。也就是说,一旦将提交发布到公共存储库,您就永远不应该对其进行变基,因为这会将旧提交替换为新提交。详情请见atlassian.com/git/tutorials/rewriting-history/git-rebase
    【解决方案3】:
    git reset --hard @{upstream}
    

    或者,更短:

    git reset --hard @{u}
    

    或者您甚至可以更进一步,设置一个别名,让您只需键入git scrub

    git config --global alias.scrub 'reset --hard @{upstream}'
    

    (这假设您的分支配置为跟踪相应的远程分支,除非您正在做一些特殊的事情,否则通常是这样。有关跟踪的更多详细信息,请参阅git-branch(1),有关分支规范语法的详细信息,请参阅git-rev-parse(1) .)

    然后你只需 git push --force 到你的叉子,如其他答案中所述。

    【讨论】:

      【解决方案4】:

      我试过这样的方法:

      $REPO=<repo>
      $ORIGIN=<user>/$REPO
      $UPSTREAM=<upstream>/$REPO
      
      $ git clone git@github.com:$ORIGIN.git
      $ cd $REPO
      $ git checkout master
      $ git remote add upstream git@github.com:$UPSTREAM.git
      $ git reset --hard upstream/master
      $ git pull --rebase upstream master
      $ git push origin master --force
      

      输出将显示警告:

      fatal: ambiguous argument 'upstream/master': 
      unknown revision or path not in the working tree.
      Use '--' to separate paths from revisions, like this:
      'git <command> [<revision>...] -- [<file>...]'
      

      所以正确的做法是把git pull放在git reset之前:

      $ git clone git@github.com:$ORIGIN.git
      $ cd $REPO
      $ git checkout master
      $ git remote add upstream git@github.com:$UPSTREAM.git
      $ git pull --rebase upstream master
      $ git reset --hard upstream/master
      $ git push origin master --force
      

      那么输出将是这样的:

      From github.com:<upstream>/<repo>
       * branch                master     -> FETCH_HEAD
       * [new branch]          master     -> upstream/master
      HEAD is now at 7a94b1790 Merge pull request #4237 from <upstream>/...
      Current branch master is up to date.
      Everything up-to-date.
      

      【讨论】:

        猜你喜欢
        • 2022-11-09
        • 2014-06-20
        • 2021-01-27
        • 2017-04-05
        • 2011-02-15
        • 2016-09-19
        • 2015-04-22
        • 2016-04-30
        相关资源
        最近更新 更多