每个经历过完整游戏项目开发的人都永远会清楚的记得从开发到运营阶段所经历过的那些痛苦:枯燥的代码提交、代码更新、编译、提交可执行程序再到测试的过程;永远改不完的BUG;修改了一处BUG结果引入了更多的BUG;添加了一点新功能导致原来的功能不能用;每次更新新版本前的战战兢兢,等等等等。
有人说技术的进步是为了懒人们的功能,也确实,当我们不想再去做那些繁琐的工作时,我们便有了这些方便的自动化工具:比如我们会自己写一个批处理文件用来自动化的提交、更新代码,调用编译程序进行编译,然后把编译的结果拷贝到一个指定的目录。我相信大部分人的程序生涯中都会编写过这样一些批处理脚本,或者使用过类似的脚本,当然,也有可能我们会把这些脚本做的更加可视化一些,比如再加一个漂亮的GUI界面,事实上我以前所参与的项目也曾经做过这些事。
而对于BUG的问题,也有了更加成熟的解决方案,比如单元测试,系统测试方法论,以及相关的测试工具与框架代码,如CPPUNIT等。
如果你正开始一个新的项目,也许你会有原来已经完成过的类似脚本拿来使用,或者你也有可能会安排一两个人手来开发一个新的自动编译工具,当然,你可以选择的一个更好的方案是使用一个现成的开源解决方案。使用开源社区提供的工具已经不是什么新鲜事了,在自动构建领域也有这样一个非常好的工具,叫做Cruise Control。
关于如何写CC的配置文件config.xml就不需要多说了,CC自带的document是最好的资料,看完自然就明白。当然,事实上我在做配置试验时也碰到了些困扰,最后是求助于google才得以解决,如果不幸你也遇到了类似的问题,比如不论怎样尝试,CC都不能正确的从SVN的仓库checkout代码,那么你可以看看这里
http://www.oracle.com/technology/products/jdev/tips/mills/cruisecontrol/jdev_svn_cc.html
其实就是Ant的SVN Task做的还不够完善,所以有人重新做了一个,并且增加了很多有用的功能,可以帮助我们实现更多的自动化任务。
另外一点就是CC的publisher了,CC本身也内建了多种发布方式,包括通过ftp上传,发布邮件通知等等,但实际上据我个人的观察,让每个程序员主动地去检查邮件或者查看某个网页是件不太容易办到的事,程序员们总会有各种各样听起来似乎非常合理的借口来说明为什么没有及时地去查看编译结果,就算是Notes附带的强大的通知程序也没有多少人愿意开。所以,必须有一种更加直接的方法来通知开发人员编译结果。
我们曾尝试了一种方法,把编译结果通过程序员们最常用的IM工具发送给他们。虽然程序员们不大善于口头交流,但是对于聊天工具却大都相当的钟爱,所以在这里将结果发给他们,他们是没有理由不去关注的。
然后就是自动化测试。我觉得完全的自动化测试过程只能在单元测试这一级,要想实现完整的系统测试与集成测试不太容易,尤其对于我所参与的网络游戏这一类项目来说,所以我也只要求了这个自动化集成环境里实现单元测试这一步。其实保证了各单元模块的功能正确,系统的bug数量就已减少了一大半。
测试的框架也比较多,从老牌的CPPUNIT到新近推出的google test frameworks,按照程序员们自己的喜好自由选择一款,最终也是通过Ant的外部Task集成到CC中。
最后是版本的发布。如果参与过游戏项目的完整运营,那一定知道游戏正式上线的版本会比较多,比较乱,如何管理好这些不同的版本就是我们的自动化集成环境可以完成的工作。比如一般会有一个正常版本,还会有一个增加了部分测试功能的外网测试版本,再加上一些为特定的服务器定制的活动,为特定的服务器修改了数值的版本,等等等等。到后面服务器维护时,经常会头疼于这些版本的管理,以及每个版本对应的pdb及map文件的管理。
如果能有一种自动化的方案帮我们将这多种版本自动生成,自动分类,自动归档,那将会是一件让人省下不少心的大好事。事实上,只要我们做好了配置,CC确实可以帮我们完成这繁琐的工作。
说完了自动编译,那就该方说说持续集成了。其实把上面说的这些工作加起来就构成了持续集成的工作,只是这些工作需要不断的去完成,当然也是通过机器自动来完成,不是手工的一项项去做。
持续集成通俗的说就是持续地,频繁地进行集成,每当有新的修改加入的时候,修改的作者能够被及时的告知他的修改是否在加入新功能的同时保证原有功能的完整。
还是用CC来说明持续集成的过程吧。另外CC虽然是用Java语言编写的,但这并不表示CC只能用来做Java项目的集成管理,C++一样可以。可以让CC定时地从SVN仓库中update最新的代码,然后调用Ant的外部命令,执行make或msbuild来编译工程,然后再调用cppunit框架来进行单元测试,接着把编译及测试结果发送到IM工具上,最后把编译的可执行文件发布到指定目录,归档。
CC其实就像一个总指挥,由它来调度外面的工作,比如自动编译,自动测试,自动发布等。而外部的每一项工作都可以自由定义,当然我们大部分都是采用的Ant来完成,因为Ant已做的足够强大。
最后想说的是,工具再强大还得要看如何去使用它。比如是不是将持续集成落到了实处,不是一个只给老板看的花架子;自动化单元测试是不是按照最初的设想在实现,程序员们有没有按照要求为每个模块每个接口编写测试用例并添加到测试框架中,等等,这都需要项目管理者来推动并监督。
虽然一开始这个过程可能会与原来的那个过程一样令人不大愉快,但是当走上正轨以后,一定会给整个开发过程带来相当大的益处。