[ 2009-12-23 9:25:00 | By: 王海鵬 ]
 

引言

Thomas Carlyle說:“人類是使用工具的動物。沒有工具,人什么都不是;有了工具,人無所不能。”金融家們創造了復雜的金融工具,并利用這些工具制造了財富神話,制造了著名的跨國公司,也制造了世界范圍的危機。軟件精英們為了讓自己的工作效率更高,有更多時間去做想做的事,也創造了各式各樣的工具。持續集成已經不是一個新概念,在這個概念發展的十多年間,出現了支持這一概念的眾多工具。這些工具的組合使用,為軟件開發提供了強大的支持。

持續集成工具的分類和功能

一般來說,持續集成工具可以分成兩大類:自動化構建工具和構建計劃安排工具。

自動化構建工具有這樣一些基本功能:代碼編譯、組件打包、程序執行和文件操作。編譯源代碼是構建的主要工作之一,為了提高效率,編譯應該根據相應的源代碼是否發生改變而有條件地執行。組件打包是將編譯的結果和其他需要包含的文件組織在一起,形成可以部署的組件。構建工具應該知道何時需要重新打包。程序執行是指構建工具能夠在它支持的平臺上,調用所有提供命令行接口的程序。構建工具應該支持創建、拷貝、刪除文件和目錄等操作。

某些自動化構建工具還有一些擴展功能:執行開發者測試、版本控制工具集成、文檔集成、部署功能、代碼品質分析、支持擴展、多平臺構建、加速構建。雖然構建工具可以通過命令行執行的方式來集成構建工具和測試工具,但如果它提供更直接的集成方式,開發者就更省力。同樣,如果構建工具能夠直接與版本控制工具集成,開發者也會覺得更方便。文檔集成是指構建工具能夠自動從源代碼中抽取并生成API文檔。構建工具還可以將打包好的組件自動部署到目標測試環境中去。構建工具一般通過一些第三方插件,支持對代碼品質進行分析。而提供插件接口,是構建工具實現可擴展性的通用方式。如果您開發的軟件需要在多個平臺上構建并測試,那么構建工具對多平臺的支持就會帶來極大的方便。對于較大的代碼集,一次構建可能需要好幾個小時,這為持續集成帶來了一些挑戰。有的構建工具支持加速構建,即在多個構建服務器的多個處理器上進行分布式構建。

常見的自動化構建工具包括Ant、NAnt、MSBuild、make、Maven、Rake等。

構建計劃安排工具有這樣一些基本功能:構建執行、版本控制集成、構建工具集成、提供反饋、為構建打上標簽。構建計劃安排工具的核心功能就是在特定時間執行自動化的構建,這可以通過輪詢版本控制庫、計劃驅動或事件通知等方式來實現。大部分構建計劃安排工具都支持大多數流行的版本控制系統,也支持大多數流行的構建工具。構建計劃安排工具至少支持通過電子郵件提供反饋信息,有一些工具可以通過即時消息、手機短信或其他設備來提供反饋。大多數構建計劃安排工具會提供某種類型的升序計數,作為構建版本的標簽。

某些構建計劃安排工具還有一些擴展功能:支持項目間依賴關系、提供用戶界面、制品發布、安全。如果項目間存在依賴關系,您可能希望在被依賴的項目重新構建時,重新構建依賴于它的項目。設計良好的用戶界面會在工作時為您節約時間。制品發布是指除了得到可部署的組件之外,一些成熟的某些構建計劃安排工具可以將文檔、測試結果、品質分析結構和其他測量指標數據格式化,便于查看。有一些工具提供了身份認證和授權等安全方面的功能,允許您指定誰能查看結果和修改配置。

常見的構建計劃安排工具包括AnthillPro、Continuum、CruiseControl、CruiseControl.NET、Draco.NET、Luntbuild、Hudson等。

下面介紹兩個頗具代表性的工具:Ant和Hudson。

Ant

Ant是Java構建工具的事實標準,一般建議,不論項目團隊成員使用哪種集成開發環境,項目都要有一個可以脫離IDE執行的Ant腳本。Ant采用插件式的設計結構,通過不同的插件來實現各種任務,其任務分類如表1所示。

Archive Tasks
 打包解包任務,支持的格式包括:BZip2、Cab、Ear、GZip、Jar、Rpm、Tar、War、Zip。
 
Audit/Coverage Tasks
 JDepend任務,調用JDepend實現代碼靜態分析,針對每個Java包生成設計品質指標數據。
 
Compile Tasks
 編譯任務,實現對Java、JSP、NetRexx等源文件的編譯。
 
Deployment Tasks
 部署任務,實現在JavaEE服務器上熱部署。
 
Documentation Tasks
 文檔生成任務,生成javadoc文檔、Apache Stylebook文檔。
 
EJB Tasks
 EJB任務,提供對1.x和2.x的EJB的支持,并支持不同供應商的應用服務器。
 
Execution Tasks
 執行任務,包括對子項目調用Ant、調用同一腳本中的另一個target、執行系統提供的命令行程序、執行Java程序、暫停和并行同步執行等功能。
 
File Tasks
 文件任務,實現對文件和目錄的操作。
 
Java2 Extensions Tasks
 Java2 擴展信息任務,對jar包中的版本、供應商等擴展信息進行檢查和操作。
 
Logging Tasks
 日志任務,將構建過程事件記錄到文件中。
 
Mail Tasks
 郵件任務,發送SMTP郵件。
 
Miscellaneous Tasks
 其他任務,各種或許會用到的小任務,例如播放wav文件。
 
.NET Tasks
 .NET任務,支持執行.NET程序、執行NUnit測試、調用NAnt、調用MSBuild、調用WiX工具。
 
Pre-process Tasks
 預處理任務,實現編譯之前的一些預處理。例如調用ANTLR、JavaCC、Native2Ascii等程序。
 
Property Tasks
 屬性任務,對腳本中的屬性變量進行判斷和操作。
 
Remote Tasks
 遠程任務,支持FTP、Rexec、Scp、SSH和Telnet。
 
SCM Tasks
 SCM任務,支持各種配置管理(版本控制)軟件,包括CVS、ClearCase、Continuus、Visual SourceSafe、Perforce、PVCS、SourceOffSite和StarTeam。
 
Testing Tasks
 測試任務,支持執行JUnit測試。
 
表1. Ant任務分類

以上介紹的只是Ant發行版所帶的一些任務。由于Ant采用的是插件結構,所以開發者可以開發自己需要的Ant任務,支持各種工具,如FindBugs、TestNG等其他代碼檢查工具和測試工具。早期的Ant沒有很好的依賴關系支持,后來則通過Ivy彌補了這一缺點。

關鍵是Ant為我們提供了一個跨平臺的Java構建工具,為持續集成提供了根本的支持。對于Java開發者來說,如果不想采用Ant,也可以考慮采用Maven。

Hudson

Hudson是一個開放源代碼的CI服務器,受到世界各地各種規模和類型的開發團隊的歡迎。關鍵是因為它非常易于安裝和使用,提供了靈活的配置方式和復雜的功能,同時支持Java項目和非Java項目,由強大的Hudson社區提供技術支持。

簡而言之,Hudson不僅僅是一個CI服務器,它的可擴展架構使它不僅是一個構建管理系統,也成為一個通用的開發生命周期管理系統,讓開發者能夠完成提升基線、打標簽、執行工作流、根據依賴關系追蹤變更、監視并圖示測試結果、查看代碼覆蓋率和違反編碼標準的情況等任務。

Hudson是最活躍,成長最快的開源社區之一,目前每周下載達4000次,有超過2萬個在工作的安裝實例。它的開發者超過160人,貢獻的工作量超過137人年,目前已發布了超過300個發行版本。Hudson實際上是現在世界上最受歡迎的開源CI服務器。

圖1是Apache軟件基金會運行Hudson的屏幕截圖,您可以在http://wiki.hudson-ci.org/display/HUDSON/Meet+Hudson 看到更多Hudson的使用案例。

圖1. Apache運行的Hudson

Huddon的主要優點包括:

易于安裝。只要執行“java –jar hudson.war”,或者將hudson.war部署到應用服務器上就可以了,不需要其他的安裝工作,也不需要建立數據庫。
易于配置。所有東西都通過Web GUI界面來配置,不需要手工修改XML文件。
支持分布式構建。Hudson支持將構建和測試負載分布到多臺機器上,圖2是Apache采用Hudson的分布式構建功能。
支持環境配置矩陣。Hudson支持在不同的環境配置下執行相同的任務,例如不同的JDK版本、不同的操作系統、不同的數據庫。執行的結果可以匯總在一起。
支持JUnit/TestNG測試報告。測試的結果可以分標簽列出、匯總,并與歷史信息一同顯示。歷史趨勢可以顯示在圖中。
追蹤依賴關系。Hudson追蹤記錄哪次構建生成了哪些jar,某次構建使用了哪些版本的jar,即使這些jar包來自于外部也可以。

圖2. Hudson支持的分布式構建

Hudson通過大量的插件來實現其豐富的功能,這些插件大致可以分為以下幾類:

SCM。Hudson缺省支持CVS和Subversion,通過安裝插件支持Accurev、Bitkeeper、ClearCase、Git、Mercurial、Perforce、StarTeam、Synergy等
構建觸發器。可以通過IRC、Ivy、Jabber、Join、Locks and Latches、Navigator來觸發執行構建。
構建工具。缺省支持Ant、Maven、shell s和Windows 批處理命令,通過安裝插件支持batch tasks、Gant、Gradle、Grails、Groovy、Jython、Kundo、MSBuild、Phing、Powershell、Python、Rake、Ruby、SCons、SCTMExecutor,Selenium等。
構建包裝。對構建的方式進行一些控制,如并發同步、啟停虛擬機等。包括Hudson Centralized Job Action、Hudson Distributed Workspace Clean、Locks and Latches、M2 Extra Steps、M2 Release、Release、VMware、Xvnc、Zen Timestamp等。
構建通知。缺省支持電子郵件通知,通過插件支持Campfire、Google Calendar、HudsonTracker (RSS feeds)、IRC、Jabber、Nabaztag、SameTime、Status Monitor、The new Emailer、TuxDroid、Twitter等。
Slave啟動和控制。缺省支持JNLP和命令行,通過插件支持SSH。
構建報告。缺省支持JUnit、javadoc和FindBugs,通過插件支持CCCC、Checkstyle、Clover、DRY、Emma、Gallio、Gnat、Grinder、Japaex、JavaNCS、JavaTest Report、MSTest、N Cover、NUint、Plot、PMD、PureCoverage、Ruby metrics、Selenium AES、Selenium hq、Serenitec、SLOCCount、Task Scanner、Testability Explorer、Violations、Warnings、WebTest Presenter等。圖3是Sonar生成的項目報告的樣例。
集群管理/分布式構建。支持DistFork、Hadoop、PXE、Selenium、Swarm等。
制品上傳。支持FTP-Publisher、java.net uploader、SCP,SFEE、SVN等。
身份認證和用戶管理。支持操作審計追蹤、LDAP、MySQL認證等。

圖3. Sonar Dashboard

結束語

工欲善其事,必先利其器。人是工具的主宰。A fool with a tool is still a fool(傻子拿著工具還是傻子)。人們總是在學習工具、使用工具、創造更好的工具,以期提高工作的效率和品質。人要有智慧,工具要先進。