mockito-kotlin
mockito-kotlin copied to clipboard
Multiple verify does not work
Hi,
my tests look like
package com.example.wichtelquiz.framework
import com.example.wichtelquiz.edm.Frage import com.nhaarman.mockitokotlin2.* import org.junit.After import org.junit.Assert.* import org.junit.Before import org.junit.Test import org.mockito.Mock import org.mockito.internal.invocation.MockitoMethod import org.mockito.internal.verification.Times
class SpielerTest { lateinit var wichtel: Spieler
@Before
fun vorJedemTest() {
wichtel = Spieler("Wichtel")
}
@After
fun nachJedemTest() {
}
@Test
fun constructor () {
assertEquals("Wichtel", wichtel.name)
assertEquals(0, wichtel.level)
assertEquals(3, wichtel.jokers.size)
assertEquals( false, Joker.PERSON in wichtel.jokers)
assertNull(wichtel.aktuelleFrage)
var knummi = Spieler("Knummi", true)
assertEquals(knummi.name, "Knummi")
assertEquals(knummi.level, 0)
assertEquals(knummi.jokers.size, 4)
assertEquals(Joker.PERSON in knummi.jokers, true)
}
@Test
fun jokerBeiKeinerFrage() {
try {
wichtel.jokerEinsetzen(Joker.ANRUF)
} catch (ex: KeineFrage ) {
assertNotNull(ex)
}
assertEquals(Joker.ANRUF in wichtel.jokers, true)
}
@Test
fun jokerWeg() {
var mock : Frage = mock()
wichtel.aktuelleFrage = mock
wichtel.jokerEinsetzen(Joker.ANRUF)
verify(mock).jokerEinsetzen(Joker.ANRUF)
assertEquals(Joker.ANRUF in wichtel.jokers, false)
}
@Test
fun falscherJoker() {
wichtel.aktuelleFrage = mock()
try {
wichtel.jokerEinsetzen(Joker.PERSON)
} catch (ex: FalscherJoker) {
assertNotNull(ex)
assertEquals(ex.joker, Joker.PERSON)
}
wichtel.jokerEinsetzen(Joker.FUENFZIGFUENFZIG)
try {
wichtel.jokerEinsetzen(Joker.FUENFZIGFUENFZIG)
} catch (ex: FalscherJoker) {
assertNotNull(ex)
assertEquals(ex.joker, Joker.FUENFZIGFUENFZIG)
}
}
@Test
fun frageLesen () {
var fragenMock: Frage = mock()
wichtel.frageLesen(fragenMock)
assertSame(fragenMock, wichtel.aktuelleFrage)
}
@Test
fun antworten() {
var mock : Frage = mock()
wichtel.aktuelleFrage = mock
wichtel.antworten(2)
verify(mock).antworten(2)
}
}
running jokerWeg alone is green but as soon as I run the complete classe jokerWeg gets red.
org.mockito.exceptions.misusing.UnfinishedVerificationException: Missing method call for verify(mock) here: -> at com.nhaarman.mockitokotlin2.VerificationKt.verify(Verification.kt:42)
Example of correct verification: verify(mock).doSomething()
Also, this error might show up because you verify either of: final/private/equals()/hashCode() methods. Those methods cannot be stubbed/verified. Mocking methods declared on non-public parent classes is not supported.
at com.example.wichtelquiz.framework.SpielerTest.jokerWeg(SpielerTest.kt:115)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:27)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:68)
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)
Process finished with exit code -1
Can you help what I am missing here? Version is 2.8.5
Cheers Silke
@Zwaartekracht Need some more context to be able to help
at com.example.wichtelquiz.framework.SpielerTest.jokerWeg(SpielerTest.kt:115) ...
Is this the same as?
var mock : Frage = mock()
What does Frage look like? Did you maybe forget to make Frage open or are you maybe using Mockito-Inline artifact or all-open plugin wrong?
Also at the end you write:
Version is 2.8.5
Mockito-kotlin latest version is 2.2.0
Hi sorry you are right:-) androidTestImplementation "com.nhaarman.mockitokotlin2:mockito-kotlin:2.2.0"
in my gradle ;-) 2.8.5 was my gson.
The Frage class is completely open as running a single test works I told that but running them all together nnot :-)
@Zwaartekracht Any chance that you could post an example of your test-class with implementations of Spieler and Frage. It doesn't have to be the exact implementation from your project. Just implementations inside the test-class that makes it possible to reproduce.
I also noticed that you use:
androidTestImplementation "com.nhaarman.mockitokotlin2:mockito-kotlin:2.2.0"
Are you maybe using inline mocking inside an instrumentation test? Because that won't work.
Yes they are instrumentation tests as I need a context. You mean mocking an app context instead of instrumentation would work.
@Zwaartekracht Not sure why jokerWeg pass when run as a single test and not when run all together. To me it sounds as if you have state leaking between your tests.
This is a longshot, but maybe try initializing your Spieler-class without lateinit var and remove the Before and After functions, you don't need them. This ensures that your subject under test (sut) is created from scratch between your tests:
class SpielerTest {
private val wichtel = Spieler("Wichtel")
@Before // Remove this function
fun vorJedemTest() {
wichtel = Spieler("Wichtel")
}
@After // Remove this function
fun nachJedemTest() {
}
...