首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 软件管理 > 软件开发 >

继续集成,to be or not to be

2012-08-26 
持续集成,to be or not to be在我的一篇帖子《持续集成工具的选择》中,有很多跟贴讨论持续集成是否真得那么

持续集成,to be or not to be

在我的一篇帖子《持续集成工具的选择》中,有很多跟贴讨论持续集成是否真得那么有用或者在什么情况下有用的问题。有感与此,便又有了这篇文章。

持续集成在目前大多数的公司里都会有这样或者那样的使用。有的会选择一些Open Source的工具,如CruiseControl,Hudson,LuntBuild等等等等,有的会购买有更好服务,更强功能的商业产品,如TeamCity,QuickBuild等等等等,而有的会选择自己实现,如Cron+Ant/Maven/Make等等。那么使用下来效果如何呢?真得达到了预期的效果吗?我想来恐怕未必吧,否则也就不会有这么多的讨论了。

持续集成与敏捷编程

在敏捷领域中,测试驱动和持续集成被称为敏捷编程的两大基石,于是乎,很多人的概念里就是持续集成是为了实现敏捷编程的。这是一个错误的认识。实际上,早于敏捷编程概念的提出,持续集成作为一个best practice就已经被很多公司采用了,只不过作为一个概念,则是由Martin大叔为了推进敏捷所倡导并由此风靡起来。持续集成本身只是一种practice,并不被什么开发模型所限制,在任何一种开发模型中都可以采用,也可以运行得非常理想。

持续集成还是阶段集成

有很多人说,我不做持续集成,照样工作的很好。因为我们一个(小)阶段出一个版本,照样控制得非常好。我得恭喜你,首先持续集成也好,阶段集成也罢,你做了,做了就好,比没有做要好很多,也使你的项目管理上了轨道了。这两者之间的区别仅是频率而已。

那么究竟那种方式更加理想,更加符合项目的开发和管理呢?其实这个问题Steve McConnell在他那本获得Jolt大奖的书《Code Complete》(代码大全)里有过回答了。他说:对于一个微型程序来说,阶段式的集成或许是最佳方法。何谓微型程序,他说就是那种两三个类的程序,而你又很走运的话,那么阶段式集成就可以是你的最佳方法了。当然,这位老兄是个老美,我们也都知道老外嘛,都比较笨一点,不会转弯一点,所以呢,他说微型程序,对于我们拥有5000年文明的中国人说,可以再扩大点吧,对于一个小型项目,就是那种二三十个类的项目,也许使用阶段集成也不会出啥子问题吧。不过,你要真的是懒到连个阶段集成都不愿意做的话,那么你至少也该到庙里点支香,求求佛祖保佑你的项目一切顺利。

为什么要做持续集成

很多人肯定非常不苟同我的看法,他们认为即使没有做持续集成,甚至没有做阶段集成,但是项目一样按时的完成,甚至提前完成,而且照样完成的非常理想,老板满意,客户满意,夫复何求?而做持续集成,无非就是动不动收到一封邮件,说这个build成功了,那个build失败了,不过就是一持续编译罢了,我自己打个命令编译一下,不就知道了吗?要做个daily build,我还要颠颠的去set up,还要花力气去配置,效果也不见得好到什么地方去。

对于这样一些问题,我想首先我们还得搞清楚,究竟为什么我们要去做持续集成,持续集成究竟可以给我们带来什么好处。同样在《Code Complete》里提到了,对于持续集成(在书中,Steve McConnell使用Incremental Integration的术语)有以下几点好处:

易于定位错误。也就是当你的持续集成失败了,说明你新加的代码或者修改的代码引起了错误,这样你很容易的就可以知道到底是谁犯了错误,可以找谁来讨论。
及早在项目里取得系统级的成果。因为代码已经被集成起来了,所以即使整个系统还不是那么可用,但至少你和你的团队都已经可以看到它已经在那了。
改善对进度的控制。这点非常明显,如果每天都在集成,当然每天都可以看到哪些功能可以使用,哪些功能还没有实现。如果你是程序员,你不用在汇报任务的时候说我完成了多少百分比而烦恼,而如果你是项目经理的话,那么你也不再烦恼程序员说完成了编码的50%到底是个什么概念。
改善客户关系。理由同上。
更加充分地测试系统中的各个单元。这也是我们常讲的Daily Build与Smoke Test相结合带来的绝大好处。
能在更短的时间里建造整个系统。这点恐怕要你实施以后才能得出结论。就我们而言,持续集成并没有为每个项目都缩短时间,但却比没有实施时,项目更加可控,也更加有保证。

随着时间的推移,持续集成带来的更多好处,也逐渐被认识到了,比如说:
有助于项目的开发数据的收集。比如说,项目代码量的变化,经常出错的Tests,经常出错的source code,等等。
与其它工具结合的持续代码质量改进。如与CheckStyle, PMD, FindBugs, Fxcop等等等等的结合。
与测试工具或者框架结合的持续测试。如与xUnit,SilkTest, LoadRunner等等的结合。
便于Code Review。在每个build里,我们都可以知道与前一个build之间有什么改动,然后针对这些改动,我们就可以实施Code Review了。
便于开发流程的管理。比如说,要把一个开发的build提交给测试组作测试,测完满意了,再提交到发布组去发布。

还有很多很多的其它的好处,也许你可以告诉我吧。

怎么做持续集成

持续集成有很多很多的好处。可是持续集成要做好的话,本身就有很多的讲究。从持续集成工具的选择到持续集成具体实施,每一点都可能影响到你使用持续集成的效果。持续集成不是持续编译,也不是仅仅用来发发邮件的工具而已。

工欲善其事,必先利其器。首先选择一个好的工具很重要,在我另一篇帖子《持续集成工具的选择》中,我已提到过了,这里不再多说。用下来,我觉得QuickBuild真得很不错。

工具选好了,具体怎么做呢?这个没有什么标准可以遵循,每个项目都是不一样的,我谈谈我们这里的具体过程吧。

首先,我们对编码有一些规范需要遵从,所以我们制定了一系列的FindBugs和PMD的规则用于检查代码。
其次,我们使用Cobertura作为我们的代码覆盖(code coverage)工具。
再次,我们使用JUnit作为我们的unit test工具
基于上述几点,我们编写了我们的Ant脚本,这个脚本有一系列的task,基本上就是:
compile, source code analytics, unit test, generate reports, generate javadoc, package artifacts

这个,也是Java领域中经常使用的一个完整的过程。

有了这样一个脚本以后,我们开始配置我们的项目到QuickBuild中去,在QuickBuild中,我们配置一个configuration,然后设定我们的SCM repository,对应于我们的ant task,我们配置了一系列的step,用于完成整个过程。由于我们的测试需要跨平台,所以对应与同一个unit test的task,我们使用QuickBuild的分布式的step功能,使之在不同平台上可以进行测试,这一点也是使用CI Server的一个好处吧。

对应于这个configuration,我们配置了四个子configuration,分布是Development Configuration, QA Configuration,Integration Configuration和Release Configuration。这几个configuration分别对应于我们开发过程的四个阶段,我们的每日构建都是在Development configuration上的,所以我们配置为每日一次,而对于其它三个则不做自动的构建。因为我们是通过Promote来做的。对于Development Configuration,我们没有对SCM自动打Label,而对于其它的,我们则对每一个Build自动对SCM进行打Label。

有了这些以后,开发工作开始了,我们每天的代码在下班前都提交到subversion里去,第二天,Development Configuration就自动的编译完成了,并且发送通知给我们。我们通常会会开一个Morning Meeting,首先我们会到在QuickBuild的页面上,看到昨天有哪些个改动,测试的状况,比如说哪些测试修正了,哪些测试还没有被修正,哪些source code没有通过代码检查。然后我们会点到具体的报告中去分析,这些报告都可以很容易的打开source code,我们可以直接在上面对各个改动做code review。通常这个工程耗时约30分钟结束。
经过这样开发之后一段时间,我们的功能很多已经就绪,就可以提交给QA作test了,由于当日的构建可能失败,或者不是我们特别想给QA的,那么我们会选择之前几日的一个好的build做Promote,这个promote就会自动触发QA Configuration去做build,QA Configuration的build做完以后,就会发送一个邮件通知QA Lead,这封邮件里QuickBuild会把所有与上一个QA build的changes都列出来,这样他就知道我们这个版本里增加了什么功能,修正了什么bug。
再如此经过几个迭代后,我们开发组和QA组一致认为功能基本实现了,bug也不多了,于是就由QA的Lead做一个Promote,触发Integration Configuration不build一个大版本交给客户,做VOC (Voice of Customer),听却客户的意见,如果客户没有什么易见的话,那么就会在Integration Configuration上做一个Promote到Release Configuration上去。

通过这样做,我们基本上可以很容易的知道每一个版本之间有什么变化,甚至我们可以很容易的重新build出任何一个时间点上的版本。而且,我们基本上无需操心什么时候给SCM打什么样的Label,因为对于我们而言,我们需要看到的只是每一个版本的build。而如果用subversion来管理的话,也许你也可以通过命令来列出在SCM中各个版本的变化,但是如果有一天,你头昏忘记打label的话,或者打错label的话,也许要找到这个问题就不是那么容易了。又也许,你可以通过一系列的命令来完成这里提到的所有功能,但是我是懒惰的,而且很容易做错事情,所以我觉得如果机器可以完成的话,就让机器去做吧。

这些都只是我们在持续集成上的一点实践,也许你有更好的方式,也许你有更多别的点子,那么也请告诉我吧。

还有很多很多关于持续集成的事情可以说,多到可以写一本书了,如果你有兴趣的话,我觉得那本《Continuous Integration: Improving Software Quality and Reducing Risk》的书可以好好看看,非常详细。

?


juvenshun 写道我不认同改进必须必须要由经济利益驱动,驱动改进的其它因素有:
* 我想做一个更优秀的程序员
* 改进能让我的编程生活更舒服一些
无疑持续集成是一个优秀程序员的基本素质之一,而且持续集成能帮助我们尽快发现问题,尽早修复,而不是在几个月后发现问题,模糊了上下文,焦头烂额。

都修炼成老菜鸟了,自然修炼不成优秀程序员了
持续集成是一个优秀程序员的基本素质之一啦,是Best Practice啦,俺们其实不怎么感冒

想了想,确实,我们缺少改进的压力 6 楼 wsgwz_2000 2009-10-28   非常感谢cristal的分享

能再说说持续集成的成本吗?是否有某些不适用的场合? 7 楼 jetspeed 2009-10-28   QB的16个configuration限制能管理几个项目? 8 楼 gigix 2009-10-28   juvenshun 写道改进的压力?或者说改进的动力?
我不认同改进必须必须要由经济利益驱动,驱动改进的其它因素有:
* 我想做一个更优秀的程序员
* 改进能让我的编程生活更舒服一些
无疑持续集成是一个优秀程序员的基本素质之一,而且持续集成能帮助我们尽快发现问题,尽早修复,而不是在几个月后发现问题,模糊了上下文,焦头烂额。

你想当然的找个错误的前提,还好意思让人家闭嘴,呵呵。
你去试试看好了
我很欣赏你的乐观,我很希望你不要被撞得头破血流而发现自己的乐观原来是那么幼稚 9 楼 juvenshun 2009-10-29   gigix 写道
你去试试看好了
我很欣赏你的乐观,我很希望你不要被撞得头破血流而发现自己的乐观原来是那么幼稚
事实上,在我之前的公司,我就开始引入持续集成并得到了不错的效果,在目前的公司,持续集成也是件和吃饭一样平常的事情。
一会让人闭嘴,一会暗讽别人幼稚,可我完全看不到你的依据所在。
10 楼 badqiu 2009-10-29   jetspeed 写道楼主能分享ant 脚本 和 配置文件就好了。 我正在按照lz的经验搭建集成环境


这个你可以下载我的试试,包含完整的编译,单元测试及相关打包.

http://code.google.com/p/rapid-framework/wiki/cruisecontrol 11 楼 yecllsl 2009-10-29   文还不错。但总感觉是“市场行为”,尤其看到首页上的广告。 12 楼 eagleinfly 2009-11-03   <p>
</p>
<div class="quote_title">cristal 写道</div>
<div class="quote_div">有了这些以后,开发工作开始了,我们每天的代码在下班前都提交到subversion里去,第二天,Development Configuration就自动的编译完成了,并且发送通知给我们</div>
?
<p>?</p>
<p>我不明白为什么要很多人一起在下班前提交, 这样如果一个人的修改有问题会导致整个build失败, 没有办法验证其他人的修改. 有什么其他的原因吗?</p>
<p>?</p>
<p>我们目前是每对pair完成一个功能后都提交,通过build grid很快知道结果, 每个人都必须保证单元测试通过, 如果失败了就得马上修改, 集成测试可以第二天修改(如果已经下班了), 好处是:?</p>
<p>1. 充分利用 build grid, 测试时间也很短</p>
<p>2. 每次build只有少数人, 有了问题容易发现</p>
<p>3. 如果build失败, 或者有人马上修复, 或者rollback上次修改, build成功前其他人不能提交新东西, 不然不知道谁break build.</p>
<p>?</p> 13 楼 myworkfirst 2009-11-04   gigix 写道juvenshun 写道改进的压力?或者说改进的动力?
我不认同改进必须必须要由经济利益驱动,驱动改进的其它因素有:
* 我想做一个更优秀的程序员
* 改进能让我的编程生活更舒服一些
无疑持续集成是一个优秀程序员的基本素质之一,而且持续集成能帮助我们尽快发现问题,尽早修复,而不是在几个月后发现问题,模糊了上下文,焦头烂额。

你想当然的找个错误的前提,还好意思让人家闭嘴,呵呵。
你去试试看好了
我很欣赏你的乐观,我很希望你不要被撞得头破血流而发现自己的乐观原来是那么幼稚
   我们公司就用上了持续集成,每相隔段时间,就build一次,自动归版本,自动部署,自动测试功能(自动测试用例还在完善),感觉挺好的。不清楚gigix认为"头破血流"以及"幼稚"是指什么?
   不过我认为,持续集成在规模大,周期长的项目中,有突出的体现. 如果比较小,周期短的项目,可以裁减部分流程。
以项目大小,取决于流程的优化,也不用太强求走到每个流程 14 楼 cristal 2009-11-08   jetspeed 写道楼主能分享ant 脚本 和 配置文件就好了。 我正在按照lz的经验搭建集成环境
Ant脚本很简单,基本上就是如下几个target
prepare, compile, checkstyle, findbugs, pmd, emma.instrument, junit, emma, all
具体过程就要看你自己的项目情况了。

配置文件?QuickBuild好像没有什么地方需要写配置文件的啊。如果是怎么设置你的configuration的话,可以看文档或者demo.pmease.com,我主要是参考wiki和这个站点来配置的。 15 楼 cristal 2009-11-08   wsgwz_2000 写道非常感谢cristal的分享

能再说说持续集成的成本吗?是否有某些不适用的场合?

持续集成本身的成本我想也许就在于配置和学习持续集成工具本身吧,还有就是购买的成本了。别的,我还真不觉得有什么其它的成本。至于不适用的场合,可能一个人的项目就不需要吧,还有就是特别小的项目不需要吧。我还真的想不出甚么情况来:)
16 楼 cristal 2009-11-08   <div class="quote_title">eagleinfly 写道</div>
<div class="quote_div">
<p>我不明白为什么要很多人一起在下班前提交, 这样如果一个人的修改有问题会导致整个build失败, 没有办法验证其他人的修改. 有什么其他的原因吗?</p>
<p>?</p>
<p>我们目前是每对pair完成一个功能后都提交,通过build grid很快知道结果, 每个人都必须保证单元测试通过, 如果失败了就得马上修改, 集成测试可以第二天修改(如果已经下班了), 好处是:?</p>
<p>1. 充分利用 build grid, 测试时间也很短</p>
<p>2. 每次build只有少数人, 有了问题容易发现</p>
<p>3. 如果build失败, 或者有人马上修复, 或者rollback上次修改, build成功前其他人不能提交新东西, 不然不知道谁break build.</p>
<p>?</p>
</div>
<p>?</p>
<p>下班前要check in只是一个约定,而不是集中在下班前做check in(有点绕,呵呵)。无论build是否会失败,没有关系,我们第二天都可以知道具体情况的,也便于第二天的code review。至于不能验证其他人的修改,对我们而言,不算特别重要,因为不是明天就要发布,昨天没有成功,今天可以继续运行嘛。导致build失败的人,在做code review的时候就可以知道是谁了,他可以在修正了错误之后,做一次手工的build来验证一下,也可以留到晚上自动做。我们只要求不要有连续几天的build失败即可。如果出现这种连续几天的失败,小组成员就会一起停下来协助出错成员修正错误直到build通过为止。</p>
<p>?</p>
<p>至于,你提到的方式的确是现在正在流行的一种方式,也很敏捷,就是利用proof build来做,在submit到SCM之前,由QuickBuild自动触发一个build,如果通过就check in,否则就不做check in。这种方式现在我们只是试验性的使用了一下,还没有感受到什么特别的好处。</p> 17 楼 cristal 2009-11-08   jetspeed 写道QB的16个configuration限制能管理几个项目?

这个恐怕要看你怎么使用configuration了,如果你一个项目对应于一个configuration的话,那么你可以管理16个项目吧。如果你像我文章里的配法,可能只够管理3~4个项目。一个项目对应于4个configuration,当然你也可以裁减这种配置来对应你自己的流程。 18 楼 rainv 2009-11-09   1.不建议下班前check in,因为如果提交了编译不过的代码第2天来到一看全是红灯就傻眼了。呵呵。
19 楼 rainv 2009-11-09   1.持续集成是迭代的方法保证程序质量的方式,无论大小项目都适合。
2.如果觉得产品质量和代码质量很重要,那么持续集成是首选,如果不是,可以跳过。 20 楼 pekkle 2010-10-19   juvenshun 写道gigix 写道
你去试试看好了
我很欣赏你的乐观,我很希望你不要被撞得头破血流而发现自己的乐观原来是那么幼稚
事实上,在我之前的公司,我就开始引入持续集成并得到了不错的效果,在目前的公司,持续集成也是件和吃饭一样平常的事情。
一会让人闭嘴,一会暗讽别人幼稚,可我完全看不到你的依据所在。


gigx说的没错,我演绎一下他的意思。
如果公司的模式是一张白纸,公司老大会支持你,你这么做(其实不管怎么做),都会有效果。
如果公司有自己的模式,被团队接受,老大也接受,认为目前没必要做手术,你的理论是执行不了的。
如果公司老大想改,抱着试试的想法,没有很大的动力,而你如果认为很给力,这样很难成功。
想想商鞅变法,如果boss不支持,他能成功吗?下面的会配合吗?
boss的压力无非是改进工作,提高效率,加上变革代价很小,他会支持
下面的压力通常来自上面

热点排行