2008-10-17 94 views
28

我剛剛閱讀了關於mock objects的維基百科文章,但我仍然不完全清楚其目的。看起來它們是由測試框架創建的對象,當實際對象太複雜或不可預知時(您完全知道模擬對象的值是因爲完全控制了它們而確定的)。什麼是模擬,什麼時候應該使用它?

但是,我的印象是,所有的測試都是用已知值的對象完成的,所以我必須錯過一些東西。例如,在課程項目中,我們的任務是使用日曆應用程序。我們的測試套件由事件對象組成,我們知道它們是什麼,所以我們可以測試多個事件對象,各種子系統和用戶界面之間的交互。我猜這些是模擬對象,但我不知道爲什麼你不這樣做,因爲沒有已知值的對象,你不能測試一個系統。

回答

26

模擬對象不僅僅是一個已知值的對象。它是一個與複雜對象具有相同接口的對象,不能在測試中使用(如數據庫連接和結果集),但是可以在測試中控制實現。

有一些模擬框架允許您即時創建這些對象,本質上允許您說出如下內容:使用foo方法將對象設爲int並返回一個bool。當我傳遞0時,它應該返回true。然後你可以測試使用foo()的代碼,以確保它適當地反應。

Martin Fowler的對嘲諷一個偉大的文章:

+0

真棒文章鏈接。謝謝 – 2008-11-13 20:30:28

9

想想客戶端和服務器軟件的經典案例。要測試客戶端,您需要服務器;要測試服務器,你需要客戶端。這使得單元測試幾乎不可能 - 不使用模擬。如果你嘲笑服務器,你可以單獨測試客戶端,反之亦然。

模擬的重點不在於重複其嘲諷事物的行爲。它更像是一個簡單的狀態機,它的狀態變化可以通過測試框架來分析。因此,客戶端模擬可能會生成測試數據,將其發送到服務器,然後分析響應。您期望對特定請求有特定響應,因此您可以測試是否獲得該請求。

6

我的一切@Lou Franco說,你一定要閱讀測試的優秀Martin Fowler的文章同意成倍於@Lou佛朗哥點你去。

任何測試雙(僞造,存根或模擬)的主要目的是隔離測試中的對象,以便您的單元測試僅測試該對象(而不是它的依賴關係以及與之協作或交互的其他類型)。

提供您的對象所依賴的接口的對象可以用來代替實際的依賴關係,因此可以期望發生某些交互。這可能很有用,但在基於狀態和基於交互的測試方面存在一些爭議。過度使用模擬期望會導致脆弱的測試。

測試雙打的另一個原因是刪除數據庫或文件系統或其他昂貴的設置或執行耗時操作的類型的依賴關係。這意味着您可以將所需的對象單元測試所需的時間降到最低。

2

下面是一個示例:如果您正在編寫填充數據庫的代碼,則可能需要檢查特定的方法是否已將數據添加到數據庫。

設置用於測試的數據庫副本有一個問題,即如果您假設在調用測試方法之前沒有記錄,之後有一條記錄,則需要將數據庫回滾到以前的狀態,因此增加了運行測試的開銷。

如果您認爲只有一條記錄比以前多了,它可能會與連接到同一數據庫的第二個測試者(甚至是第二個測試在同一代碼中)發生衝突,從而導致依賴性並使測試變得脆弱。

該模擬允許您保持測試彼此獨立並且易於設置。

這只是一個例子 - 我確信其他人可以提供更多。

我同意關於此主題的其他貢獻者100%,尤其是與Martin Fowler文章的建議。

相關問題