Android单元测试没有被嘲笑

Posted

技术标签:

【中文标题】Android单元测试没有被嘲笑【英文标题】:Android unit test not mocked 【发布时间】:2015-06-06 18:29:58 【问题描述】:

我遵循了本指南 https://sites.google.com/a/android.com/tools/tech-docs/unit-testing-support 但我被这个错误困住了:

junit.framework.AssertionFailedError: Exception in constructor: testSaveJson (java.lang.RuntimeException: Method put in org.json.JSONObject not mocked. See https://sites.google.com/a/android.com/tools/tech-docs/unit-testing-support for details.

我按照指南所说的那样通过 Gradle 构建进行了修改,但没有任何区别

 testOptions  
    unitTests.returnDefaultValues = true
  

【问题讨论】:

我们需要更多信息。添加一些代码,解释你想要实现的目标。对 JSON(反)序列化程序进行单元测试? 【参考方案1】:

JSON 与 Android SDK 捆绑在一起,因此您只会遇到一个存根。你可以拉入一个 JSON jar,它会提供真实的对象来使用。

为此,您需要将其添加到您的 build.gradle:

testImplementation 'org.json:json:20140107'

或者,您可以下载并包含该 jar。

testCompile files('libs/json.jar')

请注意,最新版本的 JSON 是为 Java 8 构建的,因此您需要获取 20140107 您可能还需要清理和重建项目。

【讨论】:

看来你现在可以使用 Gradle 拉取,所以 testCompile 'org.json:json:20140107' 很好。 您应该使用这个版本:org.json:json:20080701,它与 Android 版本匹配。在这个版本中,getString() 在 value 为 json 为 null 时返回 null,而不是抛出异常。 @NicolasCornette 您指的是哪个 Android 版本? @BenPearson 这在所有 android 版本上都是如此 只是在 build.gradle 中包含这个似乎并没有导入正确的库 - 我仍然收到“未模拟”错误。使用显式库模块需要做什么?【参考方案2】:

我认为您尝试使用 org.json.JSONObject 运行测试,它是纯 jUnit 上的 Android Framework 的一部分。

来自文档:

用于运行单元测试的 android.jar 文件不包含任何实际代码 - 由真实设备上的 Android 系统映像提供。相反,所有方法都会抛出异常(默认情况下)。

我们知道默认行为在使用 Log 或 TextUtils 等类时会出现问题,并将在未来版本中评估可能的解决方案。

您需要模拟可用于此目的的 Android 环境 Robolectric 或 InstrumentationTests

【讨论】:

那么没有办法在纯Junit测试中使用JSON? 使用 Robolectric 为我完成了这项工作。有趣的是,在我们使用 AGP 7.0 升级到 Android Studio 北极狐后出现了错误消息,而使用 Android Studio 4.2 和 AGP 4.2 我们没有问题。【参考方案3】:

您需要在 build.gradle 中添加以下内容:

android 
  // ...
  testOptions  
    unitTests.returnDefaultValues = true
  

dependencies 
//...
    testImplementation 'org.json:json:20180813'

【讨论】:

【参考方案4】:

如果您使用 Kotlin DSL 的问题的解决方案:

testOptions 
    unitTests.isReturnDefaultValues = true


testImplementation("org.json:json:20210307")

【讨论】:

【参考方案5】:
android 


testOptions 
    unitTests.returnDefaultValues = true
 

dependencies 
testImplementation libs.leakCanaryNoOp
testImplementation tests.jUnit
testImplementation tests.mockito
testImplementation(tests.mokitoKotlin) 
    exclude group: "org.jetbrains.kotlin", module: "kotlin-stdlib"
    exclude group: "org.jetbrains.kotlin", module: "kotlin-runtime"
    exclude group: "org.jetbrains.kotlin", module: "kotlin-reflect"
    exclude group: "org.mockito", module: "mockito-core"

testImplementation tests.powerMock
testImplementation tests.powerMockApiMockito
testImplementation (tests.robolectric) 
    exclude group: 'org.robolectric', module: 'robolectric-resources:'

testImplementation (tests.robolectricShadowsSupport)
    exclude group: 'org.robolectric', module: 'robolectric'

kaptTest libs.daggerCompiler

【讨论】:

我们可以对此进行更多解释吗?

以上是关于Android单元测试没有被嘲笑的主要内容,如果未能解决你的问题,请参考以下文章

Mockito Mocking Android Context PackageManager Exception

Nestjs 单元测试 - 模拟方法守卫

苦苦挣扎于单元测试和嘲弄

更新gradle后Android单元测试无法解析被测类

读取文件的方法的单元测试[重复]

通过JUnit进行Android单元测试