构建测试的体系化思维(基础篇)
讀完需要
22
分鐘速讀僅需 8 分鐘
之前寫過一篇文章《神圣的QA》,是面向想從事 QA 工作的畢業生同學的,文中有講到 QA 的五個基本職責:
理解和澄清業務需求
制定策略并設計測試
實現和執行測試
缺陷管理與分析
質量反饋與風險識別
最近有朋友希望我能分享體系化的測試需要關注哪些方面,我又想到了這五個基本職責。原文中基于“生產杯子”的需求對于五個職責有解釋,本文將展開每個職責,從測試實踐和方法集的角度來分析測試需要做什么和怎么做。
? ?
01 理解和澄清業務需求
業務需求是軟件開發的源頭,正確理解需求的正確性不言而喻,理解和澄清需求也是測試工作至關重要的一部分。
1. 理解和澄清業務需求的維度
具體該如何去理解和澄清需求呢?我認為測試人員可以從以下三個維度去理解和澄清業務需求:
關于這幾個維度的詳細內容,在文章《敏捷測試如何優化業務價值》中有介紹。
2. 需求的可測試性
正確理解業務需求以外,對需求的描述質量也需要關注,其中需求的可測試性是最為重要的一個方面:
如果需求不可測,也就不可驗收,沒辦法知道項目是否成功完成;
以可測試的方式編寫需求,才能確保需求能夠正確實現并驗證。
需求的可測試性主要體現在下面三個維度:
完備性
需求的完備性主要指流程路徑需要考慮全面,要求邏輯鏈路完整,既要有正向路徑,也要包括異常場景。
比如:正確的用戶名密碼可以登錄,不正確的用戶名和密碼登錄會發生什么,這兩者都是需要清晰定義的。
客觀性
需求的描述不要用一些主觀性的詞語,而是需要客觀的數據和示例來說明。比如下面這段主觀性的描述是個非常糟糕的需求示例:
系統應該易于有經驗的工程師使用,并且應該使得用戶的出錯盡可能少。
推薦采用“實例化需求” ( http://www.woshipm.com/pmd/4074396.html )的方式來編寫需求文檔,將業務規則通過實例表述出來,不僅易于團隊不同角色的理解,而且不容易產生歧義。
獨立性
獨立性主要是針對單個業務功能點(敏捷開發中的用戶故事),要盡量的獨立,跟其他功能邊界清晰,減少因為依賴導致的功能點不可測。
比如:輸入和輸出要在同一個功能點里可驗證,A 功能點的輸入不能通過 B 功能點的輸出來驗證。
敏捷開發中的用戶故事遵循INVEST原則( https://en.wikipedia.org/wiki/INVEST_(mnemonic) ),將可測試性和獨立性是分開描述的,我認為獨立性也會影響可測試性,在這里把獨立性作為可測試性的一個因素。
? ?
02 制定策略并設計測試
制定策略并設計測試是五個職責里最為關鍵的一個,涵蓋的內容較多。看上去是策略和測試設計兩部分,但實際上包含了測試所需要考慮的方方面面。下面挑選我認為比較有價值的內容分別介紹。
1. 一頁紙測試策略
策略是方向,要做好軟件的測試工作,離不開測試策略的指導。測試策略通常對于經驗不是太豐富的測試人員來講,可能挑戰比較大。不過,我曾經提出來的“一頁紙測試策略”可以很好地幫助測試人員去思考和制定自己項目適配的測試策略。一頁紙測試策略如下如所示:
在一頁紙測試策略里邊,清晰地定義了測試策略需要考慮的三個部分:
指導性原則:團隊為質量負責
測什么:測試的內容
怎么測:測試左移、測試右移和精益測試
更多詳情請參考我的文章《一頁紙測試策略》。
2. 測試流程與質量門禁
我們經常會發現有些團隊的測試流程定義的也很清晰,但是每個環節要求做到什么效果并沒有嚴格的要求,很多質量工作做的并不到位,導致后面測試階段測試人員的壓力巨大或者最終交付的質量并不高。
前面一頁紙測試策略里已經有包含測試流程部分,這里再次單獨提及主要是為了強調質量門禁的重要性。測試流程每個項目或團隊可能都不太一樣,但是不管測試流程包括哪些環節,每個環節的輸出結果要求務必定義清晰,也就是要清晰定義每個環節的質量門禁,如下圖所示:
注意:此圖僅為示例,實際情況需要根據自身團隊情況適配。
3. 典型測試類型
上面的流程圖示例中列出了多種不同的測試類型,而實際的測試類型遠不止這些。由于篇幅有限且這部分內容不是本文的重點,本文只介紹跟測試人員關系非常緊密的四種典型的測試類型。這四類測試的分類維度并不相同,這里不求詳盡。不清楚但又感興趣的同學,請自行網上搜索。
冒煙測試
冒煙測試來源于電路板的測試,也就是通電后看電路板是否冒煙,如果冒煙說明這塊電路板是不可能正常工作的,也就不用去驗證其他功能了。
對應到軟件的冒煙測試,就是驗證軟件的最基本行為是否正常,例如:“程序是否運行?”,“用戶界面是否打開?”或“單擊事件是否有效?”等。只有冒煙測試通過,才有進一步開展驗證軟件功能測試的必要,否則就需要先修復重新出新版本才可以。
我們發現有的團隊只對新開發功能進行冒煙測試,其實這是不太正確的,或者說這個測試就不叫冒煙測試。冒煙測試應該是對整個系統級別的基本行為進行驗證,不區分什么新舊功能。
回歸測試
回歸測試的目的是驗證新開發功能或者修復 bug 的時候,是否對已有功能有破壞。因此,回歸測試的對象主要是針對已有功能,對于新功能的測試不叫回歸。
回歸測試的策略通常有四類:
全面回歸:這種就是不分青紅皂白,對所有已有功能進行全面的測試,這種策略成本較高,但是覆蓋率較全,一般對質量要求特別高的金融類產品采用全面回歸的方式較多。
選擇性回歸:這種一般是測試會跟開發進行溝通,了解當前代碼編寫可能影響到的范圍,選擇對這些受影響的功能模塊進行回歸。這種形式可能漏掉沒有意識到但是關聯到的功能,有一定的風險,但是較為經濟的一種做法。
指標法回歸:這種一般是團隊對回歸測試的覆蓋率有要求,比如要覆蓋 50%的已有功能測試用例,執行回歸測試不能低于這個覆蓋率。這種光看指標數字的做法是最不推薦的,雖然覆蓋率達標了,但是有可能該測的沒有測到。
精準回歸:精準回歸就是當下非常熱門的精準測試,這是采用技術的手段將代碼改變所影響到的范圍跟測試用例關聯起來,精準地執行受影響的用例。這種質量最為有保證,但是精準測試實現成本是非常高的。
回歸測試可以手動進行,也可以是自動化測試,但通常回歸測試的量都會比較大,以自動化的方式進行會比較高效。
端到端測試
端到端測試基于測試覆蓋的粒度分類,是針對單元測試和接口測試等而言的。
端到端測試是從頭到尾驗證整個軟件及其與外部接口的集成,其目的是測試整個軟件的依賴性、數據完整性以及與其他系統、接口和數據庫等的通信,以模擬完整的業務流程。因此,端到端測試是最能體現用戶真實業務行為的測試,有著非常重要的價值。
但是,由于端到端測試涉及到系統各個相關組件和外部依賴,其穩定性和執行成本相對都是比較高的。于是有了覆蓋范圍較小的接口測試和單元測試,這些測試一般都是通過隔離依賴來實現的測試,此處不再細述。
探索式測試
探索式測試由 Cem Kanner 博士于 1983 年提出,是針對腳本化測試而言的。
Cem Kanner 對探索式測試的定義如下:
“探索式測試是一種軟件測試風格,它強調獨立測試人員的個人自由和職責,為了持續優化其工作的價值,將測試相關學習、測試設計、測試執行和測試結果分析作為相互支持的活動,在整個項目過程中并行地執行。”
探索式測試的核心旨在將測試學習、測試設計、測試執行和測試結果分析作為一個循環快速地迭代,以不斷收集反饋、調整測試、優化價值。
探索式測試特別需要測試人員的主觀能動性,需要有較為寬松的鼓勵測試創新的環境才能較好地開展,如果對于測試指標要求過高,測試人員主觀能動性難以發揮的情況下,探索式測試的效果也很有限。
探索式測試是一種相對自由的測試風格,不建議被各種測試模型套住,也不建議嚴格規定探索式測試的執行方式,這些都會影響到探索式測試的發揮。
更多的關于探索式測試的內容歡迎參考 Thoughtworks 同事劉冉的文章《探索式測試落地實踐》和史湘陽的文章《敏捷項目中的探索性測試》。
4. 自動化測試分層策略
前面介紹端到端測試的時候提到了不同覆蓋范圍的測試,可能有單元測試和接口測試等。自動化分層策略就是針對這些不同粒度的測試類型進行分層,根據成本、穩定性等因素建議自動化測試需要考慮不同層的覆蓋比例。
根據下圖谷歌測試定律,我們能夠很清晰的看到不同層的測試發現問題之后的修復成本的差異性,單元測試比端到端測試發現的問題修復成本要低得多,因此,通常建議測試分層應該傾向于測試金字塔 ( https://martinfowler.com/bliki/TestPyramid.html )的模式,也就是下圖右側的樣子。Thoughtworks 同事 Ham Vocke 的文章《測試金字塔實戰》 ( https://insights.thoughtworks.cn/practical-test-pyramid/ )對此有很詳細的介紹。
需要注意的是測試金字塔不是銀彈,測試策略不是一成不變的,需要根據實際情況階段性調整、演進,滿足當下產品/項目質量目標才是關鍵。
更多的關于自動化測試分層的內容,還可以參考下列文章:
《精益測試》
《微服務測試的思考與實踐》
《測試金字塔不是銀彈》
《一個遺留系統自動化測試的七年之癢》
5. 測試用例
設計測試用例是每一名測試人員必備的基本功,測試用例的好壞直接影響到測試的有效性,測試用例的重要性不言而喻,但是要設計好的測試用例也不是一件很簡單的事情。這里說的測試用例不區分手動用例和自動化用例。
好的測試用例
首先,我們有必要了解什么樣的測試用例算是好的用例。
好的測試用例應該是正好能夠覆蓋所測軟件系統、能夠測出所有問題的。因此,好的測試用例需要具備下列特點:
整體完備性,且不過度設計:有效測試用例組成的集合,能夠完全覆蓋測試需求;同時也不會有用例超出測試需求。
等價類劃分的準確性:每個等價類都能保證只要其中一個輸入測試通過,其他輸入也一定測試通過。
等價類集合的完備性:所有可能的邊界值和邊界條件都已經正確識別。
當然,因為軟件系統的復雜性,不是所有測試用例都能做到正好 100%覆蓋,只能是做到盡量的完備。
測試用例設計方法
力求完備的測試用例,就需要了解相應的測試用例設計方法。測試用例應該是結合業務需求和系統特點,綜合起來考慮設計。通常建議的用例設計方法有如下幾種:
數據流法:基于業務流程中的數據流來切分測試場景的方法。考慮業務流程中的數據流,在數據存儲或者發生變化的點進行流程的切斷,形成多個用例場景。這個在我的文章《說起 BDD,你會想到什么》里有介紹。
等價類劃分法:把程序所有可能的輸入數據劃分為若干部分,然后從每個部分中選取少數有代表性的數據作為測試用例。等價類分有效等價類和無效等價類,根據等價類劃分方法設計測試用例要注意無冗余和完備性。
邊界值法:邊界值分析方法是對等價類劃分的補充,通常取正好等于、剛剛大于或剛剛小于邊界的值作為測試數據,包括對輸入輸出的邊界值進行測試和來自等價類邊界的用例。
探索式測試模型法:推薦史亮和高翔兩位老師的著作《探索式測試實踐之路》 ( https://book.douban.com/subject/11591962/ ),書中將探索式測試按測試對象不同分為系統交互測試、交互特性測試和單個特性測試三個層次,每個層次都分別介紹了不同的探索模型。雖然我不認為探索式測試需要嚴格按照這些模型來做,但是這些模型是可以幫助測試人員在探索過程中進行思考的,同時也是設計測試用例非常有價值的參考。
關于用例設計,還可以參考下列文章:
《業務需求與系統功能》
《敏捷 QA 需要寫測試用例嗎?》
《測試用例的編寫和管理》
? ?
03 實現和執行測試
實現和執行測試就是以測試策略為指導、根據設計的測試來落地執行的相應的測試活動。這部分內容相對比較簡單,從手動測試和自動化測試兩個維度來簡單介紹。
1. 手動測試
手動測試,顧名思義就是手工執行的測試,根據是否有提前設計好的測試用例(腳本)可以分為腳本化測試和探索式測試。
腳本化測試的執行,在有成熟測試用例的前提下,相對比較簡單。但是,有些測試可能準備工作較為復雜,比如要通過長鏈路來準備測試數據、或者讓系統到達測試觸發的狀態等,還有可能要考慮不同的環境對應的配置調整,同時也會包括環境的準備和管理。這些都是測試人員要做好手工測試可能需要涉及的內容。
關于探索式測試,在《探索式測試實踐之路》 ( https://book.douban.com/subject/11591962/ )中有詳細介紹基于測程的測試管理(Session Based Test Management,SBTM)方法來執行探索式測試:將測試章程分解成一系列測程,測試人員在測程中完成一個特定測試章程的設計、執行和記錄。
同樣,這個方法對探索式測試有一定的指導意義,但是不建議嚴格規定必須按照這個模式來執行,不然的話就破壞了探索式測試的本質,達不到相應的效果。
2. 自動化測試
前面部分介紹了自動化測試的分層策略,把自動化測試的實現和執行放到這里介紹。
工具選型
自動化測試的實現依賴于自動化測試工具,對于工具的選型非常關鍵。通常在工具選型時需要考慮如下幾個因素:
滿足需求:不同的項目有不同的需求,根據需求來選擇,不求最好,只求適合就好。
易于使用:常見的易用性,以及跟寫測試的人技能匹配的易用性,都是需要考慮的。同時需要易于上手,如果一款工具對于新人不友好、很難上手的話,就很難動員大家都來積極地使用。
支持的語言:較好的做法是使用與項目開發相同的語言編寫自動化腳本,讓開發人員能夠靈活地添加測試。
兼容性:包括瀏覽器、平臺和操作系統之間的兼容。
報告機制:自動化測試的結果報告至關重要,優先選擇能夠提高完備的報告機制的工具。
測試腳本易于維護:測試代碼跟產品代碼一樣重要,對測試的維護不可忽視,需要一款易于維護的工具。
工具的穩定性:不穩定性會導致測試有效性降低,首先要保證工具本身的穩定性,不然得不償失。
代碼執行速度:測試代碼的執行速度直接影響到測試效率,比如 Selenium 和 Cypress 編寫的測試代碼執行速度就有很大差別。
測試實現
關于自動化測試的文章隨處可見,這里強調一點,不要把測試數據寫死在測試腳本里,要將數據獨立出來,做到數據驅動,以提高測試代碼的可復用性。
自動化測試的執行
是不是覺得自動化測試實現以后,執行就是簡單的跑起來就可以呢?也不是。測試的執行也需要一定的策略,例如:對不同的測試按需設置不同的執行頻率,將自動化測試跟流水線集成做到持續地測試,以持續反饋,最大化發揮自動化測試的價值。
關于自動化測試,推薦閱讀以下文章:
《新一代支持 BDD 的測試框架 Gauge+Taiko》
Thoughtworks 洞見自動化測試文集 ( https://insights.thoughtworks.cn/?s=%25E8%2587%25AA%25E5%258A%25A8%25E5%258C%2596%25E6%25B5%258B%25E8%25AF%2595 )
劉冉老師網站的自動化測試文集 ( http://liuranthinking.com/automatedtesting/ )
? ?
04 缺陷管理與分析
缺陷對軟件質量、軟件測試來講是非常寶貴的,好的缺陷管理和分析將會帶來很大的價值,但是往往容易被忽略。
缺陷管理很重要的一個部分是搞清楚缺陷的生命周期是什么樣的。往往大家覺得缺陷從發現到修復并驗證通過了就可以了,其實并不止這些。我認為缺陷的生命周期應該包括如下階段:
發現缺陷:這個比較簡單,就是發現跟期望行為不一致的系統行為,或者性能、安全等非功能性問題。缺陷可能是在測試過程中發現,也可能由用戶報告,還可以是例行日志分析或日志監控報警等等通過日志來發現。
定位和信息收集:發現缺陷之后,需要收集相應的缺陷信息并做初步定位。其中,缺陷相關信息要盡可能收集全,包括完整的重現步驟、影響范圍、用戶、平臺、數據、屏幕截圖、日志信息等。這一步有的時候可能需要開發或者運維人員幫忙。
記錄缺陷:就是將收集到的日志信息記錄在日志管理系統,關聯相應的功能模塊,并定義嚴重性。
Triage/排優先級:對于記錄的缺陷也不是所有的都要修復,所以要先對缺陷進行分類整理,確定缺陷是否有效、對有效缺陷的優先級排序,并且確定哪些是要修復以及在什么時間修復。這一步可能需要跟業務和開發人員一起來完成。
修復缺陷:這一步就交給開發人員來完成,對缺陷進行修復。
測試缺陷修復:對開發修復的缺陷進行驗證,確保缺陷本身已經修復,并且需要對相關功能進行適當的回歸測試。
添加相應的自動化測試:對于已經發現的缺陷,最好添加自動化測試,下次如果再發生類似的問題可以通過自動化測試及時地發現。自動化測試可以是單元測試、接口測試或者 UI 測試,根據實際情況結合自動化測試分層策略來定。這一步可能跟上一步順序倒過來。
統計和分析缺陷:對缺陷的數量和嚴重程度進行統計分析其同比/環比趨勢,用魚骨圖和 5 Why 法等分析缺陷發生的根因,定位缺陷引入的階段,并且分析之前缺陷預防舉措的執行效果等。
制定改進舉措預防缺陷:根據第 8 步分析的結果,制定相應的可以落地的改進舉措,以預防缺陷的發生。
定期回顧和檢查改進情況:結合缺陷的統計分析,定期回顧缺陷管理的系列活動,并檢查改進舉措的執行情況,以持續優化缺陷管理流程,更好的預防缺陷。
關于缺陷的管理和分析,我之前有寫過相應的文章,朋友們歡迎移步閱讀:
《軟件缺陷的有效管理》
《缺陷分析如何幫助質量內建》
《都是臟數據惹的禍》
? ?
05 質量反饋與風險識別
測試對產品質量狀態需要有清晰的認識,能夠及時識別質量風險,并反饋給整個團隊。
前面講到缺陷的統計分析,與質量相關的除了有缺陷信息以外,可能還有很多其他的數據,將這些數據進行收集和統計,并且可視化展示給團隊,將會幫助團隊不同角色更好地做到為質量負責。在對質量數據的統計和分析過程中可以識別到相關的質量風險,將風險也一并反饋給團隊很有必要。
質量狀態信息可能包括測試覆蓋率、缺陷相關數據、代碼凍結期長度、測試等待時間等內容,具體需要收集哪些信息還得根據項目實際的質量需求來定制化。
質量反饋建議周期性的進行,由測試人員主導定義需要收集的數據有哪些,開發人員協同測試人員一起收集相關數據,后面的分析過程可能也需要開發人員的參與。
? ?
06 寫在最后
本文為構建測試的體系化思維的基礎篇,主要是從測試的基本職責出發展開,介紹了相關的方法、工具和實踐,適合初級測試人員;當然,對于中高級測試人員,也可以對照著看看是不是這些基本職責平常都做到了,在自身的測試體系里邊是否涵蓋了相關內容。
總結
以上是生活随笔為你收集整理的构建测试的体系化思维(基础篇)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 接口自动化实战设计思路,想法及疑问(一)
- 下一篇: 缺陷定位 | 分析推理定位BUG案例(三