From bf958eb5106c06cad7d3b07e28a14ae6bf63860d Mon Sep 17 00:00:00 2001 From: Igor Demin Date: Tue, 13 Dec 2022 07:27:33 +0100 Subject: [PATCH] Improve DSL for setting a custom Compose Plugin (#2527) * Improve DSL for setting a custom Compose Plugin Fixes https://github.com/JetBrains/compose-jb/issues/2459 Readme: https://github.com/JetBrains/compose-jb/pull/2526 1. Add `dependencies: Dependencies` extension that is accessible in `compose { }` block 2. Add `Dependencies.compiler` property that can return versions of Compose compiler used by the plugin: ``` compose { kotlinCompilerPlugin.set(dependencies.compiler.forKotlin("1.7.20")) //kotlinCompilerPlugin.set(dependencies.compiler.auto) // determined by applied version of Kotlin. It is a default. } ``` 3. Add ability to set arguments for Compose Compiler. Now we can write: ``` compose { kotlinCompilerPlugin.set(dependencies.compiler.forKotlin("1.7.20")) kotlinCompilerPluginArgs.add("suppressKotlinVersionCompatibilityCheck=1.7.21") } ``` 4. Remove checks for different targets We had a separate check for JS, when we released 1.2.0. It doesn't support Kotlin 1.7.20 at that moment. It is hard to refactor this feature in the new code, so I removed it. It is not needed now and it had an ugly code. When we will need it again, we'll write it again. 5. Remove the `compose.tests.androidx.compiler.version` property from gradle.properties and remove `defaultAndroidxCompilerEnvironment` Because they are used only in one test, and it seems there is no reason to use it in another place in the future * Discussions --- .../compose/ComposeCompilerCompatability.kt | 24 +++--- .../ComposeCompilerKotlinSupportPlugin.kt | 8 +- .../org/jetbrains/compose/ComposeExtension.kt | 30 ++++++- .../org/jetbrains/compose/ComposePlugin.kt | 30 +++++-- .../ComposeCompilerArtifactProvider.kt | 44 +--------- .../integration/DesktopApplicationTest.kt | 40 ++++++++- .../ComposeCompilerArtifactProviderTest.kt | 40 +++------ .../test/utils/GradlePluginTestBase.kt | 6 -- .../compose/test/utils/TestKotlinVersions.kt | 1 - .../compose/test/utils/TestProject.kt | 8 +- .../compose/test/utils/TestProjects.kt | 3 +- .../compose/test/utils/TestProperties.kt | 6 -- .../custom-compiler-args/build.gradle | 37 +++++++++ .../main-image.expected.png | Bin .../settings.gradle | 0 .../src/main/kotlin/Main.kt | 0 .../build.gradle | 2 +- .../custom-compiler/main-image.expected.png | Bin 0 -> 140 bytes .../custom-compiler/settings.gradle | 11 +++ .../custom-compiler/src/main/kotlin/Main.kt | 76 ++++++++++++++++++ gradle-plugins/gradle.properties | 9 +-- 21 files changed, 255 insertions(+), 120 deletions(-) create mode 100644 gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/build.gradle rename gradle-plugins/compose/src/test/test-projects/application/{androidx-compiler => custom-compiler-args}/main-image.expected.png (100%) rename gradle-plugins/compose/src/test/test-projects/application/{androidx-compiler => custom-compiler-args}/settings.gradle (100%) rename gradle-plugins/compose/src/test/test-projects/application/{androidx-compiler => custom-compiler-args}/src/main/kotlin/Main.kt (100%) rename gradle-plugins/compose/src/test/test-projects/application/{androidx-compiler => custom-compiler}/build.gradle (92%) create mode 100644 gradle-plugins/compose/src/test/test-projects/application/custom-compiler/main-image.expected.png create mode 100644 gradle-plugins/compose/src/test/test-projects/application/custom-compiler/settings.gradle create mode 100644 gradle-plugins/compose/src/test/test-projects/application/custom-compiler/src/main/kotlin/Main.kt diff --git a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeCompilerCompatability.kt b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeCompilerCompatability.kt index 3523a91e5e..a771cb1300 100644 --- a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeCompilerCompatability.kt +++ b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeCompilerCompatability.kt @@ -1,16 +1,20 @@ package org.jetbrains.compose -import org.jetbrains.kotlin.gradle.plugin.KotlinPlatformType +private const val KOTLIN_COMPATABILITY_LINK = + "https://github.com/JetBrains/compose-jb/blob/master/VERSIONING.md#kotlin-compatibility" internal object ComposeCompilerCompatability { - fun compilerVersionFor(kotlinVersion: String): ComposeCompilerVersion? = when (kotlinVersion) { - "1.7.10" -> ComposeCompilerVersion("1.3.0") - "1.7.20" -> ComposeCompilerVersion("1.3.2.1") - else -> null + private val kotlinToCompiler = sortedMapOf( + "1.7.10" to "1.3.0", + "1.7.20" to "1.3.2.1", + ) + + fun compilerVersionFor(kotlinVersion: String): String { + return kotlinToCompiler[kotlinVersion] ?: throw RuntimeException( + "This version of Compose Multiplatform doesn't support Kotlin " + + "$kotlinVersion. " + + "Please see $KOTLIN_COMPATABILITY_LINK " + + "to know the latest supported version of Kotlin." + ) } } - -internal data class ComposeCompilerVersion( - val version: String, - val unsupportedPlatforms: Set = emptySet() -) diff --git a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeCompilerKotlinSupportPlugin.kt b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeCompilerKotlinSupportPlugin.kt index fe9e9d55d2..e1ce195041 100644 --- a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeCompilerKotlinSupportPlugin.kt +++ b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeCompilerKotlinSupportPlugin.kt @@ -20,10 +20,9 @@ class ComposeCompilerKotlinSupportPlugin : KotlinCompilerPluginSupportPlugin { target.plugins.withType(ComposePlugin::class.java) { val composeExt = target.extensions.getByType(ComposeExtension::class.java) - composeCompilerArtifactProvider = ComposeCompilerArtifactProvider( - kotlinVersion = target.getKotlinPluginVersion() - ) { - composeExt.kotlinCompilerPlugin.orNull + composeCompilerArtifactProvider = ComposeCompilerArtifactProvider { + composeExt.kotlinCompilerPlugin.orNull ?: + ComposeCompilerCompatability.compilerVersionFor(target.getKotlinPluginVersion()) } } } @@ -58,7 +57,6 @@ class ComposeCompilerKotlinSupportPlugin : KotlinCompilerPluginSupportPlugin { override fun applyToCompilation(kotlinCompilation: KotlinCompilation<*>): Provider> { val target = kotlinCompilation.target - composeCompilerArtifactProvider.checkTargetSupported(target) return target.project.provider { platformPluginOptions[target.platformType] ?: emptyList() } diff --git a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeExtension.kt b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeExtension.kt index 8b3644e6c6..7cbf7a7c77 100644 --- a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeExtension.kt +++ b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposeExtension.kt @@ -5,15 +5,41 @@ package org.jetbrains.compose +import org.gradle.api.Project import org.gradle.api.model.ObjectFactory import org.gradle.api.plugins.ExtensionAware +import org.gradle.api.provider.ListProperty import org.gradle.api.provider.Property import org.jetbrains.compose.desktop.application.internal.nullableProperty import javax.inject.Inject abstract class ComposeExtension @Inject constructor( - objects: ObjectFactory + objects: ObjectFactory, + project: Project ) : ExtensionAware { + /** + * Custom Compose Compiler maven coordinates. You can set it using values provided + * by [ComposePlugin.CompilerDependencies]: + * ``` + * kotlinCompilerPlugin.set(dependencies.compiler.forKotlin("1.7.20")) + * ``` + * or set it to the Jetpack Compose Compiler: + * ``` + * kotlinCompilerPlugin.set("androidx.compose.compiler:compiler:1.4.0-alpha02") + * ``` + * (see available versions here: https://developer.android.com/jetpack/androidx/releases/compose-kotlin#pre-release_kotlin_compatibility) + */ val kotlinCompilerPlugin: Property = objects.nullableProperty() -} + /** + * List of the arguments applied to the Compose Compiler. Example: + * ``` + * kotlinCompilerPluginArgs.add("suppressKotlinVersionCompatibilityCheck=1.7.21") + * ``` + * See all available arguments here: + * https://github.com/androidx/androidx/blob/androidx-main/compose/compiler/compiler-hosted/src/main/java/androidx/compose/compiler/plugins/kotlin/ComposePlugin.kt + */ + val kotlinCompilerPluginArgs: ListProperty = objects.listProperty(String::class.java) + + val dependencies = ComposePlugin.Dependencies(project) +} diff --git a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposePlugin.kt b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposePlugin.kt index 49391cdb7e..3b8b3e5d79 100644 --- a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposePlugin.kt +++ b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/ComposePlugin.kt @@ -19,7 +19,6 @@ import org.gradle.api.artifacts.repositories.MavenArtifactRepository import org.gradle.api.plugins.ExtensionAware import org.jetbrains.compose.android.AndroidExtension import org.jetbrains.compose.desktop.DesktopExtension -import org.jetbrains.compose.desktop.application.internal.ComposeProperties import org.jetbrains.compose.desktop.application.internal.configureDesktop import org.jetbrains.compose.desktop.application.internal.currentTarget import org.jetbrains.compose.desktop.preview.internal.initializePreview @@ -28,18 +27,19 @@ import org.jetbrains.compose.experimental.internal.checkExperimentalTargetsWithS import org.jetbrains.compose.experimental.internal.configureExperimental import org.jetbrains.compose.web.WebExtension import org.jetbrains.kotlin.gradle.plugin.KotlinDependencyHandler +import org.jetbrains.kotlin.gradle.plugin.getKotlinPluginVersion import org.jetbrains.kotlin.gradle.tasks.KotlinCompile internal val composeVersion get() = ComposeBuildConfig.composeVersion class ComposePlugin : Plugin { override fun apply(project: Project) { - val composeExtension = project.extensions.create("compose", ComposeExtension::class.java) + val composeExtension = project.extensions.create("compose", ComposeExtension::class.java, project) val desktopExtension = composeExtension.extensions.create("desktop", DesktopExtension::class.java) val androidExtension = composeExtension.extensions.create("android", AndroidExtension::class.java) val experimentalExtension = composeExtension.extensions.create("experimental", ExperimentalExtension::class.java) - project.dependencies.extensions.add("compose", Dependencies) + project.dependencies.extensions.add("compose", Dependencies(project)) if (!project.buildFile.endsWith(".gradle.kts")) { setUpGroovyDslExtensions(project) @@ -68,6 +68,15 @@ class ComposePlugin : Plugin { it.replacedBy(replacement, "org.jetbrains.compose isn't compatible with androidx.compose, because it is the same library published with different maven coordinates") } } + + project.tasks.withType(KotlinCompile::class.java).configureEach { + it.kotlinOptions.apply { + freeCompilerArgs = freeCompilerArgs + + composeExtension.kotlinCompilerPluginArgs.get().flatMap { arg -> + listOf("-P", "plugin:androidx.compose.compiler.plugins.kotlin:$arg") + } + } + } } } @@ -97,8 +106,9 @@ class ComposePlugin : Plugin { } } - object Dependencies { + class Dependencies(project: Project) { val desktop = DesktopDependencies + val compiler = CompilerDependencies(project) val animation get() = composeDependency("org.jetbrains.compose.animation:animation") val animationGraphics get() = composeDependency("org.jetbrains.compose.animation:animation-graphics") val foundation get() = composeDependency("org.jetbrains.compose.foundation:foundation") @@ -130,6 +140,16 @@ class ComposePlugin : Plugin { } } + class CompilerDependencies(private val project: Project) { + fun forKotlin(version: String) = "org.jetbrains.compose.compiler:compiler:" + + ComposeCompilerCompatability.compilerVersionFor(version) + + /** + * Compose Compiler that is chosen by the version of Kotlin applied to the Gradle project + */ + val auto get() = forKotlin(project.getKotlinPluginVersion()) + } + object DesktopComponentsDependencies { @ExperimentalComposeLibrary val splitPane = composeDependency("org.jetbrains.compose.components:components-splitpane") @@ -165,7 +185,7 @@ private fun composeDependency(groupWithArtifact: String) = "$groupWithArtifact:$ private fun setUpGroovyDslExtensions(project: Project) { project.plugins.withId("org.jetbrains.kotlin.multiplatform") { (project.extensions.getByName("kotlin") as? ExtensionAware)?.apply { - extensions.add("compose", ComposePlugin.Dependencies) + extensions.add("compose", ComposePlugin.Dependencies(project)) } } (project.repositories as? ExtensionAware)?.extensions?.apply { diff --git a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/internal/ComposeCompilerArtifactProvider.kt b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/internal/ComposeCompilerArtifactProvider.kt index 8f741311f1..d1da0d038e 100644 --- a/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/internal/ComposeCompilerArtifactProvider.kt +++ b/gradle-plugins/compose/src/main/kotlin/org/jetbrains/compose/internal/ComposeCompilerArtifactProvider.kt @@ -5,44 +5,16 @@ package org.jetbrains.compose.internal -import org.jetbrains.compose.ComposeCompilerCompatability import org.jetbrains.compose.internal.ComposeCompilerArtifactProvider.DefaultCompiler.pluginArtifact -import org.jetbrains.kotlin.gradle.plugin.KotlinPlatformType -import org.jetbrains.kotlin.gradle.plugin.KotlinTarget import org.jetbrains.kotlin.gradle.plugin.SubpluginArtifact -private const val KOTLIN_COMPATABILITY_LINK = - "https://github.com/JetBrains/compose-jb/blob/master/VERSIONING.md#kotlin-compatibility" - internal class ComposeCompilerArtifactProvider( - private val kotlinVersion: String, - private val customPluginString: () -> String? + private val customPluginString: () -> String ) { - fun checkTargetSupported(target: KotlinTarget) { - require(!unsupportedPlatforms.contains(target.platformType)) { - "This version of Compose Multiplatform doesn't support Kotlin " + - "$kotlinVersion for ${target.platformType} target. " + - "Please see $KOTLIN_COMPATABILITY_LINK " + - "to know the latest supported version of Kotlin." - } - } - - private val autoCompilerVersion by lazy { - requireNotNull( - ComposeCompilerCompatability.compilerVersionFor(kotlinVersion) - ) { - "This version of Compose Multiplatform doesn't support Kotlin " + - "$kotlinVersion. " + - "Please see $KOTLIN_COMPATABILITY_LINK " + - "to know the latest supported version of Kotlin." - } - } - - private val customCompilerArtifact: SubpluginArtifact? by lazy { + val compilerArtifact: SubpluginArtifact by lazy { val customPlugin = customPluginString() - val customCoordinates = customPlugin?.split(":") - when (customCoordinates?.size) { - null -> null + val customCoordinates = customPlugin.split(":") + when (customCoordinates.size) { 1 -> { val customVersion = customCoordinates[0] check(customVersion.isNotBlank()) { "'compose.kotlinCompilerPlugin' cannot be blank!" } @@ -61,14 +33,6 @@ internal class ComposeCompilerArtifactProvider( } } - private val unsupportedPlatforms: Set by lazy { - if (customCompilerArtifact != null) emptySet() else autoCompilerVersion.unsupportedPlatforms - } - - val compilerArtifact: SubpluginArtifact get() { - return customCompilerArtifact ?: pluginArtifact(version = autoCompilerVersion.version) - } - val compilerHostedArtifact: SubpluginArtifact get() = compilerArtifact.run { val newArtifactId = diff --git a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/tests/integration/DesktopApplicationTest.kt b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/tests/integration/DesktopApplicationTest.kt index 93cd24085b..b1948346ea 100644 --- a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/tests/integration/DesktopApplicationTest.kt +++ b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/tests/integration/DesktopApplicationTest.kt @@ -60,9 +60,45 @@ class DesktopApplicationTest : GradlePluginTestBase() { } } + /** + * Test the version of Compose Compiler published by Google. + * See https://developer.android.com/jetpack/androidx/releases/compose-kotlin + */ @Test - fun testAndroidxCompiler() = with(testProject(TestProjects.androidxCompiler, defaultAndroidxCompilerEnvironment)) { - gradle(":runDistributable").build().checks { check -> + fun testAndroidxCompiler() = testProject( + TestProjects.customCompiler, defaultTestEnvironment.copy( + kotlinVersion = "1.6.10", + composeCompilerPlugin = "\"androidx.compose.compiler:compiler:1.1.1\"" + ) + ).checkCustomComposeCompiler() + + @Test + fun testSettingLatestCompiler() = testProject( + TestProjects.customCompiler, defaultTestEnvironment.copy( + kotlinVersion = "1.7.20", + composeCompilerPlugin = "dependencies.compiler.forKotlin(\"1.7.20\")", + ) + ).checkCustomComposeCompiler() + + @Test + fun testSettingAutoCompiler() = testProject( + TestProjects.customCompiler, defaultTestEnvironment.copy( + kotlinVersion = "1.7.10", + composeCompilerPlugin = "dependencies.compiler.auto", + ) + ).checkCustomComposeCompiler() + + @Test + fun testKotlinCheckDisabled() = testProject( + TestProjects.customCompilerArgs, defaultTestEnvironment.copy( + kotlinVersion = "1.7.21", + composeCompilerPlugin = "dependencies.compiler.forKotlin(\"1.7.20\")", + composeCompilerArgs = "\"suppressKotlinVersionCompatibilityCheck=1.7.21\"" + ) + ).checkCustomComposeCompiler() + + private fun TestProject.checkCustomComposeCompiler() { + gradle(":runDistributable").build().checks { val actualMainImage = file("main-image.actual.png") val expectedMainImage = file("main-image.expected.png") assert(actualMainImage.readBytes().contentEquals(expectedMainImage.readBytes())) { diff --git a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/tests/unit/ComposeCompilerArtifactProviderTest.kt b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/tests/unit/ComposeCompilerArtifactProviderTest.kt index 7648fe1bcc..eb9e2e7879 100644 --- a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/tests/unit/ComposeCompilerArtifactProviderTest.kt +++ b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/tests/unit/ComposeCompilerArtifactProviderTest.kt @@ -14,27 +14,11 @@ import org.junit.jupiter.api.Test import org.junit.jupiter.api.Assertions.* internal class ComposeCompilerArtifactProviderTest { - @Test - fun defaultCompilerArtifact() { - assertArtifactEquals( - Expected.jbCompiler, - Actual.compiler(null, TestProperties.composeCompilerCompatibleKotlinVersion) - ) - } - - @Test - fun defaultCompilerHostedArtifact() { - assertArtifactEquals( - Expected.jbCompilerHosted, - Actual.compilerHosted(null, TestProperties.composeCompilerCompatibleKotlinVersion) - ) - } - @Test fun customVersion() { assertArtifactEquals( Expected.jbCompiler.copy(version = "10.20.30"), - Actual.compiler("10.20.30", TestProperties.composeCompilerCompatibleKotlinVersion) + Actual.compiler("10.20.30") ) } @@ -42,10 +26,7 @@ internal class ComposeCompilerArtifactProviderTest { fun customCompiler() { assertArtifactEquals( Expected.googleCompiler.copy(version = "1.3.1"), - Actual.compiler( - "androidx.compose.compiler:compiler:1.3.1", - TestProperties.androidxCompilerCompatibleKotlinVersion - ) + Actual.compiler("androidx.compose.compiler:compiler:1.3.1") ) } @@ -54,10 +35,7 @@ internal class ComposeCompilerArtifactProviderTest { // check that we don't replace artifactId for non-jb compiler assertArtifactEquals( Expected.googleCompiler.copy(version = "1.3.1"), - Actual.compilerHosted( - "androidx.compose.compiler:compiler:1.3.1", - TestProperties.composeCompilerCompatibleKotlinVersion - ) + Actual.compilerHosted("androidx.compose.compiler:compiler:1.3.1") ) } @@ -68,9 +46,9 @@ internal class ComposeCompilerArtifactProviderTest { testIllegalCompiler("") } - private fun testIllegalCompiler(pluginString: String?) { + private fun testIllegalCompiler(pluginString: String) { try { - Actual.compiler(pluginString, "") + Actual.compiler(pluginString) } catch (e: Exception) { return } @@ -79,11 +57,11 @@ internal class ComposeCompilerArtifactProviderTest { } object Actual { - fun compiler(pluginString: String?, kotlinVersion: String) = - ComposeCompilerArtifactProvider(kotlinVersion) { pluginString }.compilerArtifact + fun compiler(pluginString: String) = + ComposeCompilerArtifactProvider { pluginString }.compilerArtifact - fun compilerHosted(pluginString: String?, kotlinVersion: String) = - ComposeCompilerArtifactProvider(kotlinVersion) { pluginString }.compilerHostedArtifact + fun compilerHosted(pluginString: String) = + ComposeCompilerArtifactProvider { pluginString }.compilerHostedArtifact } object Expected { diff --git a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/GradlePluginTestBase.kt b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/GradlePluginTestBase.kt index 9b5d0ba48b..9727c59a15 100644 --- a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/GradlePluginTestBase.kt +++ b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/GradlePluginTestBase.kt @@ -15,12 +15,6 @@ abstract class GradlePluginTestBase { val defaultTestEnvironment: TestEnvironment get() = TestEnvironment(workingDir = testWorkDir) - val defaultAndroidxCompilerEnvironment: TestEnvironment - get() = defaultTestEnvironment.copy( - kotlinVersion = TestKotlinVersions.AndroidxCompatible, - composeCompilerArtifact = "androidx.compose.compiler:compiler:${TestProperties.androidxCompilerVersion}" - ) - fun testProject( name: String, testEnvironment: TestEnvironment = defaultTestEnvironment diff --git a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestKotlinVersions.kt b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestKotlinVersions.kt index e1f37b09f4..bfa4c10336 100644 --- a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestKotlinVersions.kt +++ b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestKotlinVersions.kt @@ -7,5 +7,4 @@ package org.jetbrains.compose.test.utils object TestKotlinVersions { val Default = TestProperties.composeCompilerCompatibleKotlinVersion - val AndroidxCompatible = TestProperties.androidxCompilerCompatibleKotlinVersion } \ No newline at end of file diff --git a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProject.kt b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProject.kt index a73c4f4a30..20e39180a0 100644 --- a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProject.kt +++ b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProject.kt @@ -14,13 +14,15 @@ data class TestEnvironment( val workingDir: File, val kotlinVersion: String = TestKotlinVersions.Default, val composeGradlePluginVersion: String = TestProperties.composeGradlePluginVersion, - val composeCompilerArtifact: String? = null, - val composeVerbose: Boolean = true + val composeCompilerPlugin: String? = null, + val composeCompilerArgs: String? = null, + val composeVerbose: Boolean = true, ) { private val placeholders = linkedMapOf( "COMPOSE_GRADLE_PLUGIN_VERSION_PLACEHOLDER" to composeGradlePluginVersion, "KOTLIN_VERSION_PLACEHOLDER" to kotlinVersion, - "COMPOSE_COMPILER_ARTIFACT_PLACEHOLDER" to composeCompilerArtifact, + "COMPOSE_COMPILER_PLUGIN_PLACEHOLDER" to composeCompilerPlugin, + "COMPOSE_COMPILER_PLUGIN_ARGS_PLACEHOLDER" to composeCompilerArgs, ) fun replacePlaceholdersInFile(file: File) { diff --git a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProjects.kt b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProjects.kt index 1a6863e839..81f0611c07 100644 --- a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProjects.kt +++ b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProjects.kt @@ -9,7 +9,8 @@ object TestProjects { const val jvm = "application/jvm" const val mpp = "application/mpp" const val proguard = "application/proguard" - const val androidxCompiler = "application/androidx-compiler" + const val customCompiler = "application/custom-compiler" + const val customCompilerArgs = "application/custom-compiler-args" const val jvmKotlinDsl = "application/jvmKotlinDsl" const val moduleClashCli = "application/moduleClashCli" const val javaLogger = "application/javaLogger" diff --git a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProperties.kt b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProperties.kt index ef4bd4423d..51949bfe3f 100644 --- a/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProperties.kt +++ b/gradle-plugins/compose/src/test/kotlin/org/jetbrains/compose/test/utils/TestProperties.kt @@ -17,12 +17,6 @@ object TestProperties { val composeJsCompilerCompatibleKotlinVersion: String get() = notNullSystemProperty("compose.tests.js.compiler.compatible.kotlin.version") - val androidxCompilerVersion: String - get() = notNullSystemProperty("compose.tests.androidx.compiler.version") - - val androidxCompilerCompatibleKotlinVersion: String - get() = notNullSystemProperty("compose.tests.androidx.compiler.compatible.kotlin.version") - val composeGradlePluginVersion: String get() = notNullSystemProperty("compose.tests.compose.gradle.plugin.version") diff --git a/gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/build.gradle b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/build.gradle new file mode 100644 index 0000000000..7427f86df8 --- /dev/null +++ b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/build.gradle @@ -0,0 +1,37 @@ +import org.gradle.nativeplatform.platform.internal.DefaultNativePlatform +import org.jetbrains.compose.desktop.application.dsl.TargetFormat + +plugins { + id "org.jetbrains.kotlin.jvm" + id "org.jetbrains.compose" +} + +repositories { + google() + jetbrainsCompose() +} + +dependencies { + implementation "org.jetbrains.kotlin:kotlin-stdlib" + implementation compose.desktop.currentOs +} + +compose { + kotlinCompilerPlugin.set(COMPOSE_COMPILER_PLUGIN_PLACEHOLDER) + kotlinCompilerPluginArgs.add(COMPOSE_COMPILER_PLUGIN_ARGS_PLACEHOLDER) + + desktop { + application { + mainClass = "Main" + nativeDistributions { + targetFormats(TargetFormat.Dmg, TargetFormat.Msi, TargetFormat.Deb) + } + + def projectPath = project.projectDir.absolutePath + if (DefaultNativePlatform.currentOperatingSystem.isWindows()) { + projectPath = projectPath.replace("\\", "\\\\") + } + args(projectPath) + } + } +} diff --git a/gradle-plugins/compose/src/test/test-projects/application/androidx-compiler/main-image.expected.png b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/main-image.expected.png similarity index 100% rename from gradle-plugins/compose/src/test/test-projects/application/androidx-compiler/main-image.expected.png rename to gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/main-image.expected.png diff --git a/gradle-plugins/compose/src/test/test-projects/application/androidx-compiler/settings.gradle b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/settings.gradle similarity index 100% rename from gradle-plugins/compose/src/test/test-projects/application/androidx-compiler/settings.gradle rename to gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/settings.gradle diff --git a/gradle-plugins/compose/src/test/test-projects/application/androidx-compiler/src/main/kotlin/Main.kt b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/src/main/kotlin/Main.kt similarity index 100% rename from gradle-plugins/compose/src/test/test-projects/application/androidx-compiler/src/main/kotlin/Main.kt rename to gradle-plugins/compose/src/test/test-projects/application/custom-compiler-args/src/main/kotlin/Main.kt diff --git a/gradle-plugins/compose/src/test/test-projects/application/androidx-compiler/build.gradle b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/build.gradle similarity index 92% rename from gradle-plugins/compose/src/test/test-projects/application/androidx-compiler/build.gradle rename to gradle-plugins/compose/src/test/test-projects/application/custom-compiler/build.gradle index 3b66bdad8b..c67e4bf613 100644 --- a/gradle-plugins/compose/src/test/test-projects/application/androidx-compiler/build.gradle +++ b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/build.gradle @@ -17,7 +17,7 @@ dependencies { } compose { - kotlinCompilerPlugin.set("COMPOSE_COMPILER_ARTIFACT_PLACEHOLDER") + kotlinCompilerPlugin.set(COMPOSE_COMPILER_PLUGIN_PLACEHOLDER) desktop { application { diff --git a/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/main-image.expected.png b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/main-image.expected.png new file mode 100644 index 0000000000000000000000000000000000000000..525220fb6bf3e4ebbd146242c0fb222cc0a89ad5 GIT binary patch literal 140 zcmeAS@N?(olHy`uVBq!ia0vp^AT}2V8<6ZZI=>f4u@pObhHwBu4M$1`knim2;us<^ zwe`$FUIqmY=Zk&EUgUh+yTEP2g(cIMRR(b#5}5W~s71NPO0p?qecQJFdeh9kv$pKN ll@Xe|C0usPYQ9^6;;*_1PE?xit literal 0 HcmV?d00001 diff --git a/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/settings.gradle b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/settings.gradle new file mode 100644 index 0000000000..43d540efb8 --- /dev/null +++ b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/settings.gradle @@ -0,0 +1,11 @@ +pluginManagement { + plugins { + id 'org.jetbrains.kotlin.jvm' version 'KOTLIN_VERSION_PLACEHOLDER' + id 'org.jetbrains.compose' version 'COMPOSE_GRADLE_PLUGIN_VERSION_PLACEHOLDER' + } + repositories { + mavenLocal() + gradlePluginPortal() + } +} +rootProject.name = "simple" \ No newline at end of file diff --git a/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/src/main/kotlin/Main.kt b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/src/main/kotlin/Main.kt new file mode 100644 index 0000000000..e7d73f0092 --- /dev/null +++ b/gradle-plugins/compose/src/test/test-projects/application/custom-compiler/src/main/kotlin/Main.kt @@ -0,0 +1,76 @@ +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.* +import androidx.compose.foundation.shape.CircleShape +import androidx.compose.foundation.shape.GenericShape +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.ExperimentalComposeUiApi +import androidx.compose.ui.Modifier +import androidx.compose.ui.draw.clip +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.graphics.Shape +import androidx.compose.ui.renderComposeScene +import org.jetbrains.skia.EncodedImageFormat +import java.io.File +import java.util.* + +object Main { + @JvmStatic + @OptIn(ExperimentalComposeUiApi::class) + fun main(args: Array) { + val workingDir = args.getOrNull(0)?.let { File(it) } + workingDir?.mkdirs() + if (workingDir == null || !workingDir.isDirectory) { + error("Working directory must be passes as the first argument. '$workingDir' is not a directory") + } + + val image = renderComposeScene(height = 10, width = 10) { + mainShape() + } + val encodedImage = image.encodeToData(EncodedImageFormat.PNG) ?: error("Could not encode image as png") + workingDir.resolve("main-image.actual.png").writeBytes(encodedImage.bytes) + + val mainMethods = this.javaClass.declaredMethods + .mapTo(TreeSet()) { it.name } + .joinToString("\n") + workingDir.resolve("main-methods.actual.txt").writeText(mainMethods) + } + + @Composable + fun mainShape() { + triangle(Color.Magenta) + } + + @Composable + fun unused() { + transitivelyUnused() + } + + @Composable + fun transitivelyUnused() { + triangle(Color.Gray) + } + + @Composable + fun keptByKeepRule() { + fillShape(Color.Blue, CircleShape) + } +} + +@Composable +fun triangle(color: Color) { + fillShape(color, GenericShape { size, _ -> + moveTo(size.width / 2f, 0f) + lineTo(size.width, size.height) + lineTo(0f, size.height) + }) +} + +@Composable +fun fillShape(color: Color, shape: Shape){ + Column(modifier = Modifier.fillMaxWidth().wrapContentSize(Alignment.Center)) { + Box( + modifier = Modifier.clip(shape).fillMaxSize().background(color) + ) + } +} \ No newline at end of file diff --git a/gradle-plugins/gradle.properties b/gradle-plugins/gradle.properties index 9679715ba7..f3d7de787c 100644 --- a/gradle-plugins/gradle.properties +++ b/gradle-plugins/gradle.properties @@ -3,17 +3,12 @@ kotlin.code.style=official # Default version of Compose Libraries used by Gradle plugin compose.version=1.2.1 -# The latest version of Compose Compiler used by Gradle plugin. Used only in tests. +# The latest version of Compose Compiler used by Gradle plugin. Used only in tests/CI. compose.tests.compiler.version=1.3.2.1 -# The latest version of Kotlin compatible with compose.tests.compiler.version. Used only in tests. +# The latest version of Kotlin compatible with compose.tests.compiler.version. Used only in tests/CI. compose.tests.compiler.compatible.kotlin.version=1.7.20 # The latest version of Kotlin compatible with compose.tests.compiler.version for JS target. Used only on CI. compose.tests.js.compiler.compatible.kotlin.version=1.7.20 -# Version of Compose Compiler published by Google. -# Used to check if our plugin is compatible with it. -# https://developer.android.com/jetpack/androidx/releases/compose-kotlin -compose.tests.androidx.compiler.version=1.1.1 -compose.tests.androidx.compiler.compatible.kotlin.version=1.6.10 # __SUPPORTED_GRADLE_VERSIONS__ compose.tests.gradle.versions=7.0.2, 7.6