簡體   English   中英

Powermock驗證靜態方法中的私有靜態方法調用

[英]Powermock verify private static method call in static method

我想知道是否有一種方法可以驗證並調用為從測試中的公共靜態方法調用的私有靜態方法創建的模擬程序。

這是我正在測試的公共靜態方法

public static String methodUnderTest(String p1){
   return privateStaticMethod(p1);
}

private static String privateStaticMethod(String p1){
        return "dummy";
}

我使用powermokito模擬了私有靜態方法,如下所示:

@RunWith(PowerMockRunner.class)
@PrepareForTest(fullyQualifiedNames = "ClassUnderTest")
public class ClassUnderTestTest {

    @Test
    public void test_sometest() throws Exception {
         PowerMockito.spy(ClassUnderTest.class);

         PowerMockito.doReturn("whatever").when(ClassUnderTest.class, "privateStaticMethod","something");

         String retValue =  ClassUnderTest.methodUnderTest("something");  
         assertEquals(retValue, "whatever");            
    }
}

現在,有沒有一種方法可以驗證privateStaticMethod被調用了?

原來真的很復雜。

如果這可以奏效,則解決方案可能會遵循此處的內容 不幸的是我沒有PowerMockito設置,所以我自己不能測試此代碼:

// tell powermock(ito) that you want to do PARTIAL static mocking
PowerMockito.spy(ClassUnderTest.class);
// give it the mocking SPEC for that static method that needs mocking
PowerMockito.doReturn("whatever").when(ClassUnderTest.class, "privateStaticMethod","something");
// tell it to INVOKE the real method when the public one is called
PowerMockito.doCallRealMethod().when(Util, "methodUnderTest", any());

// now assert that the mock spec kicked in
assertThat(ClassUnderTest.methodUnderTest("something"), is("whatever"));

上面使用了Hamcrest is()匹配器, any()將是(Power)Mockito參數匹配器。 確保導入正確!

當您更改公用方法並且不調用該專用方法和/或返回其他內容時,以上操作將失敗。

但是真正的答案是:您應該避免這種測試。 上面的代碼隱式驗證了此私有方法的調用:如果未調用該私有方法,您將收到不同的結果!

但是這里的真正意義是:您不應該測試這些東西。 您的公共方法如何獲得其結果與您的測試完全無關。 您的公共方法有一個合同,如何實現是實現細節

您的方法將單元測試轉變為生產代碼的(過於復雜!)重新實現。 這意味着:您打算更改實施的第二次測試就需要調整。 更糟糕的是,由於您將方法名稱作為原始字符串傳遞,因此您甚至不會注意到,直到運行時,該方法突然停止返回whatever ,而給了dummy

因此,這里的真正答案是:

  • 首先,盡可能避免使用靜態方法,因此您無需從事模擬靜態方法的工作
  • 忘記測試這樣的實現細節。

驗證是否調用了私有方法毫無意義 您的公共方法的調用者應該返回“什么進來,什么回來”的信息。 在該級別上,其他任何內容都無關緊要。

並給出了OP的評論:

  • 除了“狀態”之外,還有更多的靜態問題。 它殺死了多態性,並且還導致對靜態代碼所在類的直接,硬性依賴
  • 這不僅使單元測試更加困難,而且任何類型的測試都變得更加困難
  • 從我的個人經驗來看:當人們告訴我“我的新編寫的代碼需要PowerMock(ito)”時,我知道他們無需這樣做就可以創建難以測試的代碼。 絕對有可能(並且很希望)以可以用較少侵入性的模擬框架很好地測試的方式編寫生產代碼。

換句話說:如果您不能在Mockito中編寫簡單的直接測試,那么很可能您創建了難以測試的生產代碼,那么最好花時間和精力使生產代碼更容易測試。 而不是使用PowerMock(ito)錘通過解決症狀來“解決”您的問題。 是的,這很重要。 我們來自基於PowerMock的“太多靜態”代碼庫,只是在某個時候告訴人們“不再”。 從那時起,當我們需要模擬時,我們使用Mockito。 由於在不同地方“更改為靜態”而導致的離奇的“單元測試失敗”的數量下降到0。我們的生產代碼變得更好

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM