33

我一直试图用 mockk 模拟一些东西:

我在 gradle 上有以下设置

root:
  |-- App (just a sample app for the SDK)
  |-- SDK (SDK we develop) << apply plugin: 'com.android.library'
       |-- SDKimpl.kt
  |-- Foo (wrapper around a .jar library) << apply plugin: 'com.android.library'
       |-- Foo.kt

所以我正在androidTest为 SDK 编写一个并尝试模拟Foo.kt. Foo 类没有什么不寻常的,只是直接class Foo(private val someParams) {

所以使用androidTestImplementation "io.mockk:mockk-android:1.8.13"模拟去:

val mock: Foo = mockk()
// val mock: Foo = mockkClass(Foo::class) // also tried this
every { mock.getData() } returns listOf("1", "2", "3")

我总是遇到以下崩溃:

io.mockk.MockKException: Missing calls inside every { ... } block.
at io.mockk.impl.recording.states.StubbingState.checkMissingCalls(StubbingState.kt:14)
at io.mockk.impl.recording.states.StubbingState.recordingDone(StubbingState.kt:8)
at io.mockk.impl.recording.CommonCallRecorder.done(CommonCallRecorder.kt:42)

还试图收集信息:

  • 在 JVM 测试文件夹中运行。它被嘲笑没有问题,但我无法以 JVM 运行我的测试
  • 在模块androidTest内部运行。Foo遇到同样的崩溃
  • 使用 mockkClass(Foo::class)。发生了一些崩溃
  • 使用注释@MockKMockKAnnotations.init(this). 发生了一些崩溃。
  • Log.devery {line 和 inside方法之前添加getData(),似乎在模拟设置期间调用了类中的实际真实方法。这对我来说似乎非常奇怪。

知道这里出了什么问题吗?

编辑:

根据要求,完整代码。我目前正在研究一个孤立的项目以尝试隔离错误,所以 Foo 只是:

class Foo {

    fun getData(): String {
        Log.d(TAG, "invoked foo.getData()")
        return "trolololo"
    }

}

然后我有FooTest androidTest

class FooTest {

    @Test
    fun mock_foo() {
        val foo = mockk<Foo>()
        every { foo.getData() } returns "zero"
        assertEquals("zero", foo.getData())
    }

}
4

8 回答 8

19

这似乎是一个 Mockk 打开的问题:https ://github.com/mockk/mockk/issues/182

2 个可能的快速修复(选择一个):

  1. 在模拟器中运行检测测试 >= Android-P
  2. Foo类设置为开放(以及您要模拟的方法)
于 2018-12-24T17:07:54.040 回答
15

尝试检查官方指南,看看缺少什么。

就我而言,我试图在 Kotlin 中模拟一个扩展,但错过了mockkStatic

fun Date.asMyTime() : DateTime = DateTime(this, DateTimeZone.getDefault())

mockkStatic("packageName.FileNameKt") // This is what I was missing
every {
    DateTime().asMyTime()
} returns mock(DateTime::class.java)
于 2019-05-17T13:25:33.163 回答
14

就我而言,我忘记spyk了我申请的课程every {...}

val presenter = spyk(MyPresenter())

every { view.myFun(any()) } returns Unit
于 2020-04-02T22:45:48.977 回答
5

就我而言,我错过了

@Before
fun setUp() {
    MockKAnnotations.init(this)
}
于 2020-06-03T11:24:38.350 回答
2

确保对象真的是模拟对象,而不是真实对象。

例如:

- Sdk sdk = Sdk()
+ Sdk sdk = mockk()
  every { sdk.crypto } returns mockk()
于 2020-11-10T02:26:05.063 回答
1

就我而言,我尝试使用 mock() 函数来模拟,而不是 mock k () (double k)

于 2020-11-16T13:08:33.363 回答
1

我的问题是我使用了一个没有 getter 的 java 类

public class KeyStorePasswordPair {
    public KeyStore keyStore;
    public String keyPassword;

    public KeyStorePasswordPair(KeyStore keyStore, String keyPassword) {
        this.keyStore = keyStore;
        this.keyPassword = keyPassword;
    }
}

我需要为变量添加吸气剂以使模拟工作:

public class KeyStorePasswordPair {
    public KeyStore getKeyStore() {
        return keyStore;
    }

    public String getKeyPassword() {
        return keyPassword;
    }

    private KeyStore keyStore;
    private String keyPassword;

    public KeyStorePasswordPair(KeyStore keyStore, String keyPassword) {
        this.keyStore = keyStore;
        this.keyPassword = keyPassword;
    }
}

于 2022-01-03T09:16:57.507 回答
-1

试试这样

`when`(mock.getData()).thenReturn(listOf("1", "2", "3"))
于 2021-03-03T10:15:26.413 回答