Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mocking doesn't work for a functional interface returning a value class #1242

Open
3 tasks done
uwared opened this issue Apr 19, 2024 · 0 comments
Open
3 tasks done

Comments

@uwared
Copy link

uwared commented Apr 19, 2024

Prerequisites

Please answer the following questions for yourself before submitting an issue.

  • I am running the latest version
  • I checked the documentation and found no answer
  • I checked to make sure that this issue has not already been filed

Expected Behavior

The test below, which mocks a functional interface returning a value class, passes:

Minimal reproducible code
package com.example

import io.kotest.matchers.shouldBe
import io.mockk.every
import io.mockk.impl.annotations.InjectMockKs
import io.mockk.impl.annotations.MockK
import io.mockk.junit5.MockKExtension
import org.junit.jupiter.api.Test
import org.junit.jupiter.api.extension.ExtendWith
import org.springframework.stereotype.Component

@JvmInline
value class ValueClass(val value: Int)

interface ValueClassInterface : () -> ValueClass

@Component
class ExampleComponent(
    private val valueClassInterface: ValueClassInterface,
) {
    fun testFunction(): ValueClass {
        return valueClassInterface()
    }
}

@ExtendWith(MockKExtension::class)
class ValueClassTest {

    @MockK
    lateinit var valueClassInterface: ValueClassInterface

    @InjectMockKs
    lateinit var exampleComponent: ExampleComponent

    @Test
    fun test() {
        every { valueClassInterface() } returns ValueClass(1)
        exampleComponent.testFunction() shouldBe ValueClass(1)
    }
}

Current Behavior

The test is failing with an exception:

Stacktrace
Unknown origin of public abstract operator fun invoke(): R defined in kotlin.Function0[FunctionInvokeDescriptor@17ba57f0] (class kotlin.reflect.jvm.internal.impl.builtins.functions.FunctionInvokeDescriptor)
kotlin.reflect.jvm.internal.KotlinReflectionInternalError: Unknown origin of public abstract operator fun invoke(): R defined in kotlin.Function0[FunctionInvokeDescriptor@17ba57f0] (class kotlin.reflect.jvm.internal.impl.builtins.functions.FunctionInvokeDescriptor)
	at kotlin.reflect.jvm.internal.RuntimeTypeMapper.mapSignature(RuntimeTypeMapper.kt:226)
	at kotlin.reflect.jvm.internal.KFunctionImpl.<init>(KFunctionImpl.kt:52)
	at kotlin.reflect.jvm.internal.CreateKCallableVisitor.visitFunctionDescriptor(util.kt:314)
	at kotlin.reflect.jvm.internal.CreateKCallableVisitor.visitFunctionDescriptor(util.kt:291)
	at kotlin.reflect.jvm.internal.impl.descriptors.impl.FunctionDescriptorImpl.accept(FunctionDescriptorImpl.java:826)
	at kotlin.reflect.jvm.internal.KDeclarationContainerImpl.getMembers(KDeclarationContainerImpl.kt:62)
	at kotlin.reflect.jvm.internal.KClassImpl$Data$declaredNonStaticMembers$2.invoke(KClassImpl.kt:173)
	at kotlin.reflect.jvm.internal.KClassImpl$Data$declaredNonStaticMembers$2.invoke(KClassImpl.kt:173)
	at kotlin.reflect.jvm.internal.ReflectProperties$LazySoftVal.invoke(ReflectProperties.java:70)
	at kotlin.reflect.jvm.internal.ReflectProperties$Val.getValue(ReflectProperties.java:32)
	at kotlin.reflect.jvm.internal.KClassImpl$Data.getDeclaredNonStaticMembers(KClassImpl.kt:173)
	at kotlin.reflect.jvm.internal.KClassImpl$Data$allNonStaticMembers$2.invoke(KClassImpl.kt:182)
	at kotlin.reflect.jvm.internal.KClassImpl$Data$allNonStaticMembers$2.invoke(KClassImpl.kt:182)
	at kotlin.reflect.jvm.internal.ReflectProperties$LazySoftVal.invoke(ReflectProperties.java:70)
	at kotlin.reflect.jvm.internal.ReflectProperties$Val.getValue(ReflectProperties.java:32)
	at kotlin.reflect.jvm.internal.KClassImpl$Data.getAllNonStaticMembers(KClassImpl.kt:182)
	at kotlin.reflect.jvm.internal.KClassImpl$Data$allMembers$2.invoke(KClassImpl.kt:188)
	at kotlin.reflect.jvm.internal.KClassImpl$Data$allMembers$2.invoke(KClassImpl.kt:188)
	at kotlin.reflect.jvm.internal.ReflectProperties$LazySoftVal.invoke(ReflectProperties.java:70)
	at kotlin.reflect.jvm.internal.ReflectProperties$Val.getValue(ReflectProperties.java:32)
	at kotlin.reflect.jvm.internal.KClassImpl$Data.getAllMembers(KClassImpl.kt:188)
	at kotlin.reflect.jvm.internal.KClassImpl.getMembers(KClassImpl.kt:206)
	at kotlin.reflect.full.KClasses.getFunctions(KClasses.kt:89)
	at kotlin.reflect.jvm.ReflectJvmMapping.getKotlinFunction(ReflectJvmMapping.kt:144)
	at io.mockk.core.ValueClassSupport.maybeUnboxValueForMethodReturn(ValueClassSupport.kt:26)
	at io.mockk.proxy.jvm.advice.Interceptor.call(Interceptor.kt:22)
	at io.mockk.proxy.jvm.advice.BaseAdvice.handle(BaseAdvice.kt:42)
	at io.mockk.proxy.jvm.advice.jvm.JvmMockKProxyInterceptor.interceptNoSuper(JvmMockKProxyInterceptor.java:44)
	at com.example.ValueClassInterface$Subclass0.invoke(Unknown Source)
	at com.example.ValueClassInterface$Subclass0.invoke(Unknown Source)
	at com.example.ValueClassTest$test$1.invoke-oVKG3qc(ValueClassTest.kt:37)
	at com.example.ValueClassTest$test$1.invoke(ValueClassTest.kt:37)
	at io.mockk.impl.eval.RecordedBlockEvaluator$record$block$1.invoke(RecordedBlockEvaluator.kt:24)
	at io.mockk.impl.eval.RecordedBlockEvaluator$enhanceWithRethrow$1.invoke(RecordedBlockEvaluator.kt:76)
	at io.mockk.impl.recording.JvmAutoHinter.autoHint(JvmAutoHinter.kt:23)
	at io.mockk.impl.eval.RecordedBlockEvaluator.record(RecordedBlockEvaluator.kt:39)
	at io.mockk.impl.eval.EveryBlockEvaluator.every(EveryBlockEvaluator.kt:30)
	at io.mockk.MockKDsl.internalEvery(API.kt:94)
	at io.mockk.MockKKt.every(MockK.kt:143)
        at com.example.ValueClassTest.test(ValueClassTest.kt:37)

Context

  • MockK version: 1.3.10
  • OS: macOS Sonoma 14.4.1
  • Kotlin version: 1.9.23
  • JDK version: OpenJDK 21.0.2
  • JUnit version: 5.10.2
  • Type of test: unit test
@uwared uwared changed the title Mocking doesn't work for a fucntional interface returing a value class Mocking doesn't work for a functional interface returning a value class Apr 22, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant