我正在寻找一种简单的方法来查明在我的库的
build.gradle
脚本(在任务中)中是否正在为调试或发布模式构建Android应用程序。
我有一个名为
prepareHermes
的任务,它提取 .aar 文件。我目前总是提取调试变体,但在发布版本中我想使用发布变体:
task prepareHermes() {
doLast {
def IS_DEBUG = // TODO: here
def aarName = IS_DEBUG ? "hermes-debug.aar" : "hermes-release.aar"
def hermesAAR = file("$hermesPackagePath/android/${aarName}")
if (!hermesAAR.exists()) {
throw new GradleScriptException("The hermes-engine npm package is missing \"android/${aarName}\"", null)
}
def soFiles = zipTree(hermesAAR).matching({ it.include "**/*.so" })
copy {
from soFiles
from "$reactNative/ReactAndroid/src/main/jni/first-party/hermes/Android.mk"
into "$thirdPartyNdkDir/hermes"
}
}
}
此任务稍后会在各个地方使用(请参阅完整代码此处),因此制作两个单独的任务(
prepareHermesDebug
和prepareHermesRelease
)有点不方便,因为我有大量重复的代码。 (此任务是其他一些任务的依赖项,如完整代码所示。)
您还可以生成任意数量的任务:
[ 'debug', 'release' ].each{ name ->
task "prepareHermes-$name"{
doLast {
def aarName = "hermes-${name}.aar"
def hermesAAR = file "$hermesPackagePath/android/$aarName"
// the rest...
}
}
}
然后,如果您运行
gradlew tasks
,您将在输出中看到 prepareHermes-debug
和 prepareHermes-release
使用
gradle.startParameter.taskRequests
来确定当前变体不是一个好主意。**
gradle.startParameter.taskRequests
API 位于底层,并且它不是 Variant Aware。不支持以下场景:
./gradlew clean assemble
上述命令会生成
Debug
和 Release
工件,这会破坏使用 taskRequests
的检查脚本。
制作两个单独的任务(prepareHermesDebug和prepareHermesRelease)有点不方便......
是的,我们将使用
onVariants{}
API 来做类似的事情。基本上,它会迭代所有变体对象,以便您有机会分别注册 Variant Aware 任务:
androidComponents {
onVariants { variant ->
project.tasks.register<AarUploadTask>("${variant.name}AarUpload") {
aar.set(variant.artifacts.get(SingleArtifact.AAR))
}
}
}
abstract class AarUploadTask: DefaultTask() {
@get:InputFile
abstract val aar: RegularFileProperty
@TaskAction
fun taskAction() {
println("Uploading ${aar.get().asFile.absolutePath} to fantasy server...")
}
}
通过上面新的 Variant&Artifact API(抱歉,在 Kotlin DSL 中,但是您可以轻松地将其转换为 Groovy),您可以获取 Variant 对应的
.aar
并将其方便地传递给自定义任务(不再需要硬编码)。
从 android/gradle-receipt 检查完整脚本,并从 扩展 Android Gradle 插件查看更多 API 文档。
使用 Groovy 等效项进行编辑
要在 Groovy 中执行相同的操作,您必须显式指定选择器,因为 Google 在 Kotlin 中编写了
onVariants
API,虽然 Kotlin 和 Groovy 都有默认参数,但它们通过 Java 进行互操作,而 Java 没有默认参数。
androidComponents {
// We have to manually specify selector().all() because
// AGP is written in Kotlin, and even though both Kotlin and Groovy have default parameters
// they interop with Java, which does NOT have default parameters
// This thread explains:
// https://slack-chats.kotlinlang.org/t/487047/androidcomponets-onvariants-println-variant-it-why-does-this
onVariants(selector().all()) { variant ->
}
}
在示例中使用 Kotlin 代码会导致如下错误:
Could not find method onVariants() for arguments [build_3ywhpguii6fsrnofcs3ky05l6$_run_closure3$_closure4@75ab9409] on extension 'androidComponents' of type com.android.build.gradle.internal.plugins.LibraryPlugin$LibraryAndroidComponentsExtensionImplCompat.