Gradle Kotlin 规范插件用于模块化结构 - 共享构建逻辑

Gradle Kotlin 规范插件用于模块化结构 - 共享构建逻辑

Gradle Kotlin 规范插件用于模块化结构 - 共享构建逻辑_第1张图片
我们中的许多人都遇到过Groovy的困难,并习惯于将其转换为Kotlin DSL。 然后,作为Android工程师,在完全使用Kotlin编写的项目上工作是纯粹的喜悦。

我们假设采用基于功能的模块化应用程序结构,并应用版本目录(version catalog)功能。我们将充分管理构建逻辑,使其集中化并可由模块重用。
以下是通过创建您的自定义插件脚本来促进Gradle构建配置成为集中化构建逻辑的步骤。

我们所有人都通常采用的方法是将自定义脚本放置到默认的buildSrc模块中。先前不推荐使用buildSrc实现,因为它会使构建缓存失效,并在每次更改依赖项时同步整个项目。它现在被视为Gradle 8中的一个包含式构建。

项目级声明

在项目设置脚本中,我们将配置脚本移动到一个构建逻辑复合构建模块中。
第一个 pluginManagement 块确保 Gradle 使用适当的插件存储库。我们将我们的新模块包含在构建中,并明确指定我们需要的存储库。
另一个关键元素是集中式依赖声明中的解析模式,你可以声明以强制 Gradle 始终获取正确的依赖项。在此示例中,我们将使用项目设置中声明的存储库。

settings.gradle.kts

@file:Suppress("UnstableApiUsage")

enableFeaturePreview("VERSION_CATALOGS")
enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS")

pluginManagement {
    includeBuild("build-logic")
    repositories {
        gradlePluginPortal()
        google()
        mavenCentral()
    }
}

dependencyResolutionManagement {
    repositoriesMode.set(RepositoriesMode.PREFER_SETTINGS)
    repositories {
        google()
        mavenCentral()
    }
}

rootProject.name = "GradleKotlinConventionPlugins"

include(":app")

Gradle Kotlin 规范插件用于模块化结构 - 共享构建逻辑_第2张图片

共享逻辑复合模块

在设置脚本中启用版本目录功能后,我们开始使用新的复合模块。

settings.gradle.kts

@Suppress("UnstableApiUsage")
dependencyResolutionManagement {
    versionCatalogs {
        create("libs") {
            from(files("../gradle/libs.versions.toml"))
        }
    }
}

rootProject.name = "build-logic"

现在,我们将我们的新模块定义为Kotlin脚本,通过启用Kotlin DSL并强制使用预编译的脚本插件将其作为 Kotlin 源集的一部分。
因此,作为项目构建的组成部分的复合模块负责配置,这通常是我们在项目级 Gradle 构建脚本中处理的。 我们将 Gradle 特定的声明移动到那里。

build.gradle.kts

plugins {
    `kotlin-dsl`
    `kotlin-dsl-precompiled-script-plugins`
}

repositories {
    google()
    mavenCentral()
    gradlePluginPortal()
}

dependencies {
    implementation(libs.kotlin.gradlePlugin)
    implementation(libs.gradle)
}

tasks.test {
    useJUnitPlatform()
}

类型为基础的规范

在基于特征的模块化应用结构中,我们有主应用模块、功能模块和共享模块(用于一些可重用的逻辑或数据)等。

我们确定的主要规范插件包括:

  • Kotlin 库规范
  • Android 库规范
  • Android 可组合库规范

Kotlin 库规范

Kotlin 库惯例通常用于声明一些 API 或共享一些逻辑。它是一个覆盖了 JDK 版本的 Java 库。

kotlin-library-conventions.gradle.kts

plugins {
    `java-library`
    kotlin("jvm")
}

kotlin {
    jvmToolchain(jdkVersion = 11)
}

task("testUnitTest") {
    dependsOn("test")
}

Gradle Kotlin 规范插件用于模块化结构 - 共享构建逻辑_第3张图片

Kotlin Android 库规范

Kotlin Android 库规范适用于默认启用 ViewBinding 功能的特征模块。

kotlin-android-library-conventions.gradle.kts

plugins {
    id("com.android.library")
    kotlin("android")
}

@Suppress("UnstableApiUsage")
android {
    . . .

    compileOptions {
        isCoreLibraryDesugaringEnabled = true
        targetCompatibility = JavaVersion.VERSION_11
        sourceCompatibility = JavaVersion.VERSION_11
    }

    kotlinOptions {
        jvmTarget = JavaVersion.VERSION_11.toString()
    }

    buildFeatures {
        viewBinding = true
    }
}

dependencies {
    . . .
}

Kotlin Android Compose库规范

它是先前库约定的扩展,具有与 Jetpack Compose 相关的声明。

kotlin-android-composable-library-conventions.gradle.kts

plugins {
    id("kotlin-android-library-conventions")
}

@Suppress("UnstableApiUsage")
android {
    buildFeatures.compose = true
    composeOptions.kotlinCompilerExtensionVersion = libs.versionKotlinCompiler
}

dependencies {
    implementation(platform(libs.libAndroidxComposeBom))
    implementation(libs.libAndroidxComposeFoundation)
}

创建新模块时,通过应用传统插件和额外的依赖项来定义构建脚本会更加容易。我们也可以考虑将组合模块应用于另一个项目。

当我们创建一个新模块时,可以通过应用公约插件和附加的依赖项,更容易地定义构建脚本。我们还可以考虑将组合模块应用于另一个项目。

feature-build.gradle.kts

plugins {
    id("kotlin-android-library-conventions")
    id("test-conventions")
}

dependencies {
    implementation(libs.androidX.appCompat)
    implementation(libs.google.material)
}

结论

总之,模块化是我们解决诸多问题的主要关注点,如代码库大小、可扩展性、可读性、代码质量、代码重复等。我们通常会按照特性来划分模块,将特性代码进行隔离。Google Android团队最近也发布了一份应用程序模块化指南,采用了相同的方法。

https://developer.android.com/topic/modularization

但也有一些与版本目录相关的限制性问题。库不是直接可访问的,我们需要创建一些扩展函数来解决这个问题。插件在插件块中也不被识别。这个问题似乎在Gradle 8中已经得到解决。

您可以在我的Github规范repository中找到所有的源代码。

https://github.com/uteke/gradle-kotlin-convention-plugins

你可能感兴趣的:(Android开发工具,kotlin,android,android,studio)