jpi*_*tel 13 git github git-merge
我有一个拉请求,Github说它无法自动合并.这个改变主要是一些提交,但没有冲突.
手动合并我没有任何冲突,我得到这个输出:
(on master)
$git merge otherbranch
[vim pops up for commit message, :wq]
Auto-merging <file>
Merge made by the 'recursive' strategy.
<file> | 1 +
1 file changed, 1 insertion(+)
Run Code Online (Sandbox Code Playgroud)
这就是为什么Github无法自动合并的原因?它无论如何都会从命令行自动合并.这对Github来说不够自动吗?
小智 13
原因是git merge默认情况下使用称为"递归"合并的策略.它能够执行3向合并:从一侧获取补丁,并将该补丁应用到另一侧,以生成新文件.它也是递归地执行此操作,在更复杂的情况下,已经发生了大量分支和合并,并且两个提交被合并有多个合并基础.
我最近遇到了同样的情况:
$ git merge-base --all 90d64557 05b3dd8f
711d1ad9772e42d64e5ecd592bee95fd63590b86
f303c59666877696feef62844cfbb7960d464fc1
$
Run Code Online (Sandbox Code Playgroud)
有2个合并基础,无法进行3向合并.因此,'递归'策略通过首先递归到这两个提交的合并来解决这个问题:
$ git merge-base 711d1ad9 f303c596
3f5db59435ffa4a453e5e82348f478547440e7eb
$
Run Code Online (Sandbox Code Playgroud)
好的,只有一个合并基础,因此可以开始3向合并.两边的变化是什么?
$ git diff --stat 3f5db594 711d1ad9
normalize/coll.py | 116 ++++++++++++++++++++++++++++++++++++++-----------
normalize/visitor.py | 49 ++++++++++-----------
tests/test_property.py | 10 +++--
3 files changed, 120 insertions(+), 55 deletions(-)
$ git diff --stat 3f5db594 f303c596
normalize/identity.py | 38 +++++++++++++++++++++++++++++++-------
tests/test_property.py | 2 ++
2 files changed, 33 insertions(+), 7 deletions(-)
$
Run Code Online (Sandbox Code Playgroud)
这两个差异都对同一个文件进行了更改,因此无法使用从每一侧获取每个文件的较新版本(索引合并)的简单策略来解析它们.相反,git从一侧获取新文件,并尝试从另一端应用补丁.结果是组合提交,可以像这样模拟:
$ git checkout -b tmp
Switched to a new branch 'tmp'
$ git reset --hard f303c59666877696feef62844cfbb7960d464fc1
HEAD is now at f303c59 record_id: throw a more helpful error if record identity is not hashable
$ git merge 711d1ad9772e42d64e5ecd592bee95fd63590b86
Auto-merging tests/test_property.py
Merge made by the 'recursive' strategy.
normalize/coll.py | 116 ++++++++++++++++++++++++++++++++++++++-----------
normalize/visitor.py | 49 ++++++++++-----------
tests/test_property.py | 10 +++--
3 files changed, 120 insertions(+), 55 deletions(-)
$ git diff --stat 3f5db594 HEAD tests/test_property.py
tests/test_property.py | 12 +++++++++---
1 file changed, 9 insertions(+), 3 deletions(-)
$
Run Code Online (Sandbox Code Playgroud)
然后使用此合并结果作为起点返回到原始的3向合并; 这也涉及对同一文件的更改:
$ git diff --stat HEAD 90d64557| grep selector
normalize/selector.py | 17 +--
tests/test_selector.py | 19 ++--
$ git diff --stat HEAD 05b3dd8f| grep selector
normalize/selector.py | 29 +++++++++++++++++------------
tests/test_selector.py | 9 +++++++++
$
Run Code Online (Sandbox Code Playgroud)
然而,更改是对文件的不同部分,因此取得差异并将其应用到另一侧是成功的.
所以,C git能够通过首先在两个起始点的两个合并基础上进行3向合并,然后在合并的两个原始提交上进行另一个3向合并以及中间结果来解析此合并.第一次合并.
Github的自动解决方案不会这样做.它不一定是无能为力的,而且我不确定它实施了多少递归策略,但它在谨慎方面犯了错误,这正是你所期望的那样的大绿色按钮:-).
不,这不是合并.它是关于重订基期.
你应该尝试在你的本地仓库(克隆你的叉子)otherbranch之上进行改造master.
首先,确保master是原始上游repo中最新的master:

cd /your/local/repo
git remote add upstream /url/original/repo
git fetch upstream
# Make sure you don't have any local commmit on your master
git branch -f master upstream/master # reset your master branch
# to the one from upstream repo
git checkout otherbranch
git rebase master
Run Code Online (Sandbox Code Playgroud)
该rebase将产生冲突,你应该解决,git add然后git rebase --continue.
最后,只需push --force将你的分支分支到你的分支:这将自动更新你的拉取请求(没有别的办法).
git push -u -f otherbranch origin
Run Code Online (Sandbox Code Playgroud)
(如果它已被推过一次,git push单独应该就够了)
| 归档时间: |
|
| 查看次数: |
12262 次 |
| 最近记录: |