用Mockk模拟常量值

时间:2019-11-15 12:53:49

标签: kotlin mockk

我们当前有一个仅包含常量值的对象。

object Constants {
    const val VERSION = V1
}

但是,这些常量的值将来可能会更改。因此,如果VERSION值未满足某些条件,我想确保测试中断。我们使用Mockk进行模拟,因此我尝试根据docs来模拟Constants对象

mockkObject(Constants)
every { Constants.VERSION } returns -1
assertThat(Constants.VERSION).isEqualTo(-1)

不幸的是,这无法编译并出现以下错误:io.mockk.MockKException: Missing calls inside every { ... } block.

有没有办法模拟常量值?还是应该为常量提供getter方法并模拟它们?

3 个答案:

答案 0 :(得分:0)

kotlin don't have getters中的常量,这就是您例外的原因:io.mockk.MockKException: Missing calls inside every { ... } block。没有可以模拟的函数来检索值。

我建议您重新考虑测试常数的目标(这不是典型的测试用例),或者进行解决。解决方法可能是:

  • 为每个要模拟的常量创建一个吸气剂
  • Constants放入另一个类中,这将返回Constants对象,并且您可以测试每个字段(使用assertJ fieldByField
  • 将const值放入可以测试的文本或属性文件中

答案 1 :(得分:0)

一种可能性是使用 PowerMockMockito 中的 Whitebox;是的,您可以将 Whitebox 与 MockK 一起使用。 Whitebox 的优点是您可以自由地将常量设置为您想要的任何值,而无需麻烦地创建除单元测试外无用的包装类。

示例:

import org.powermock.reflect.Whitebox

Whitebox.setInternalState(Constants::class.java, (Constants::VERSION).name, 1)

答案 2 :(得分:0)

你可以用枚举类替换常量,然后用 MockObject 模拟它们。例如:

class MyClass {

enum class MyConstants( val param: String ) {
VERSION( "V1" ),
TEMP_FOLDER_PATH( "usr/temp/");
   }

 //to use in code:
 var tempFolder : String = MyConstants.TEMP_FOLDER_PATH.param
} 

稍后在单元测试中模拟它:

 mockObject( MyClass.MyConstants.TEMP_FOLDER_PATH )
 every { MyClass.MyConstants.TEMP_FOLDER_PATH.param } returns "whatever is needed"