首页 > 解决方案 > 用 mockito 模拟内部类

问题描述

我有一个正在测试的课程,标记为“内部”

internal class UnderTest{
    fun methodToTest(){}
}

在我的 JUnit 测试中,我想测试 UnderTest import com.nhaarman.mockito_kotlin.mock

class SimpleTest{
    val mock = mock<UnderTest>()

    @Test
    fun test(){
        assertThat(....)
    } 
}

这里有点奇怪,因为 Android Studio 首先抱怨 UnderTest 不可见“公共属性暴露了它的私有类型”。那是因为 UnderTest 被标记为内部。

我将测试本身更改为内部的,这导致编译器再次感到高兴:

import com.nhaarman.mockito_kotlin.mock

internal class SimpleTest{
    val mock = mock<UnderTest>()

    @Test
    fun test(){
        assertThat(....)
    } 
}

运行这个测试会导致一个 mockito 异常,就像在旧的 mockito 版本中一样

Cannot mock/spy class com.name.UnderTest
Mockito cannot mock/spy because :
- final class

我想为这些内部类编写单元测试,但是如何不从 UnderTest 类中删除 internal 修饰符呢?

谢谢

标签: androidunit-testingkotlinmockitojunit4

解决方案


问题不在于类是internal(它相当于public在同一个模块中),而是它是final. 默认情况下,Kotlin 中的所有类都是final除非你用open.

因此,如果您想模拟您的课程,您应该将其标记为internal open class Xyz. 请注意,有一个 Maven/Gradle 插件会自动为您打开所有类:all-open plugin

例如,给定以下 Kotlin 类:

internal open class Foo

以下单元测试通过:

class FooTest {
    @Test
    fun shouldPass() {
        Mockito.mock(Foo::class.java)
    }
}

推荐阅读