Skip to content

@PropertyValue from one module not visible to @Property in another module — MissingPropertyException #28

@dmitry-stakhov

Description

@dmitry-stakhov

Environment

  • Koin BOM: 4.2.1
  • Koin Annotations Compiler Plugin: 1.0.0-RC1
  • Project type: Kotlin Multiplatform (shared module) + Android (app module)

Description

@PropertyValue declared in one module is not resolved by @Property in another module, causing MissingPropertyException at runtime.

Minimal reproducible example

Module A (shared, KMP commonMain):

class Greeting(val message: String)

@Module
@ComponentScan
@Configuration
class ModuleA {
    @Single
    fun greeting(
        @Property("host") host: String,
    ): Greeting = Greeting("Hello from $host")
}

Module B (app, Android):

@Module(includes = [ModuleA::class])
@ComponentScan
@Configuration
class ModuleB

@PropertyValue("host")
val host = "https://example.com"

Initialization:

fun main() {
    startKoin {
        modules(ModuleB::class)
    }
    val greeting = getKoin().get<Greeting>()
    println(greeting.message) // crashes
}

Crash

MissingPropertyException: Property 'host' not found
    at org.koin.core.scope.Scope.getProperty(Scope.kt:430)

Expected behavior

@PropertyValue("host") in Module B registers the value globally, making it available to @Property("host") in Module A.

Actual behavior

The property is not found at resolution time. It appears that @PropertyValue annotations are only processed within the compilation unit where they are declared. Since Module A and Module B are separate Gradle modules (separate KSP/compiler plugin runs), the generated code for Module A has no knowledge of the property values declared in Module B.

Also tried

Annotating the parameter with @Provided in Module A to signal it will be supplied externally:

@Single
fun greeting(
    @Provided @Property("host") host: String,
): Greeting = Greeting("Hello from $host")

This did not resolve the issue — same MissingPropertyException.

Workaround

Pass properties explicitly via properties() in startKoin:

startKoin {
    properties(mapOf("host" to "https://example.com"))
    modules(ModuleB::class)
}

Notes

  • @PropertyValue works correctly when declared in the same module/compilation unit as the @Property consumer.
  • The issue is specific to cross-module usage where each module is a separate Gradle module with its own KSP processing.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions