Kotlin
Once can compile Kotlin libraries, runnable main classes, and host-side tests for the Java virtual machine, build Kotlin sources inside Android targets, and produce Kotlin/Native frameworks for Apple consumers.
Prerequisites
Install the pinned Kotlin compiler and Java Development Kit through mise:
mise install
mise exec -- kotlinc -version
mise exec -- java -versionDeclare a Library and Binary
[[target]]
name = "Greeting"
kind = "kotlin_jvm_library"
srcs = ["src/main/kotlin/dev/once/greeting/**/*.kt"]
[target.attrs]
module_name = "greeting"
jvm_target = "17"
[[target]]
name = "Hello"
kind = "kotlin_jvm_binary"
srcs = ["src/main/kotlin/dev/once/hello/**/*.kt"]
deps = ["./Greeting"]
[target.attrs]
main_class = "dev.once.hello.MainKt"
args = ["Once"]Inspect and run the graph:
once query schema kotlin_jvm_library
once query target ./Hello
once build ./Hello
once run ./HelloThe library and binary compile to Java archives. The run capability builds the archive first, then starts the main class with the complete runtime classpath.
Model Classpath Roles
Use deps for normal compile and runtime libraries. More precise relationships belong under [target.dependencies]:
[target.dependencies]
associates = ["./FriendModule"]
exported_deps = ["./PublicTypes"]
provided_deps = ["./CompileApi"]
runtime_deps = ["./RuntimeSupport"]associatespasses Kotlin friend paths so internal declarations are visible.exported_depsalso propagates to downstream compile and runtime classpaths.provided_depsappears only while compiling.runtime_depsappears only while running.
Once validates every role against its own provider contract. This catches a runtime artifact in a compiler-only role before invoking Kotlin.
Use Compiler Plug-ins
Pass package-relative compiler plug-in Java archives and their options through attributes:
[target.attrs]
compiler_plugin_jars = ["tools/serialization-plugin.jar"]
compiler_plugin_options = [
"plugin:org.example.serialization:enabled=true",
]The archive contents and options participate in the action key. Generated source directories and Kotlin symbol processing are not implemented yet, so keep those pipelines in a script target until their outputs can be represented as normal graph artifacts.
Run Host-side Tests
Declare kotlin_jvm_test with normal compile dependencies and optional runtime-only dependencies:
[[target]]
name = "GreetingTests"
kind = "kotlin_jvm_test"
srcs = ["src/test/kotlin/**/*.kt"]
deps = ["./Greeting"]
[target.dependencies]
runtime_deps = ["./TestRuntime"]
[target.attrs]
labels = ["unit"]Run the target with once test GreetingTests. The runner discovers zero-argument methods whose names begin with test, and it also recognizes JUnit and Kotlin test annotations when those libraries are present on the classpath. Once writes the standard once.test_results.v1 record, so test discovery, affected-test queries, and Model Context Protocol tools see the same shape as other ecosystems.
Android and Apple
Use android_library or android_binary for Android Kotlin sources because those target kinds also own resources and application packaging. Use kotlin_apple_framework when an Apple target should consume Kotlin/Native code as a framework.
Supported Target Kinds
Java source compilation, resource packaging, annotation processing, Kotlin symbol processing, incremental compilation, interface archive generation, and test framework lifecycle integration remain outside the typed Kotlin Java virtual machine surface. Android local tests remain available through android_local_test.
