2012-08-06 103 views
3

可以說,我有一個看起來像這樣的方法:EasyMock的期望私有方法調用

public static String[] parseFoo(Foo anObject){ 
    Foo anotherObject = parseFoo2(anObject); 
... 
} 

private static Foo parseFoo2(Foo anObject){ 
... 
} 

而且這兩種方法都在同一個班。 parseFoo2只是一個輔助方法,可以幫助parseFoo完成一些工作。我試圖測試parseFoo方法。是否有任何人在EasyMock的,我可以像我可以指定實例方法的方式parseFoo2規定對私有方法調用的返回值呼籲與

EasyMock.createMock(...); 
anObject.expect(...).andReturn(...); 

的對象,因爲我想測試的公共方法,但我不想進入私有方法並測試其中的實現。

謝謝

回答

12

不要這樣做。 好的單元測試的一個角落是它應該儘可能少地依賴實現細節。嘲笑一個私人方法就是這樣。

爲什麼? 因爲這會讓你的單元測試非常脆弱。考慮一下你在一週內回到這段代碼的情況,並決定你並不真的需要parseFoo2方法,並且你真的想要內聯它的代碼。或者你想把這個方法分成兩個或更多個更小的方法。所有非常有效的重構實踐 - 但他們將打破單元測試!

你不想在每次你做一個簡單的重構時追逐單元測試。因此,嘲笑私人方法被認爲是不好的做法。

+2

這個答案太絕對了,需要一個哲學的觀點,即私人方法沒有應該被提出的內部契約。如果該方法在類中的幾個地方使用,就像公共方法一樣,它需要維護它的行爲模式。另外,如果你有一個方法調用幾個方法(全部是私有的),每個方法都有2-3個邏輯路徑,測試頂層方法變得非常複雜。沒有什麼比在需要檢查時失敗的複雜測試更糟糕:)。我更喜歡頻繁的路障經常可預測的成本。 – Gus 2012-08-20 15:08:18

+2

@格斯,我不同意。從實用的角度來看,測試高粒度的私有方法會阻止您輕鬆重構代碼。我會同意,隨着複雜性的增長,它應該被分解爲應該單獨測試的因素。在這種情況下應該考慮類。從哲學的角度來看,我認爲一個班的私人部分不是一個應該測試的單元。它是一個實現細節,而測試應該反映來自被測對象的要求,而不是它的內部工作。 – Vitaliy 2012-08-20 17:03:27

+0

我會同意,有時您需要模擬一種私人方法 - 例如,在內部(私人)邏輯的嘲諷非常複雜並且錯過了測試點的情況下。但這些案例相對較少,通常指向另一個設計流程。無論如何,它並不屬於OP的用例。 – Vitaliy 2012-08-20 17:13:39

0

如果您仍然想使用EasyMock,因爲改變它並不依賴於您(在企業中工作),您可以使用反射來更改您的方法返回的私有字段或任何專用字段。

例如,您可以將這些方法放在輔助類中。並根據需要使用它們。

+0

你有沒有能夠得到這個工作?到目前爲止,我已經嘗試了幾次,但都沒有運氣 – HardcoreBro 2013-06-26 13:45:10

+0

在我的情況下,parseFoo2是在另一個類,但我需要修改它返回什麼,最後一個私人靜態字段的那個類的權利嗎?所以.. public static void helpMethodForStaticFiled(Class class,String fieldName,Object fieldValue ){ Field field = class.getDeclaredField(fieldName); field.setAccessible(true); field.set(null,fieldValue); field.setAccessible(false); } 現在如果我在類MyClass中有一個私有的靜態MyField myField,我會這樣做: helpMethodForStaticFiled(MyClass.class,「myField」,new MyField()); – dalvarezmartinez1 2013-07-08 08:22:25

相關問題