在"git svn clone"之后,我仍然没有很棒的分支合并提交?

Dra*_*uan 3 git git-svn

在我做了git svn clone --stdlayout ...后,一切看起来都不错,我已经转换了远程分支.但是当git log --graph时,我没有看到任何分支合并图.这是正常的吗?

vad*_*hev 6

自从2008年夏天发布的1.5.0版以来,Subversion确实支持合并跟踪.Subversion将有关已执行合并的信息保存为在合并目标上设置的svn:mergeinfo属性,可以是分支目录,如^/trunk /,或任何其他目录.

Git和Subversion中的合并跟踪机制之间存在重大差异:

  1. 整个分支合并.

    当你在master分支上时,命令

    $ git merge some-branch
    
    Run Code Online (Sandbox Code Playgroud)

    导致合并提交,其第一个父级设置为master引用的提交 ,第二个父级设置为some-branch引用的提交(我不考虑此处的快进和冲突合并).

    对于混帐这意味着创建合并提交包括整个历史都的主人一些分支.

    当您检出^/trunk / branch到svn工作副本然后运行

    $ svn merge ^/branches/some-branch trunk-working-copy
    
    Run Code Online (Sandbox Code Playgroud)

    Subversion将在trunk-working-copy目录中设置svn:mergeinfo属性,如下所示:

    /branches/some-branch:10-20,30-40,50-60
    
    Run Code Online (Sandbox Code Playgroud)

    范围10-20,30-40,50-60包括那些尚未从^/branches/some-branch /(Subversion自动检测它们)合并到^/trunk / branch的修订版本.

    Mergeinfo属性只指定曾经合并到分支中的那些修订.并且由用户来检查所有这些合并的修订是否包括分支的整个历史.

  2. Cherry-pick合并.

    当您需要将来自单个提交的更改合并到分支中时,您将运行

    $ git cherry-pick bc347a8
    
    Run Code Online (Sandbox Code Playgroud)

    之后,git创建一个具有相应更改的提交,并将单个父级设置为之前由master分支引用的提交.

    也就是说,git不会为cherry-pick创建任何类型的合并提交.因此,git无法通过其图形结构跟踪樱桃选择的提交.

    与Subversion相反,它通过调整svn:mergeinfo属性来跟踪樱桃选择合并:

    $ svn merge -c100 ^/branches/some-branch trunk-working-copy
    
    Run Code Online (Sandbox Code Playgroud)

    这个命令很简单,它调整svn:mergeinfo如下:

    /branches/some-branch:100
    
    Run Code Online (Sandbox Code Playgroud)

    这意味着Subversion跟踪樱桃选择合并.

因此,您在翻译后不会进行合并提交.据我所知,git-svn在合并历史方面存在一些问题.

但作为subgit开发人员,我不得不说subgit应该正确处理合并跟踪信息.很可能在您的分支上设置的svn:mergeinfo属性不包括合并到它们的分支的整个历史记录.这是如何发生的:

  • 您使用过旧的svn客户端(<1.5),因此您的分支机构没有足够的合并跟踪信息.
  • 您已经执行了挑选并跳过了一些修订范围,从添加到svn:mergeinfo.
  • 你有svn:mergeinfo设置在不是分支目录的目录上,即它们不是^/trunk /,^/branches/some-branch等(对于标准布局).

要解决此问题,您必须找到合并跟踪信息的跳过部分并将其添加到分支中:

  1. 尝试查找尚未合并的修订版本:

    $ svn mergeinfo --show-revs eligible ^/branches/some-branch/@HEAD ^/trunk/@HEAD
    
    Run Code Online (Sandbox Code Playgroud)

    输出必须包括尚未从^/branches/some-branch /^/trunk /合并的所有修订版本.

  2. 尝试通过svn合并尚未合并的修订版.

    • 如果您认为所有更改都已合并,请使用svn merge命令的--record-only选项;
    • 如果您不太确定,最好执行正常的svn合并,这将应用所有缺失的更改.
  3. 使用subgit你也可以通过git方法合并,然后将创建的合并提交推送到subgit powered repository,这样它就会将这些合并提交转换为svn版本,并使用正确的svn:mergeinfo.

作为一个很好的奖励你可以参考与合并跟踪相关的SubGit规范,它有一些漂亮的图表,我已经在上面说过了.