亲爱的博士,
你在比较苹果和橙子。git-submodules类似于svn:externals,也就是svn-submodules。事实上,当您使用-r
将svn子模块附加到特定版本时,行为几乎相同。要使用svn-submodules进行提交,您必须分别在每个子模块目录中进行提交,就像使用git-submodules一样。
然而有一个很大的区别:大多数开发人员,在开发的某个阶段都喜欢连接到每个子模块的分支,而这在git-submodules中不被支持。这对于协调开发非常有用。(谷歌的Repo工具是Git的包装器,旨在与Gerrit(一种代码审查工具)一起使用,有点类似。但请相信我:远离Repo。它解决了不同的问题。)巨大的缺点是您无法恢复代码库的确切轮廓。这似乎还好,但我听说过一些可怕的故事。
你的替代选择不是Subversion,而是一个单一的代码库,可以使用Git、Subversion或其他工具。但你实际上想要一个单一的代码库和多个仓库的组合,对吗?你想要每个方案的好处,因此你需要更复杂的解决方案。
其中一个想法是有一个主项目代码库,在这里进行大部分开发,另外还有几个独立的仓库,从中分发模块。
proj/.git
proj/subA
proj/subB
subA/.git
subB/.git
你可以使用
rsync在它们之间移动代码。美妙的是,你已经清晰地区分了开发和分发。你像平常一样开发你的大型项目,包括分支、合并等。当你准备将子目录作为库分发时,你可以决定想要哪个版本的库,并将其复制到自己的仓库中。如果需要进行合并而不是仅仅复制,可以使用
git subtree merge strategy。
还有另一个系统,建立在子树合并策略之上。它被称为git-subtrees,是git-1.7.11的一部分。 这里是其操作的良好描述。 从图片中可以看出,它的时间轴可能看起来很混乱,但从功能上讲,它正是您想要的。 这里是最近的一篇文章,提供了极好的建议。
如果您不介意使用git-submodules的额外“更新”步骤,但对其处理冲突的方式感到不满,可以尝试giternal。 作者已经包含了一个脚本,以显示其行为与git-submodules和braid(用于售卖子模块,但不合并它们)相比较。
个人而言,我喜欢git-slave,它是一个简单的git包装器。基本上,它将你的gits
命令应用到所有的repo中作为git
命令。这只是一种便利方式。它非常易于理解,对各个repo没有任何影响,并且非常适合分支切换(这在git-subtrees中尚未得到支持)。