Support AGP 9 built-in Kotlin and the KMP android library plugin#543
Merged
Conversation
AGP 9 enables built-in Kotlin by default and rejects org.jetbrains.kotlin.android, so the plugin never saw its only Android trigger and silently configured nothing on AGP 9 projects. - React to com.android.base when the built-in `kotlin` extension is present, in addition to org.jetbrains.kotlin.android; a flag prevents double configuration on AGP 8 where both fire - Fall back to testImplementation when testApi does not exist (AGP 9 removed it) - Codec auto-detection selects protobuf-javalite for Android projects detected via com.android.base, not just via the KGP android plugin - Tolerate a missing <target>Test KotlinSourceSet: the AGP KMP android target (com.android.kotlin.multiplatform.library) has androidHostTest/androidDeviceTest instead of androidTest - Fall back to the base generateProto/generateTestProto tasks for JVM-like KMP targets whose Gradle source sets don't exist (the AGP KMP android target creates none) - Order ArtProfile tasks after generateProto: AGP derives baselineProfiles directories as siblings of Kotlin source directories, which lands inside generateProto's output and otherwise trips Gradle's implicit-dependency validation - Integration tests: AGP version is overridable via -Dandroid-integration.version; android-test-fixtures applies the KGP android plugin only on AGP < 9; new multiplatform-android module exercises the KMP android target and is included only on AGP 9+ - CI: new integration-agp9 job runs the integration suite with AGP 9.2.1 on all three OSes, with and without the configuration cache
Replaces the source-set-srcDir approach for com.android.kotlin.multiplatform.library with the variant API. Generated sources are registered per component with addGeneratedSourceDirectory via a sync task, so source sets correspond exactly to compilations: androidMain gets main protos, androidHostTest gets test protos when host tests are enabled. Device tests are not wired. - New AndroidKmpLibrary object handles the target; ProtoktBuild dispatches to it and no longer needs the generateProto task-name fallback or optional test source sets - protokt-gradle-plugin adds a compileOnly dependency on com.android.tools.build:gradle-api; runtime classes load only when the AGP KMP library plugin is present - ArtProfile ordering constraint kept: commonMain's generated srcDir still participates in the android compilation, so AGP still derives a baselineProfiles sibling inside generateProto's output - multiplatform-android integration module enables host tests and exercises main and test protos in them
addGeneratedSourceDirectory relocates the wired DirectoryProperty into an AGP-managed location, which forced a sync task to copy generateProto output. Add the generated directories to the androidMain and androidHostTest Kotlin source sets directly, with explicit compile-task dependencies, matching how every other source-set-less KMP target is wired. Drops the sync task and the compileOnly dependency on com.android.tools.build:gradle-api.
- Replace the androidConfigured flag with a hasPlugin check: the com.android.base callback runs after the plugins block, so checking for org.jetbrains.kotlin.android there is race-free on AGP 8 - Use the<KotlinMultiplatformExtension>() in AndroidKmpLibrary - Construct messages directly in multiplatform-android tests instead of through a commonMain factory - android-test-fixtures: compileSdk 31 -> 36. Platform 31 is not preinstalled on GitHub runners and its on-demand download corrupts intermittently, failing random integration matrix rows
ogolberg
approved these changes
Jul 7, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
AGP 9 enables built-in Kotlin by default and fails the build if
org.jetbrains.kotlin.androidis applied. That plugin id was protokt's only Android trigger, so on AGP 9 protokt configured nothing.Single-platform Android
com.android.basewhen the built-inkotlinextension is present and the KGP android plugin is not (avoiding double configuration on AGP 8).testApitotestImplementationsince AGP 9 removedtestApi.optimal()codec detection selectsprotobuf-javalitefor these projects, matchingkotlin("android")behavior.KMP android target (
com.android.kotlin.multiplatform.library)Previously failed at apply time. Protokt now wires it like other source-set-less KMP targets, with source sets mapping exactly to compilations:
src/main/proto→androidMain;src/test/proto→androidHostTestwhen host tests are enabled. Device tests are not wired.ArtProfiletasks are ordered aftergenerateProto: AGP derivesbaselineProfilesdirectories as siblings of Kotlin source directories, which lands insidegenerateProto's output and otherwise trips Gradle's implicit-dependency validation. Bit of an annoyance.Tests and CI
-Dandroid-integration.versionoverrides AGP in the integration suite;android-test-fixturescovers the legacy path on AGP 8 and built-in Kotlin on 9.multiplatform-androidmodule (AGP 9+ only) exercises the KMP android target, including host tests.integration-agp9CI job runs the suite with AGP 9.2.1 on all three OSes, with and without the configuration cache. Separate job because AGP 9 forces KGP 2.2.10+ onto the buildscript classpath, which would invalidate the older-Kotlin matrix rows.android-test-fixturescompileSdk bumped 31 → 36; platform 31 is not preinstalled on runners and its download corrupts intermittently.