不同构件的开发者之间通常处于一种生产者与消费者的关系,即生产者交付工件提供给消费者使用。生产者交付的工件类型有:原始(Original)工件(源码、构建脚本、配置文件等),中间(Derived)工件(Obj文件、lib库等),最终产品(Product)工件(可执行文件、Dll库等),其它临时(Temporal)工件(编译器产生的临时文件等)。消费者将使用这些工件。C++项目中这种消费关系包含:编译引用他方的公开(public)头文件、链接他方的静态库文件(或Obj文件)、以及生成的最终执行文件调用他方的动态链接库等。
除了原始(Original)工件,其它派生工件都可以通过构建过程来自动生成,为了简化生产者与消费者的依赖关系,保持派生工件对原始工件版本的一致性,并减轻配置管理的开销,生产者应尽量只向消费者提交原始工件,消费者则依靠构建脚本生成他们需要的派生工件(出于效率考量,在构建开销较大时,消费者也可以直接使用生产者构建出的最终产品工件,其后果是版本冲突的风险变大,配置管理的开销增加)。
为了满足只提交原始工件的需要,编制自动化程度很高和高质量的构建脚本变得格外重要,如果构建过程增加了消费者的负担,或者出现了构建失败的情况,消费者将更倾向于直接从生产者手中拿到构建后的产品工件。
理想情况下,生产者可能在消费者开始使用前就交付了其依赖的工件,但通常团队会采用并行开发模式,消费者必须在生产者完成交付前就开始工作,因此开发替代的桩(Stub)代码,甚至为了调试方便而专门开发摹仿(Mock)代码,成了家常便饭。根据实际需要,替代代码可以由生产者自身或消费者来开发。针对这种状况,在编写构建脚本时,应提供相应的编译、链接选项,使得消费者可以自由选择将交付代码或桩(Stub)代码编译、链接到他的构造工作版本中,同时集成员还可以利用这些选项来开展增量式的迭代集成。
1.2 源码目录组织原则开发目录组织结构从来就是关系到项目健康成长的关键因素。开发(产品)目录提供了项目团队进行开发、管理等活动的统一共享场所,它需要满足不同涉众(角色),在不同的阶段,对不同类型工件进行访问的多种场景需求。因为项目的编码实施、集成等活动相互间的依赖关系远比其它文档编写类活动要复杂,协同整合更为困难,使得合理的源码组织结构变得极为重要,构架师和配置管理员必须投入更多精力关注开发(产品)目录中的源码组织部分。
源码目录组织的首要原则是目录结构的统一,项目中应当采用统一的分类方式、同一的风格、一致的命名格式来创建所有构件的源码目录。本项目中涉及到第三方库、项目构件、子系统、系统四类构件,其源码目录结构采用同一的基础目录结构,并根据各自需要做了相应的扩展。
开发(产品)目录的组织应当尽量在同一级的目录中采用同一种分类标准。目录分类标准有:按照工件类型(src/bin/lib/doc/mdl/script/web/xdoc),按照工件功能或用途(build/test/interface/example),按照活动组织(plan/requirement/design),按照归属关系(第三方库3rd Lib/基础构件Components/子系统Subsystem),等等。
如下图所示,本项目中,第一级目录按照归属关系来划分,源码构件的第二级目录按照构件设计包结构来划分,源码构件的第三级目录则按照工件类型并结合工件用途来划分。
开发(产品)目录应当面向团队协作,既要做到实施员在私有空间开发时相对独立,不受他人工作的影响,又能保证与他人的工作成果同步,并顺利地实现集成。这将依赖软件配置管理工具的支持,方能较好地达成上述目标。
开发(产品)目录本身可以看作是项目的一个工件,随着项目的进展也在不断地调整和演进,代码需要经历重构,目录结构也不例外。在项目初期就完全固定目录结构是不现实的。当前支持对目录进行版本控制,并能方便修改目录结构的配置管理工具不多,其中以ClearCase为主要代表,这也是本项目选用ClearCase的原因之一。
本文地址:http://com.8s8s.com/it/it37288.htm