如何验证Mock对象上是否有任意方法被调用?避免逐个校验
验证Mock对象是否有任意方法被调用的简洁方案
这问题我太懂了——一个个写verify(mock).methodX()确实烦得要死,尤其是Mock方法多的时候。下面给你分享几种我实际项目里用过的简洁方案,都是基于Mockito(Java生态最常用的Mock框架):
方法一:利用Mockito的mockingDetails获取所有调用记录
这是最靠谱、最通用的方案,能直接获取Mock对象上所有的方法调用记录,然后判断是否有调用发生。
代码示例
import org.mockito.Mockito; import org.mockito.invocation.InvocationOnMock; import java.util.List; import static org.assertj.core.api.Assertions.assertThat; // 假设你的Mock对象是:YourMockClass mock = Mockito.mock(YourMockClass.class); // 先执行你的业务逻辑(比如触发调用Mock的代码) // yourServiceUnderTest.doSomething(mock); // 获取Mock的所有调用记录 List<InvocationOnMock> allInvocations = Mockito.mockingDetails(mock).getInvocations(); // 验证至少有一次方法调用 assertThat(allInvocations).isNotEmpty();
进阶用法
- 验证调用次数:比如要确保恰好被调用一次,可以用
assertThat(allInvocations).hasSize(1); - 过滤无关调用:如果不想把
toString()、equals()这类默认方法的调用算进去,可以过滤记录:
import java.util.stream.Collectors; List<InvocationOnMock> relevantInvocations = allInvocations.stream() .filter(invocation -> { String methodName = invocation.getMethod().getName(); return !methodName.equals("toString") && !methodName.equals("equals"); }) .collect(Collectors.toList()); assertThat(relevantInvocations).isNotEmpty();
方法二:用verify配合通用方法(慎用)
如果你的Mock对象没有重写toString(),可以利用这个所有对象都有的方法做验证,但这个方法有局限性——如果你的业务逻辑里没触发任何Mock方法调用,但代码里打印了Mock对象,toString()也会被调用,导致误判。
代码示例
import static org.mockito.Mockito.verify; import static org.mockito.Mockito.atLeastOnce; // 验证至少有一次调用(包括toString) verify(mock, atLeastOnce()).toString();
注意:这个方法只适合你确定不会有默认方法调用干扰的场景,优先推荐第一种方法。
内容的提问来源于stack exchange,提问作者Ala Messaoudi
相关产品推荐
相关产品推荐

