question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

NullPointerException happens when mock a suspend function B called by another function A

See original GitHub issue

Below code should print 3, but actually it throws below error. Even after I remove all suspend, the print value is 0 instead of 3. It can be reproduced locally even I copy this test to this repo, https://github.com/mockito/mockito-kotlin/blob/main/mockito-kotlin/src/test/kotlin/test/CoroutinesTest.kt

import kotlinx.coroutines.runBlocking
import org.junit.jupiter.api.Test
import org.mockito.kotlin.doReturn
import org.mockito.kotlin.mock

class A{
    suspend fun a():Int{
        return b()
    }
    suspend fun b(): Int{
        return 2
    }
}

class HelloTest {
    @Test
    fun testBWasCalledByA() = runBlocking{
        val a = mock<A>{
            onBlocking { b() } doReturn 3
        }
        val res = a.a()
        println(res)
    }
}
java.lang.NullPointerException: Cannot invoke "java.lang.Number.intValue()"

 

                at org.example.HelloTest$testBWasCalledByA$1.invokeSuspend(HelloTest.kt:24)

                at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)

                at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:56)

                at kotlinx.coroutines.EventLoopImplBase.processNextEvent(EventLoop.common.kt:274)

                at kotlinx.coroutines.BlockingCoroutine.joinBlocking(Builders.kt:84)

                at kotlinx.coroutines.BuildersKt__BuildersKt.runBlocking(Builders.kt:59)

                at kotlinx.coroutines.BuildersKt.runBlocking(Unknown Source)

                at kotlinx.coroutines.BuildersKt__BuildersKt.runBlocking$default(Builders.kt:38)

                at kotlinx.coroutines.BuildersKt.runBlocking$default(Unknown Source)

                at org.example.HelloTest.testBWasCalledByA(HelloTest.kt:20)

                at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)

                at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:64)

                at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)

                at java.base/java.lang.reflect.Method.invoke(Method.java:564)

                at org.junit.platform.commons.util.ReflectionUtils.invokeMethod(ReflectionUtils.java:389)

                at org.junit.jupiter.engine.execution.ExecutableInvoker.invoke(ExecutableInvoker.java:115)

                at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.lambda$invokeTestMethod$6(TestMethodTestDescriptor.java:167)

                at org.junit.jupiter.engine.execution.ThrowableCollector.execute(ThrowableCollector.java:40)

                at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.invokeTestMethod(TestMethodTestDescriptor.java:163)

                at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.execute(TestMethodTestDescriptor.java:110)

                at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.execute(TestMethodTestDescriptor.java:57)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$execute$3(HierarchicalTestExecutor.java:83)

                at org.junit.platform.engine.support.hierarchical.SingleTestExecutor.executeSafely(SingleTestExecutor.java:66)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:77)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$null$2(HierarchicalTestExecutor.java:92)

                at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:183)

                at java.base/java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:177)

                at java.base/java.util.Iterator.forEachRemaining(Iterator.java:133)

                at java.base/java.util.Spliterators$IteratorSpliterator.forEachRemaining(Spliterators.java:1801)

                at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484)

                at java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:474)

                at java.base/java.util.stream.ForEachOps$ForEachOp.evaluateSequential(ForEachOps.java:150)

                at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateSequential(ForEachOps.java:173)

                at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)

                at java.base/java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:497)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$execute$3(HierarchicalTestExecutor.java:92)

                at org.junit.platform.engine.support.hierarchical.SingleTestExecutor.executeSafely(SingleTestExecutor.java:66)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:77)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$null$2(HierarchicalTestExecutor.java:92)

                at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:183)

                at java.base/java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:177)

                at java.base/java.util.Iterator.forEachRemaining(Iterator.java:133)

                at java.base/java.util.Spliterators$IteratorSpliterator.forEachRemaining(Spliterators.java:1801)

                at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484)

                at java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:474)

                at java.base/java.util.stream.ForEachOps$ForEachOp.evaluateSequential(ForEachOps.java:150)

                at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateSequential(ForEachOps.java:173)

                at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)

                at java.base/java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:497)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.lambda$execute$3(HierarchicalTestExecutor.java:92)

                at org.junit.platform.engine.support.hierarchical.SingleTestExecutor.executeSafely(SingleTestExecutor.java:66)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:77)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:51)

                at org.junit.platform.engine.support.hierarchical.HierarchicalTestEngine.execute(HierarchicalTestEngine.java:43)

                at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:170)

                at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:154)

                at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:90)

                at com.intellij.junit5.JUnit5IdeaTestRunner.startRunnerWithArgs(JUnit5IdeaTestRunner.java:69)

                at com.intellij.rt.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:33)

                at com.intellij.rt.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:230)

                at com.intellij.rt.junit.JUnitStarter.main(JUnitStarter.java:58)

Issue Analytics

  • State:closed
  • Created 2 years ago
  • Comments:5

github_iconTop GitHub Comments

2reactions
bohsencommented, Apr 12, 2021
@Test
fun testBWasCalledByA() = runBlocking{
    val a = mock<A>{
        onBlocking { b() } doReturn 3
    }
    val res = a.a()
    println(res)
}

@ToffeeLu As for the example you’ve provided you invoke an unstubbed function on your mock (this line: val res = a.a()) . Maybe try:

open class A{
    open suspend fun a():Int{
        return b()
    }
    open suspend fun b(): Int{
        return 2
    }
}

class HelloTest {
    @Test
    fun testBWasCalledByA() = runBlocking{
        val a = mock<A>{
            onBlocking { b() } doReturn 3
        }
        val res = a.b() // invoke the stubbed function instead
        println(res)
    }
}

I’ve also added open declarations to your class under test (class A). Not needed if you use inline-mockmaker, AllOpen-plugin or similar.

0reactions
ToffeeLucommented, Apr 13, 2021

Thanks @bohsen , close for now. Will send PR later for the WIKI.

Read more comments on GitHub >

github_iconTop Results From Across the Web

unit test coroutine nullpointerexception when mocking
You tried to chain invocations when stubbing a method. whenever(searchCriteriaProvider.provideTrendingSearch().trendingSearches) .
Read more >
NullPointerException when coAnswering mocked method with ...
It looks like coAnswers doesn't play well with suspend lambda arguments on the mocked method. Here's an example: class FooTest { class Foo ......
Read more >
Java NullPointerException - Detect, Fix, and Best Practices
NullPointerException is raised in an application when we are trying to do some operation on null where an object is required.
Read more >
NullPointerException in stubbed method of mocked class
I'm getting a NullPointerException for a method that I have stubbed in a mocked class. The odd thing is that I do not...
Read more >
NullPointerException on compiling suspend inline fun with ...
NullPointerException on compiling suspend inline fun with typealias to suspend function type. 7. Is duplicated by 6. Is duplicated by 6 issues (0...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found