让我们假设(为简单起见)我们有一个具有客户端和服务器功能的应用程序。有一个更好的主意是将一个存储库用于两个或两个单独的存储库?
混合它们可能会更容易跟踪相关的更改并维护相关的分支(即协议演化),但另一方面,会使单个开发更加混乱...
让我们假设(为简单起见)我们有一个具有客户端和服务器功能的应用程序。有一个更好的主意是将一个存储库用于两个或两个单独的存储库?
混合它们可能会更容易跟踪相关的更改并维护相关的分支(即协议演化),但另一方面,会使单个开发更加混乱...
Answers:
如果您使用的是git或mercurial,则可能需要查看子模块或子存储库。
客户端,服务器及其接口文件将位于其自己的存储库中,但将在超级存储库级别绑定在一起。这将允许您在顶层进行一次检出,git
或者hg
检出每个子模块/子存储库的适当提交。
仅当客户端和服务器彼此适合时才提交超级存储库,因此超级存储库将只为您提供签出工作系统的选项-因此您将永远不会尝试针对旧版本运行新客户端服务器,反之亦然。
子模块/子存储库为您提供了使用单独存储库的所有优点,以及单个整体存储库的优点,但付出了一些额外的复杂性。
这个答案并不是要提倡git
或hg
超越其他SCM,而恰恰是我只足够了解这些 SCM 才知道存在该选项。例如,我不了解svn
外部工作原理。
分离!
实际上,我可能会有三个存储库,一个用于客户端库和相应的仅客户端库,一个用于服务器库(以及相应的库),以及一个用于共享库的库(合并了暴露两个库之间功能的API接口) ,以及其他任何共享代码)。我认为这确实是关键,共享代码应放入自己的单独存储库中。这样,您可以确保客户端和服务器之间的互操作性始终处于同一版本,并且与每个使用者的设计隔离。
显然,这并非总是可能的,具体取决于您使用的特定通信框架,但是很可能存在共享代码,这些代码指示数据传输对象的格式或自定义协议(或其他示例)中的握手步骤。 。
假设您有一个相当不错的持续集成和QA设置(根据我的经验,这是一个相当大的假设,但是我还是要做出一个假设。如果您没有QA部门,则至少应获得一些CI),您应该无需使用单仓库模式来防御可能的代码不匹配,您的CI服务器将标记库的互操作性,或者您的质量保证团队将捕获运行时错误(或者,更好的是,您的单元测试也可以)。
拆分存储库的好处在于可以分别对系统的各个部分进行版本控制。是否想要复制上周的服务器并与本周的客户端一起运行,以尝试解决性能问题的根源?别担心。
在Mercurial中,可以使用此方案,->
用于表示子仓库关系:
product -> client -|-> (many components)
|-> shared component A
-> server -|-> (many components)
|-> shared component A
产品具有子仓库客户端,服务器。每个子仓库都有它们的组件作为子仓库,可能在两者之间共享至少一个子仓库。
标记可能应该在前两个级别上完成,而不要低于该级别。
提交是在组件级别完成的,超级仓库可以有效地跟踪产品的命名分支和版本。命名分支/书签通常在可用性(即可培训性)和与子存储库的兼容性方面优于克隆分支。
hg倾向于以下假设:超级仓库是产品,并且提交是在最高级别完成的,但是当多个产品使用相同的组件时,这种情况就不会特别有效。:-)
我认为如果过渡到git,该方案不会有太大变化,但是我还没有在git中尝试过。
在最简单的方法是使用一个单一的储存库,所以除非你像复杂的缘故复杂,那么这应该是默认选择在没有令人信服的理由,否则。
客户和服务器开发是否将由不同的组织进行?客户端(或服务器)是否会有多种实现?客户端开源和服务器实现是秘密的吗?如果所有这些问题的答案都是“否”,那么比单个存储库更复杂的事物可能只会带来不便,而没有任何好处。
如果确实选择维护单独的代码库,则将需要有关如何进行管理的明确策略,以避免不兼容性和依赖性。经过最初的几次打few之后,您可能会发现最安全的事情是始终一起检出两个存储库,一起构建它们,然后一起部署它们……这显然破坏了分离它们的整个目的!
模块化是一个不错的属性,但是拆分存储库并不是实现此目的的工具。正如上一段所暗示的那样,您可以将高度耦合的组件拆分为多个代码库(不希望),同样,您可以在同一代码库内具有高度模块化的组件(希望)。
我多次(成功地)提倡我的团队合并现有的git存储库,因为它简化了开发和部署。
暂时忘记存储库。如果您不与任何人共享,您将如何在计算机上组织这两个项目?团队的其他成员将如何做?你会...
将客户端和服务器的所有源文件都放在同一目录中?
创建一个主项目目录,其中包含客户端和服务器的子目录?
将两个项目完全分开?
一旦就团队达成共识,您就可以将项目检入代码存储库。我能想到的所有修订控制工具都乐于再现您喜欢的任何目录结构-它们一点也不关心哪个文件属于哪个项目。除了一个小的管理差异外,拥有一个或两个(或六个)存储库之间的差异通常不会很大。
例如,对于Subversion,客户端和服务器的单独存储库与单个组合存储库之间的最大区别在于修订号的更改方式。使用单一存储库,每次将代码提交到客户端或服务器时,版本号都会增加。使用单独的存储库,对服务器项目的提交不会更改客户端的总修订版号。