|
英文原文:Implementing Automated Governance for Coding Standards
作者:Mark Figley 譯者:羅小平
多數(shù)大型開發(fā)組織都有一套自己的編碼和實(shí)踐規(guī)范。但是對(duì)這些團(tuán)隊(duì)而言,光是將這些規(guī)范文檔化,并保證實(shí)時(shí)更新,就是一個(gè)巨大的挑戰(zhàn)。此外,在工作中長期、忠實(shí)地執(zhí)行這些規(guī)范和標(biāo)準(zhǔn),難度就更大。我們團(tuán)隊(duì)在這些方面做了積極探索,在整個(gè)構(gòu)建過程(build process)中實(shí)現(xiàn)了代碼規(guī)范的自動(dòng)化監(jiān)管。
積極主動(dòng)、未雨綢繆是工作取得好成果的重要保證。即使在很成熟的組織中,建立了代碼復(fù)審流程,審查結(jié)果也能直接反饋給責(zé)任人,但如果復(fù)審是在事后進(jìn)行,仍然存在很大風(fēng)險(xiǎn)。因?yàn)檫@個(gè)時(shí)候,錯(cuò)誤已成現(xiàn)實(shí),很可能已經(jīng)進(jìn)入測(cè)試和產(chǎn)品環(huán)境,從而造成實(shí)質(zhì)性損失;而這時(shí)候再回頭修改,開發(fā)人員也有抵觸情緒,缺乏積極性。從我們的經(jīng)驗(yàn)看,構(gòu)建過程必須自始至終處于受控之中,在所有的軟件開發(fā)過程中,對(duì)應(yīng)的代碼審查工作都應(yīng)該自動(dòng)完成。只有這樣,錯(cuò)誤代碼才能在第一時(shí)間消除,從而避免到最后階段采取回溯式審查方法所產(chǎn)生的成本高昂和開發(fā)人員抵觸等問題。不帶任何感情色彩的自動(dòng)化系統(tǒng)可實(shí)時(shí)向開發(fā)人員反饋Web頁形式的報(bào)告,幫助他們解決可能存在的問題;而且通過反復(fù)提醒,也可以讓開發(fā)人員被動(dòng)熟悉新的編程規(guī)范。
中心化的構(gòu)建過程管理
為保證我們的上述策略真正落到實(shí)處,必須做好兩項(xiàng)工作:
- 構(gòu)建過程必須是基于服務(wù)端的、中心化管理的。我們?cè)贏nt腳本基礎(chǔ)上自行開發(fā)了一個(gè)構(gòu)建管理系統(tǒng)(Build Management System,BMS),因?yàn)槟菚r(shí)候像AntHill、Maven等產(chǎn)品還沒有發(fā)展成熟。如果是現(xiàn)在,我肯定會(huì)選擇第三方的BMS,而不是自己從頭做起。自己開發(fā),方便實(shí)現(xiàn)一些特殊的定制化需求,但現(xiàn)在很多第三方BMS都有功能集成能力。
- 必須樹立這樣的觀念:深度使用BMS,是團(tuán)隊(duì)大幅提高代碼質(zhì)量的唯一途徑。我這不是搞教條,在這個(gè)問題上,其實(shí)別無選擇。如果開發(fā)人員可以繞過監(jiān)管系統(tǒng),直接將Java類文件FTP傳送到服務(wù)器,那么我們正在這里討論的解決方案的有效性就大打折扣了。我們應(yīng)該控制對(duì)服務(wù)器上相關(guān)目錄的訪問,只將寫入權(quán)限授予負(fù)責(zé)運(yùn)行JVM過程(即我們的構(gòu)建系統(tǒng)的宿主)的帳戶,這樣,開發(fā)人員必須通過BMS,才能將代碼傳遞到生產(chǎn)和測(cè)試環(huán)境。這樣一個(gè)過程,有連個(gè)顯而易見的好處:(1)保證在測(cè)試和生產(chǎn)環(huán)境中的源代碼控制;(2)確保在這些環(huán)境的所有代碼都通過了自動(dòng)化的軟件審查。
工具化的軟件自動(dòng)審查
我們使用的代碼自動(dòng)審查工具是Parasoft的Jtest,當(dāng)然還有很多工具可以完成類似功能。總的來說,Jtest是一個(gè)有效的管理工具,不過也存在一些問題。比如在使用之前,必須搭建一個(gè)基礎(chǔ)運(yùn)行環(huán)境;另外,它并不是一個(gè)黑盒式的解決方案,這也是背離我們希望的。Jtest包括靜態(tài)分析和動(dòng)態(tài)分析。其動(dòng)態(tài)分析功能比較強(qiáng)大,不過這已超出了本文的討論范圍。
4年前,我們團(tuán)隊(duì)因?yàn)閿?shù)據(jù)庫連接未關(guān)閉問題焦頭爛額。資源未能在try/catch/finally塊中得到正確清理(大家是否感覺很熟悉?),因此引入了Jtest。在當(dāng)時(shí),Rod Johnson大仙(譯者注:Spring框架和《Expert One-on-One J2EE Development without EJB》的作者)還沒有下凡,沒有給我們帶來JdbcTemplate,因此很多公司都還在與此問題奮戰(zhàn)。而解決這類問題,恰是Jtest的強(qiáng)項(xiàng)。其運(yùn)作原理是:分析Java類的結(jié)構(gòu)和內(nèi)容,檢查它們與既定規(guī)則的匹配程度。比如規(guī)則可能是這樣的:若在某個(gè)方法體中創(chuàng)建或從連接池中取得了數(shù)據(jù)庫連接,那么必須保證存在一個(gè)try/catch/finally塊,且在finally塊中關(guān)閉了連接,或?qū)⑦B接放回了連接池。4年前,我們就利用Jtest設(shè)立了這樣一個(gè)規(guī)則,將其嚴(yán)重程度定位一級(jí),并在構(gòu)建系統(tǒng)中設(shè)置:當(dāng)Jtest錯(cuò)誤出現(xiàn)時(shí),構(gòu)建過程自動(dòng)暫停當(dāng)前工作。這個(gè)系統(tǒng)工作得很好,數(shù)據(jù)庫連接問題再也沒有出現(xiàn)過。
現(xiàn)在,我們有了Rod和他的JdbcTemplate,但對(duì)于那些還沒有轉(zhuǎn)換到Spring的遺留Java應(yīng)用來說,上述規(guī)則仍可發(fā)揮作用。此外,Jtest還可以強(qiáng)制執(zhí)行很多其他結(jié)構(gòu)性標(biāo)準(zhǔn)檢查工作。比如,我們團(tuán)隊(duì)實(shí)施日志標(biāo)準(zhǔn)后,就引入了另一項(xiàng)規(guī)則,以杜絕代碼中再出現(xiàn)System.out.println語句的可能。上述這些功能,不過是Jtest的冰山一角。在Jtest魔盒中,規(guī)則多達(dá)數(shù)百項(xiàng),你還可以根據(jù)自己需要?jiǎng)?chuàng)建新的規(guī)則。
但現(xiàn)在的一個(gè)問題是,Parasoft對(duì)服務(wù)端Jtest的支持不夠理想。該公司的主要產(chǎn)品是一個(gè)Eclipse插件,此插件負(fù)責(zé)在IDE內(nèi)部對(duì)代碼執(zhí)行靜態(tài)和動(dòng)態(tài)分析。這不是我所想要的,我需要的是一個(gè)基于服務(wù)端的Jtest產(chǎn)品,服務(wù)端環(huán)境可以集成并調(diào)用它的功能。Parasoft認(rèn)為我們討論的這種最終式的組織控制和監(jiān)管,可以通過購買IDE插件(安裝到所有開發(fā)者的IDE),外加一個(gè)中心化的Parasoft報(bào)告服務(wù)器實(shí)現(xiàn)。但我們發(fā)現(xiàn)事實(shí)并非如此。Parasoft不能保證所有開發(fā)人員在將代碼簽入CVS前都會(huì)自覺執(zhí)行靜態(tài)檢查。我們沒有辦法控制這類插件,沒有Jtest插件報(bào)告“停!在有一級(jí)錯(cuò)誤前你不能簽入”這樣的控制點(diǎn)。因此,這種審查不宜放在客戶端執(zhí)行,而必須有一個(gè)中心化的控制點(diǎn),也就是一個(gè)中心化的BMS。我們需要的是服務(wù)端版本的Jtest,由我們自己完成對(duì)它的集成(雖然有點(diǎn)麻煩)。
當(dāng)然,我得再次強(qiáng)調(diào),Jtest不是唯一選擇。Adrian Colyer等人談到過利用ASPectJ完成代碼強(qiáng)制檢查。在中心化的監(jiān)管服務(wù)器上,這樣的功能很容易實(shí)現(xiàn)。我不能確定Jtest是否能滿足你的全部要求,不過它有免費(fèi)的優(yōu)勢(shì)。其他同類型產(chǎn)品以及eclipse插件一般能完成Jtest的不同部分功能。如果你想圖省事,可以選擇eclipse中的標(biāo)準(zhǔn)插件JDT,它支持從格式和句法兩個(gè)方面對(duì)源代碼做標(biāo)準(zhǔn)檢查。
實(shí)施監(jiān)管的最佳實(shí)踐
軟件自動(dòng)化監(jiān)管策略遠(yuǎn)比你選擇什么樣的技術(shù)構(gòu)建解決方案更為重要。如下是我們多年來從實(shí)踐中總結(jié)的經(jīng)驗(yàn)教訓(xùn):
- 監(jiān)管結(jié)構(gòu)要簡單。我們只有1、2、3共三種等級(jí)規(guī)則。違反第一等級(jí)規(guī)則時(shí),工作將暫停,項(xiàng)目將無法進(jìn)入測(cè)試和生產(chǎn)階段,直道問題解決。第二等級(jí)主要是指一個(gè)預(yù)備階段。它告訴開發(fā)人員,在下一個(gè)6-12月內(nèi),此等級(jí)的問題會(huì)上升到第一等級(jí),因此在此之前應(yīng)該將這些問題解決掉。第三等級(jí)問題不具實(shí)質(zhì)危害。這個(gè)等級(jí)只是建議解決某些問題,但在上升到其他等級(jí)前,這些問題不會(huì)對(duì)工作造成影響。
- 實(shí)施過程盡可能保守些。我在上面提到過,Jtest包括數(shù)百條規(guī)則,但在應(yīng)用初期,我們只實(shí)施了兩個(gè)第一等級(jí)規(guī)則。原因很簡單:循序漸進(jìn),免得一下子出現(xiàn)太多問題,讓項(xiàng)目經(jīng)理手忙腳亂、無所適從。
- 實(shí)施前做好壓力分析。公布新的第一等級(jí)規(guī)則前,你應(yīng)該對(duì)問題出現(xiàn)的頻率、修改代碼所造成的時(shí)間和財(cái)務(wù)成本作到心中有數(shù)。這一點(diǎn)并不困難——你只需用新規(guī)則對(duì)現(xiàn)在項(xiàng)目做一次靜態(tài)分析,然后考察分析報(bào)告。由此可避免第一等級(jí)規(guī)則實(shí)施后,讓整個(gè)組織難以為繼,最后又將其降級(jí)為第二等級(jí)的情況出現(xiàn)。如果分析結(jié)果顯示壓力很高,那么可首先確定為第二等級(jí),到以后合適時(shí)期再提升等級(jí)。實(shí)施嚴(yán)格的第一等級(jí)規(guī)則之前,應(yīng)該反復(fù)多次考察,必須確保管理者理解它帶來的沖擊并支持這樣的決定;而一旦實(shí)施,就應(yīng)該堅(jiān)決執(zhí)行。
- 充分溝通。和你的團(tuán)隊(duì)就新規(guī)則及其價(jià)值、實(shí)施的原因充分交流溝通。在絕大多數(shù)情況下,他們一般都能支持你,但你也不應(yīng)該讓他們無征兆“驚喜”。
盡管我們?cè)趯?shí)施過程中,還遇到了很多細(xì)節(jié)問題,但這樣一個(gè)主動(dòng)的、自動(dòng)化的軟件審查過程給我們的組織帶來了巨大利益。我們的軟件質(zhì)量得到了提升,而且更重要的是,依靠這樣一個(gè)可信賴的系統(tǒng),無需投入大量精力維護(hù)。人工維護(hù)過程的工作量非常浩繁。通過合理設(shè)計(jì)你的支持結(jié)構(gòu),的確可以在投入成本更低的前提下,給整個(gè)組織帶來更高的安全性。
作者簡介
Mark Figley:擁有8億美元資產(chǎn)的美聯(lián)保險(xiǎn)公司(AIG United Guaranty)的架構(gòu)組負(fù)責(zé)人。
it知識(shí)庫:代碼規(guī)范的自動(dòng)化監(jiān)管,轉(zhuǎn)載需保留來源!
鄭重聲明:本文版權(quán)歸原作者所有,轉(zhuǎn)載文章僅為傳播更多信息之目的,如作者信息標(biāo)記有誤,請(qǐng)第一時(shí)間聯(lián)系我們修改或刪除,多謝。