Kiểm thử đơn vị hộp đen là gì?


11

Gần đây tôi đã có bài kiểm tra cuối cùng cho một khóa học kỹ thuật phần mềm cho chương trình thạc sĩ của mình và một trong những câu hỏi trong bài kiểm tra là:

Unit Testing is considered:
a. White-box Testing
b. Black-box Testing
c. Either

Trong 7 năm kinh nghiệm phát triển phần mềm của tôi, kiểm thử đơn vị luôn áp dụng cách tiếp cận hộp trắng. Người kiểm tra luôn có kiến ​​thức đầy đủ về việc thực hiện bài học trong khi viết bài kiểm tra. Kiểm thử hộp đen luôn xuất hiện sau trong các hình thức tích hợp, hệ thống và kiểm tra chấp nhận.

Tuy nhiên, câu trả lời chính xác cho bài kiểm tra (theo giáo sư) là kiểm tra đơn vị có thể là kiểm tra hộp trắng hoặc đen.

Tôi đã thực hiện một số nghiên cứu và có vẻ như nhiều trường hợp "thử nghiệm đơn vị hộp đen" được sử dụng để mô tả cách tiếp cận thử nghiệm đầu tiên trong đó các thử nghiệm đơn vị được viết trước khi mã. Tuy nhiên theo tôi đây vẫn là thử nghiệm hộp trắng. Mặc dù việc triển khai chưa tồn tại, nhưng bất cứ ai đang viết bài kiểm tra thường có một ý tưởng khá hay về cách mã nguồn sẽ được thực hiện.

Ai đó có thể vui lòng giải thích cho tôi cách thử nghiệm đơn vị hộp đen hoạt động (nếu nó thực sự là một thứ) và nó khác với thử nghiệm đơn vị hộp trắng như thế nào?


4
Làm thế nào giáo sư làm rõ điều này khi bạn hỏi họ về điều này? (xem thêm Tại sao câu hỏi phỏng vấn làm cho Kỹ thuật phần mềm kém. Câu hỏi thường gặp? )
gnat

"bất cứ ai đang viết các bài kiểm tra thường có một ý tưởng tốt đẹp về cách thức kiểm tra sẽ được thực hiện" - nó không phải về việc liệu bạn biết làm thế nào kiểm tra được thực hiện, nhưng cho dù bạn biết (trắng) hay không (màu đen) như thế nào là điều bạn đang thử nghiệm được thực hiện.
Jesper

@Jesper xin lỗi. Tôi muốn nói "làm thế nào mã nguồn sẽ được thực hiện". Tôi đã sửa nó trong câu hỏi.
backcab

2
While the implementation does not yet exist, whoever is writing the test generally has a pretty good idea about how the source code is going to be implemented.- Có, nhưng bản thân bài kiểm tra thì không. Kiểm thử hộp trắng có nghĩa là kiểm tra một cái gì đó bên trong phương thức hoặc lớp, như giá trị của một biến. Điều đó không có nghĩa là người viết bài kiểm tra biết đoạn mã được kiểm tra trông như thế nào.
Robert Harvey

Câu trả lời:


20

Giáo sư của bạn đã đúng: kiểm tra đơn vị có thể là hộp đen hoặc hộp trắng. Sự khác biệt là ít hơn về những gì người kiểm tra biết, mà nhiều hơn về cách bạn tạo các trường hợp kiểm thử.

Với thử nghiệm hộp đen, bạn chỉ nhìn vào giao diện và (nếu nó tồn tại) thông số kỹ thuật cho một thành phần. Khi một hàm có chữ ký int foo(int a, int b), sau đó tôi có thể tạo ngay một vài trường hợp thử nghiệm chỉ bằng cách kiểm tra các số nguyên thú vị: zero, one, trừ một, số có nhiều chữ số, INT_MAX, INT_MAX - 1, v.v. Các thử nghiệm hộp đen là tuyệt vời vì chúng độc lập với việc thực hiện. Nhưng họ cũng có thể bỏ lỡ các trường hợp quan trọng.

Với một thử nghiệm hộp trắng, tôi xem xét việc thực hiện, tức là mã nguồn và tạo các trường hợp thử nghiệm từ đó. Ví dụ: tôi có thể muốn đạt được phạm vi bao phủ 100% đường dẫn cho một chức năng. Sau đó tôi chọn các giá trị đầu vào để tất cả các đường dẫn được thực hiện. Các thử nghiệm hộp trắng là tuyệt vời vì chúng có thể thực hiện triệt để một đoạn mã, với độ tin cậy cao hơn nhiều so với các thử nghiệm hộp đen. Nhưng họ có thể chỉ đang thử nghiệm chi tiết thực hiện, không thực sự là hành vi quan trọng. Trong một số trường hợp, chúng rõ ràng là một sự lãng phí thời gian.

Vì một thử nghiệm hộp trắng có nguồn gốc từ việc thực hiện, nó chỉ có thể được viết sau đó. Một thử nghiệm hộp đen có nguồn gốc từ thiết kế / giao diện / đặc điểm kỹ thuật và do đó có thể được viết trước hoặc sau khi thực hiện. TDD không rõ ràng là hộp đen hoặc hộp trắng. Do tất cả các hành vi được thể hiện đầu tiên bằng một thử nghiệm và sau đó mã tối thiểu cho hành vi đó được triển khai, TDD dẫn đến các trường hợp thử nghiệm tương tự với thử nghiệm hộp trắng. Nhưng khi chúng ta xem xét luồng thông tin, các kiểm tra TDD không xuất phát từ mã nguồn, mà từ các yêu cầu bên ngoài. Do đó, TDD giống hộp đen hơn.


3
"Vì một thử nghiệm hộp trắng có nguồn gốc từ việc triển khai, nên nó chỉ có thể được viết sau đó" - tốt, nếu tôi sẽ viết một thử nghiệm thất bại theo kiểu TDD cho tính năng mới tiếp theo tôi muốn thêm vào chức năng hoặc lớp hiện có của mình , Trước tiên, tôi xem xét việc triển khai hiện tại để tìm hiểu những gì không được hỗ trợ, vì vậy tôi có thể thiết kế một bài kiểm tra có ý nghĩa hơn - ban đầu thất bại -. Tôi gọi đây là một cách tiếp cận thử nghiệm whitebox đầu tiên, không phải là một thử nghiệm được viết sau đó. (Tuy nhiên, +1 từ tôi).
Doc Brown

4

Nếu bạn đang thực hiện Phát triển dựa trên thử nghiệm, thì về lý thuyết, tất cả các thử nghiệm đơn vị của bạn phải là hộp đen. Đây là "cách tiếp cận thử nghiệm đầu tiên" của bạn. Bạn viết hợp đồng (giao diện), viết các bài kiểm tra cho hợp đồng đó, và sau đó hợp đồng được thực hiện bằng cách thực hiện. Do đó, bài kiểm tra không biết gì và không biết gì về việc thực hiện.

Rốt cuộc, khi bạn viết một bài kiểm tra, bạn đang kiểm tra cái gì? Phương pháp / chức năng công cộng.

Nếu bạn định viết giao diện cho một lớp, sau đó viết các bài kiểm tra, và sau đó bạn bị xe buýt đâm, anh chàng viết lớp trong khi bạn ở bệnh viện sẽ có thể làm như vậy từ giao diện của bạn, phải không? Anh ta không nên vứt nó đi và viết giao diện và bài kiểm tra của riêng mình.

Trường hợp điều này sụp đổ phần nào là khi bạn cần chế giễu một cái gì đó mà việc thực hiện phụ thuộc vào, nhưng nếu bạn thấy mình trong tình huống mà bạn đang chế giễu một thứ không bao giờ được phơi bày công khai, thì bạn đã phạm sai lầm, và bạn cần phải tìm đến Dependency Injection et al . Do đó, tôi cho rằng việc kiểm tra đơn vị hộp trắng, không phải màu đen, phải là ngoại lệ.

Xem xét 'Thử nghiệm trên nhà vệ sinh - Hành vi kiểm tra Không thực hiện' , trong đó việc triển khai của một lớp bị thay đổi nhưng các thử nghiệm vẫn phải hợp lệ.

Tuy nhiên, nếu bạn cần đảm bảo phạm vi bảo hiểm mã của mình (nghĩa là đảm bảo tất cả các đường dẫn có điều kiện được kiểm tra trong khi triển khai), thì bạn hoàn toàn cần phải kiểm tra đơn vị hộp trắng, bởi vì cách duy nhất bạn có thể biết là gì đường dẫn là bằng cách nhìn vào các đường dẫn trong việc thực hiện.


2
If you were to write the interface for a class, and then write the tests, and then you get hit by a bus, the guy who writes the class while you're in hospital should be able to do so from your interface, right?-- Không chính xác. Hầu hết các hợp đồng API chỉ thực sự xác định chữ ký phương thức, không phải ngữ nghĩa hoặc hành vi.
Robert Harvey

Bạn đúng; Tôi đã đưa ra một điều chắc chắn rằng giao diện của bạn sẽ bao gồm thông số kỹ thuật mà nó được viết, chứ không chỉ là văn bản của MyClassInterface.
AdamJS

@RobertHarvey đúng là hầu hết các giao diện không mô tả rõ ràng ngữ nghĩa hoặc hành vi, nhưng tôi nghĩ nó thường ở đó một cách ngầm định. Nếu không có thì mã yêu cầu ngữ nghĩa nhất định sẽ không thể phụ thuộc vào sự trừu tượng. Và không có gì để ngăn chặn các giao diện bao gồm các chi tiết về ngữ nghĩa và hành vi như các bình luận / docblocs. Ví dụ: xem github.com/php-fig/http-message/blob/master/src/
Kẻ

3

Tôi sẽ lập luận rằng tất cả các bài kiểm tra đơn vị được viết tốt vốn dĩ là "hộp đen". Chắc chắn tôi có thể có một triển khai trong tâm trí khi tôi viết bài kiểm tra, nhưng việc thực hiện đó có thể thay đổi khi tôi tái cấu trúc. Vì vậy, kiểm tra chỉ nên sử dụng các API công khai trong quá trình kiểm tra để kiểm tra chức năng, chứ không phải thực hiện. Nó không quan tâm đến các chi tiết thực hiện, vì vậy thử nghiệm hộp đen của nó.

Nếu tôi viết các bài kiểm tra truy cập các khía cạnh nội bộ hoặc riêng tư của đơn vị được kiểm tra, thì tôi đang kiểm tra các chi tiết triển khai: Tôi đang kiểm tra hộp trắng. Nhưng tôi cũng đang viết các bài kiểm tra dễ vỡ có thể dễ dàng phá vỡ khi thay đổi triển khai. Vì vậy, các thử nghiệm hộp trắng như vậy là một ý tưởng tồi và nên tránh.

Kết luận: nếu bạn kiểm tra hộp trắng với các bài kiểm tra đơn vị, bạn có các bài kiểm tra được xây dựng kém. Chỉ kiểm tra lại hộp với các bài kiểm tra đơn vị. Giáo sư của bạn là chính xác: nó có thể là một trong hai. Nhưng chỉ khi làm xấu.


1

Tôi chỉ đang trong quá trình viết bài kiểm tra đơn vị thực hiện kiểm tra hộp đen. Đó là, tôi đang thử nghiệm các phương thức công khai trong một lớp và bằng hàm ý logic kiểm tra kết quả trong các phương thức riêng mà chúng gọi.

Tôi thực hiện điều này bằng cách thay đổi đầu vào thành phương thức công khai đang được thử nghiệm và thử nghiệm đầu ra dự kiến ​​được xác định hoặc thay đổi bằng logic trong các phương thức riêng hỗ trợ, việc thực hiện "thử nghiệm đơn vị" của tôi không cần biết gì.

Vì vậy, không có gì ngăn cản bạn thực hiện kiểm tra hộp đen trong các bài kiểm tra đơn vị và các bài kiểm tra sẽ bị hỏng nếu ai đó gây rối với việc triển khai logic hỗ trợ ẩn. Trong thực tế, đây có vẻ như là một cách tiếp cận ưu việt hơn, hiệu quả hơn so với đơn vị hộp trắng kiểm tra mọi thứ trong một lớp vì lợi ích của nó. Tôi với giáo sư.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.