如何用Mockito在Java中Mock静态类内的静态方法及链式调用?
问题描述
我有一个Java类OuterClass,其中包含静态方法getInnerClass()。想要为调用getInnerClass().getType()的方法编写单元测试,并mockgetType()的行为,同时不执行getInnerClass()内部的逻辑,直接返回mock的InnerClass实例供后续链式调用。
简化后的代码如下:
public class OuterClass { public static InnerClass getInnerClass() { // 这里的逻辑不想在测试中执行 } public static class InnerClass { private String type; public String getType() { return type; } } }
环境信息:
- JUnit 5
- Spring Boot 3
我曾尝试mockInnerClass的getType(),但因为getInnerClass()是静态方法,测试时会实际调用它,导致不符合预期。也试过mockStatic但没成功,求可行的实现方式。
解决方案
要实现不调用原静态方法getInnerClass(),同时mock其返回的InnerClass的getType()行为,需要用Mockito的mockStatic来静态mockOuterClass,指定getInnerClass()返回预先mock好的InnerClass实例。
正确测试代码示例
import org.junit.jupiter.api.Test; import org.mockito.Mockito; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.mockito.Mockito.when; public class YourTestClass { @Test void testChainedStaticMethodCall() { // 1. Mock InnerClass实例,配置getType()的返回值 OuterClass.InnerClass mockInner = Mockito.mock(OuterClass.InnerClass.class); when(mockInner.getType()).thenReturn("mockedType"); // 2. 静态mock OuterClass,让getInnerClass()返回mock实例 try (Mockito.MockedStatic<OuterClass> mockedOuter = Mockito.mockStatic(OuterClass.class)) { mockedOuter.when(OuterClass::getInnerClass).thenReturn(mockInner); // 3. 执行目标调用链(模拟业务代码中的调用) String result = OuterClass.getInnerClass().getType(); // 4. 验证结果符合预期 assertEquals("mockedType", result); } } }
关键说明
MockedStatic的作用域:必须用try-with-resources包裹,确保静态mock在测试结束后自动清除,避免污染其他测试用例。- 静态方法mock方式:通过
mockedOuter.when(OuterClass::getInnerClass)指定静态方法的返回值,不会触发原方法的执行。 - 链式mock顺序:先创建并配置
InnerClass的mock实例,再让静态方法返回该实例,保证后续getType()调用走mock逻辑。
注意事项
- 确保Mockito版本在3.4.0及以上(Spring Boot 3默认依赖的版本满足要求),该版本才支持
mockStatic功能。 - 若测试的是Spring组件方法,无需额外
@MockBean(除非业务逻辑依赖其他Bean),上述纯Mockito方案即可解决问题。
内容的提问来源于stack exchange,提问作者Aryan Gupta
相关产品推荐
相关产品推荐

