From 95d742d670a6ad06b594675386b036f238358014 Mon Sep 17 00:00:00 2001 From: Thomas Wirth Date: Thu, 11 Jun 2020 01:27:32 +0200 Subject: [PATCH 1/2] Set APK naming at variant configuration time to avoid issues with android studio * use single mapping filename for AAB and APK * copy files and delete original by default, allow keeping original files --- .../eu/nanogiants/gradle/VersioningPlugin.kt | 80 +++++++++++-------- .../gradle/VersioningPluginExtension.kt | 1 + .../gradle/ext/ApplicationVariantExt.kt | 6 +- .../eu/nanogiants/gradle/ext/TaskExt.kt | 54 ++++++++++--- 4 files changed, 91 insertions(+), 50 deletions(-) diff --git a/src/main/kotlin/eu/nanogiants/gradle/VersioningPlugin.kt b/src/main/kotlin/eu/nanogiants/gradle/VersioningPlugin.kt index 517e395..535094e 100644 --- a/src/main/kotlin/eu/nanogiants/gradle/VersioningPlugin.kt +++ b/src/main/kotlin/eu/nanogiants/gradle/VersioningPlugin.kt @@ -7,6 +7,7 @@ package eu.nanogiants.gradle import com.android.build.gradle.AppExtension import com.android.build.gradle.internal.api.BaseVariantOutputImpl +import eu.nanogiants.gradle.ext.addPrintOutputAction import eu.nanogiants.gradle.ext.addRenameArtifactAction import eu.nanogiants.gradle.ext.addRenameMappingAction import eu.nanogiants.gradle.ext.generateOutputName @@ -24,59 +25,68 @@ class VersioningPlugin : Plugin { override fun apply(project: Project) { with(project) { - val extension = extensions.create("versioning", VersioningPluginExtension::class.java) + val ext = extensions.create("versioning", VersioningPluginExtension::class.java) tasks.register("printVersions") { it.group = "Versioning" it.description = "Prints the Android version information." it.doLast { - extension.getVersionName() - extension.getVersionCode() + ext.getVersionName() + ext.getVersionCode() } } pluginManager.withPlugin("com.android.application") { - val appExtension = extensions.getByType(AppExtension::class.java) - val baseName = convention.findPlugin(BasePluginConvention::class.java)?.archivesBaseName ?: name + val appExt = extensions.getByType(AppExtension::class.java) - tasks.configureEach { task -> - if (task.name.matches(bundleRegex)) { - val variantName = task.name.substringAfter("bundle").decapitalize(Locale.ROOT) + appExt.applicationVariants.configureEach { variant -> + if (!ext.excludeBuildTypes.listContains(variant.buildType.name)) { + val baseName = convention.findPlugin(BasePluginConvention::class.java)?.archivesBaseName ?: name + variant.outputs.configureEach { + val newApkName = variant.generateOutputName(baseName, "apk") + (it as BaseVariantOutputImpl).outputFileName = newApkName + } + } + } - appExtension.applicationVariants.configureEach { variant -> - if (variant.name == variantName && !extension.excludeBuildTypes.listContains(variant.buildType.name)) { - val bundleName = "$baseName-${variant.baseName}.aab" - val newBundleName = variant.generateOutputName(baseName, "aab") - val bundleOutputPath = "${buildDir.absolutePath}/outputs/bundle/$variantName/" + afterEvaluate { + val baseName = convention.findPlugin(BasePluginConvention::class.java)?.archivesBaseName ?: name + tasks.configureEach { task -> + if (task.name.matches(bundleRegex)) { + val variantName = task.name.substringAfter("bundle").decapitalize(Locale.ROOT) - task.addRenameArtifactAction(bundleName, newBundleName, bundleOutputPath) + appExt.applicationVariants.configureEach { variant -> + if (variant.name == variantName && !ext.excludeBuildTypes.listContains(variant.buildType.name)) { + val bundleName = "$baseName-${variant.baseName}.aab" + val newBundleName = variant.generateOutputName(baseName, "aab") + val bundleOutputPath = "${buildDir.absolutePath}/outputs/bundle/${variant.name}/" - if (variant.buildType.isMinifyEnabled) { - variant.mappingFileProvider.orNull?.firstOrNull()?.let { - val newMappingName = variant.generateOutputName(baseName, "txt", "aab") - task.addRenameMappingAction(it, newMappingName) + task.addRenameArtifactAction(bundleName, newBundleName, bundleOutputPath, ext.keepOriginalArtifacts) + + if (variant.buildType.isMinifyEnabled) { + variant.mappingFileProvider.orNull?.firstOrNull()?.let { + val newMappingName = variant.generateOutputName(baseName, "txt") + task.addRenameMappingAction(it, newMappingName, ext.keepOriginalArtifacts) + } } } } - } - } else if (task.name.matches(assembleRegex)) { - val variantName = task.name.substringAfter("assemble").decapitalize(Locale.ROOT) + } else if (task.name.matches(assembleRegex)) { + val variantName = task.name.substringAfter("assemble").decapitalize(Locale.ROOT) - appExtension.applicationVariants.configureEach { variant -> - if (variant.name == variantName && !extension.excludeBuildTypes.listContains(variant.buildType.name)) { - val apkOutputPath = "${buildDir.absolutePath}/outputs/apk/$variantName/" - - variant.outputs.configureEach { - val apkName = (it as BaseVariantOutputImpl).outputFileName - val newApkName = variant.generateOutputName(baseName, "apk") - - task.addRenameArtifactAction(apkName, newApkName, apkOutputPath) - } + appExt.applicationVariants.configureEach { variant -> + if (variant.name == variantName && !ext.excludeBuildTypes.listContains(variant.buildType.name)) { + variant.outputs.configureEach { + val apkName = (it as BaseVariantOutputImpl).outputFileName + val apkOutputPath = "${buildDir.absolutePath}/outputs/apk/$variantName/" + task.addPrintOutputAction(apkOutputPath, apkName) + } - if (variant.buildType.isMinifyEnabled) { - variant.mappingFileProvider.orNull?.firstOrNull()?.let { - val newMappingName = variant.generateOutputName(baseName, "txt", "apk") - task.addRenameMappingAction(it, newMappingName) + if (variant.buildType.isMinifyEnabled) { + variant.mappingFileProvider.orNull?.firstOrNull()?.let { + val newMappingName = variant.generateOutputName(baseName, "txt") + task.addRenameMappingAction(it, newMappingName, ext.keepOriginalArtifacts) + } } } } diff --git a/src/main/kotlin/eu/nanogiants/gradle/VersioningPluginExtension.kt b/src/main/kotlin/eu/nanogiants/gradle/VersioningPluginExtension.kt index 9121cce..0ff024f 100644 --- a/src/main/kotlin/eu/nanogiants/gradle/VersioningPluginExtension.kt +++ b/src/main/kotlin/eu/nanogiants/gradle/VersioningPluginExtension.kt @@ -13,4 +13,5 @@ open class VersioningPluginExtension { fun getVersionName(checkBranch: Boolean = false) = Versioning.getVersionName(checkBranch) var excludeBuildTypes: String? = null + var keepOriginalArtifacts: Boolean = false } \ No newline at end of file diff --git a/src/main/kotlin/eu/nanogiants/gradle/ext/ApplicationVariantExt.kt b/src/main/kotlin/eu/nanogiants/gradle/ext/ApplicationVariantExt.kt index 4809b80..94eedfd 100644 --- a/src/main/kotlin/eu/nanogiants/gradle/ext/ApplicationVariantExt.kt +++ b/src/main/kotlin/eu/nanogiants/gradle/ext/ApplicationVariantExt.kt @@ -7,7 +7,7 @@ package eu.nanogiants.gradle.ext import com.android.build.gradle.api.ApplicationVariant -internal fun ApplicationVariant.generateOutputName(baseName: String, extension: String, suffix: String = ""): String { +internal fun ApplicationVariant.generateOutputName(baseName: String, extension: String): String { return StringBuilder().apply { append(baseName) productFlavors.forEach { @@ -20,10 +20,6 @@ internal fun ApplicationVariant.generateOutputName(baseName: String, extension: append(versionCode.toString()) append("-") append(buildType.name) - if (suffix.isNotEmpty()) { - append("-") - append(suffix) - } if (extension == "apk" && !isSigningReady) { append("-unsigned") } else if (extension == "txt") { diff --git a/src/main/kotlin/eu/nanogiants/gradle/ext/TaskExt.kt b/src/main/kotlin/eu/nanogiants/gradle/ext/TaskExt.kt index 7293daf..cca81f6 100644 --- a/src/main/kotlin/eu/nanogiants/gradle/ext/TaskExt.kt +++ b/src/main/kotlin/eu/nanogiants/gradle/ext/TaskExt.kt @@ -8,30 +8,64 @@ package eu.nanogiants.gradle.ext import org.gradle.api.Task import java.io.File -internal fun Task.addRenameArtifactAction(oldOutput: String, newOutput: String, outputPath: String) { +internal fun Task.addRenameArtifactAction( + oldOutput: String, + newOutput: String, + outputPath: String, + keepOriginal: Boolean +) { println(newOutput) doLast { val newFile = File(outputPath + newOutput) - val success = File(outputPath + oldOutput).renameTo(newFile) - if (success) { - println("Created file://${newFile.absolutePath}") + val oldFile = File(outputPath + oldOutput) + + if (oldFile.exists()) { + oldFile.copyTo(newFile, overwrite = true) + if (newFile.exists()) { + if (!keepOriginal) oldFile.delete() + println("Created file://${newFile.absolutePath}") + } else { + logger.error("Creating $newOutput from $oldOutput failed.") + } } else { - logger.error("Renaming $oldOutput to $newOutput failed.") + if (newFile.exists()) { + println("Cached output $oldOutput was already renamed. Set 'keepOriginalArtifacts' if you like to keep those files.") + } else { + logger.error("$oldOutput and $newOutput not found. Try a clean build.") + } } } } -internal fun Task.addRenameMappingAction(oldOutput: File, newOutput: String) { +internal fun Task.addRenameMappingAction(oldOutput: File, newOutput: String, keepOriginal: Boolean) { println(newOutput) doLast { val newFile = File(oldOutput.absolutePath.replaceAfterLast("/", newOutput)) - val success = oldOutput.renameTo(newFile) - if (success) { - println("Created file://${newFile.absolutePath}") + + if (oldOutput.exists()) { + oldOutput.copyTo(newFile, overwrite = true) + if (newFile.exists()) { + if (!keepOriginal) oldOutput.delete() + println("Created $newOutput") + } else { + logger.error("Creating $newOutput from mapping.txt failed.") + } } else { - logger.error("Renaming mapping.txt to $newOutput failed.") + if (newFile.exists()) { + println("Cached output mapping.txt was already renamed. Set 'keepOriginalArtifacts' if you like to keep those files.") + } else { + logger.error("mapping.txt and $newOutput not found. Try a clean build.") + } } } +} + +internal fun Task.addPrintOutputAction(filepath: String, filename: String) { + println(filename) + + doLast { + if (File(filepath).exists()) println("Created file://${filepath + filename}") + } } \ No newline at end of file From 8d1ef72dfd0a4c6f088d81c630ab107b9bacf905 Mon Sep 17 00:00:00 2001 From: Thomas Wirth Date: Thu, 11 Jun 2020 01:27:56 +0200 Subject: [PATCH 2/2] Update readme and bump version to 2.2.0 --- README.md | 17 ++++++++++------- build.gradle.kts | 2 +- 2 files changed, 11 insertions(+), 8 deletions(-) diff --git a/README.md b/README.md index 14501f3..8fb75e7 100644 --- a/README.md +++ b/README.md @@ -12,7 +12,7 @@ buildscript { jcenter() } dependencies { - classpath 'eu.nanogiants:android-versioning:2.1.2' + classpath 'eu.nanogiants:android-versioning:2.2.0' } } ``` @@ -45,24 +45,27 @@ Build Variant `productionStoreDebug` ```groovy android { defaultConfig { - archivesBaseName = "MyAppName" + archivesBaseName = "myAppName" } } ``` Artifacts: ``` -MyAppName-production-store-3.9.0-3272-debug.apk -MyAppName-production-store-3.9.0-3272-debug.aab +myAppName-production-store-3.9.0-3272-debug.apk +myAppName-production-store-3.9.0-3272-debug.aab +myAppName-production-store-3.9.0-3272-mapping.txt ``` #### Note: -Since Android Studio does not know about the artifact renaming, the `locate` or `analyze` links in the event log and notifications will stop working. To compensate that, the plugin prints file URI for every renamed artifact. +Because Android Studio does not know about the AAB renaming, the `locate` or `analyze` links in the event log and notifications will only work for APK files by default. You can set `keepOriginalArtifacts` to keep the original files. The plugin also prints the file URI for renamed artifacts. #### Optional: -You can define a comma separated list of buildTypes (e.g. debug) to be excluded from the artifact naming. +* `excludeBuildTypes`: comma separated list of buildTypes (e.g. debug) to be excluded from the artifact naming +* `keepOriginalArtifacts`: copy artifact files instead of renaming them ```groovy // app build.gradle versioning { - excludeBuildTypes = "debug" { + excludeBuildTypes = "debug" // default: null + keepOriginalArtifacts = true // default: false } ``` diff --git a/build.gradle.kts b/build.gradle.kts index d9727c8..ff8ff4b 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -8,7 +8,7 @@ plugins { } group = "eu.nanogiants" -version = "2.1.2" +version = "2.2.0" repositories { google()