昨天我們在 Build Step 裡開啟 Coverage 的功能,讓 TeamCity 在運行測試後一併產生覆蓋率報告,方便我們了解程式碼庫的狀態及趨勢。不過實務上來說,大概很少人會每一個 Build Log 都點進去看覆蓋率報告。對於開發者來說,與其說在意覆蓋率的「數值」,更在意的是覆蓋率的「變化」。
在軟體測試領域,有一種作法叫「童子軍原則」,對於童子軍來說,「離開營地前,讓營地比使用前更加乾淨」;而對開發者來說,「提交程式碼後,至少不能讓覆蓋率往下掉」。所以若是 TeamCity 能在覆蓋率數值降低時直接視為建置失敗,主動通知我們,是不是就能變成某種形式的品質控管,多一隻眼睛幫我們監看著?
TeamCity 的確有考量到這個需求,設計了稱為 Failure Condition 的功能。簡單來說,我們可以為 Build 設定失敗條件,這個條件的形式很多,可以是 Build 過程中有錯誤訊息,也可以是 Build 的時間過久、Crash、記憶體超載。或是跟數值有關,比方說覆蓋率低於多少、產生來的成品檔案超過大小、Inspection 錯誤的數量多於多少…等。只要這個條件一發生,即便建置任務有完成,這次的建置工作也算失敗。而當建置失敗時,TeamCity 就會主動通知我們,滿足我們需要監看品質的需求。
為了要示範 TeamCity Failure Condition 的功能,我們先故意降低程式庫的覆蓋率。降低的方式很簡單,我們在 ShoppingCart
這個類別裡新增幾個方法,但都故意不寫測試。這樣程式碼的數量增加了,但測試沒有跟著測試到,整體的覆蓋率就會降低了。
首先打開 ShoppingCart
類別,在裡面新增 2 個方法,內容只是隨機的回傳整數和布林值。
class ShoppingCart {
// ...
fun dummyInt(): Int {
return Random.nextInt()
}
fun dummyBoolean(): Boolean {
return Random.nextBoolean()
}
}
再打開 ShoppingCartTest
類別,執行測試並產生覆蓋率報告後,我們可以看到 IntelliJ IDEA 的 Coverage 面板顯示的 Method 百分比從原本的 100% 降到 66%、Line 百分比從原本的 100% 降到 71%。
接著回到 TeamCity,打開專案的 Build Configuration,切到左邊側邊欄的 Failure Conditions 設定。我們可以看到 TeamCity 已經內建了數個自動開啟的 Failure Condition,比方說當其中一個 Build Step 發生錯誤(one of build steps exited with an error)、有任一個測試失敗(at least one test failed)或是當建置因為記憶體過載而當掉時(an out-of-memory or crash is detected)就會直接視為建置失敗。
而我們今天要練習的,是設定 TeamCity 當「Method 覆蓋率低於上一次成功建置的數值」時就視為建置失敗。點擊畫面下方 Add failure condition 按鈕新增一個條件,出現類型選單時,選擇 Fail build on metric change。
接著設定條件,首先設定觀測指標是 Method 覆蓋率百分比(percentage of method coverage),要比較的對象是上一次成功建置的數值(compared to, value from, Latest successful build),差異不可低於 1%(is less by at least 1 percent),完成後按 Save 儲存。
在 IntelliJ IDEA 完成 Commit & Push 後回到 TeamCity 看建置結果,從 Build 詳細頁面我們可以看到,雖然建置是有成功且測試也都通過,但因為 Method 覆蓋率低於上一次的 100%,所以建置工作也被認定為失敗。
經過今天的介紹,相信大家對如何將測試覆蓋率應用在 CI 流程有更實際的應用案例,也更清楚如何將覆蓋率數值的變化趨勢用在 TeamCity 的建置流程中,協助團隊更有效率的掌握程式碼庫品質變化,讓維護工作可以更輕鬆。明天我們將開始探索 CI 在產生 API 文件上的應用,敬請期待!