我写的测试案例:
public class AClassUnderTest {
// This test class has a method call
public Long methodUnderTest() {
// Uses the FinalUtilityClass which contains static final method
FinalUtilityClass.myStaticFinalMethod(<3-parameters-here>);
// I want to mock above call so that test case for my "methodUnderTest" passes
}
}
我有一个最后一堂课。
public final class FinalUtilityClass {
/**
* Method has 3 parameters
*/
public static final MyBean myStaticFinalMethod(<3-parameters-here>) {
}
}
我已经在我的测试类中添加了以下代码:
@RunWith(PowerMockRunner.class)
@PrepareForTest({ FinalUtilityClass.class })
我想编写测试用例来嘲笑它。
我想模仿myStaticFinalMethod()
的调用,以便我可以获得预期的MyBean
instatnce,我可以在其他代码中使用它来传递我的测试用例。
<3-parameters-here>
是Calendar,String,String。
我尝试过 :
1)
PowerMockito.mock(FinalUtilityClass.class)
PowerMockito.when(FinalUtilityClass.myStaticFinalMethod(<3-parameters-here>).thenReturn(new MyBean());
2)
PowerMockito.mockStatic(FinalUtilityClass.class)
PowerMockito.when(FinalUtilityClass.myStaticFinalMethod(<3-parameters-here>).thenReturn(new MyBean());
第3)
PowerMockito.spy(FinalUtilityClass.class)
PowerMockito.when(FinalUtilityClass.myStaticFinalMethod(<3-parameters-here>).thenReturn(new MyBean());
但没有任何对我有用。请在static final
类中建议模拟final
方法的正确方法。
答案 0 :(得分:7)
模拟对静态方法的调用需要以下steps:
@RunWith(PowerMockRunner.class)
注释。@PrepareForTest(ClassThatContainsStaticMethod.class)
注释PowerMock.mockStatic(ClassThatContainsStaticMethod.class)
模拟此类的所有方法当您按照文档记录这些步骤时,您的测试应该可行。由于OP似乎对PowerMock与PowerMockito相混淆 - 这或多或少都是同样的事情:
PowerMock和PowerMockito基于相同技术。他们只是有不同的连接器&#34;与EasyMock或Mockito合作。所以,是的,上面的示例说明PowerMock.mockStatic()
- 但PowerMockito也有mockStatic()
个方法。从这个意义上说:核心事物(例如关于带注释的准备)是相同的。例如,请参阅here(它们非常接近,链接的教程说&#34; PowerMock简介&#34; - 虽然它确实引入了PowerMockito。
而你似乎不相信我 - 请看这个例子:
package ghostcat.test;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
final class ClassWithStatic {
public final static int ignoreMethodCall(String a, String b, int c) {
System.out.println("SHOULD NOT SHOW UP: " + a);
return c;
}
}
@RunWith(PowerMockRunner.class)
@PrepareForTest(ClassWithStatic.class)
public class MockStaticTest {
@Test
public void test() {
PowerMockito.mockStatic(ClassWithStatic.class);
PowerMockito.when(ClassWithStatic.ignoreMethodCall("a", "b", 5)).thenReturn(42);
org.junit.Assert.assertEquals(ClassWithStatic.ignoreMethodCall("a", "b", 5), 42);
}
}
该测试通过;并且不会打印任何东西。因此最终的静态方法被嘲笑。
答案 1 :(得分:0)
我遇到了类似的问题,这花费了我很多时间。
我解决了,基于这个Mock system class with PowerMock documentation,当我意识到@PrepareForTest({ SomeClassToBePreparedForTesting.class })
必须接收调用最终类中定义的静态方法的类时,所以准备测试,在你的情况下,必须收到 AClassUnderTest.class
。
@RunWith(PowerMockRunner.class)
@PrepareForTest({ AClassUnderTest.class })
使用目标静态方法模拟最终类的正确方法是使用 PowerMock.mockStatic(FinalClassThatDefinesStaticMethod.class)
,在您的情况下使用 FinalUtilityClass.class
。
PowerMockito.mockStatic(FinalUtilityClass.class)
PowerMockito.when(FinalUtilityClass.method(params)).thenReturn(return);
此外,如果您有一些问题,例如:“不可能模拟最终方法”,您可以创建文件 org/powermock/extensions/configuration.properties
并设置此配置 mockito.mock-maker-class=mock-maker-inline
就像 PowerMockito documentation 呈现的那样.