From 200a24b75217fc3ea272fd25249c4e1a5d82e5b4 Mon Sep 17 00:00:00 2001 From: Zac Sweers Date: Mon, 14 Oct 2024 17:37:48 -0400 Subject: [PATCH 1/3] Set up skeleton for better properties --- .../better-gradle-properties/build.gradle.kts | 26 +++++++++++++++++++ .../gradle.properties | 3 +++ .../foundry-gradle-plugin/build.gradle.kts | 1 + settings.gradle.kts | 1 + 4 files changed, 31 insertions(+) create mode 100644 platforms/gradle/better-gradle-properties/build.gradle.kts create mode 100644 platforms/gradle/better-gradle-properties/gradle.properties diff --git a/platforms/gradle/better-gradle-properties/build.gradle.kts b/platforms/gradle/better-gradle-properties/build.gradle.kts new file mode 100644 index 000000000..3d5e44949 --- /dev/null +++ b/platforms/gradle/better-gradle-properties/build.gradle.kts @@ -0,0 +1,26 @@ +/* + * Copyright (C) 2024 Slack Technologies, LLC + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +import org.jetbrains.kotlin.gradle.plugin.KotlinPlatformType + +plugins { + alias(libs.plugins.kotlin.jvm) + alias(libs.plugins.mavenPublish) + alias(libs.plugins.lint) +} + +dependencies { + compileOnly(gradleApi()) +} diff --git a/platforms/gradle/better-gradle-properties/gradle.properties b/platforms/gradle/better-gradle-properties/gradle.properties new file mode 100644 index 000000000..36ce11ad4 --- /dev/null +++ b/platforms/gradle/better-gradle-properties/gradle.properties @@ -0,0 +1,3 @@ +POM_ARTIFACT_ID=better-gradle-properties +POM_NAME=Better Gradle Properties +POM_DESCRIPTION=Better Gradle Properties diff --git a/platforms/gradle/foundry-gradle-plugin/build.gradle.kts b/platforms/gradle/foundry-gradle-plugin/build.gradle.kts index 1260d7832..70f89ce64 100644 --- a/platforms/gradle/foundry-gradle-plugin/build.gradle.kts +++ b/platforms/gradle/foundry-gradle-plugin/build.gradle.kts @@ -90,6 +90,7 @@ dependencies { implementation(libs.moshi) implementation(libs.oshi) { because("To read hardware information") } implementation(libs.rxjava) + implementation(projects.platforms.gradle.betterGradleProperties) implementation(projects.tools.cli) implementation(projects.tools.foundryCommon) implementation(projects.tools.skippy) diff --git a/settings.gradle.kts b/settings.gradle.kts index 639ef60f5..01e911545 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -148,6 +148,7 @@ rootProject.name = "foundry" // Please keep these in alphabetical order! include( ":platforms:gradle:agp-handlers:agp-handler-api", + ":platforms:gradle:better-gradle-properties", ":platforms:gradle:foundry-gradle-plugin", ":platforms:intellij:artifactory-authenticator", ":platforms:intellij:compose", From 03b4ab860f291c364d0d1ddb522689f6d7562cf3 Mon Sep 17 00:00:00 2001 From: Zac Sweers Date: Tue, 15 Oct 2024 13:04:28 -0400 Subject: [PATCH 2/3] Extract better gradle properties project --- .../better-gradle-properties/build.gradle.kts | 6 +--- .../gradle/properties/GitExecProviders.kt} | 14 ++++---- .../properties}/HasConfigurableValues.kt | 24 ++++++------- .../gradle/properties}/PropertyResolver.kt | 2 +- .../gradle/properties}/PropertyUtil.kt | 34 +++++++++---------- .../foundry/gradle/ApkVersioningPlugin.kt | 4 +-- .../kotlin/foundry/gradle/FoundryExtension.kt | 2 +- .../foundry/gradle/FoundryGradleUtil.kt | 4 +-- .../foundry/gradle/FoundryProperties.kt | 6 ++-- .../foundry/gradle/FoundryRootPlugin.kt | 13 ++++--- .../kotlin/foundry/gradle/FoundryTools.kt | 6 ++-- .../main/kotlin/foundry/gradle/Platforms.kt | 2 +- .../gradle/StandardProjectConfigurations.kt | 2 +- .../avoidance/ComputeAffectedProjectsTask.kt | 2 +- .../GenerateAndroidTestProjectPathsTask.kt | 2 +- .../avoidance/GenerateDependencyGraphTask.kt | 2 +- .../gradle/dependencyrake/DependencyRake.kt | 2 +- .../kotlin/foundry/gradle/kgp/KgpTasks.kt | 2 +- .../kotlin/foundry/gradle/lint/DetektTasks.kt | 4 +-- .../foundry/gradle/stats/ModuleStats.kt | 4 +-- .../gradle/tasks/AndroidTestApksTask.kt | 2 +- .../foundry/gradle/tasks/BootstrapTask.kt | 4 +-- .../tasks/CheckDependencyVersionsTask.kt | 2 +- .../gradle/tasks/PrintFossaDependencies.kt | 2 +- .../robolectric/UpdateRobolectricJarsTask.kt | 2 +- .../foundry/gradle/unittest/UnitTests.kt | 4 +-- 26 files changed, 73 insertions(+), 80 deletions(-) rename platforms/gradle/{foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/GitExecValueSource.kt => better-gradle-properties/src/main/kotlin/foundry/gradle/properties/GitExecProviders.kt} (81%) rename platforms/gradle/{foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util => better-gradle-properties/src/main/kotlin/foundry/gradle/properties}/HasConfigurableValues.kt (65%) rename platforms/gradle/{foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util => better-gradle-properties/src/main/kotlin/foundry/gradle/properties}/PropertyResolver.kt (99%) rename platforms/gradle/{foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util => better-gradle-properties/src/main/kotlin/foundry/gradle/properties}/PropertyUtil.kt (78%) diff --git a/platforms/gradle/better-gradle-properties/build.gradle.kts b/platforms/gradle/better-gradle-properties/build.gradle.kts index 3d5e44949..1cc2c06d9 100644 --- a/platforms/gradle/better-gradle-properties/build.gradle.kts +++ b/platforms/gradle/better-gradle-properties/build.gradle.kts @@ -13,14 +13,10 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -import org.jetbrains.kotlin.gradle.plugin.KotlinPlatformType - plugins { alias(libs.plugins.kotlin.jvm) alias(libs.plugins.mavenPublish) alias(libs.plugins.lint) } -dependencies { - compileOnly(gradleApi()) -} +dependencies { compileOnly(gradleApi()) } diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/GitExecValueSource.kt b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/GitExecProviders.kt similarity index 81% rename from platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/GitExecValueSource.kt rename to platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/GitExecProviders.kt index 3cc18e1d3..2caf78318 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/GitExecValueSource.kt +++ b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/GitExecProviders.kt @@ -13,7 +13,7 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -package foundry.gradle.util +package foundry.gradle.properties import java.io.ByteArrayOutputStream import java.nio.charset.Charset @@ -25,19 +25,17 @@ import org.gradle.api.provider.ValueSource import org.gradle.api.provider.ValueSourceParameters import org.gradle.process.ExecOperations -internal fun ProviderFactory.gitVersionProvider(): Provider { - return gitExecProvider("git", "--version") -} - -internal fun ProviderFactory.gitExecProvider(vararg args: String): Provider { +public fun ProviderFactory.gitExecProvider(vararg args: String): Provider { require(args.isNotEmpty()) { "Args list is empty" } return of(GitExecValueSource::class.java) { parameters.args.addAll(*args) } } // Adapted from // https://docs.gradle.org/8.1/userguide/configuration_cache.html#config_cache:requirements:external_processes -internal abstract class GitExecValueSource : ValueSource { - @get:Inject abstract val execOperations: ExecOperations +internal abstract class GitExecValueSource +@Inject +constructor(private val execOperations: ExecOperations) : + ValueSource { override fun obtain(): String { val args = parameters.args.get() diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/HasConfigurableValues.kt b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/HasConfigurableValues.kt similarity index 65% rename from platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/HasConfigurableValues.kt rename to platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/HasConfigurableValues.kt index ceac3bc79..ec49e5e39 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/HasConfigurableValues.kt +++ b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/HasConfigurableValues.kt @@ -13,7 +13,7 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -package foundry.gradle.util +package foundry.gradle.properties import org.gradle.api.file.ConfigurableFileCollection import org.gradle.api.provider.ListProperty @@ -26,52 +26,52 @@ import org.gradle.api.provider.SetProperty * APIs adapted from `HasConfigurableValues.kt` in AGP. Copied for binary safety. */ -internal fun ConfigurableFileCollection.fromDisallowChanges(vararg arg: Any) { +public fun ConfigurableFileCollection.fromDisallowChanges(vararg arg: Any) { from(*arg) disallowChanges() } -internal fun Property.setDisallowChanges(value: T?) { +public fun Property.setDisallowChanges(value: T?) { set(value) disallowChanges() } -internal fun Property.setDisallowChanges(value: Provider) { +public fun Property.setDisallowChanges(value: Provider) { set(value) disallowChanges() } -internal fun ListProperty.setDisallowChanges(value: Provider>) { +public fun ListProperty.setDisallowChanges(value: Provider>) { set(value) disallowChanges() } -internal fun ListProperty.setDisallowChanges(value: Iterable?) { +public fun ListProperty.setDisallowChanges(value: Iterable?) { set(value) disallowChanges() } -internal fun MapProperty.setDisallowChanges(map: Provider>) { +public fun MapProperty.setDisallowChanges(map: Provider>) { set(map) disallowChanges() } -internal fun MapProperty.setDisallowChanges(map: Map?) { +public fun MapProperty.setDisallowChanges(map: Map?) { set(map) disallowChanges() } -internal fun SetProperty.setDisallowChanges(value: Provider>) { +public fun SetProperty.setDisallowChanges(value: Provider>) { set(value) disallowChanges() } -internal fun SetProperty.setDisallowChanges(value: Iterable?) { +public fun SetProperty.setDisallowChanges(value: Iterable?) { set(value) disallowChanges() } -internal fun ListProperty.setDisallowChanges( +public fun ListProperty.setDisallowChanges( value: Provider>?, handleNullable: ListProperty.() -> Unit, ) { @@ -79,7 +79,7 @@ internal fun ListProperty.setDisallowChanges( disallowChanges() } -internal fun MapProperty.setDisallowChanges( +public fun MapProperty.setDisallowChanges( map: Provider>?, handleNullable: MapProperty.() -> Unit, ) { diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/PropertyResolver.kt b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyResolver.kt similarity index 99% rename from platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/PropertyResolver.kt rename to platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyResolver.kt index e58bdf0c2..ef9b80c00 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/PropertyResolver.kt +++ b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyResolver.kt @@ -13,7 +13,7 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -package foundry.gradle.util +package foundry.gradle.properties import org.gradle.api.Project import org.gradle.api.provider.Provider diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/PropertyUtil.kt b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyUtil.kt similarity index 78% rename from platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/PropertyUtil.kt rename to platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyUtil.kt index 6d94964cb..28314276f 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/util/PropertyUtil.kt +++ b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyUtil.kt @@ -15,7 +15,7 @@ */ @file:JvmName("PropertyUtil") -package foundry.gradle.util +package foundry.gradle.properties import java.util.Properties import kotlin.contracts.contract @@ -30,7 +30,7 @@ import org.gradle.api.provider.ValueSourceParameters // null returns. This // abuses kotlin contracts to safe cast without a null check. // https://github.com/gradle/gradle/issues/12388 -internal fun sneakyNull(value: T? = null): T { +public fun sneakyNull(value: T? = null): T { markAsNonNullForGradle(value) return value } @@ -38,15 +38,15 @@ internal fun sneakyNull(value: T? = null): T { // Gradle's map {} APIs sometimes are interpreted by Kotlin to be non-null only but legally allow // null returns. This // abuses kotlin contracts to safe cast without a null check. -internal fun markAsNonNullForGradle(value: T?) { +public fun markAsNonNullForGradle(value: T?) { contract { returns() implies (value != null) } } /** Implementation of provider holding a start parameter's parsed project properties. */ -internal abstract class StartParameterProperties : +public abstract class StartParameterProperties : ValueSource, StartParameterProperties.Parameters> { - interface Parameters : ValueSourceParameters { - val properties: MapProperty + public interface Parameters : ValueSourceParameters { + public val properties: MapProperty } override fun obtain(): Map? { @@ -55,9 +55,9 @@ internal abstract class StartParameterProperties : } /** Implementation of provider holding a local properties file's parsed [Properties]. */ -internal abstract class LocalProperties : ValueSource { - interface Parameters : ValueSourceParameters { - val propertiesFile: RegularFileProperty +public abstract class LocalProperties : ValueSource { + public interface Parameters : ValueSourceParameters { + public val propertiesFile: RegularFileProperty } override fun obtain(): Properties? { @@ -69,12 +69,12 @@ internal abstract class LocalProperties : ValueSource Project.getOrCreateExtra(key: String, body: (Project) -> T): T { +public fun Project.getOrCreateExtra(key: String, body: (Project) -> T): T { with(project.extensions.extraProperties) { if (!has(key)) { set(key, body(project)) @@ -99,14 +99,14 @@ private fun Project.localPropertiesProvider( return provider.map { it.getProperty(key) } } -internal fun Project.createPropertiesProvider(filePath: String): Provider { +public fun Project.createPropertiesProvider(filePath: String): Provider { return project.providers.of(LocalProperties::class.java) { parameters.propertiesFile.setDisallowChanges(project.layout.projectDirectory.file(filePath)) } } /** Returns a provider of a property _only_ contained in this project's local.properties. */ -internal fun Project.localProperty(key: String): Provider { +public fun Project.localProperty(key: String): Provider { return localPropertiesProvider( key, "foundry.properties.provider.local-properties", @@ -117,7 +117,7 @@ internal fun Project.localProperty(key: String): Provider { /** Returns a provider of a property _only_ contained in this project's local gradle.properties. */ // Local gradle properties are not compatible with configuration caching and thus not accessible // from providers.gradleProperty -_-. https://github.com/gradle/gradle/issues/13302 -internal fun Project.localGradleProperty(key: String): Provider { +public fun Project.localGradleProperty(key: String): Provider { return localPropertiesProvider( key, "foundry.properties.provider.local-gradle-properties", @@ -125,15 +125,15 @@ internal fun Project.localGradleProperty(key: String): Provider { ) } -internal fun Provider.mapToBoolean(): Provider { +public fun Provider.mapToBoolean(): Provider { return map(String::toBoolean) } -internal fun Provider.mapToInt(): Provider { +public fun Provider.mapToInt(): Provider { return map(String::toInt) } @Suppress("RedundantNullableReturnType") -internal fun Project.synchronousEnvProperty(env: String, default: String? = null): String? { +public fun Project.synchronousEnvProperty(env: String, default: String? = null): String? { return providers.environmentVariable(env).getOrElse(sneakyNull(default)) } diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/ApkVersioningPlugin.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/ApkVersioningPlugin.kt index 26e745850..5c56f96e7 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/ApkVersioningPlugin.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/ApkVersioningPlugin.kt @@ -19,8 +19,8 @@ package foundry.gradle import com.android.build.api.variant.ApplicationAndroidComponentsExtension import com.android.build.gradle.AppPlugin -import foundry.gradle.util.localGradleProperty -import foundry.gradle.util.setDisallowChanges +import foundry.gradle.properties.localGradleProperty +import foundry.gradle.properties.setDisallowChanges import java.util.Properties import org.gradle.api.DefaultTask import org.gradle.api.Plugin diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryExtension.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryExtension.kt index fe04b8dac..fd2cf8b8f 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryExtension.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryExtension.kt @@ -30,9 +30,9 @@ import foundry.gradle.agp.PermissionAllowlistConfigurer import foundry.gradle.anvil.AnvilMode import foundry.gradle.compose.COMPOSE_COMPILER_OPTION_PREFIX import foundry.gradle.dependencies.FoundryDependencies +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.util.addKspSource import foundry.gradle.util.configureKotlinCompilationTask -import foundry.gradle.util.setDisallowChanges import java.io.File import javax.inject.Inject import org.gradle.api.Action diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryGradleUtil.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryGradleUtil.kt index 2fb35284e..44d8290fd 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryGradleUtil.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryGradleUtil.kt @@ -23,8 +23,8 @@ import com.google.common.base.CaseFormat import foundry.gradle.agp.VersionNumber import foundry.gradle.dependencies.DependencyDef import foundry.gradle.dependencies.DependencyGroup -import foundry.gradle.util.gitExecProvider -import foundry.gradle.util.mapToBoolean +import foundry.gradle.properties.gitExecProvider +import foundry.gradle.properties.mapToBoolean import java.io.File import java.util.Locale import java.util.Optional diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryProperties.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryProperties.kt index 1f1a79b54..b3d251760 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryProperties.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryProperties.kt @@ -18,9 +18,9 @@ package foundry.gradle import foundry.common.FoundryKeys import foundry.gradle.anvil.AnvilMode import foundry.gradle.artifacts.SgpArtifact -import foundry.gradle.util.PropertyResolver -import foundry.gradle.util.getOrCreateExtra -import foundry.gradle.util.sneakyNull +import foundry.gradle.properties.PropertyResolver +import foundry.gradle.properties.getOrCreateExtra +import foundry.gradle.properties.sneakyNull import java.io.File import java.util.Locale import org.gradle.api.Project diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryRootPlugin.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryRootPlugin.kt index ebc4719ae..6555325f4 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryRootPlugin.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryRootPlugin.kt @@ -29,6 +29,11 @@ import foundry.gradle.develocity.NoOpBuildScanAdapter import foundry.gradle.develocity.findAdapter import foundry.gradle.lint.DetektTasks import foundry.gradle.lint.LintTasks +import foundry.gradle.properties.StartParameterProperties +import foundry.gradle.properties.createPropertiesProvider +import foundry.gradle.properties.gitExecProvider +import foundry.gradle.properties.setDisallowChanges +import foundry.gradle.properties.sneakyNull import foundry.gradle.stats.ModuleStatsTasks import foundry.gradle.tasks.AndroidTestApksTask import foundry.gradle.tasks.CoreBootstrapTask @@ -39,14 +44,8 @@ import foundry.gradle.tasks.KtfmtDownloadTask import foundry.gradle.tasks.SortDependenciesDownloadTask import foundry.gradle.tasks.robolectric.UpdateRobolectricJarsTask import foundry.gradle.unittest.UnitTests -import foundry.gradle.util.StartParameterProperties import foundry.gradle.util.Thermals import foundry.gradle.util.ThermalsData -import foundry.gradle.util.createPropertiesProvider -import foundry.gradle.util.gitExecProvider -import foundry.gradle.util.gitVersionProvider -import foundry.gradle.util.setDisallowChanges -import foundry.gradle.util.sneakyNull import java.util.Locale import javax.inject.Inject import org.gradle.api.Plugin @@ -428,7 +427,7 @@ internal class FoundryRootPlugin @Inject constructor(private val buildFeatures: val revsFile = foundryProperties.gitIgnoreRevsFile ?: return // "git version 2.24.1" - val gitVersion = providers.gitVersionProvider().get() + val gitVersion = providers.gitExecProvider("git", "--version").get() val versionNumber = parseGitVersion(gitVersion) @Suppress( "ReplaceCallWithBinaryOperator" diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryTools.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryTools.kt index 77a0da05f..ef84b2f17 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryTools.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryTools.kt @@ -24,13 +24,13 @@ import foundry.gradle.FoundryTools.Companion.SERVICE_NAME import foundry.gradle.FoundryTools.Parameters import foundry.gradle.agp.AgpHandler import foundry.gradle.agp.AgpHandlers +import foundry.gradle.properties.LocalProperties +import foundry.gradle.properties.setDisallowChanges +import foundry.gradle.properties.sneakyNull import foundry.gradle.util.JsonTools -import foundry.gradle.util.LocalProperties import foundry.gradle.util.Thermals import foundry.gradle.util.ThermalsWatcher -import foundry.gradle.util.setDisallowChanges import foundry.gradle.util.shutdown -import foundry.gradle.util.sneakyNull import java.io.File import java.util.ServiceLoader import java.util.concurrent.ExecutorService diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/Platforms.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/Platforms.kt index 52830bb75..4e1555efa 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/Platforms.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/Platforms.kt @@ -21,8 +21,8 @@ import foundry.gradle.dependencies.DependencyCollection import foundry.gradle.dependencies.DependencyDef import foundry.gradle.dependencies.flattenedPlatformCoordinates import foundry.gradle.dependencies.identifierMap +import foundry.gradle.properties.sneakyNull import foundry.gradle.util.JsonTools -import foundry.gradle.util.sneakyNull import java.io.File import okio.buffer import okio.source diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/StandardProjectConfigurations.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/StandardProjectConfigurations.kt index a3bf7e3cf..f9b4aec44 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/StandardProjectConfigurations.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/StandardProjectConfigurations.kt @@ -40,13 +40,13 @@ import foundry.gradle.dependencyrake.RakeDependencies import foundry.gradle.kgp.KgpTasks import foundry.gradle.lint.LintTasks import foundry.gradle.permissionchecks.PermissionChecks +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.tasks.AndroidTestApksTask import foundry.gradle.tasks.CheckManifestPermissionsTask import foundry.gradle.tasks.SimpleFileProducerTask import foundry.gradle.tasks.publishWith import foundry.gradle.tasks.robolectric.UpdateRobolectricJarsTask import foundry.gradle.unittest.UnitTests -import foundry.gradle.util.setDisallowChanges import net.ltgt.gradle.errorprone.CheckSeverity import net.ltgt.gradle.errorprone.errorprone import net.ltgt.gradle.nullaway.nullaway diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/ComputeAffectedProjectsTask.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/ComputeAffectedProjectsTask.kt index abf7b2c49..b9ef92ee3 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/ComputeAffectedProjectsTask.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/ComputeAffectedProjectsTask.kt @@ -18,10 +18,10 @@ package foundry.gradle.avoidance import com.jraska.module.graph.DependencyGraph import foundry.common.FoundryLogger import foundry.gradle.FoundryProperties +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.property import foundry.gradle.util.JsonTools import foundry.gradle.util.gradle -import foundry.gradle.util.setDisallowChanges import foundry.skippy.AffectedProjectsComputer import foundry.skippy.SkippyRunner import java.io.ObjectInputStream diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/GenerateAndroidTestProjectPathsTask.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/GenerateAndroidTestProjectPathsTask.kt index 76da6c462..17432f54f 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/GenerateAndroidTestProjectPathsTask.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/GenerateAndroidTestProjectPathsTask.kt @@ -17,8 +17,8 @@ package foundry.gradle.avoidance import foundry.gradle.artifacts.Resolver import foundry.gradle.artifacts.SgpArtifact +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.register -import foundry.gradle.util.setDisallowChanges import org.gradle.api.DefaultTask import org.gradle.api.Project import org.gradle.api.file.ConfigurableFileCollection diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/GenerateDependencyGraphTask.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/GenerateDependencyGraphTask.kt index 962cf20d3..42b5c0f3f 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/GenerateDependencyGraphTask.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/avoidance/GenerateDependencyGraphTask.kt @@ -18,8 +18,8 @@ package foundry.gradle.avoidance import com.jraska.module.graph.DependencyGraph import com.jraska.module.graph.assertion.GradleDependencyGraphFactory import foundry.gradle.FoundryProperties +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.register -import foundry.gradle.util.setDisallowChanges import java.io.ObjectOutputStream import org.gradle.api.DefaultTask import org.gradle.api.Project diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/dependencyrake/DependencyRake.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/dependencyrake/DependencyRake.kt index 1c17733f7..b9ace15ed 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/dependencyrake/DependencyRake.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/dependencyrake/DependencyRake.kt @@ -26,8 +26,8 @@ import com.autonomousapps.model.ProjectCoordinates import foundry.gradle.artifacts.Resolver import foundry.gradle.artifacts.SgpArtifact import foundry.gradle.convertProjectPathToAccessor +import foundry.gradle.properties.mapToBoolean import foundry.gradle.property -import foundry.gradle.util.mapToBoolean import java.io.File import javax.inject.Inject import org.gradle.api.DefaultTask diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/kgp/KgpTasks.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/kgp/KgpTasks.kt index 37de8c004..dbafd14ed 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/kgp/KgpTasks.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/kgp/KgpTasks.kt @@ -26,8 +26,8 @@ import foundry.gradle.configure import foundry.gradle.lint.DetektTasks import foundry.gradle.not import foundry.gradle.onFirst +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.util.configureKotlinCompilationTask -import foundry.gradle.util.setDisallowChanges import java.io.File import java.util.concurrent.atomic.AtomicBoolean import org.gradle.api.GradleException diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/lint/DetektTasks.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/lint/DetektTasks.kt index aa620480f..8affbc339 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/lint/DetektTasks.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/lint/DetektTasks.kt @@ -23,13 +23,13 @@ import foundry.gradle.avoidance.SkippyArtifacts import foundry.gradle.configure import foundry.gradle.configureEach import foundry.gradle.isRootProject +import foundry.gradle.properties.setDisallowChanges +import foundry.gradle.properties.sneakyNull import foundry.gradle.register import foundry.gradle.tasks.DetektDownloadTask import foundry.gradle.tasks.SimpleFileProducerTask import foundry.gradle.tasks.SimpleFilesConsumerTask import foundry.gradle.tasks.publish -import foundry.gradle.util.setDisallowChanges -import foundry.gradle.util.sneakyNull import io.gitlab.arturbosch.detekt.Detekt import io.gitlab.arturbosch.detekt.DetektCreateBaselineTask import io.gitlab.arturbosch.detekt.DetektPlugin diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/stats/ModuleStats.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/stats/ModuleStats.kt index 4b0a0a05d..79f809b1a 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/stats/ModuleStats.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/stats/ModuleStats.kt @@ -33,10 +33,10 @@ import foundry.gradle.convertProjectPathToAccessor import foundry.gradle.dependsOn import foundry.gradle.getByType import foundry.gradle.namedLazy +import foundry.gradle.properties.mapToBoolean +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.register import foundry.gradle.util.JsonTools -import foundry.gradle.util.mapToBoolean -import foundry.gradle.util.setDisallowChanges import java.io.File import java.util.concurrent.atomic.AtomicBoolean import javax.inject.Inject diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/AndroidTestApksTask.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/AndroidTestApksTask.kt index 6d3a6e8d4..5a122030c 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/AndroidTestApksTask.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/AndroidTestApksTask.kt @@ -17,8 +17,8 @@ package foundry.gradle.tasks import foundry.gradle.artifacts.Resolver import foundry.gradle.artifacts.SgpArtifact +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.register -import foundry.gradle.util.setDisallowChanges import kotlin.io.path.ExperimentalPathApi import kotlin.io.path.absolutePathString import kotlin.io.path.extension diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/BootstrapTask.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/BootstrapTask.kt index 046e9787c..2ab2b52c4 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/BootstrapTask.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/BootstrapTask.kt @@ -21,6 +21,8 @@ import foundry.gradle.FoundryProperties import foundry.gradle.isCi import foundry.gradle.isRootProject import foundry.gradle.listProperty +import foundry.gradle.properties.mapToInt +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.property import foundry.gradle.register import foundry.gradle.serviceOf @@ -28,8 +30,6 @@ import foundry.gradle.tasks.BootstrapPropertiesMode.APPEND import foundry.gradle.tasks.BootstrapPropertiesMode.LOG import foundry.gradle.tasks.BootstrapUtils.DaemonArgsProvider import foundry.gradle.tasks.BootstrapUtils.computeDaemonArgs -import foundry.gradle.util.mapToInt -import foundry.gradle.util.setDisallowChanges import java.io.File import java.util.Locale import java.util.Properties diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/CheckDependencyVersionsTask.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/CheckDependencyVersionsTask.kt index 42a05a8f8..e05e915c5 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/CheckDependencyVersionsTask.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/CheckDependencyVersionsTask.kt @@ -17,8 +17,8 @@ package foundry.gradle.tasks import foundry.gradle.capitalizeUS import foundry.gradle.getVersionsCatalog +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.register -import foundry.gradle.util.setDisallowChanges import org.gradle.api.GradleException import org.gradle.api.Project import org.gradle.api.artifacts.Configuration diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/PrintFossaDependencies.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/PrintFossaDependencies.kt index 11199c8d0..635c5f3f5 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/PrintFossaDependencies.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/PrintFossaDependencies.kt @@ -16,8 +16,8 @@ package foundry.gradle.tasks import foundry.gradle.capitalizeUS +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.register -import foundry.gradle.util.setDisallowChanges import org.gradle.api.Project import org.gradle.api.artifacts.Configuration import org.gradle.api.file.RegularFileProperty diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/robolectric/UpdateRobolectricJarsTask.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/robolectric/UpdateRobolectricJarsTask.kt index 415f4f1a4..332d498e1 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/robolectric/UpdateRobolectricJarsTask.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/tasks/robolectric/UpdateRobolectricJarsTask.kt @@ -16,10 +16,10 @@ package foundry.gradle.tasks.robolectric import foundry.gradle.FoundryProperties +import foundry.gradle.properties.setDisallowChanges import foundry.gradle.register import foundry.gradle.robolectricJars import foundry.gradle.tasks.BootstrapTask -import foundry.gradle.util.setDisallowChanges import java.io.File import org.gradle.api.DefaultTask import org.gradle.api.Project diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/unittest/UnitTests.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/unittest/UnitTests.kt index fb0e2f737..08a965a92 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/unittest/UnitTests.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/unittest/UnitTests.kt @@ -24,11 +24,11 @@ import foundry.gradle.ciUnitTestAndroidVariant import foundry.gradle.configureEach import foundry.gradle.isActionsCi import foundry.gradle.isCi +import foundry.gradle.properties.setDisallowChanges +import foundry.gradle.properties.synchronousEnvProperty import foundry.gradle.tasks.SimpleFileProducerTask import foundry.gradle.tasks.SimpleFilesConsumerTask import foundry.gradle.tasks.publish -import foundry.gradle.util.setDisallowChanges -import foundry.gradle.util.synchronousEnvProperty import kotlin.math.max import kotlin.math.roundToInt import org.gradle.api.Project From ed539b87264fc7697322b6ebef8f57908642ae40 Mon Sep 17 00:00:00 2001 From: Zac Sweers Date: Tue, 15 Oct 2024 14:23:34 -0400 Subject: [PATCH 3/3] Extract better gradle properties project --- CHANGELOG.md | 8 ++ .../api/better-gradle-properties.api | 78 ++++++++++++++++++ .../better-gradle-properties/build.gradle.kts | 6 +- .../gradle/properties/GitExecProviders.kt | 22 ++++-- .../gradle/properties/PropertyResolver.kt | 9 ++- .../foundry/gradle/ApkVersioningPlugin.kt | 4 +- .../foundry/gradle/FoundryGradleUtil.kt | 40 ++-------- .../foundry/gradle/FoundryProperties.kt | 18 ----- .../foundry/gradle/FoundryRootPlugin.kt | 48 ----------- .../gradle/StandardProjectConfigurations.kt | 3 +- .../foundry/gradle/FoundryGradleUtilTest.kt | 79 ------------------- 11 files changed, 125 insertions(+), 190 deletions(-) create mode 100644 platforms/gradle/better-gradle-properties/api/better-gradle-properties.api delete mode 100644 platforms/gradle/foundry-gradle-plugin/src/test/kotlin/foundry/gradle/FoundryGradleUtilTest.kt diff --git a/CHANGELOG.md b/CHANGELOG.md index 2a2bd0eec..dbfa54aa3 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,14 @@ Changelog **Unreleased** -------------- +- **New**: Extract `better-gradle-properties` artifact, which is our hierarchical Gradle properties solution that better handles properties in Gradle. This is what powers `FoundryProperties` but is now extracted to be more portable. + - This checks in the following order of priority + - project-local `local.properties` + - project-local `gradle.properties` + - root-project `local.properties` + - root-project/global `gradle.properties` +- Remove defunct `foundry.git.hooksPath` and `foundry.git.ignoreRevsFile` properties. + 0.20.2 ------ diff --git a/platforms/gradle/better-gradle-properties/api/better-gradle-properties.api b/platforms/gradle/better-gradle-properties/api/better-gradle-properties.api new file mode 100644 index 000000000..0309b03ad --- /dev/null +++ b/platforms/gradle/better-gradle-properties/api/better-gradle-properties.api @@ -0,0 +1,78 @@ +public final class foundry/gradle/properties/GitExecProvidersKt { + public static final fun gitExecProvider (Lorg/gradle/api/provider/ProviderFactory;[Ljava/lang/String;)Lorg/gradle/api/provider/Provider; +} + +public final class foundry/gradle/properties/HasConfigurableValuesKt { + public static final fun fromDisallowChanges (Lorg/gradle/api/file/ConfigurableFileCollection;[Ljava/lang/Object;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/ListProperty;Ljava/lang/Iterable;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/ListProperty;Lorg/gradle/api/provider/Provider;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/ListProperty;Lorg/gradle/api/provider/Provider;Lkotlin/jvm/functions/Function1;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/MapProperty;Ljava/util/Map;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/MapProperty;Lorg/gradle/api/provider/Provider;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/MapProperty;Lorg/gradle/api/provider/Provider;Lkotlin/jvm/functions/Function1;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/Property;Ljava/lang/Object;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/Property;Lorg/gradle/api/provider/Provider;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/SetProperty;Ljava/lang/Iterable;)V + public static final fun setDisallowChanges (Lorg/gradle/api/provider/SetProperty;Lorg/gradle/api/provider/Provider;)V +} + +public abstract class foundry/gradle/properties/LocalProperties : org/gradle/api/provider/ValueSource { + public fun ()V + public synthetic fun obtain ()Ljava/lang/Object; + public fun obtain ()Ljava/util/Properties; +} + +public abstract interface class foundry/gradle/properties/LocalProperties$Parameters : org/gradle/api/provider/ValueSourceParameters { + public abstract fun getPropertiesFile ()Lorg/gradle/api/file/RegularFileProperty; +} + +public final class foundry/gradle/properties/PropertyResolver { + public fun (Lorg/gradle/api/Project;Lkotlin/jvm/functions/Function1;Lkotlin/jvm/functions/Function1;)V + public synthetic fun (Lorg/gradle/api/Project;Lkotlin/jvm/functions/Function1;Lkotlin/jvm/functions/Function1;ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public final fun booleanProvider (Ljava/lang/String;)Lorg/gradle/api/provider/Provider; + public final fun booleanProvider (Ljava/lang/String;Lorg/gradle/api/provider/Provider;)Lorg/gradle/api/provider/Provider; + public final fun booleanProvider (Ljava/lang/String;Z)Lorg/gradle/api/provider/Provider; + public static synthetic fun booleanProvider$default (Lfoundry/gradle/properties/PropertyResolver;Ljava/lang/String;ZILjava/lang/Object;)Lorg/gradle/api/provider/Provider; + public final fun booleanValue (Ljava/lang/String;Lorg/gradle/api/provider/Provider;)Z + public final fun booleanValue (Ljava/lang/String;Z)Z + public static synthetic fun booleanValue$default (Lfoundry/gradle/properties/PropertyResolver;Ljava/lang/String;ZILjava/lang/Object;)Z + public final fun intProvider (Ljava/lang/String;I)Lorg/gradle/api/provider/Provider; + public final fun intProvider (Ljava/lang/String;Lorg/gradle/api/provider/Provider;)Lorg/gradle/api/provider/Provider; + public static synthetic fun intProvider$default (Lfoundry/gradle/properties/PropertyResolver;Ljava/lang/String;IILjava/lang/Object;)Lorg/gradle/api/provider/Provider; + public final fun intValue (Ljava/lang/String;I)I + public final fun intValue (Ljava/lang/String;Lorg/gradle/api/provider/Provider;)I + public static synthetic fun intValue$default (Lfoundry/gradle/properties/PropertyResolver;Ljava/lang/String;IILjava/lang/Object;)I + public final fun optionalStringProvider (Ljava/lang/String;)Lorg/gradle/api/provider/Provider; + public final fun optionalStringProvider (Ljava/lang/String;Ljava/lang/String;)Lorg/gradle/api/provider/Provider; + public static synthetic fun optionalStringProvider$default (Lfoundry/gradle/properties/PropertyResolver;Ljava/lang/String;Ljava/lang/String;ILjava/lang/Object;)Lorg/gradle/api/provider/Provider; + public final fun optionalStringValue (Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String; + public static synthetic fun optionalStringValue$default (Lfoundry/gradle/properties/PropertyResolver;Ljava/lang/String;Ljava/lang/String;ILjava/lang/Object;)Ljava/lang/String; + public final fun providerFor (Ljava/lang/String;)Lorg/gradle/api/provider/Provider; + public final fun stringValue (Ljava/lang/String;)Ljava/lang/String; + public final fun stringValue (Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String; +} + +public final class foundry/gradle/properties/PropertyUtil { + public static final fun createPropertiesProvider (Lorg/gradle/api/Project;Ljava/lang/String;)Lorg/gradle/api/provider/Provider; + public static final fun getOrCreateExtra (Lorg/gradle/api/Project;Ljava/lang/String;Lkotlin/jvm/functions/Function1;)Ljava/lang/Object; + public static final fun localGradleProperty (Lorg/gradle/api/Project;Ljava/lang/String;)Lorg/gradle/api/provider/Provider; + public static final fun localProperty (Lorg/gradle/api/Project;Ljava/lang/String;)Lorg/gradle/api/provider/Provider; + public static final fun mapToBoolean (Lorg/gradle/api/provider/Provider;)Lorg/gradle/api/provider/Provider; + public static final fun mapToInt (Lorg/gradle/api/provider/Provider;)Lorg/gradle/api/provider/Provider; + public static final fun markAsNonNullForGradle (Ljava/lang/Object;)V + public static final fun sneakyNull (Ljava/lang/Object;)Ljava/lang/Object; + public static synthetic fun sneakyNull$default (Ljava/lang/Object;ILjava/lang/Object;)Ljava/lang/Object; + public static final fun synchronousEnvProperty (Lorg/gradle/api/Project;Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String; + public static synthetic fun synchronousEnvProperty$default (Lorg/gradle/api/Project;Ljava/lang/String;Ljava/lang/String;ILjava/lang/Object;)Ljava/lang/String; +} + +public abstract class foundry/gradle/properties/StartParameterProperties : org/gradle/api/provider/ValueSource { + public fun ()V + public synthetic fun obtain ()Ljava/lang/Object; + public fun obtain ()Ljava/util/Map; +} + +public abstract interface class foundry/gradle/properties/StartParameterProperties$Parameters : org/gradle/api/provider/ValueSourceParameters { + public abstract fun getProperties ()Lorg/gradle/api/provider/MapProperty; +} + diff --git a/platforms/gradle/better-gradle-properties/build.gradle.kts b/platforms/gradle/better-gradle-properties/build.gradle.kts index 1cc2c06d9..b1887874d 100644 --- a/platforms/gradle/better-gradle-properties/build.gradle.kts +++ b/platforms/gradle/better-gradle-properties/build.gradle.kts @@ -19,4 +19,8 @@ plugins { alias(libs.plugins.lint) } -dependencies { compileOnly(gradleApi()) } +dependencies { + implementation(libs.okio) + + compileOnly(gradleApi()) +} diff --git a/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/GitExecProviders.kt b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/GitExecProviders.kt index 2caf78318..1f28612cd 100644 --- a/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/GitExecProviders.kt +++ b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/GitExecProviders.kt @@ -15,9 +15,8 @@ */ package foundry.gradle.properties -import java.io.ByteArrayOutputStream -import java.nio.charset.Charset import javax.inject.Inject +import okio.Buffer import org.gradle.api.provider.ListProperty import org.gradle.api.provider.Provider import org.gradle.api.provider.ProviderFactory @@ -25,6 +24,13 @@ import org.gradle.api.provider.ValueSource import org.gradle.api.provider.ValueSourceParameters import org.gradle.process.ExecOperations +/** + * Returns a new UTF8 String [Provider] backed by a [ValueSource] that produces a `git` exec + * operation with the given [args]. + * + * Because this is a gradle property that could be used at configuration-time, it's recommended to + * be careful when using this to avoid accidental often configuration-cache invalidations. + */ public fun ProviderFactory.gitExecProvider(vararg args: String): Provider { require(args.isNotEmpty()) { "Args list is empty" } return of(GitExecValueSource::class.java) { parameters.args.addAll(*args) } @@ -40,12 +46,14 @@ constructor(private val execOperations: ExecOperations) : override fun obtain(): String { val args = parameters.args.get() check(args.isNotEmpty()) { "Args list is empty" } - val output = ByteArrayOutputStream() - execOperations.exec { - commandLine(args) - standardOutput = output + val buffer = Buffer() + buffer.outputStream().use { output -> + execOperations.exec { + commandLine(args) + standardOutput = output + } } - return String(output.toByteArray(), Charset.defaultCharset()).trim { it <= ' ' } + return buffer.readUtf8().trim() } interface Parameters : ValueSourceParameters { diff --git a/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyResolver.kt b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyResolver.kt index ef9b80c00..e19307e9d 100644 --- a/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyResolver.kt +++ b/platforms/gradle/better-gradle-properties/src/main/kotlin/foundry/gradle/properties/PropertyResolver.kt @@ -19,7 +19,14 @@ import org.gradle.api.Project import org.gradle.api.provider.Provider /** - * A property resolver that handles multiple property sources. + * A property resolver that handles multiple property sources in a hierarchical fashion for + * [providerFor]. + * + * This checks in the following order of priority + * - project-local `local.properties` + * - project-local `gradle.properties` + * - root-project `local.properties` + * - root-project/global `gradle.properties` * * @property project The project to resolve properties for. * @property startParameterProperty A provider of a property _only_ contained in the project's start diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/ApkVersioningPlugin.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/ApkVersioningPlugin.kt index 5c56f96e7..bd94b00ad 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/ApkVersioningPlugin.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/ApkVersioningPlugin.kt @@ -95,8 +95,8 @@ internal class ApkVersioningPlugin : Plugin { ) // Register a version properties task. This is run on ci via android_preflight.sh - val shortGitShaProvider = project.gitSha - val longGitShaProvider = project.fullGitSha + val shortGitShaProvider = project.gitShaProvider() + val longGitShaProvider = project.fullGitShaProvider() project.tasks.register("generateVersionProperties") { outputFile.setDisallowChanges( project.layout.buildDirectory.file("intermediates/versioning/version.properties") diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryGradleUtil.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryGradleUtil.kt index 44d8290fd..b0d56ac66 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryGradleUtil.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryGradleUtil.kt @@ -20,9 +20,6 @@ import com.android.build.api.variant.ApplicationAndroidComponentsExtension import com.android.build.api.variant.LibraryAndroidComponentsExtension import com.android.build.api.variant.TestAndroidComponentsExtension import com.google.common.base.CaseFormat -import foundry.gradle.agp.VersionNumber -import foundry.gradle.dependencies.DependencyDef -import foundry.gradle.dependencies.DependencyGroup import foundry.gradle.properties.gitExecProvider import foundry.gradle.properties.mapToBoolean import java.io.File @@ -54,14 +51,8 @@ public val Project.isBuildkite: Boolean public val Project.isCi: Boolean get() = isActionsCi || isBuildkite -/** Useful helper for resolving a `group:name:version` bom notation for a [DependencyGroup]. */ -internal fun DependencyGroup.toBomDependencyDef(): DependencyDef { - checkNotNull(bomArtifact) { "No bom found for group ${this::class.simpleName}" } - return DependencyDef(group, bomArtifact, gradleProperty = groupGradleProperty) -} - /** Returns the git branch this is running on. */ -public fun Project.gitBranch(): Provider { +public fun Project.gitBranchProvider(): Provider { return when { isBuildkite -> providers.environmentVariable("BUILDKITE_BRANCH") else -> @@ -71,21 +62,6 @@ public fun Project.gitBranch(): Provider { } } -private val GIT_VERSION_REGEX = Regex("git version (\\d+\\.\\d+(\\.\\d+)?).*") - -/** - * Parses a git [VersionNumber] from a given [gitVersion], usually from a command line `git - * --version` output. - */ -internal fun parseGitVersion(gitVersion: String?): VersionNumber { - if (!gitVersion.isNullOrBlank()) { - return GIT_VERSION_REGEX.find(gitVersion)?.groupValues?.get(1)?.let(VersionNumber::parse) - ?: VersionNumber.UNKNOWN - } - - return VersionNumber.UNKNOWN -} - @OptIn(ExperimentalPathApi::class) internal fun robolectricJars(gradleUserHomeDir: File, createDirsIfMissing: Boolean = true): File { val foundryHome = File(gradleUserHomeDir, "foundry") @@ -143,15 +119,13 @@ public enum class SupportedLanguagesEnum { BETA, } -public val Project.fullGitSha: Provider - get() { - return providers.gitExecProvider("git", "rev-parse", "HEAD") - } +public fun Project.fullGitShaProvider(): Provider { + return providers.gitExecProvider("git", "rev-parse", "HEAD") +} -public val Project.gitSha: Provider - get() { - return providers.gitExecProvider("git", "rev-parse", "--short", "HEAD") - } +public fun Project.gitShaProvider(): Provider { + return providers.gitExecProvider("git", "rev-parse", "--short", "HEAD") +} public val Project.ciBuildNumber: Provider get() { diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryProperties.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryProperties.kt index b3d251760..b6cd67f72 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryProperties.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryProperties.kt @@ -476,24 +476,6 @@ internal constructor( public val platformProjectPath: String? get() = optionalStringProperty("foundry.location.foundry-platform") - /** - * Opt-in path for commit hooks in the consuming repo that should be automatically installed - * automatically. This is passed into [org.gradle.api.Project.file] from the root project. - * - * Corresponds to git's `core.hooksPath`. - */ - public val gitHooksFile: File? - get() = fileProperty("foundry.git.hooksPath") - - /** - * Opt-in path for a pre-commit hook in the consuming repo that should be automatically installed - * automatically. This is passed into [org.gradle.api.Project.file] from the root project. - * - * Corresponds to git's `blame.ignoreRevsFile`. - */ - public val gitIgnoreRevsFile: File? - get() = fileProperty("foundry.git.ignoreRevsFile") - /** * Optional file location for an `affected_projects.txt` file that contains a list of projects * affected in this build. diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryRootPlugin.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryRootPlugin.kt index 6555325f4..6ef33b06f 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryRootPlugin.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/FoundryRootPlugin.kt @@ -31,7 +31,6 @@ import foundry.gradle.lint.DetektTasks import foundry.gradle.lint.LintTasks import foundry.gradle.properties.StartParameterProperties import foundry.gradle.properties.createPropertiesProvider -import foundry.gradle.properties.gitExecProvider import foundry.gradle.properties.setDisallowChanges import foundry.gradle.properties.sneakyNull import foundry.gradle.stats.ModuleStatsTasks @@ -162,7 +161,6 @@ internal class FoundryRootPlugin @Inject constructor(private val buildFeatures: val latestCompileSdkWithSources = foundryProperties.latestCompileSdkWithSources(compileSdk) AndroidSourcesConfigurer.patchSdkSources(compileSdk, project, latestCompileSdkWithSources) } - project.configureGit(foundryProperties) } project.configureFoundryRootBuildscript( foundryProperties.versions.jdk.asProvider(project.providers), @@ -417,53 +415,7 @@ internal class FoundryRootPlugin @Inject constructor(private val buildFeatures: return stableKeyword || STABLE_REGEX.matches(version) } - private fun Project.configureGit(foundryProperties: FoundryProperties) { - // Only run locally - if (!isCi) { - foundryProperties.gitHooksFile?.let { hooksPath -> - // Configure hooks - providers.gitExecProvider("git", "config", "core.hooksPath", hooksPath.canonicalPath).get() - } - - val revsFile = foundryProperties.gitIgnoreRevsFile ?: return - // "git version 2.24.1" - val gitVersion = providers.gitExecProvider("git", "--version").get() - val versionNumber = parseGitVersion(gitVersion) - @Suppress( - "ReplaceCallWithBinaryOperator" - ) // Groovy classes don't seem to export equals() correctly - when { - versionNumber.equals(VersionNumber.UNKNOWN) -> { - logger.lifecycle( - "Could not infer git env from '$gitVersion'. This can happen if it's the pre-installed " + - "git version from Apple, please consider using a custom git installation from Homebrew or otherwise." - ) - } - versionNumber < MIN_GIT_VERSION_FOR_IGNORE_REVS -> { - logger.lifecycle( - "Current git version ($versionNumber) is too low to use " + - "blame.ignoreRevsFile (2.23+). Please consider updating!" - ) - } - else -> { - logger.debug("Configuring blame.ignoreRevsFile") - providers - .gitExecProvider("git", "config", "blame.ignoreRevsFile", file(revsFile).canonicalPath) - .get() - } - } - } - } - private companion object { - /** - * Minimum supported version of git to use blame.ignoreRevsFile. - * - * See - * https://www.moxio.com/blog/43/ignoring-bulk-change-commits-with-git-blame#git-2.23-to-the-rescue. - */ - val MIN_GIT_VERSION_FOR_IGNORE_REVS = VersionNumber.parse("2.23") - private val STABLE_REGEX = "^[0-9,.v-]+(-android)?(-r)?$".toRegex() } } diff --git a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/StandardProjectConfigurations.kt b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/StandardProjectConfigurations.kt index f9b4aec44..09f028ec9 100644 --- a/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/StandardProjectConfigurations.kt +++ b/platforms/gradle/foundry-gradle-plugin/src/main/kotlin/foundry/gradle/StandardProjectConfigurations.kt @@ -723,7 +723,8 @@ internal class StandardProjectConfigurations( pluginManager.withPlugin("com.bugsnag.android.gradle") { val branchMatchesPatternProvider = - foundryProperties.bugsnagEnabledBranchPattern.zip(gitBranch()) { pattern, branch -> + foundryProperties.bugsnagEnabledBranchPattern.zip(gitBranchProvider()) { pattern, branch + -> if (pattern == null || branch == null) { return@zip false } diff --git a/platforms/gradle/foundry-gradle-plugin/src/test/kotlin/foundry/gradle/FoundryGradleUtilTest.kt b/platforms/gradle/foundry-gradle-plugin/src/test/kotlin/foundry/gradle/FoundryGradleUtilTest.kt deleted file mode 100644 index 7e7b95630..000000000 --- a/platforms/gradle/foundry-gradle-plugin/src/test/kotlin/foundry/gradle/FoundryGradleUtilTest.kt +++ /dev/null @@ -1,79 +0,0 @@ -/* - * Copyright (C) 2022 Slack Technologies, LLC - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * https://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package foundry.gradle - -import com.google.common.truth.Truth.assertThat -import foundry.gradle.agp.VersionNumber -import org.junit.Test - -class FoundryGradleUtilTest { - - @Test - fun standardGitParse() { - val gitVersionOutput = "git version 2.24.0" - val parsed = parseGitVersion(gitVersionOutput) - assertThat(parsed.toString()).isEqualTo("2.24.0") - } - - @Test - fun shortGitParse() { - val gitVersionOutput = "git version 2.24" - val parsed = parseGitVersion(gitVersionOutput) - assertThat(parsed.toString()).isEqualTo("2.24.0") - } - - @Test - fun hubParse() { - // GitHub's "hub" tool changes the output of 'git --version' - val gitVersionOutput = - """ - git version 2.24.0 - hub version 2.13.0 - """ - .trimIndent() - val parsed = parseGitVersion(gitVersionOutput) - assertThat(parsed.toString()).isEqualTo("2.24.0") - } - - @Test - fun appleGit() { - // Apple appends some stuff on the end - val gitVersionOutput = - """ - git version 2.37.1 (Apple Git-137.1) - """ - .trimIndent() - val parsed = parseGitVersion(gitVersionOutput) - assertThat(parsed.toString()).isEqualTo("2.37.1") - } - - @Test - fun unrecognizedFallsBackToUnknown() { - val gitVersionOutput = - """ - garbage - """ - .trimIndent() - val parsed = parseGitVersion(gitVersionOutput) - assertThat(parsed).isEqualTo(VersionNumber.UNKNOWN) - } - - @Test - fun nullFallsBackToUnknown() { - val parsed = parseGitVersion(null) - assertThat(parsed).isEqualTo(VersionNumber.UNKNOWN) - } -}