运行 在编译 Kotlin 代码之前从 gradle CMake

Run CMake from gradle before compile Kotlin code

使用 Gradle 5.4.1,我想为 Android 应用构建一个 CMake 项目。这可以在 app/build.gradle 中完成:

externalNativeBuild {
    cmake {
        // Provides a relative path to your CMake build script.
        version "3.13.0+"
        path "../subproject/CMakeLists.txt"
    }
}

该项目使用 SWIG 生成共享库和一些 Java 文件。我可以通过 -DJAVA_OUTPUT_DIR=generated/java.

指定 Java 来源的输出目录

如何强制 gradle 在编译主应用程序源代码 (Kotlin) 之前等待 CMake 构建?源代码导入生成的 JAVA 个文件,目前构建过程因缺少 Java 个文件而失败。似乎 gradle 运行 cmake 和 Kotlin 编译器并行。

额外问题:如何将生成的源输出目录作为生成的源添加到AndroidStudio 项目树中?树中有一个用于生成源的特殊条目。

版本信息:

$ ./gradlew --version

------------------------------------------------------------
Gradle 5.4.1
------------------------------------------------------------

Build time:   2019-04-26 08:14:42 UTC
Revision:     261d171646b36a6a28d5a19a69676cd098a4c19d

Kotlin:       1.3.21
Groovy:       2.5.4
Ant:          Apache Ant(TM) version 1.9.13 compiled on July 10 2018
JVM:          11.0.5 (Debian 11.0.5+10-post-Debian-1deb10u1)
OS:           Linux 4.19.0-6-amd64 amd64

您应该将 cmake 任务添加为 compileKotlin 任务的依赖项。

Gradle 任务是部分排序的(一些任务应该在其他一些任务之前启动)。依赖关系就是用来表达这种关系的。

声明对 externalNativeBuild 的依赖 - 将其附加到 build.gradle

project.afterEvaluate {
    if (tasks.findByName("externalNativeBuildDebug")) {
        compileDebugKotlin.dependsOn externalNativeBuildDebug
    }
    if (tasks.findByName("externalNativeBuildRelease")) {
        compileReleaseKotlin.dependsOn externalNativeBuildRelease  
    }
}
  • 什么是afterEvaluate?这是 gradle 的生命周期阶段。这是读取和应用所有定义的时间。阅读更多 here.

  • 什么是externalNativeBuildDebugexternalNativeBuildRelease?这些是对 externalNativeBuild 任务的引用,具体取决于特定的构建命令

虽然接受的答案效果很好,但我使用 libraryVariants 来做到这一点。我个人觉得它更优雅。这是我的 Kotlin DSL 脚本的样子:

android {
    libraryVariants.all {
        tasks.findByName("compile${name.capitalize()}Kotlin")
            ?.dependsOn(tasks.findByName("externalNativeBuild${name.capitalize()}"))
    }
}

此解决方案的显着优势在于它与您的构建变体无关,并且如果您有 change/add 个变体,它将继续工作而无需修改。