我最近开始做一个新项目,其中包括基于Robolectric的单元测试。
当在Android Studio(v3.6)中运行时,所有的测试都成功通过。但奇怪的是,当我在使用 ./gradlew test
在终端上进行测试时,出现了非常吓人的错误。
java.lang.VerifyError: Stack map does not match the one at exception handler 56
Exception Details:
Location:
com/google/android/gms/measurement/internal/zzjy.zza(Landroid/net/Uri;)Landroid/os/Bundle; @56: astore
Reason:
Type 'java/lang/String' (current frame, locals[5]) is not assignable to null (stack map, locals[5])
Current Frame:
bci: @51
flags: { }
locals: { 'com/google/android/gms/measurement/internal/zzjy', 'android/net/Uri', 'java/lang/String', 'java/lang/String', 'java/lang/String', 'java/lang/String' }
stack: { 'java/lang/UnsupportedOperationException' }
Stackmap Frame:
bci: @56
flags: { }
locals: { 'com/google/android/gms/measurement/internal/zzjy', 'android/net/Uri', 'java/lang/String', 'java/lang/String', 'java/lang/String', null }
stack: { 'java/lang/UnsupportedOperationException' }
Bytecode:
// redacted..
Exception Handler Table:
bci [16, 53] => handler: 56
Stackmap Table:
same_frame(@6)
full_frame(@53,{Object[#2],Object[#145],Object[#129],Object[#129],Object[#129],Object[#129]},{})
full_frame(@56,{Object[#2],Object[#145],Object[#129],Object[#129],Object[#129],Null},{Object[#143]})
full_frame(@74,{Object[#2],Object[#145],Object[#129],Object[#129],Object[#129],Object[#129]},{})
same_frame(@104)
append_frame(@128,Object[#172])
same_frame(@143)
same_frame(@160)
same_frame(@177)
append_frame(@201,Object[#129])
append_frame(@225,Object[#129])
append_frame(@249,Object[#129])
append_frame(@273,Object[#129])
append_frame(@297,Object[#129])
full_frame(@300,{Object[#2],Object[#145],Object[#129],Object[#129],Object[#129],Object[#129]},{})
at com.google.android.gms.measurement.internal.zzfl.<init>(com.google.android.gms:play-services-measurement-impl@@17.1.0:42)
at com.google.android.gms.measurement.internal.zzfl.zza(com.google.android.gms:play-services-measurement-impl@@17.1.0:285)
at com.google.firebase.analytics.FirebaseAnalytics.getInstance(com.google.android.gms:play-services-measurement-api@@17.1.0:9)
// redacted..
at org.robolectric.android.internal.AndroidTestEnvironment.lambda$installAndCreateApplication$0(AndroidTestEnvironment.java:276)
at org.robolectric.android.internal.AndroidTestEnvironment$$Lambda$45/1286999442.run(Unknown Source)
at org.robolectric.util.PerfStatsCollector.measure(PerfStatsCollector.java:75)
at org.robolectric.android.internal.AndroidTestEnvironment.installAndCreateApplication(AndroidTestEnvironment.java:276)
at org.robolectric.android.internal.AndroidTestEnvironment.setUpApplicationState(AndroidTestEnvironment.java:169)
at org.robolectric.RobolectricTestRunner.beforeTest(RobolectricTestRunner.java:301)
at org.robolectric.internal.SandboxTestRunner$2.lambda$evaluate$0(SandboxTestRunner.java:243)
at org.robolectric.internal.SandboxTestRunner$2$$Lambda$28/968645498.run(Unknown Source)
at org.robolectric.internal.bytecode.Sandbox.lambda$runOnMainThread$0(Sandbox.java:89)
at org.robolectric.internal.bytecode.Sandbox$$Lambda$29/1700079137.call(Unknown Source)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
为什么测试在Android Studio中通过,但在终端中失败?
为什么在Android Studio中测试通过,但在终端中测试失败?
这是因为从Android Studio调用时使用的JDK和从终端调用时使用的JDK版本不匹配。
当从终端调用时,Gradle使用的是哪个JDK版本?
从终端运行时,Gradle使用的是定义在 JAVA_HOME
- 在我的机器上指向(旧版本)1.8.0-51。
当从Android Studio调用Gradle时,Gradle使用的是哪个JDK版本?
从2.2版本开始Android Studio中捆绑了一份最新的OpenJDK。例如,Android Studio 3.6使用OpenJDK v1.8.0-212。
当你想让Gradle在Android Studio中运行你的任务时使用的JDK版本可以在以下地址找到 Project Structure
> SDK Location
> JDK Location
. 默认情况下,它被配置为使用捆绑的OpenJDK版本。
我是如何解决这个错误的?
为了在Android Studio中重现错误,我已经改变了 JDK Location
到 JAVA_HOME
再次运行测试(从Android Studio),瞧!我只在终端看到的错误现在也出现在Android Studio中。
为了解决在终端运行测试时出现的故障,我更新了由 JAVA_HOME
到最新的(1.8.0-251),现在在Android Studio和使用 gradlew
从终端。