Mockito spy场景下遭遇UnfinishedStubbingException问题求助
我之前也碰到过类似的问题,结合你的代码和报错信息,咱们从这几个方向排查:
1. 检查Mockito Runner和JUnit Rule的冲突
你的子类用了@RunWith(MockitoJUnitRunner.class),但抽象类里又通过@Before手动创建Spy并Stub方法,同时还使用了JUnitSoftAssertions这个Rule。在Mockito 1.x和JUnit 4的组合中,MockitoRunner和JUnit Rule的初始化顺序可能会打乱Mockito内部的Stubbing状态,导致异常。
解决办法:
- 如果你的测试类没有用到
@Mock这类Mockito注解,直接删掉子类的@RunWith(MockitoJUnitRunner.class)就行——你是手动创建Spy的,不需要Mockito Runner来管理实例。 - 如果需要保留Mockito注解的支持,把Mockito Runner替换成Mockito Rule,这样能和
JUnitSoftAssertions兼容:
在抽象类中添加:
然后移除子类的@Rule public MockitoRule mockitoRule = MockitoJUnit.rule();@RunWith(MockitoJUnitRunner.class)。
2. 排查functionInstance()中的构造逻辑
虽然你只是返回new MyFunction(),但如果MyFunction的构造函数里直接或间接调用了getDescription()方法,那么在创建Spy实例时,这个真实方法会被执行。而此时你正在执行Mockito.doReturn("Bla").when(function).getDescription()的Stubbing操作,Mockito不允许在Stubbing过程中调用真实对象的方法,这就会触发UnfinishedStubbingException。
验证方法:
临时注释掉setUp()中的Stubbing代码,运行测试看是否还报错。如果不报错,再检查MyFunction的构造函数、初始化块里有没有调用getDescription()或者依赖它的方法。
解决办法:
调整MyFunction的构造逻辑,避免在构造时调用会被Stub的方法;或者改用Mockito.mock()创建Mock对象(而非Spy),不过这取决于你是否需要保留真实方法的逻辑。
3. 尝试升级Mockito版本
你用的Mockito 1.10.19是比较老旧的版本,和JUnit 4.12可能存在一些已知的兼容性bug。可以尝试升级到Mockito 1.x系列的最新版本(比如1.10.24),或者直接升级到Mockito 2.x(Mockito 2.x需要JUnit 4.12+支持,你的版本刚好满足),很多旧版本的Stubbing异常问题在新版本中已经被修复。
内容的提问来源于stack exchange,提问作者JeanValjean

