git 如何更新 GitHub 分叉存储库?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/7244321/
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

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-10 11:44:26  来源:igfitidea点击:

How do I update a GitHub forked repository?

gitgithubpull-requestgit-fork

提问by Lea Hayes

I recently forked a project and applied several fixes. I then created a pull request which was then accepted.

我最近分叉了一个项目并应用了几个修复程序。然后我创建了一个 pull request,然后它被接受了。

A few days later another change was made by another contributor. So my fork doesn't contain that change.

几天后,另一位贡献者进行了另一项更改。所以我的叉子不包含那个变化。

How can I get that change into my fork? Do I need to delete and re-create my fork when I have further changes to contribute? Or is there an update button?

我怎样才能把那个零钱放到我的叉子里?当我有进一步的更改要贡献时,是否需要删除并重新创建我的分叉?或者有更新按钮吗?

回答by Mark Longair

In your local clone of your forked repository, you can add the original GitHub repository as a "remote". ("Remotes" are like nicknames for the URLs of repositories - originis one, for example.) Then you can fetch all the branches from that upstream repository, and rebase your work to continue working on the upstream version. In terms of commands that might look like:

在分叉存储库的本地克隆中,您可以将原始 GitHub 存储库添加为“远程”。(“远程”就像存储库 URL 的昵称 -origin例如,是一个。)然后您可以从该上游存储库中获取所有分支,并重新设置您的工作以继续在上游版本上工作。就可能如下所示的命令而言:

# Add the remote, call it "upstream":

git remote add upstream https://github.com/whoever/whatever.git

# Fetch all the branches of that remote into remote-tracking branches,
# such as upstream/master:

git fetch upstream

# Make sure that you're on your master branch:

git checkout master

# Rewrite your master branch so that any commits of yours that
# aren't already in upstream/master are replayed on top of that
# other branch:

git rebase upstream/master

If you don't want to rewrite the history of your master branch, (for example because other people may have cloned it) then you should replace the last command with git merge upstream/master. However, for making further pull requests that are as clean as possible, it's probably better to rebase.

如果您不想重写 master 分支的历史记录(例如因为其他人可能已经克隆了它),那么您应该将最后一个命令替换为git merge upstream/master. 但是,为了进一步发出尽可能干净的拉取请求,最好重新设置基础。



If you've rebased your branch onto upstream/masteryou may need to force the push in order to push it to your own forked repository on GitHub. You'd do that with:

如果你已经将你的分支重新建立在upstream/master你的基础上,你可能需要强制推送以便将它推送到你自己在 GitHub 上的分叉存储库。你会这样做:

git push -f origin master

You only need to use the -fthe first time after you've rebased.

您只需要-f在重新定位后第一次使用。

回答by lobzik

Starting in May 2014, it is possible to update a fork directly from GitHub. This still works as of September 2017, BUTit will lead to a dirty commit history.

从 2014 年 5 月开始,可以直接从 GitHub 更新分叉。这在 2017 年 9 月仍然有效,它会导致脏提交历史。

  1. Open your fork on GitHub.
  2. Click on Pull Requests.
  3. Click on New Pull Request. By default, GitHub will compare the original with your fork, and there shouldn't be anything to compare if you didn't make any changes.
  4. Click switching the baseif you see that link. Otherwise, manually set the base forkdrop down to your fork, and the head forkto the upstream. Now GitHub will compare your fork with the original, and you should see all the latest changes. enter image description here
  5. Create pull requestand assign a predictable name to your pull request (e.g., Update from original).
  6. Scroll down to Merge pull request, but don't click anything yet.
  1. 在 GitHub 上打开您的分叉。
  2. 单击Pull Requests
  3. 单击New Pull Request。默认情况下,GitHub 会将原始文件与您的 fork 进行比较,如果您没有进行任何更改,则不应有任何可比较的内容。
  4. switching the base如果您看到该链接,请单击。否则,手动设置base fork下拉到你的叉子,然后设置head fork到上游。现在 GitHub 会将您的 fork 与原始版本进行比较,您应该会看到所有最新的更改。 在此处输入图片说明
  5. Create pull request并为您的拉取请求指定一个可预测的名称(例如,Update from original)。
  6. 向下滚动到Merge pull request,但不要单击任何内容。

Now you have three options, but each will lead to a less-than-clean commit history.

现在您有三个选项,但每个选项都会导致不完整的提交历史。

  1. The default will create an ugly merge commit.
  2. If you click the dropdown and choose "Squash and merge", all intervening commits will be squashed into one. This is most often something you don't want.
  3. If you click Rebase and merge, all commits will be made "with" you, the original PRs will link to your PR, and GitHub will display This branch is X commits ahead, Y commits behind <original fork>.
  1. 默认将创建一个丑陋的合并提交。
  2. 如果您单击下拉列表并选择“压缩并合并”,则所有中间提交都将被压缩为一个。这通常是您不想要的。
  3. 如果您单击Rebase and merge,所有提交都将“与”您一起进行,原始 PR 将链接到您的 PR,并且 GitHub 将显示This branch is X commits ahead, Y commits behind <original fork>

So yes, you can keep your repo updated with its upstream using the GitHub web UI, but doing so will sully your commit history. Stick to the command lineinstead - it's easy.

所以是的,您可以使用 GitHub Web UI 更新您的存储库及其上游,但这样做会破坏您的提交历史。坚持使用命令行- 这很容易。

回答by jumpnett

Here is GitHub's official document on Syncing a fork:

这是 GitHub 上关于同步叉的官方文档:

Syncing a fork

The Setup

Before you can sync, you need to add a remote that points to the upstream repository. You may have done this when you originally forked.

Tip: Syncing your fork only updates your local copy of the repository; it does not update your repository on GitHub.

$ git remote -v
# List the current remotes
origin  https://github.com/user/repo.git (fetch)
origin  https://github.com/user/repo.git (push)

$ git remote add upstream https://github.com/otheruser/repo.git
# Set a new remote

$ git remote -v
# Verify new remote
origin    https://github.com/user/repo.git (fetch)
origin    https://github.com/user/repo.git (push)
upstream  https://github.com/otheruser/repo.git (fetch)
upstream  https://github.com/otheruser/repo.git (push)

Syncing

There are two steps required to sync your repository with the upstream: first you must fetch from the remote, then you must merge the desired branch into your local branch.

Fetching

Fetching from the remote repository will bring in its branches and their respective commits. These are stored in your local repository under special branches.

$ git fetch upstream
# Grab the upstream remote's branches
remote: Counting objects: 75, done.
remote: Compressing objects: 100% (53/53), done.
remote: Total 62 (delta 27), reused 44 (delta 9)
Unpacking objects: 100% (62/62), done.
From https://github.com/otheruser/repo
 * [new branch]      master     -> upstream/master

We now have the upstream's master branch stored in a local branch, upstream/master

$ git branch -va
# List all local and remote-tracking branches
* master                  a422352 My local commit
  remotes/origin/HEAD     -> origin/master
  remotes/origin/master   a422352 My local commit
  remotes/upstream/master 5fdff0f Some upstream commit

Merging

Now that we have fetched the upstream repository, we want to merge its changes into our local branch. This will bring that branch into sync with the upstream, without losing our local changes.

$ git checkout master
# Check out our local master branch
Switched to branch 'master'

$ git merge upstream/master
# Merge upstream's master into our own
Updating a422352..5fdff0f
Fast-forward
 README                    |    9 -------
 README.md                 |    7 ++++++
 2 files changed, 7 insertions(+), 9 deletions(-)
 delete mode 100644 README
 create mode 100644 README.md

If your local branch didn't have any unique commits, git will instead perform a "fast-forward":

$ git merge upstream/master
Updating 34e91da..16c56ad
Fast-forward
 README.md                 |    5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

Tip: If you want to update your repository on GitHub, follow the instructions here

同步分叉

设置

在同步之前,您需要添加一个指向上游存储库的远程。您最初分叉时可能已经这样做了。

提示:同步您的 fork 只会更新您的本地存储库副本;它不会更新您在 GitHub 上的存储库。

$ git remote -v
# List the current remotes
origin  https://github.com/user/repo.git (fetch)
origin  https://github.com/user/repo.git (push)

$ git remote add upstream https://github.com/otheruser/repo.git
# Set a new remote

$ git remote -v
# Verify new remote
origin    https://github.com/user/repo.git (fetch)
origin    https://github.com/user/repo.git (push)
upstream  https://github.com/otheruser/repo.git (fetch)
upstream  https://github.com/otheruser/repo.git (push)

同步

将您的存储库与上游同步需要两个步骤:首先您必须从远程获取,然后您必须将所需的分支合并到您的本地分支中。

获取

从远程存储库获取将引入其分支及其各自的提交。这些存储在您的本地存储库中的特殊分支下。

$ git fetch upstream
# Grab the upstream remote's branches
remote: Counting objects: 75, done.
remote: Compressing objects: 100% (53/53), done.
remote: Total 62 (delta 27), reused 44 (delta 9)
Unpacking objects: 100% (62/62), done.
From https://github.com/otheruser/repo
 * [new branch]      master     -> upstream/master

我们现在将上游的 master 分支存储在本地分支中,upstream/master

$ git branch -va
# List all local and remote-tracking branches
* master                  a422352 My local commit
  remotes/origin/HEAD     -> origin/master
  remotes/origin/master   a422352 My local commit
  remotes/upstream/master 5fdff0f Some upstream commit

合并

现在我们已经获取了上游存储库,我们希望将其更改合并到我们的本地分支中。这将使该分支与上游同步,而不会丢失我们的本地更改。

$ git checkout master
# Check out our local master branch
Switched to branch 'master'

$ git merge upstream/master
# Merge upstream's master into our own
Updating a422352..5fdff0f
Fast-forward
 README                    |    9 -------
 README.md                 |    7 ++++++
 2 files changed, 7 insertions(+), 9 deletions(-)
 delete mode 100644 README
 create mode 100644 README.md

如果您的本地分支没有任何独特的提交,git 将改为执行“快进”:

$ git merge upstream/master
Updating 34e91da..16c56ad
Fast-forward
 README.md                 |    5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

提示:如果您想更新 GitHub 上的存储库,请按照此处的说明进行操作

回答by Sahar Rabinoviz

A lot of answers end up moving your fork one commit aheadof the parent repository. This answer summarizes the steps found herewhich will move your fork to the same commit as the parent.

许多答案最终会将您的 fork 移动到父存储库之前一次提交。此答案总结了此处找到的步骤这些步骤会将您的 fork 移动到与 parent 相同的提交

  1. Change directory to your local repository.

    • Switch to master branch if you are not git checkout master
  2. Add the parent as a remote repository, git remote add upstream <repo-location>

  3. Issue git fetch upstream
  4. Issue git rebase upstream/master

    • At this stage you check that commits what will be merged by typing git status
  5. Issue git push origin master

  1. 将目录更改为本地存储库。

    • 如果不是,请切换到 master 分支 git checkout master
  2. 将父级添加为远程存储库, git remote add upstream <repo-location>

  3. 问题 git fetch upstream
  4. 问题 git rebase upstream/master

    • 在此阶段,您检查是否提交了将通过键入合并的内容 git status
  5. 问题 git push origin master

For more information about these commands, refer to step 3.

有关这些命令的更多信息,请参阅步骤 3

回答by Benny Neugebauer

Foreword:Your fork is the "origin" and the repository you forked from is the "upstream".

前言:你的fork是“源头”,你fork的仓库是“上游”。

Let's assume that you cloned already your fork to your computer with a command like this:

假设您已经使用如下命令将 fork 克隆到您的计算机:

git clone [email protected]:your_name/project_name.git
cd project_name

If that is given then you need to continue in this order:

如果给出,那么您需要按以下顺序继续:

  1. Add the "upstream" to your cloned repository ("origin"):

    git remote add upstream [email protected]:original_author/project_name.git
    
  2. Fetch the commits (and branches) from the "upstream":

    git fetch upstream
    
  3. Switch to the "master" branch of your fork ("origin"):

    git checkout master
    
  4. Stash the changes of your "master" branch:

    git stash
    
  5. Merge the changes from the "master" branch of the "upstream" into your the "master" branch of your "origin":

    git merge upstream/master
    
  6. Resolve merge conflicts if any and commit your merge

    git commit -am "Merged from upstream"
    
  7. Push the changes to your fork

    git push
    
  8. Get back your stashed changes (if any)

    git stash pop
    
  9. You're done! Congratulations!

  1. 将“上游”添加到您克隆的存储库(“来源”):

    git remote add upstream [email protected]:original_author/project_name.git
    
  2. 从“上游”获取提交(和分支):

    git fetch upstream
    
  3. 切换到 fork 的“master”分支(“origin”):

    git checkout master
    
  4. 隐藏你的“主”分支的变化:

    git stash
    
  5. 将来自“上游”的“主”分支的更改合并到“源”的“主”分支中:

    git merge upstream/master
    
  6. 解决合并冲突(如果有)并提交合并

    git commit -am "Merged from upstream"
    
  7. 将更改推送到您的 fork

    git push
    
  8. 取回您隐藏的更改(如果有)

    git stash pop
    
  9. 你完成了!恭喜!

GitHub also provides instructions for this topic: Syncing a fork

GitHub 还提供了有关此主题的说明:Syncing a fork

回答by Slion

If, like me, you never commit anything directly to master, which you should really, you can do the following.

如果像我一样,你从不直接向 master 提交任何东西,你真的应该这样做,你可以执行以下操作。

From the local clone of your fork, create your upstream remote. You only need to do that once:

从你的 fork 的本地克隆,创建你的上游远程。你只需要这样做一次:

git remote add upstream https://github.com/whoever/whatever.git

Then whenever you want to catch up with the upstream repository master branch you need to:

然后,每当您想赶上上游存储库主分支时,您都需要:

git checkout master
git pull upstream master

Assuming you never committed anything on master yourself you should be done already. Now you can push your local master to your origin remote GitHub fork. You could also rebase your development branch on your now up-to-date local master.

假设你从来没有对主人自己做过任何事情,你应该已经完成​​了。现在您可以将您的本地 master 推送到您的 origin 远程 GitHub fork。您还可以在您现在最新的本地 master 上重新建立您的开发分支。

Past the initial upstream setup and master checkout, all you need to do is run the following command to sync your master with upstream: git pull upstream master.

在初始上游设置和主检出之后,您需要做的就是运行以下命令以将您的主与上游同步:git pull upstream master

回答by isedwards

Since November 2013 there has been an unofficial feature request open with GitHub to ask them to add a very simple and intuitive method to keep a local fork in sync with upstream:

自 2013 年 11 月以来,GitHub 公开了一个非官方的功能请求,要求他们添加一个非常简单直观的方法来保持本地分叉与上游同步:

https://github.com/isaacs/github/issues/121

https://github.com/isaacs/github/issues/121

Note: Since the feature request is unofficial it is also advisable to contact [email protected]to add your support for a feature like this to be implemented. The unofficial feature request above could be used as evidence of the amount of interest in this being implemented.

注意:由于功能请求是非官方的,因此建议您联系[email protected]以添加您对要实现的此类功能的支持。上面的非官方功能请求可以用作对此正在实施的兴趣量的证据。

回答by Lucero

As of the date of this answer, GitHub has not (or shall I say no longer?) this feature in the web interface. You can, however, ask [email protected]to add your vote for that.

截至本回答发布之日,GitHub 还没有(或者我应该不再说?)Web 界面中的此功能。但是,您可以要求[email protected]为此添加您的投票。

In the meantime, GitHub user bardiharborow has created a tool to do just this:https://upriver.github.io/

与此同时,GitHub 用户 bardiharborow 创建了一个工具来做到这一点:https ://upiver.github.io/

Source is here: https://github.com/upriver/upriver.github.io

来源在这里:https: //github.com/upiver/upiver.github.io

回答by Shital Shah

If you are using GitHub for Windows or Mac then now they have a one-click feature to update forks:

如果你在 Windows 或 Mac 上使用 GitHub,那么现在他们有一个一键式功能来更新分叉:

  1. Select the repository in the UI.
  2. Click "Update from user/branch" button the top.
  1. 在 UI 中选择存储库。
  2. 单击顶部的“从用户/分支更新”按钮。

回答by max630

Actually, it is possible to create a branch in your fork from any commit of the upstream in the browser:

实际上,可以从浏览器中上游的任何提交在您的分支中创建一个分支:

Enter image description here

在此处输入图片说明

You can then fetch that branch to your local clone, and you won't have to push all that data back to GitHub when you push edits on top of that commit. Or use the web interface to change something in that branch.

然后,您可以将该分支提取到您的本地克隆,并且当您在该提交之上推送编辑时,您不必将所有数据推送回 GitHub。或者使用 Web 界面更改该分支中的某些内容。

How it works (it is a guess, I don't know how exactly GitHub does it): forks share object storage and use namespacesto separate users' references. So you can access all commits through your fork, even if they did not exist by the time of forking.

它是如何工作的(这是一个猜测,我不知道 GitHub 到底是怎么做的):fork 共享对象存储并使用命名空间来分隔用户的引用。所以你可以通过你的分叉访问所有提交,即使它们在分叉时不存在。