業(yè)務(wù)導(dǎo)向且支持開發(fā)過程的測(cè)試
這一象限的測(cè)試通常稱作功能測(cè)試或驗(yàn)收測(cè)試。驗(yàn)收測(cè)試確保用戶故事的驗(yàn)收條件得到滿足。在開發(fā)一個(gè)用戶故事之前,就應(yīng)該寫好驗(yàn)收測(cè)試,采取完美的自動(dòng)化形式。像驗(yàn)收條件一樣,驗(yàn)收測(cè)試可以測(cè)試系統(tǒng)特性的方方面面,包括其功能(functionality)、容量(capability)、易用性(usability)、安全性(security)、可變性(modifiability)和可用性(availability)等。關(guān)注于功能正確性的驗(yàn)收測(cè)試稱作功能驗(yàn)收測(cè)試,而非功能驗(yàn)收測(cè)試歸于圖中的第四象限。如果對(duì)于功能與非功能測(cè)試有模糊認(rèn)識(shí)且常常搞不清他們的區(qū)別,
在敏捷環(huán)境中,驗(yàn)收測(cè)試是致關(guān)重要的,因?yàn)樗麄兛梢曰卮鹑缦乱恍﹩栴}。對(duì)開發(fā)人員來說,它回答了“我怎么知道我做完了呢?”對(duì)用戶來說,它回答了“我得到我想要的功能了嗎?”當(dāng)驗(yàn)收測(cè)試通過以后,它所覆蓋到的需求或用戶故事都可被認(rèn)為是完成了。因此,在理想情況下,客戶或用戶會(huì)寫驗(yàn)收測(cè)試,因?yàn)樗麄兌x了每一個(gè)需求的滿足條件。時(shí)新的自動(dòng)化功能測(cè)試工具,比如Cucumber、JBehave、Concordion以及Twist,都旨在把測(cè)試腳本與實(shí)現(xiàn)分離,以達(dá)到這種理想狀態(tài),并提供某種機(jī)制方便地將二者進(jìn)行同步。在這種方式下,由用戶來寫測(cè)試腳本是可能的,而開發(fā)人員和測(cè)試人員則要致力于實(shí)現(xiàn)這些測(cè)試腳本。
總之,對(duì)于每個(gè)需求或用戶故事來說,根據(jù)用戶執(zhí)行的動(dòng)作,一定會(huì)找到應(yīng)用程序中一個(gè)中規(guī)中矩的執(zhí)行路徑,這稱為Happy Path。Happy Path通常如下方式來描述:“假如[當(dāng)測(cè)試開始時(shí),系統(tǒng)所處狀態(tài)的一些重要特征],當(dāng)[用戶執(zhí)行某些動(dòng)作后],那么[系統(tǒng)新的狀態(tài)的一些重要特征]?!庇袝r(shí)這稱為測(cè)試的“given-when-then”書寫模型。
然而,除最簡(jiǎn)單的系統(tǒng)外,任何用例的初始狀態(tài)、被執(zhí)行的動(dòng)作以及執(zhí)行后的結(jié)果狀態(tài)都會(huì)有所不同。有時(shí)候,這些變化會(huì)形成不同的用例,也就是無所謂的Alternate Path。另外,這些變化還可以引發(fā)一些錯(cuò)誤處理。從而導(dǎo)致無所謂的Sad Path。很明顯,還有很多測(cè)試,因?yàn)閷?duì)于其中的可變因素,給予不同的值會(huì)得到不同的結(jié)果。等價(jià)劃分分析(equivalence partitioning analysis)和邊界值分析可以幫助你得到盡可能小的用例集合,并保證測(cè)試覆蓋完整的需求。然而,即便如此,你也要憑直覺來挑選一些最為相關(guān)的用例。
系統(tǒng)的驗(yàn)收測(cè)試應(yīng)該運(yùn)行在類生產(chǎn)環(huán)境中。例如手工驗(yàn)收測(cè)試,它通常是將應(yīng)用部署在用戶驗(yàn)收測(cè)試(UAT)環(huán)境后進(jìn)行的。這個(gè)環(huán)境應(yīng)該盡可能與生產(chǎn)環(huán)境相似(無論是配置還是應(yīng)用程序的狀態(tài))。不過對(duì)于那些外部服務(wù)來說,我們可能會(huì)使用一些模擬(mock)技術(shù)。測(cè)試人員通過應(yīng)用程序的標(biāo)準(zhǔn)用戶界面來執(zhí)行測(cè)試工作。自動(dòng)化驗(yàn)收測(cè)試也應(yīng)該運(yùn)行在類生產(chǎn)環(huán)境之上,并且測(cè)試用具(test harness)與應(yīng)用交互的方式應(yīng)該和真正的用戶使用使用應(yīng)用的方式相同。
自動(dòng)化測(cè)試驗(yàn)收
自動(dòng)化驗(yàn)收測(cè)試有很多很有價(jià)值的特性。
它加快了反饋速度,因?yàn)殚_發(fā)人員可以通過運(yùn)行自動(dòng)化測(cè)試,來確認(rèn)是否完成了一個(gè)特定需求,而不用去問測(cè)試人員。
它減少了測(cè)試人員的工作負(fù)荷。
它讓測(cè)試人員集中精力做探索性測(cè)試和高價(jià)值的活動(dòng),而不是被無聊的重復(fù)性工作所累。
這些驗(yàn)收測(cè)試也是一組回歸測(cè)試套件。當(dāng)開發(fā)大型應(yīng)用或者在大規(guī)模團(tuán)隊(duì)中工作時(shí),由于采用了框架或許多模塊,對(duì)應(yīng)用某一部分的更改很可能會(huì)影響其余特性,所以這一點(diǎn)尤其重要。
就像行為驅(qū)動(dòng)開發(fā)(BDD)所建議的那樣,使用人類可讀的測(cè)試以及測(cè)試套件名,我們就可以從這些測(cè)試中自動(dòng)生成需求說明文檔。像Cucumber和Twist這樣的工具,就是為了讓分析人員可以把需求寫成可執(zhí)行的測(cè)試腳本而設(shè)計(jì)的。這種方法的好處在于通過驗(yàn)收測(cè)試生成的需求文檔從來不會(huì)過時(shí),因?yàn)槊看螛?gòu)建都會(huì)自動(dòng)生成它。
回歸測(cè)試也是一個(gè)特別重要的話題。在前面的象限圖中并沒有回歸測(cè)試,因?yàn)樗强缦笙薜??;貧w測(cè)試是自動(dòng)化測(cè)試的全集。它們用來確保任何修改都不會(huì)破壞現(xiàn)有的功能,還會(huì)讓代碼重構(gòu)變得容易些,因?yàn)榭梢酝ㄟ^回歸測(cè)試來證明重構(gòu)沒有改變系統(tǒng)的任何行為。在寫自動(dòng)化驗(yàn)收測(cè)試時(shí),應(yīng)該時(shí)刻牢記,這些測(cè)試是回歸測(cè)試套件的組成部分。
然而,自動(dòng)化驗(yàn)收測(cè)試的維護(hù)成本可能很高。如果寫得不好,它們會(huì)使交付團(tuán)隊(duì)付出極大的維護(hù)成本。由于這個(gè)原因,有些人不建議創(chuàng)建大而復(fù)雜的自動(dòng)化測(cè)試集合,比如James Shore[dayXYv]就持這種觀點(diǎn)。然而,通過使用正確的工具,并遵循好的實(shí)踐原則,完全可以大大降低創(chuàng)建并維護(hù)自動(dòng)化驗(yàn)收測(cè)試的成本,從而令收益大于付出。
同樣需要記住的是,并不是所有的東西都需要自動(dòng)化。對(duì)于某些方面的測(cè)試來說,用手工方法做更好。易用性測(cè)試及界面一致性等方面很難通過自動(dòng)化測(cè)試來驗(yàn)證。盡管有時(shí)候測(cè)試人員會(huì)將自動(dòng)操作作為探索性測(cè)試的一部分,比如初始化環(huán)境、準(zhǔn)備測(cè)試數(shù)據(jù)等,但探索性測(cè)試不可能被完全自動(dòng)化。很多情況下,手工測(cè)試就足夠了,甚至優(yōu)于自動(dòng)化測(cè)試。總之,我們傾向于將自動(dòng)化驗(yàn)收測(cè)試限于完全覆蓋Happy Path的行為,并僅覆蓋其他一些極其重要的部分。這是一種安全且高效的策略,但前提條件是其他類型的自動(dòng)化回歸測(cè)試是很全面的。一般我們將代碼覆蓋率高于80%的測(cè)試視為“全面的”測(cè)試,但測(cè)試質(zhì)量也非常重要,單單使用覆蓋率這一指標(biāo)是不夠的。我們這里所說的測(cè)試覆蓋率包括單元測(cè)試、組件測(cè)試和驗(yàn)收測(cè)試,每一種測(cè)試都應(yīng)該覆蓋應(yīng)用程序的80%(我們并不認(rèn)同60%的單元測(cè)試覆蓋率加上20%的驗(yàn)收測(cè)試覆蓋率就等于80%的覆蓋率這一天真的想法)。
作為對(duì)自動(dòng)化驗(yàn)收測(cè)試覆蓋率比較好的一種評(píng)估方法,可以考慮下面的情形:假設(shè)要替換系統(tǒng)中的某一部分(比如持久層,使用另一種實(shí)現(xiàn)來替換它)。當(dāng)你完成替換時(shí),運(yùn)行了自動(dòng)化測(cè)試,并且測(cè)試全部通過了。你有多大自信心,認(rèn)為系統(tǒng)可以正常運(yùn)行呢?一個(gè)好的自動(dòng)化測(cè)試套件應(yīng)該給你足夠的信心執(zhí)行重構(gòu),甚至對(duì)應(yīng)用程序架構(gòu)進(jìn)行重構(gòu)。而且,假如測(cè)試能全通過,就證明應(yīng)用程序的行為沒有受到影響。
對(duì)于軟件開發(fā)的各個(gè)方面,各個(gè)項(xiàng)目之間都會(huì)有所不同,你需要監(jiān)控到底花了多長(zhǎng)時(shí)間做重復(fù)性的手工測(cè)試,以便于決定什么時(shí)候把它們自動(dòng)化。一個(gè)很好的經(jīng)驗(yàn)法則就是,一旦對(duì)同一個(gè)測(cè)試重復(fù)做過多次手工操作,并且你確信不會(huì)花太多時(shí)間來維護(hù)這個(gè)測(cè)試時(shí),就要把它自動(dòng)化。更多關(guān)于何時(shí)做自動(dòng)化的內(nèi)容,
需要寫的最重要的自動(dòng)化測(cè)試是那些對(duì)Happy Path的測(cè)試。每個(gè)需求或用戶故事都應(yīng)該有對(duì)Happy Path的自動(dòng)化驗(yàn)收測(cè)試,而且應(yīng)至少有一個(gè)。這些測(cè)試應(yīng)該被每位開發(fā)人員當(dāng)做冒煙測(cè)試來使用,從而能夠?yàn)椤笆欠衿茐牧艘延械墓δ堋碧峁┛焖俜答?。也就是說,這類測(cè)試應(yīng)該是自動(dòng)化的第一目標(biāo)。
當(dāng)你有時(shí)間寫更多的自動(dòng)化測(cè)試時(shí),很難在Happy Path和Sad Path之間進(jìn)行選擇。如果你的應(yīng)用程序比較穩(wěn)定,那么Alternate Path應(yīng)該是你的首選,因?yàn)樗鼈兪怯脩羲x的場(chǎng)景。如果你的應(yīng)用有較多的缺陷并且經(jīng)常崩潰的話,那么戰(zhàn)略性地應(yīng)用對(duì)Sad Path的測(cè)試會(huì)幫助你識(shí)別那些問題域并修復(fù)它們,而且自動(dòng)化可以保證應(yīng)用程序保持在穩(wěn)定狀態(tài)。