Code Coverage 在單元測試裡的意義,不是追求某個漂亮百分比,而是幫團隊觀察測試覆蓋率的相對趨勢、找出沒有測到的情境,並判斷哪些 production code 可能其實不會被執行。真正有用的做法,是讓 CI 在 build 時自動跑測試,確認每次修改後 coverage 不要往下掉。
如何用 Code Coverage 衡量單元測試成果?
Code Coverage 應該先用來確認測試有被自動執行,再用來追蹤趨勢。覆蓋率大於 0% 只是起點,長期是否往上才是更有意義的訊號。
在 build 的時候要自動去跑測試,可以使用 CI/CD 當作工具。第一步不是立刻要求高覆蓋率,而是先讓 coverage 大於 0%,確定每一次 build 都真的會跑測試。
接著要關心相對趨勢大於絕對數字。也就是評估 Code Coverage 的數值有沒有比昨天高,或至少不要因為新的 production code 修改而往下掉。
每一次針對 production code 的修改都要加上測試,coverage 就會慢慢往上,不會往下。這件事也會鼓勵團隊持續 commit,讓持續整合真的運作起來,而不是累積一大包改動才一次送出。

哪些單元測試的投資報酬率最高?
單元測試的目標是提升產品品質,所以應優先補最能降低風險的案例。修 Bug、常用情境、主要流程、金錢與安全相關邏輯,通常比追求全面覆蓋更值得先做。
假設某段 production code 沒有 Bug、也不是高風險流程,其實不一定要急著為它補測試。測試要花時間寫,也要花時間維護,所以應該先問:哪些測試的投資報酬率最高?
我會用這個順序判斷優先級:
| 優先順序 | 測試目標 | 為什麼先測 |
|---|---|---|
| 1 | 要修正的 Bug | Bug 越晚發現,修正成本通常越高 |
| 2 | 實務上常跑到的 scenario | 使用者每天碰到的路徑最需要穩定 |
| 3 | 最主要的情境 | 核心流程壞掉時,產品品質最容易被感受到 |
| 4 | 和錢有關的邏輯 | 金額、付款、計費錯誤很難事後補救 |
| 5 | 和人命有關的邏輯 | 例如自動駕駛系統,錯誤成本不是一般缺陷等級 |
| 6 | 最常改到的 code | 經常修改的區域最容易被改壞 |
這份排序的重點,是把 coverage 從「數字競賽」拉回「風險管理」。先測會痛的地方,coverage 才會對產品品質有幫助。
Code Coverage 可以看出哪些問題?
Code Coverage 最有用的訊號,是指出哪些情境沒有被測試覆蓋。未覆蓋程式碼可能代表漏測,也可能代表 Dead Code,需要回頭判斷是否要補測試或清掉程式碼。
Code Coverage 的意義可以拆成兩件事:
- 觀察沒有被覆蓋到的情境,判斷要不要補測試。
- 找出 Dead Code,也就是根本不會跑到的 code。
未覆蓋不一定代表錯。某些例外處理、低機率分支、平台相容性路徑,本來就不會在一般情境中被跑到。但 coverage 會把這些地方標出來,讓團隊可以討論:這段是重要情境漏測,還是已經不再需要的程式碼?
如果一段 production code 長期沒有被 coverage 打到,也沒有人能說清楚什麼情境會執行它,那段 code 就值得被懷疑。要不是補上測試確認行為,要不就是整理需求後移除。
既有程式碼要怎麼開始導入 Code Coverage?
既有程式碼導入 Code Coverage 時,最適合從 Bug 修正與新專案開始。不要一開始就要求全面重寫測試,先守住新增與修正的程式碼,coverage 才比較容易穩定上升。
從實務上看,兩個最好導入的方式是:
- 針對所有 Bug 的修改去寫測試。
- 針對新的專案去寫測試。
接著要確認 Code Coverage 不可以往下掉。這條規則很重要,因為既有程式碼可能很大、很亂,短時間內不可能全部補齊測試;但至少可以要求新的修改不要讓情況更差。
如果現在有一陀難以測試的既有 code,要在裡面增加新功能,我會先把那段 code 抽成 method,再抽成新的 class。接著針對既有 code 的 public 情境先寫測試,這樣需要測試的範圍會變小很多,也比較不會一開始就被複雜依賴卡住。

測試品質要怎麼維持?
測試程式本身也需要重構,否則 coverage 數字會留下來,理解成本卻會越來越高。好的測試應該讓人一眼看懂情境、動作與預期結果。
測試品質可以從三件事檢查:
- 測試的程式一定要重構。
- 測試的語意一定要清楚明白。
- 寫測試的難度會反映程式本身的好壞。
一般來說,Assert 可以抽成一個 function,讓測試更容易理解。讀測試時,應該可以很簡單地從語意看出這個測試要做什麼,而不是一路追進每個細節才知道預期結果。
如果某段 production code 很難寫測試,通常也代表那段 code 的相依關係、責任邊界或命名有問題。這時候不要只怪測試難寫,應該回頭看 production code 是否需要拆 method、拆 class,或用 Fake Object 隔離外部依賴。
延伸閱讀
- 單元測試 Fake Object 教學:隔離時間與外部依賴的 C# 範例
- Python Socket.IO Client 4.5.1 不會自動重連:503 後的排查與手動重連寫法
- PHP 使用 SOAP:SoapServer 與 SoapClient 基本架設
- 生成只包含專案使用的 Library 列表:用 pipreqs 產生 requirements.txt
常見問題
Code Coverage 越高,單元測試品質就越好嗎?
不一定。Code Coverage 只能表示程式碼有被測試執行過,不代表測試真的驗證了重要行為。coverage 要搭配測試語意、Assert 品質與高風險情境覆蓋一起看。
Code Coverage 一開始應該設定多少門檻?
既有專案可以先要求 coverage 大於 0%,並讓 CI 每次 build 都自動跑測試。比起一開始設定很高門檻,更重要的是不要讓 coverage 因為新的 production code 修改而往下掉。
修 Bug 時為什麼要補單元測試?
Bug 修正通常是高投資報酬率的測試切入點,因為缺陷越晚發現,修正成本越高。替 Bug 補測試,也能避免同一個問題在未來重複出現。
未覆蓋的程式碼一定要補測試嗎?
未覆蓋的程式碼不一定都要補測試,但一定值得被檢查。團隊要判斷未覆蓋區域是重要情境漏測、低風險分支,還是根本不會執行的 Dead Code。
既有爛 code 要怎麼開始補測試?
可以先把要修改的既有 code 抽成 method,再逐步抽成新的 class。先測 public 情境,讓測試範圍縮小,再慢慢處理更深層的相依關係。
參考資料
本文未新增外部參考資料,內容保留 2018-07-28 的單元測試筆記,並整理為可搜尋、可摘錄的 Markdown 結構。
最後更新
本文最後更新於 2026-08-28。2018-07-28 的筆記內容已保留核心觀點,並補上 GEO Answer Blocks、比較表、圖片、延伸閱讀與 FAQ。
關於作者 {#author}
Claire Chang | 企業 AI 導入與流程轉型顧問。專注於 AI Agent 架構設計、ERP 系統整合與企業 AI 治理。
首次發布:2018-07-28