Git and GitHub concepts: Reviewing updated pull requests locally

谁说胖子不能爱 提交于 2019-12-04 06:33:02

问题


I follow the generic OSS structure:

  1. the OSS' remote repository hosted on GitHub
  2. a fork of the OSS remote repository to my own remote repository
  3. a clone of the fork on my remote repository to create a local repository

Thus, a contributor would create a new branch locally, push the changes to his/her remote repository, and then open a pull request to the OSS' remote repository.

This has been working well. However, the main issue comes when I try to review another contributor's pull request by fiddling with it locally.

So I have fetched a pull request made to the OSS' remote repository using this command:

git fetch upstream pull/<PR#>/head:<branchName>

followed by git checkout <branchName>

and it was successful. I played around with the PR, and reviewed it on GitHub. Then, the contributor updated the PR by pushing new commits to their branch (on their remote repo), which was automatically reflected in the PR.

Now, I want to be able to get the updates locally so that I can try the changes again. I understand that my copy of the PR branch does not track the remote branch by default, so I tried to set it to track the PR:

git branch --set-upstream upstream/pull/<PR#>/head:<branchName>

like how I have done when I first fetched the branch. However, I got the response that

error: the requested upstream branch 'pull//head:' does not exist

I tried again with:

git branch --set-upstream-to upstream/pull/<PR#>/head:<branchName>

which also failed with the same error.

Then, I thought, is it because a PR is like a 'reflection' of the branch on someone's remote repository, so if I want to track an upstream branch I should track from the person's remote repository?

So I added the contributors' remote repository as a remote, and tried again:

git branch --set-upstream-to <newRemote> <branchName>

and I still faced the same error.

I did some Googling, and I found this, but I do not want to get all the pull requests. I also found links like this one but nope, not the help that I need there.

Can anyone point out what is wrong with the way that I am doing things now? Thanks!

Edit: Is there an easier way to do things aside from what has been proposed by Marina Liu - MSFT below?


回答1:


You can use any of below options to update the PR in local repo.

Option 1: delete the local source branch and recreate to get the update

As you use the commands to get the source branch of the PR locally:

git fetch upstream pull/<PR#>/head:<branchName>
git checkout <branchname>

If the PR is updated (new commits are pushed to the fork repo), you can delete and recreate by:

git checkout master
git branch -D <branchname>
git fetch upstream pull/<PR#>/head:<branchName>
git checkout <branchname>

Option 2: add the fork repo as a remote for your local repo

You can add the fork repo as a remote for your local repo by

git remote add fork1 <URL for the fork repo> -f

Then you can create a local branch for the PR source branch by

git checkout -b <branchname> fork1/<branchname>

If the PR has been updated, you just need to execute below commands to get the update:

git fetch fork1
git checkout <branchname> #If HEAD is not on the <branchname>
git reset --hard fork1/<branchname>



回答2:


The problem—or at least the first one—here is that you cannot use an upstream to refer to a GitHub pull request reference.

In Git, an upstream on a branch consists of two parts:

  • The name of a remote, such as origin
  • The name of a branch on that remote, such as master

Git puts these two together to get refs/heads/master—this is the name on the remote—then runs this string through the fetch setting(s) for the remote. The standard fetch setting for the remote named origin is +refs/heads/*:refs/remotes/origin/*, so if the upstream is currently set to the pair <origin, master>, the name that Git looks up in your own repository is refs/remotes/origin/master, which is your remote-tracking name for their master.

Note the assumption in here that the name on the remote begins with refs/heads/.

The actual name of a pull reference on GitHub begins with refs/pull/, not refs/heads/, so that the full name of the commit you want for pull request #123 is refs/pull/123/head. There is no way to spell this that starts with refs/heads/ because this is not a branch name.

Now, you can—as suggested in your first link—add an extra fetch setting:

[remote "origin"]
    fetch = +refs/heads/*:refs/remotes/origin/*
    fetch = +refs/pull/*/head:refs/remotes/origin/pr/*

which causes their refs/pull/123/head to associate with your refs/remotes/origin/pr/123. Depending on your particular Git version, some of this sometimes or even mostly works. Some Git versions get rather confused at times. If you try it and it works for you, that's great, just be prepared to clean up a bit of a mess if you upgrade or downgrade Git versions for some reason.

The aliases found via your second link are better. These fetch from one specific pull request, creating a local branch name (or overwriting it if it already exists—this is a bit dangerous but as long as you don't name your own branches pr/integer you will be fine). You could improve them, writing a real git-pr script that creates a local branch—be sure to use the full name format, refs/heads/pr/number, to guarantee correctness—and sets some additional information so that, when you are on that branch, git pr updates the branch automatically.

(If I get some spare time, I might write my own script, because this would be pretty handy.)



来源:https://stackoverflow.com/questions/49767697/git-and-github-concepts-reviewing-updated-pull-requests-locally

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!