Test coverage là một chỉ số quan trọng trong kiểm thử phần mềm về chất lượng và hiệu quả. Bài viết này chúng ta sẽ tìm hiểu khái niệm test coverage, kỹ thuật, số liệu và cách cải thiện nó.
Thế giới đã chứng kiến một số sự kiện thảm khốc do các lỗi phổ biến trong phần mềm. Một sự kiện như vậy, mà cá nhân tôi nhớ lại, là việc khai trương Heathrow Terminal 5, Vương quốc Anh vào năm 2008.
Các kỹ sư đã khá tự tin về hoạt động của hệ thống xử lý hành lý của khách hàng do đã trải qua quá trình kiểm thử nghiêm ngặt . Tuy vậy hệ thống xử lý hành lý không thể đối phó khi đối mặt với một số tình huống thực tế; dẫn đến việc tắt hoàn toàn hệ thống. Trong 10 ngày sau đó, khoảng 42.000 hành lý không thể đi cùng chủ sở hữu và hơn 500 chuyến bay đã bị hủy.
Tất cả điều này là do các kỹ sư không thực hiện được phạm vi thử nghiệm của các tình huống có thể xảy ra trong thực tế.
Trong bài viết này, chúng ta sẽ thảo luận về tất cả các khía cạnh của test coverage – phạm vi kiểm thử, và cách nó ảnh hưởng trực tiếp đến việc sản xuất, cho dù đó là phát triển phần mềm tùy chỉnh hoặc kiểm thử phần mềm.
Test Coverage là gì?
Test coverage được định nghĩa là một kỹ thuật xác định xem các trường hợp thử nghiệm có thực sự bao trùm mã ứng dụng hay không và bao nhiêu mã được thực hiện khi chạy các trường hợp thử nghiệm đó.
Nếu có 10 yêu cầu và 100 thử nghiệm được tạo và nếu 90 thử nghiệm được thực hiện thì phạm vi thử nghiệm là 90%. Bây giờ, dựa trên số liệu này, người kiểm tra có thể tạo các trường hợp kiểm tra bổ sung cho các kiểm tra còn lại. Dưới đây là một số lợi thế của test coverage.
- Bạn có thể xác định các lỗ hổng trong yêu cầu, trường hợp kiểm tra và lỗi ở cấp độ sớm và cấp mã.
- Bạn có thể ngăn ngừa rò rỉ lỗi không mong muốn bằng cách sử dụng phân tích test coverage.
- Test coverage cũng giúp kiểm tra hồi quy, ưu tiên trường hợp kiểm thử, tăng cường bộ kiểm thử và tối thiểu hóa bộ kiểm thử.
Các kỹ thuật Test Coverage
Statement Coverage
Statement Coverage đảm bảo rằng tất cả các dòng lệnh trong mã nguồn đã được kiểm tra ít nhất một lần. Nó cung cấp các chi tiết của cả hai khối mã được thực thi và thất bại trong tổng số các khối mã.
Hãy để hiểu nó với ví dụ về sơ đồ sau. Trong ví dụ đã cho, đường dẫn 1A-2C-3D-E-4G-5H này bao gồm tất cả các câu lệnh và do đó nó chỉ yêu cầu trên một trường hợp thử nghiệm để đáp ứng tất cả các yêu cầu. Một trường hợp thử nghiệm có nghĩa là một Statement Coverage.
Trong mã nguồn phức tạp, một đường dẫn không đủ để bao gồm tất cả các câu lệnh. Trong trường hợp đó, bạn cần viết nhiều trường hợp kiểm tra để bao quát tất cả các câu lệnh.
Ưu điểm:
- Nó có thể được áp dụng trực tiếp vào mã đối tượng và không yêu cầu xử lý mã nguồn.
- Nó xác minh những gì mã nguồn viết được dự kiến sẽ thực thi và không thực thi
Nhược điểm:
- Nó chỉ bao gồm các điều kiện “true” của mã nguồn.
- Statement Coverage hoàn toàn không quan tâm với các toán tử logic (|| và &&)
Decision/Branch coverage
Các nhà phát triển không thể viết mã trong một chế độ liên tục, tại bất kỳ điểm nào họ cần phân nhánh mã để đáp ứng các yêu cầu chức năng. Sự phân nhánh trong mã thực sự là một bước nhảy từ điểm quyết định này sang điểm khác. Branch coverage kiểm tra mọi đường dẫn có thể hoặc chi nhánh trong mã được kiểm thử.
Branch coverage có thể được tính bằng cách tìm số đường dẫn tối thiểu để đảm bảo rằng tất cả các cạnh đã được che phủ. Trong ví dụ đã cho, không có đường dẫn duy nhất đảm bảo vùng phủ sóng của tất cả các cạnh cùng một lúc.
Ví dụ: nếu bạn đi theo đường dẫn 1A-2C-3D-E-4G-5H này bao gồm số cạnh tối đa (A, C, D, E, G và H), bạn vẫn sẽ bỏ lỡ hai cạnh B và F. Bạn cần đi theo một đường dẫn khác 1A-2B-E-4F để che hai cạnh còn lại. Bằng cách kết hợp hai con đường trên, bạn có thể đảm bảo đi qua tất cả các con đường. Đối với ví dụ này, phạm vi kiểm thử chi nhánh của chúng tôi là 2 vì chúng tôi đang theo hai đường dẫn và nó yêu cầu hai trường hợp thử nghiệm để đáp ứng các yêu cầu.
Ưu điểm:
- Nó bao gồm cả các điều kiện đúng và sai không có khả năng được gọi trong statement coverage.
- Nó đảm bảo tất cả các nhánh được kiểm thử.
Nhược điểm:
Nó bỏ qua các nhánh trong các biểu thức Boolean xảy ra do các toán tử ngắn mạch.
Path Coverage
Path Coverage là một phương pháp kiểm tra cấu trúc liên quan đến việc sử dụng mã nguồn của chương trình để tìm mọi đường dẫn thực thi có thể.
Path Coverage đảm bảo phạm vi của tất cả các đường dẫn từ đầu đến cuối. Trong ví dụ này, có bốn đường dẫn có thể kiểm thử:
- 1A-2B-E-4F
- 1A-2B-E-4G-5H
- 1A-2C-3D-E-4G-5H
- 1A-2C-3D-E-4F
- Nó giúp giảm các test thừa.
- Cung cấp phạm vi kiểm tra cao vì nó bao gồm tất cả các câu lệnh và các nhánh trong mã.
Nhược điểm:
- Đánh giá mỗi đường dẫn là một thách thức cũng như tốn thời gian vì một số đường dẫn theo cấp số nhân của số nhánh. Ví dụ, một hàm chứa 10 câu lệnh if có 1024 đường dẫn để kiểm tra.
- Đôi khi nhiều đường dẫn không thể thực hiện do mối quan hệ của dữ liệu.
Condition Coverage
Condition Coverage sẽ kiểm tra phạm vi điều kiện nếu cả hai kết quả (có nghĩa là “true” hay “fail”) của mọi điều kiện đã được thực hiện. Kết quả của điểm quyết định chỉ liên quan để kiểm tra các điều kiện. Nó đòi hỏi hai trường hợp thử nghiệm cho mỗi điều kiện cho hai kết quả.
Số liệu Test Coverage là gì?
Số liệu test coverage đo lường nỗ lực kiểm thử và giúp trả lời câu hỏi “Bao nhiêu phần của ứng dụng đã được kiểm thử? Số liệu test coverage có thể được chia thành ba phần: số liệu cấp mã, số liệu kiểm tra tính năng và số liệu cấp độ ứng dụng.
Có nhiều công thức khác nhau để tính toán các kết quả này và tạo báo cáo mức độ bao phủ kiểm thử.
Số liệu cấp mã
Tỷ lệ phần trăm testcase được thực hiện
Nó cũng được gọi là các bài kiểm thử được thực hiện được tính bằng tỷ lệ phần trăm của các testcase được thực hiện / thực hiện trong tổng số các testcase.
Ưu điểm là bạn có được cái nhìn tổng quan về tiến trình kiểm thử bằng cách đếm số lần testcase đã pass và fail.
Nhược điểm là việc đếm các testcase pass không liên quan đến chất lượng của các testcase đó. Ví dụ, một số testcase có thể pass vì nó kiểm tra điều kiện đơn giản hoặc một số lỗi trong mã của testcase đó dẫn đến testcase đó không hoạt động đúng theo yêu cầu.
Số liệu kiểm tra tính năng
Độ bao phủ yêu cầu
Độ bao phủ yêu cầu được sử dụng để xác định các trường hợp kiểm thử bao gồm các yêu cầu phần mềm được xử lý tốt như thế nào. Đối với điều đó, bạn chỉ cần chia số lượng yêu cầu được bao phủ trên tổng số yêu cầu trong phạm vi cho một sprint, phát hành hoặc dự án.
Các trường hợp kiểm thử theo yêu cầu
Số liệu này được sử dụng để xem những tính năng nào đang được kiểm thử và số lượng kiểm thử phù hợp với yêu cầu. Hầu hết các yêu cầu chứa nhiều trường hợp kiểm thử. Điều rất quan trọng là phải biết trường hợp kiểm thử nào bị lỗi đối với một yêu cầu cụ thể để viết lại các trường hợp kiểm thử cho các yêu cầu cụ thể khác.
Số liệu này rất quan trọng đối với các bên liên quan vì nó cho thấy tiến trình phát triển ứng dụng / phần mềm.
Số liệu cấp ứng dụng
Mật độ khiếm khuyết
Mật độ khiếm khuyết là thước đo tổng số khiếm khuyết đã biết chia cho kích thước của thực thể phần mềm được đo.
Nó được sử dụng để xác định các khu vực cần tự động hóa. Nếu mật độ khiếm khuyết cao cho các chức năng cụ thể hơn nó yêu cầu kiểm tra lại. Để giảm các nỗ lực kiểm tra lại, các trường hợp kiểm tra các lỗi đã biết có thể được tự động hóa.
Điều quan trọng là phải xem xét mức độ ưu tiên của khiếm khuyết (thấp hoặc cao) trong khi đánh giá các khiếm khuyết.
Ví dụ, nhiều khiếm khuyết ưu tiên thấp có thể vượt qua vì các tiêu chí chấp nhận đã được thỏa mãn. Mặt khác, chỉ có một khuyết điểm ưu tiên cao có thể ngăn cản các tiêu chí chấp nhận được thỏa mãn.
Các yêu cầu bên ngoài Test Coverage
Sau khi tính toán phạm vi yêu cầu, bạn sẽ tìm thấy một số yêu cầu không được bao phủ. Bây giờ, điều quan trọng là phải biết về từng yêu cầu chưa được đề cập và giai đoạn yêu cầu là gì.
Số liệu này giúp kiểm tra các kỹ sư và nhà phát triển để xác định và loại bỏ các yêu cầu chưa được khám phá khỏi tổng số yêu cầu trước khi họ gửi chúng đến giai đoạn sản xuất.
Làm thế nào để cải thiện Test Coverage?
Xóa mã “chết”
Test coverage có thể hiểu là tỷ lệ số dòng mã được bao phủ trên tổng số mã trong ứng dụng (cover_code / total_code). Bạn có thể tăng phạm vi test coverage bằng cách giảm mẫu số là tổng mã. Điều này có thể được thực hiện bằng cách xóa mã chết hoặc những đoạn mã thừa. Thông thường, mã “chết” có thể được tìm thấy trong lịch sử phát triển chương trình khi các tính năng đã được thay đổi. Bằng cách này, bạn có thể tăng tổng tỷ lệ bao phủ mã của mình mà không cần viết bất kỳ testcase bổ sung nào.
Mã “chết” có thể được tìm thấy dễ dàng bằng cách kiểm tra thủ công hoặc sử dụng các công cụ tự động hóa. Trước khi loại bỏ mã “chết”, bạn cần thực hiện kiểm tra chức năng và đảm bảo nó thực hiện chính xác theo yêu cầu. Bạn cũng có thể sử dụng các công cụ phân tích để xác định mã “chết” không sử dụng trong mã nguồn.
Xoá các đoạn mã trùng lặp
Xóa mã trùng lặp có thể cải thiện tỷ lệ test coverage theo cách tương tự như xóa mã “chết”.
Kết luận
Các nhà phát triển ngày nay có hệ thống hơn và các tổ chức tìm kiếm các biện pháp kiểm tra tính đầy đủ và hiệu quả để hiển thị các tiêu chí hoàn thành kiểm thử. Trong đó, test coverage được coi là đặc biệt có giá trị. Dựa vào tỉ lệ test coverage giúp chúng ta giảm thiểu rủi ro tối đa trong phát triển phần mềm.