Reputation: 3742
I have Kotlin classes and Groovy/Spock tests. When I mock a Kotlin class and set a property value on the mock, it fails to carry through to Kotlin.
Here is a Kotlin entity class, and a class which uses it:
open class TestEntity(var prop: String) {
}
class AClassUnderTest {
fun useATestEntity(testEntity: TestEntity) {
System.out.println("Checking it isn't null within Kotlin code: " + (testEntity.prop))
System.out.println("Code which assumes it is not null: " + testEntity.prop.length)
}
}
And here is a test which mocks TestEntity, mocks the getProp() method, then calls a Kotlin method to use it:
class AClassUnderTestTest extends Specification {
def "UseATestEntity"() {
given:
def cut = new AClassUnderTest()
def testEntityMock = GroovyMock(TestEntity)
testEntityMock.getProp() >> "abc"
System.out.println("Checking it isn't null after mocking: " + (testEntityMock.prop))
when:
System.out.println("Checking it isn't null during when clause: " + (testEntityMock.prop))
cut.useATestEntity(testEntityMock)
then:
noExceptionThrown()
}
}
The expected behavior is that the demo println's all show "abc" and the method succeeds
The observed behavior is that the println within Kotlin shows the property is null, and the method fails:
Checking it isn't null after mocking: abc
Checking it isn't null during when clause: abc
Checking it isn't null within Kotlin code: null
Expected no exception to be thrown, but got 'java.lang.NullPointerException'
What am I doing wrong?
How can I mock a Kotlin class and set a value on it such that the mocked value is retrieved in Kotlin code as well as Groovy code?
Already tried:
Upvotes: 2
Views: 563
Reputation: 3742
Solved: the property itself must be declared open as well:
open class TestEntity(
open var prop: String // <-- has to be declared open to be mockable!
) {
}
Upvotes: 2