简体   繁体   English

如何正确同步主 git 分支、远程分支和本地分支?

[英]How to properly sync main git branch, remote branch and local branch?

We use github for tracking our code.我们使用 github 来跟踪我们的代码。 Each developer creates a remote branch from the main branch and a local branch from the remote branch.每个开发人员从主分支创建一个远程分支,从远程分支创建一个本地分支。

Let's say the main branch is A, the remote branch is B, and the local branch is C.假设主分支是 A,远程分支是 B,本地分支是 C。

Let's say a file README has just one line in it:假设一个文件 README 中只有一行:

LineX

At the beginning, this file has the same contents on all three branches.一开始,这个文件在所有三个分支上都有相同的内容。

Let's say I add one line into this file in my local branch.假设我在本地分支的这个文件中添加了一行。

LineX
LineY

Meanwhile, someone added another line on branch A and committed it.同时,有人在分支 A 上添加了另一行并提交了它。

LineX
LineZ

Here is how the contents would look at that point:以下是内容在这一点上的样子:

Branch A:
   LineX
   LineZ

Branch B:
   LineX

Branch C:
   LineX
   LineY

I need to pull the changes from Branch A into C so that my local content would become:我需要将分支 A 中的更改拉入 C 以便我的本地内容变为:

LineX
LineY
LineZ

Also, I feel Branch B must be synced with A. Otherwise, my code review will show two lines of changes instead of one line.另外,我觉得 B 分支必须与 A 同步。否则,我的代码审查将显示两行更改而不是一行。

I am wondering what is the proper way to do this.我想知道这样做的正确方法是什么。 Thanks.谢谢。

If there is no commit history in branch C when branch A into branch C如果分支 A 进入分支 C 时分支 C 中没有提交历史

$ checkout Branch_A 
$ pull Branch_A 
$ checkout Branch_C
$ merge Branch_A

branch C becomes as follow like this.分支 C 如下所示。

LineX
LineZ

In this case, compare the branches before working (git diff) You need to check which commit was made through the git log.在这种情况下,在工作之前比较分支(git diff)您需要通过 git 日志检查哪个提交。

tl;dr: Instead of syncing B with A , you'll be syncing B with C , and then doing a Pull Request from B to A which will show only the new changes you made on your local branch C . tl; dr:您将BA同步,而不是将BC同步,然后从BA执行拉取请求,这将仅显示您在本地分支C上所做的新更改。

Details:细节:

Although you can do this:虽然你可以这样做:

We use github for tracking our code.我们使用 github 来跟踪我们的代码。 Each developer creates a remote branch from the main branch and a local branch from the remote branch.每个开发人员从主分支创建一个远程分支,从远程分支创建一个本地分支。

the far more common way is to not worry about the remote branch until you are ready to do a code review or Pull Request (ie share your code).更常见的方法是在您准备好进行代码审查或拉取请求(即共享您的代码)之前不要担心远程分支。 Each developer initially only needs to think about main ("Branch A" in your example), and their local my-feature branch ("Branch C" in your example).每个开发人员最初只需要考虑main (在您的示例中为“Branch A”)和他们的本地my-feature分支(在您的示例中为“Branch C”)。 The local branch is created from the remote main branch.本地分支是从远程主分支创建的。

Let's call your remote origin .让我们调用您的远程origin To begin working on something new:开始研究新事物:

# Get the latest copy of the remote main branch:
git fetch

# Create a new local branch starting from main
git switch -c my-feature origin/main --no-track

# or the older syntax using checkout instead of switch
git checkout -b my-feature origin/main --no-track

At this point my-feature will be equivalent to the remote version of main .此时my-feature将等同于main的远程版本。 Note you don't even need to have a local branch main checked out, possibly ever!请注意,您甚至可能永远不需要签出本地分支main

When it's time to update your feature branch with new contents on main you can either rebase or merge:当需要使用main上的新内容更新功能分支时,您可以变基或合并:

# update my-feature from latest main via rebase
git fetch
git rebase origin/main my-feature

# or update my-feature from latest main via merge
git switch my-feature
git fetch
git merge origin/main

Tip: if you have already pushed my-feature and then you rebase it, the next push will need to be a force push.提示:如果你已经推送my-feature然后你 rebase 它,下一次推送需要强制推送。 This won't be necessary if you merge instead.如果您改为合并,这将不是必需的。 Your repo admin should be able to provide guidance on whether force pushing feature branches is encouraged/discouraged.您的 repo 管理员应该能够就是否鼓励/不鼓励强制推送功能分支提供指导。

Note it's at this regular updating step (merge or rebase) that you would achieve your example of:请注意,您将在此常规更新步骤(合并或变基)中实现以下示例:

LineX
LineY
LineZ

Since the lines are next to each other you would have conflicts, and during conflict resolution you would accept both lines from each side to yield the desired result.由于这些线彼此相邻,因此您会遇到冲突,并且在解决冲突期间,您将接受来自每一侧的两条线以产生所需的结果。 If the lines were in different parts of the file the merge or rebase would like finish cleanly without conflicts.如果这些行位于文件的不同部分,则合并或变基希望干净地完成而不会发生冲突。

Once you are ready to create a Pull Request or do a code review, or collaborate with someone so they can see your branch, you need to push your branch to create its remote counterpart ("Branch B" in your example).一旦您准备好创建拉取请求或进行代码审查,或与某人合作以便他们可以看到您的分支,您需要推送您的分支以创建其远程副本(在您的示例中为“Branch B”)。

# the first time you push, set up to track it
git push -u origin my-feature

# any subsequent pushes:
git push

Note the PR gets setup on GitHub from my-feature to main .请注意 PR 在 GitHub 上从my-feature设置到main From a developer's (recently fetched) local machine, this is equivalent to origin/my-feature to origin/main , or in your example, PR'ing B into A .从开发人员的(最近获取的)本地机器上,这相当于origin/my-featureorigin/main ,或者在您的示例中,PR'ing B into A Developers typically make their changes on their local branch C and continuously update its remote tracking branch B by pushing.开发人员通常在其本地分支C上进行更改,并通过推送不断更新其远程跟踪分支B

Side Note: The wording of your first paragraph kind of implies that you already have this process setup and have been using it.旁注:您第一段的措辞暗示您已经拥有此流程设置并一直在使用它。 If you want to avoid changing that process it's fine, as it's compatible with the rest of what's described in this answer.如果您想避免更改该过程,那很好,因为它与此答案中描述的 rest 兼容。 The initial creation of the remote branch doesn't really hurt anything.远程分支的初始创建并没有真正伤害任何东西。 Although unconventional, if nothing else its existence could signal to other developers that you started working on something.虽然非常规,但它的存在可能会向其他开发人员发出信号,表明您开始从事某项工作。 The only difference would be instead of creating a new local branch from origin/main , you would instead:唯一的区别是不是从origin/main创建一个新的本地分支,而是:

# on Github, create my-feature from main, and then locally:
git fetch

# checkout a local copy of my-feature
git switch my-feature

# or the older syntax using checkout instead of switch
git checkout my-feature

Everything else would be the same as above, except you wouldn't need to set up the remote tracking branch with push -u .其他一切都与上面相同,除了您不需要使用push -u设置远程跟踪分支。 You would simply use git push to update your branch.您只需使用git push更新您的分支。 (Or, git push --force-with-lease if you're rebasing onto a newer origin/main .) (或者, git push --force-with-lease如果您要重新定位到较新的origin/main 。)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM