繁体   English   中英

如何模拟一个由另一个静态方法调用的静态方法?

[英]How to mock a static method which be called by another static method?

我想测试一个静态方法A,该方法在同一类中调用另一个静态方法B。 如何模拟方法B?

模拟静态方法快速总结

Use the @RunWith(PowerMockRunner.class) annotation at the class-level of the test case.
Use the @PrepareForTest(ClassThatContainsStaticMethod.class) annotation at the class-level of the test case.
Use PowerMock.mockStatic(ClassThatContainsStaticMethod.class) to mock all methods of this class.
Use PowerMock.replay(ClassThatContainsStaticMethod.class) to change the class to replay mode.
Use PowerMock.verify(ClassThatContainsStaticMethod.class) to change the class to verify mode.

示例在PowerMock中模拟静态方法需要在PowerMock中使用“ mockStatic”方法。 假设您有一个名为ServiceRegistrator的类,带有一个名为registerService的方法,如下所示:

public long registerService(Object service) {
   final long id = IdGenerator.generateNewId();
   serviceRegistrations.put(id, service);
   return id;
}

这里的兴趣点是我们要模拟的对IdGenerator.generateNewId()的静态方法调用。 IdGenerator是一个帮助程序类,仅为该服务生成一个新的ID。 看起来像这样:

public class IdGenerator {

   /**
    * @return A new ID based on the current time.
    */
   public static long generateNewId() {
      return System.currentTimeMillis();
   }
}

使用PowerMock,一旦您告诉PowerMock准备IdGenerator类进行测试,就可以像使用EasyMock的任何其他方法一样期待对IdGenerator.generateNewId()的调用。 您可以通过在测试用例的类级别添加注释来实现。 只需使用@PrepareForTest(IdGenerator.class)即可完成。 您还需要告诉JUnit使用PowerMock执行测试,该测试通过使用@RunWith(PowerMockRunner.class)完成。 没有这两个注释,测试将失败。

实际的测试实际上非常简单:

@Test
public void testRegisterService() throws Exception {
        long expectedId = 42;

        // We create a new instance of test class under test as usually.
        ServiceRegistartor tested = new ServiceRegistartor();

        // This is the way to tell PowerMock to mock all static methods of a
        // given class
        mockStatic(IdGenerator.class);

        /*
         * The static method call to IdGenerator.generateNewId() expectation.
         * This is why we need PowerMock.
         */
        expect(IdGenerator.generateNewId()).andReturn(expectedId);

        // Note how we replay the class, not the instance!
        replay(IdGenerator.class);

        long actualId = tested.registerService(new Object());

        // Note how we verify the class, not the instance!
        verify(IdGenerator.class);

        // Assert that the ID is correct
        assertEquals(expectedId, actualId);
}

请注意,即使类是最终的,也可以在类中模拟静态方法。 该方法也可以是最终的。 要仅模拟类的特定静态方法,请参阅文档中的部分模拟部分。

参考:powermock Wiki

如果这两个函数在同一个类中,则可以简单地调用而不使用任何对象或类名;如果它们在不同的函数中,则可以使用类名互相调用,希望这会有所帮助。 :)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM