我还有最后一节课,大概是这样的:

public final class RainOnTrees{

   public void startRain(){

        // some code here
   }
}

我在其他一些类中使用这个类,像这样:

public class Seasons{

   RainOnTrees rain = new RainOnTrees();

   public void findSeasonAndRain(){

        rain.startRain();

    }
}

在我的JUnit测试类Seasons.java中,我想模拟RainOnTrees类。我怎么能用Mockito做到这一点?


当前回答

没有尝试final,但私有,使用反射删除修饰符工作!已经进一步检查,它不为最终工作。

其他回答

使用Powermock。这个链接展示了如何做到这一点:https://github.com/jayway/powermock/wiki/MockFinal

如果你需要在Android的测试中使用Mockito(即在Android设备中运行),你不能使用Mockito -inline。有一个特殊的模拟android版本也没有解决“最终类”的问题。唯一可行的解决方案似乎是Dexmaker库。唯一的限制是它只能在Android P (Android 9, API 28)或更高版本上运行。导入方式如下:

androidTestImplementation "com.linkedin.dexmaker:dexmaker-mockito-inline:2.28.1"

注意,还有一个“dexmaker-mockito”版本,它也不适用于final类。确保您导入了“dexmaker-mockito-inline”。

我也有同样的问题。由于我试图模拟的类是一个简单的类,所以我只是创建了它的一个实例并返回该实例。

我猜,您之所以将它作为final,是因为您希望阻止其他类扩展RainOnTrees。正如Effective Java所建议的(第15项),有另一种方法来保持类接近于扩展而不使其成为final:

删除最后一个关键字; 将其构造函数设为private。没有类能够扩展它,因为它不能调用超构造函数; 创建一个静态工厂方法来实例化你的类。 //这里没有final关键字。 公共类RainOnTrees { 公共静态RainOnTrees newInstance() { 返回新的RainOnTrees(); } 私有RainOnTrees() { //私有构造函数。 } 公共无效startRain() { //这里有一些代码 } }

通过使用这种策略,您将能够使用Mockito并使用很少的样板代码保持类关闭以供扩展。

我克服了这条信息:

org.mockito.exceptions.base.MockitoException: 不能模拟/间谍类org.slf4j.impl.Log4jLoggerAdapter Mockito不能模仿/侦察,因为: 最终类或匿名类

从这个:log = spy(log);

用这个代替:

log = mock(Logger.class);

这样就有用了。

我猜“默认”记录器适配器是final类的一个实例,所以我不能“侦察”它,但我可以模拟整个事情。去图…

这可能意味着你可以用其他一些“非最终”实例来代替它,如果你有的话。或者简化版本等等。就其价值而言……