測試的革命 作者:Sam Guckenheimer 翻譯:Blueski 日期:2003-1-20
愛因斯坦在1915年發(fā)表了廣義相對論,當時這還只是一項偉大的科學猜想。4年后,Arthur Eddington和一個英國科學家組成的小組完成了一項重要的實驗,在實驗中他們拍攝了在日蝕過程中Hyades星云的圖片, 該實驗表明,因受日蝕影響,圖片中產(chǎn)生了很大的誤差幅度,由此證明了愛因斯坦關于空間的彎曲和光的重力效應的預測。大眾媒體隨即 給予愛因斯坦和Eddington很高的榮譽。同時也因為他們兩人都是和平主義者,所以被一起推崇為在這個飽受戰(zhàn)爭滄桑的世界上 的英雄。 雖然媒體顯得急不可待,但值得注意的是,廣義相對論在當時的科學界仍受到廣泛的爭議。直到半個世紀以后,人們才終于迎來了具 有決定性的實驗結果。當時Thomas Kuhn寫下了《科學革命的結構(The Structure of Scientific Revolutions)》一書,相對論被作為是革命性變革的完美例子– 一種新的觀念完全替代了一整套舊的信仰。
今年7月,我代表Rational Edge采訪了Cem Kaner。當時他借用了Kuhn的結構對目前軟件測試領域盛行的各種爭議和尚未確證的理論進行了分類。
后來,Rational Edge發(fā)表了我和軟件測試方面的其他專家的一些訪談。有些讀者卻質(zhì)疑我的選擇,他們會問:“這和我現(xiàn)在做的主要工作有什么關系 ?” 因此,在本文中,我想把所有這些課題放在一起,并對自己關于未來測試領域的發(fā)展的前瞻進行闡述。我可以斷言的是,測試人員、開發(fā) 人員、項目管理人員、公司管理人員和最終用戶們都期待著看到在這10年里軟件測試實踐方面將要發(fā)生的大變革。其原因很簡單,– 軟件質(zhì)量的低下已經(jīng)使美國經(jīng)濟蒙受巨大損失,NIST估計[注1] ,每年損失約600億美元,而Standish組織的數(shù)據(jù)則是2000億美元。所以改進軟件質(zhì)量已成為取得高投資回報率(ROI )的直接途徑,只有那些把握了軟件質(zhì)量的企業(yè)才會贏得勝利,其余的則將被人們所遺忘。 這些實踐和工具又是什么呢?我認為隨著時間的發(fā)展,以下五種趨勢會得到發(fā)展和應用。 1. 測試驅(qū)動型的軟件開發(fā)。在軟件生命周期的各個階段中,這些階段包括測試、需求分析、使用形像化符號進行的規(guī)格說明,以及基于UM L和其它新標準的實踐; 2. 探索性學習和發(fā)現(xiàn),這將成為迭代開發(fā)過程的一個組成部份; 3. 組件測試和易測試性設計,這將成為軟件開發(fā)不可分割的組成部份; 4. 更加重視適當?shù)募寄艿膽?,減少預先寫好的文檔,這將成為優(yōu)秀軟件過程的基本原則之一; 5. 使用自動化測試來取代目前嚴重影響測試效率的冗余繁復的人工過程。 下面讓我來對這些趨勢進行說明。
測試驅(qū)動型開發(fā)
這一實踐在RUP過程中又稱為“測試第一的設計(test-first design)”,而在很多XP( eXtreme Programming)文章中則稱之為“測試第一的開發(fā)(test-first programming)”。這一設想的提出至今已有近十年了,但是直到最近才得以在開發(fā)這一層次上取得很大的支持,這要在很大 程度上感謝敏捷方法組織。他們的核心思想是,在你寫一行代碼之前,你要先寫一行對其失效所進行的測試。在該測試的描述中應包含一 個程序代碼實際運行的實例。Martin Fowler將這樣的測試稱為“帶實例的規(guī)格說明(specification by example)”。 Brain Marick和其他一些敏捷測試的支持者已經(jīng)提出建議,要把測試驅(qū)動開發(fā)的概念擴展到所有的層次,包括系統(tǒng)測試和產(chǎn)品級測試[注2] 。Marick很清晰地表述了他的觀點:“我并不想寫出一套用于捕捉用戶愿望的需求,取而代之的是,我要寫出一套測試,一旦這些 測試能夠通過,產(chǎn)品就能使她滿意。所以我放棄需求編寫的步驟,而直接把需求分析加入到測試的創(chuàng)建過程中去。” [注3]這些測試腳本就象是可執(zhí)行的規(guī)格說明,當程序代碼通過了測試,那么這些程序代碼也將和規(guī)格說明保持一致。 如果你的代碼是使用Java,而且你的測試也在Java中測試,那么測試很可能會基于JUnit,你可能要么是 一個人,要么是編寫的兩人組中的一個,不管是哪一種情況,都很容易看到,這時Marick的方法是可行的。Marick相信這是 可伸縮的,可以適合于小團體,或者在有一個用戶在場的條件下進行“交談式測試的創(chuàng)建(conversational test creation)”的實踐。但是,如果有人要了解需求,這些需求卻是在測試設計中被捕捉的,而你并不在場,無法直接為他們進行 解釋,這樣就存在明顯的問題。在這種前提下,我并不認為測試一定要在程序語言中體現(xiàn)。即使對需求有了“精確”的表達,也不足以解 決可理解性的問題。對于這一問題,Leffingwell和Widrig有很好的描述 [注4],下圖即是基于他們的觀點。
圖1:可理解性問題(基于Leffingwell和Widrig的觀點)
實際上,Leffingwell和Widrig并沒有真正地考慮到測試的問題。他們的主要目的是想讓需求具備很高的可理解性 ,以便于讓用戶和投資者能夠充份理解。他們沒有解決這樣的問題,即如何把規(guī)格說明提交給其他投資者和生命周期的其它階段。作為一 種爭議,他們認為有必要保留一部份不明確性。而實際上,不明確的需求顯然會讓測試人員發(fā)瘋。 Marick提出的測試驅(qū)動型開發(fā)方法則走向另一個極端:測試代表了需求,測試的表現(xiàn)形式是一些可編譯、可執(zhí)行的代碼。但是,如 果測試(需求)的唯一表現(xiàn)形式是代碼的話,你就很難和商務人員/投資者/客戶進行有效溝通,甚至也很難和其他測試人員及開發(fā)人員 進行溝通。所有這些人都認為測試的形式本該是數(shù)據(jù)和流程,所以如果要以那種方式來做的話,你的測試必須變得非常容易進行交流。 一些公司正致力于為這種隔閡提供解決之道。Rational正積極參與一個OMG團體關于UML測試預定義項目,該項目可以 把測試表示為數(shù)據(jù)和可視化的流程,例如順序圖和活動圖。我們正在開發(fā)一些工具來對待以下三種表示方法,代碼,數(shù)據(jù)和流程,并取代 類似的測試視圖。 在過去,我們制作了這些“實例化規(guī)格說明”,按照RUP的命名方法,可稱之為“用例實現(xiàn)”。“實例化規(guī)格說明”和“用例實現(xiàn) ”的相似性可以通過援引最近的一個使用Agile方法的工作團體的報告來說明: [一個參與者] 提到,和他一起工作的人都很喜歡使用“測試第一”的開發(fā)方式。當測試框架被開發(fā)好以后,特別是當用于組織運行的測試腳本被定義好 時,他們的工作變得更為容易。而用例在組織起來開發(fā)腳本時會有所幫助。他們的測試可以捕捉到用戶的需要。人們之所以喜歡這樣的方 法,其原因是它提供了他們工作所需的結構。在Agile方法中,需求以“案例(story)”的形式存在。于是,測試腳本將以接 口已明確定義好的形式把這些“案例”編織在一起。這意味著結對編程的人可以根據(jù)他們需要的順序相互測試接口 [注5]。 類似地,OMG測試預定義工作組發(fā)現(xiàn),將UML排列起來也很容易。你可以將一個用例實現(xiàn)轉成為測試,這只需增加兩件東西:驗證工 作(例如,“現(xiàn)在用測試來檢查這個軟件中的條件。”)以及裁決(例如,通過、失敗,或者暫不決定)。這樣的信息在規(guī)格說明中隨處 可以捕捉到,所以UML符號可以讓我們測試人員有了表達的手段。 于是,只需要額外做一點點努力,就可以使測試對客戶來說變得很容易理解:數(shù)據(jù)表和可視化流程。然后,當有軟件需 要測試的時候,測試已準備就緒。這一實踐使測試驅(qū)動型開發(fā)在系統(tǒng)級測試上也具有實用的價值,因為在設計工件和測試設計工件之間確 實沒有什么區(qū)別。僅僅只要增加驗證的注解以及進行裁決就可以了。在比較容易理解的可視化流程和數(shù)據(jù)的幫助下,你不再需要把系統(tǒng)設 計從測試設計中分離出來。而且由于這些流程具有一個可執(zhí)行的形式(生成的代碼),因此可以把每一次創(chuàng)建作為測試來執(zhí)行。這使整個 團隊得到了解放,并成為Kent Beck和Erich Gamma所說的”受影響的測試(test infected)”: “…這是一種測試的類型,只要使用非常小的投入即可使你成為一個更快的、更多產(chǎn)的、更具預見性的、壓力更小的開發(fā)者。” -Kent Beck和Erich Gamma《Test Infected: Programmers Love Writing Tests》[注6]
探索性學習
這第二種趨勢認識到了這樣的現(xiàn)實,即我們通常很難把問題描述得十分正確:需求在演變,我們需要簡化(扁平化)或者把著名的“ 錯誤-代價”曲線顛倒過來。這里的核心思想是:我所說的每一項,不管是在產(chǎn)品、測試或者跟蹤排錯的第一步,都在運行軟件時通過探 索性發(fā)現(xiàn),才使得可視化-可執(zhí)行-設計-測試的整個過程和結果變得更為真實。 實時分析工具,例如Rational PurifyPlus就帶有制作精良的非常明確的實例,例如發(fā)現(xiàn)內(nèi)存錯誤和性能上的瓶頸。你還可以用它們來支持更廣泛的探索,尤 其是在由各種不同組件所構成的系統(tǒng)中。80%的企業(yè)級行為都是對某些組件的重新組裝,包括對遺留下來的成份進行更新或補充等等, 而不是從頭開始設計。 在軟件運行時你會發(fā)現(xiàn)很多新的信息,至少和設計時一樣多。這也是RUP強調(diào)要把可運行的軟件作為每一次迭代的組成部份的緣故 。你發(fā)現(xiàn)的每一樣東西都應該是可視的,并且放在你用于設計的同樣的工件中。對運行著的系統(tǒng)的跟蹤是一種UML的迭代,經(jīng)過驗證和 裁決,可以轉化為一種可復用的測試。數(shù)據(jù)也值得進行概括,并形成新的等價類的基礎,等等。 當前,大多數(shù)探索性測試的提倡者,尤其是Kaner和Bach,都把這作為使用后即可放棄的行為[注7] 。但我認為,我們一旦把所探索到的內(nèi)容無縫地加入到設計中去后,就會發(fā)現(xiàn),這是高度可重用的。事實上,這是實時分析的一個新的應 用:通過探索而發(fā)現(xiàn)的有價值的東西的捕獲和利用。
組件測試和易測試性設計
第三種趨勢是關于理解測試人員和開發(fā)人員的相對角色,并為每種角色分配合適的工具。Rational把提供組件測試和易測試 性設計作為一種最佳實踐,這已有很長的歷史。我認為對這些做法的采納源自于對質(zhì)量的基本理解。當前,太多的測試人員的行為都受限 于規(guī)格說明的模式,其中有很多浪費。其實開發(fā)人員才有責任去保證所開發(fā)出來的軟件和規(guī)格要求相一致,他們應該使用合適的工具和過 程來達到這樣的目的。 Boris Beizer描述了2種不同角色的區(qū)別: 獨立測試的目的是提供一種不同的觀察點,由此產(chǎn)生了不同的測試,并且在比開發(fā)人員所采用的開發(fā)環(huán)境更豐富的環(huán)境中執(zhí)行測試。 自我測試(self-testing)的目的是消除那些bug,這可以在相對更簡單、更明確的單元/組件環(huán)境,或者低層次的系統(tǒng) 測試中進行,并且只需花費較低的代價。[注8] 測試驅(qū)動型開發(fā)提供更大的能力。如果規(guī)格說明就是可執(zhí)行的測試,而測試進行沒有產(chǎn)生別的問題,那么就可以認為軟件和規(guī)格說明 相符。其它的單元測試過程也只是為了保證同樣的事情:就規(guī)格說明而言,不管它們是什么內(nèi)容,代碼總是與之相符合的。如果不符合, 那么就是開發(fā)人員的問題。Kent Beck非常清楚測試驅(qū)動型開發(fā)所帶來的效果: 如果測試驅(qū)動編碼的缺陷密度達到足夠低的話,那么專業(yè)測試的角色將不可避免地發(fā)生改變。以前的是“成人監(jiān)護”方式,而現(xiàn)在更類似 于一種擴音器,它宣稱測試要更多地驗證的是系統(tǒng)必須做什么。[注9] 這需要整個團隊接受這樣的一個前提,即保證軟件符合規(guī)格說明是開發(fā)人員的職責。這使得測試者可以有更多精力用于發(fā)現(xiàn)和避免一 些別的問題,從客戶或者用戶的角度來看,這些問題的存在可能會使軟件所應有的價值有所降低。Brian Marick針對這些冗長煩瑣做法的錯誤性寫過一篇很著名的文章[注10]。那些文檔通常已說明了一個系統(tǒng)中的多于一半的錯誤,他聲稱,因此你就需要專門有一個過程來讓你的測試人員用來發(fā)現(xiàn)這些問題。 易測試性的設計在這里具有重要的意義?,F(xiàn)在很多軟件已改用基于服務的構架,這種構架是基于組件的構架的一種擴展,隨之而來的 是新增加的復雜性,即組件可以在沒有警告的情況下發(fā)生改變,其可靠性的問題是極為嚴重的。大多數(shù)IT經(jīng)理會接受99%的可靠性, 我敢打賭,他們會認為這一標準甚至已經(jīng)高于他們所用的買來或構建的組件。但是,如果你構建的系統(tǒng)有超過100個組件,每個組件具 有99%的可靠性,那么整個系統(tǒng)的可靠性是0.99的100次方,實際上僅有37%。順便提一下,這也是為什么那些有高可靠性要 求的市場,例如電信業(yè),會要求“5個9”的可靠性,即99.999%。在這樣的情況下,你就可以使用100個組件,綜合起來仍有 99.9%的可靠性。 這一基本原理實際上要求軟件進行易測試性的設計,就象30年前市場形成時硬件所做的一樣。 Bertrand Meyer是這一領域研究的領先者,他提出了按合約設計,其意思是把對類及調(diào)用該類的客戶端之間的關系的檢視作為一種正式的協(xié)議 ,這表達了每個團體的權利和義務[注11]。Meyer的概念已被廣泛接受,其標志之一就是合約設計的規(guī)格語言WSDL的誕生,該語言是Web Service標準的核心[注12]。 我認為人們正越來越多地接受易測試性設計。易測試性已成為諸如Web Service等框架和標準的一個補充的組成部份。接口也正成為技術平臺和操作系統(tǒng)的一部份。一個比較簡單的例子是,J2EE和 .NET 中預定義開放式接口和API映射,可以允許工具來檢查在運行時刻環(huán)境中發(fā)生了什么。另一個真實而有益的趨勢是人們正使用象Rat ional XDETM這樣的工具,通過設計模式的方法來構建應用–而易測試性已被置入在設計模式中。模式所構造的組件包括外在的用于測試 的接口 — 即組件的一些適當?shù)膅etter和setter方法。 易測試性設計的一個實用的法則是,你已在GUI和表示層的后面對業(yè)務邏輯或軟件的行為進行了訪問。Bret Pettichord主張,易測試性設計應該是關于可見性和控制的設計[注13] 。你通過較低層獲得其外在接口,從而得到所需要的可見性,在測試的時候,通過很多開放的接口來允許你直接看到軟件中的聲明。同樣 地,你需要接口來讓你能夠控制應用,由此你才可以避免使用GUI,而是通過自動化框架來驅(qū)動應用。
重視技能
第四種趨勢是增進軟件測試專業(yè)技術知識的水準。在.com流行的年代中有這樣的誤解,即使沒有很深的測試技術知識、業(yè)務應用 方面的領域知識以及充份的培訓,你也能有效地進行測試。但當你面對一個分布式的應用–例如,一個特別的基于Web的應用,就會 發(fā)生問題。Hung Nguyen關于基于Web應用的測試論著是這種觀點最好的代表[注14] 。Nguyen認為,測試人員應該知道技術是如何對他們所看到的各種錯誤產(chǎn)生影響的。他們需要對技術問題有所理解,例如配置的問 題,以及他們所檢查的技術本身內(nèi)含的問題。各種細節(jié)上的理解,例如了解應用服務器中Bean和Container管理的持續(xù)性之 間的區(qū)別,可以直接影響到你發(fā)現(xiàn)特定缺陷的能力。 所以,現(xiàn)在的測試人員除了測試本身的技術以外,還需要理解開發(fā)技術和領域知識。例如,假設你在瀏覽器中看到一個錯 誤:“404 - Page not found”這樣的錯誤可能是錯誤的鏈接所引起,也可能是因為某些服務失效而產(chǎn)生。一個好的測試人員并不會在出錯頁上就停下來, 他會進一步診斷出錯的原因。他不僅需要對該失效的服務具備足夠多的認識和理解,而且他要通過查看其它使用該服務的頁面來驗證自己 的猜測。這就是一種Bug隔離的重要技能。 另一種技能是成為一個很好的探索者。以前,測試方面的很多論述對計劃和腳本有很多要求,但現(xiàn)實情況下,一個好的測試人員就是 一個好的探索者。他們喜歡在測試過程中發(fā)現(xiàn)一些暗示,并知道怎么來進行跟蹤。這樣的暗示有時很簡單,例如一個頁面要很長時間才能 加載。那么對于一個好的測試人員來說,他可能會想,這其中發(fā)生了什么?然后繼續(xù)了解要通過什么路徑可以進一步發(fā)現(xiàn)答案。Jame s Bach所寫的一些內(nèi)容可能是在探索性測試方面最好的材料[注15],其中有該課題的最佳練習。我認為這顯然也是一個重要的技能,每個團隊都需要這樣的技能。 我們在Rational學院的課程中已經(jīng)非常重視如何去應用基本的軟件測試技術。可以和Florida Tech的Cem Kaner一起開始那些專為測試人員提供的軟件測試基本原理的新課程[注16] 。該課程并不專注于測試工具,而是專注于如何成為一名很好的軟件測試人員,尤其是當你正在應用迭代開發(fā)過程的時候。最后,測試人 員的生產(chǎn)能力和開發(fā)人員的生產(chǎn)能力是同樣重要的,只有富有經(jīng)驗的測試人員才能使產(chǎn)品讓客戶獲得很高的投資回報率(ROI)。Ra tional已經(jīng)發(fā)現(xiàn),一個更快、更經(jīng)濟、更高質(zhì)量的開發(fā)過程的關鍵就是迭代式開發(fā)過程。迭代式過程可以使測試在整個開發(fā)周期中 得以提前,從而可以更早地發(fā)現(xiàn)錯誤,修改錯誤也相對更加容易,其成本也相對更低。 但是,我認為現(xiàn)在的測試人員還沒有得到很好的訓練以勝任迭代開發(fā)過程中的測試工作要求,項目經(jīng)理也沒有得到很好的 訓練以正確地認識測試在迭代項目中所扮演的角色,開發(fā)人員也沒有得到很好的訓練以得到他們需要了解的測試相關技術,例如基礎等價 類劃分。因此我們在RUP(Rational Unified Process)和Rational學院中增加了大量關于測試的材料。而且我們還將繼續(xù)擴充這些材料以幫助測試人員、開發(fā)人員和 項目經(jīng)理們在迭代過程的協(xié)同工作中做得更好。
自動化測試
第五種趨勢是關于測試自動化方面。目前,為了實行測試自動化,測試人員和開發(fā)人員要花費80%的精力來使(自動化 )測試成為可能,而只有20%被用于使(自動化)測試變得更有意義。這一可怕的事實使很多人最終放棄了測試自動化。同樣,目前的 自動化軟件質(zhì)量(ASQ) 工具提供商正花費80%的精力用于重復工作,他們必須重新創(chuàng)建一個基礎平臺來支持相應的測試和排錯工作,而僅有20%的精力來為 測試和開發(fā)人員提供可見的有價值的功能。 最近,Rational、IBM和其它一些公司開展了一個開發(fā)源碼的項目,其目標就是要把這兩個百分數(shù)顛倒過來。該項目被命名為 Hyades,取自Eddington用來校驗愛因斯坦理論的星云的名字,并由Eclipse.org負責。它的目標也包括加強 實驗性觀察,測試過程及軟件度量,最終實現(xiàn)更具實用性的測試自動化。
對于使用Eclipse的開發(fā)人員和測試人員來說,Hyades既是一種集成測試及跟蹤,也是環(huán)境監(jiān)控程序。Eclipse 為整個測試過程提供了標準、工具和互操作性,以使測試能更早地移植到應用生命周期中去。對ASQ提供商和集成商來說,Hyade s為自動化測試、跟蹤、預定義、監(jiān)控和資源管理提供了一個可擴展的架構和平臺。和目前的測試與跟蹤工具所不同的是,Hyades 將提供一個統(tǒng)一數(shù)據(jù)模型(實現(xiàn)了UML測試預定義),這是一種標準的用戶工作的流程,包括一套統(tǒng)一的API及相關工具,可以在排 列的目標項之間連續(xù)地工作。
總結:測試實踐的大變革
Rational和一些競爭對手盡管自己也提供商業(yè)測試工具,為什么還要加入到象Hyades這樣的開放源碼項目 中去呢? 我的很多同事也問過這樣的問題。其核心理由就是上面所說的80/20比例。所有人都很想改變這個比例。 80%的基礎平臺對用戶來說是不可見的,它難以分辨,也難以維護。每當測試所用軟件的環(huán)境條件更新的時候,(新的編譯器,新的庫 文件,新的操作系統(tǒng)補丁,等等),測試工具就必須隨之更新。如果你是一位富有經(jīng)驗的實時分析或自動化工具的用戶,你可能早已感受 到這種脆弱。你也許已經(jīng)不止一次在考慮要更換開發(fā)環(huán)境,因為有些工具不支持一些新的版本。這一維護成本給工具提供商帶來了巨大的 壓力,因此工具商們決定無償?shù)貫樾碌囊婀ぷ?,并分享其成果,進而滿足用戶的需要。Hyades項目必將為我們的用戶提供其價值 。
對Hyades來說,它是由一系列分散的努力所組成。在我所歸納的五種趨勢中,Hyades是其中的一個組成部份,它將同時 為測試人員和開發(fā)人員提供新的測試支持方式。這是一種技術,它可以在生命周期的一開始就推動測試,帶來工具方面更好的協(xié)同性,通 過改進測試,新的效果會明顯地加入到軟件中去。它將為這10年里我能所能看到的在測試實踐上的改革提供有力的支持。我相信這種技 術,以及其它有類似目標和基礎的技術,代表著我們產(chǎn)業(yè)的未來。我們這些已被卷入到Hyades項目中的人都有一種使命感,我們不 能辜負Hyades這一名稱: 讓我們描畫出金牛座的頭部–Hyades星云中的恒星,這對我們來說意義重大,這將帶給我們快樂,并使我們能夠 測量整個宇宙
|