You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

将Gradle插件迁移至AGP 9.0.0时遇到同步错误求助

AGP 9.0.0(搭配Gradle 9.3.0)迁移同步错误解决

问题背景

将AGP从8.13.2(搭配Gradle 9.1.0)升级至9.0.0(搭配Gradle 9.3.0)后,build-logic模块下的插件同步失败。项目插件实现参考NIA App架构,Android专属模块使用com.android.library插件,共享模块使用com.android.kotlin.multiplatform.library插件。

环境配置

build-logic\gradle.properties

org.gradle.parallel=true
org.gradle.caching=true
org.gradle.configureondemand=true
org.gradle.configuration-cache=true
org.gradle.configuration-cache.parallel=true

build-logic模块build.gradle.kts

import org.jetbrains.kotlin.gradle.dsl.JvmTarget

plugins {
    `kotlin-dsl`
    alias(libs.plugins.android.lint)
}

group = "pl.doz.hornet.buildlogic"

java {
    sourceCompatibility = JavaVersion.VERSION_17
    targetCompatibility = JavaVersion.VERSION_17
}

kotlin {
    compilerOptions {
        jvmTarget = JvmTarget.JVM_17
    }
}

dependencies {
    compileOnly(libs.android.gradleApiPlugin)
    compileOnly(libs.android.tools.common)
    compileOnly(libs.compose.gradlePlugin)
    compileOnly(libs.kotlin.gradlePlugin)
    compileOnly(libs.ksp.gradlePlugin)
    compileOnly(libs.room.gradlePlugin)
    lintChecks(libs.androidx.lint.gradle)
}

tasks {
    validatePlugins {
        enableStricterValidation = true
        failOnWarning = true
    }
}

gradlePlugin {
    plugins {
        register("androidApplication") {
            id = libs.plugins.hornet.android.application.get().pluginId
            implementationClass = "AndroidApplicationConventionPlugin"
        }
        register("androidApplicationCompose") {
            id = libs.plugins.hornet.androidApplicationCompose.get().pluginId
            implementationClass = "AndroidApplicationComposeConventionPlugin"
        }
        register("androidLibrary") {
            id = libs.plugins.hornet.android.library.asProvider().get().pluginId
            implementationClass = "AndroidLibraryConventionPlugin"
        }
        register("androidLibraryCompose") {
            id = libs.plugins.hornet.android.library.compose.get().pluginId
            implementationClass = "AndroidLibraryComposeConventionPlugin"
        }
        register("androidFlavors") {
            id = libs.plugins.hornet.androidFlavors.get().pluginId
            implementationClass = "AndroidFlavorsConventionPlugin"
        }
        register("sharedLibrary") {
            id = libs.plugins.hornet.sharedLibrary.get().pluginId
            implementationClass = "SharedLibraryConventionPlugin"
        }
        register("room") {
            id = libs.plugins.hornet.room.get().pluginId
            implementationClass = "RoomConventionPlugin"
        }
        register("ktor") {
            id = libs.plugins.hornet.ktor.get().pluginId
            implementationClass = "KtorConventionPlugin"
        }
        register("koin") {
            id = libs.plugins.hornet.koin.get().pluginId
            implementationClass = "KoinConventionPlugin"
        }
        register("lint") {
            id = libs.plugins.hornet.androidLint.get().pluginId
            implementationClass = "LintConventionPlugin"
        }
        register("featureApi") {
            id = libs.plugins.hornet.feature.api.get().pluginId
            implementationClass = "FeatureApiConventionPlugin"
        }
        register("featureImpl") {
            id = libs.plugins.hornet.feature.impl.get().pluginId
            implementationClass = "FeatureImplConventionPlugin"
        }
        register("featureAndroidImpl") {
            id = libs.plugins.hornet.android.feature.impl.get().pluginId
            implementationClass = "AndroidFeatureImplConventionPlugin"
        }
    }
}

build-logic模块settings.gradle.kts

pluginManagement {
    repositories {
        gradlePluginPortal()
        google()
    }
}

dependencyResolutionManagement {
    repositories {
        google {
            content {
                includeGroupByRegex("com\\.android.*")
                includeGroupByRegex("com\\.google.*")
                includeGroupByRegex("androidx.*")
            }
        }
        mavenCentral()
    }
    versionCatalogs {
        create("libs") {
            from(files("../gradle/libs.versions.toml"))
        }
    }
}

rootProject.name = "build-logic"
include(":convention")

同步错误信息

15:37 No type arguments expected for interface CommonExtension : ExtensionAware.
17:21 Cannot infer type for type parameter 'T'. Specify it explicitly.
17:21 Unresolved reference. None of the following candidates is applicable because of a receiver type mismatch:
fun <T> T.apply(block: T.() -> Unit): T
17:27 Cannot infer type for type parameter 'T'. Specify it explicitly.
18:9 Unresolved reference 'buildFeatures'.
19:13 Unresolved reference 'compose'.

出错代码(AndroidCompose相关)

import com.android.build.api.dsl.CommonExtension
import org.gradle.api.Project
import org.gradle.api.provider.Provider
import org.gradle.kotlin.dsl.configure
import org.gradle.kotlin.dsl.dependencies
import org.jetbrains.kotlin.compose.compiler.gradle.ComposeCompilerGradlePluginExtension

/**
 * Configure Compose-specific options
 */
internal fun Project.configureAndroidCompose(
    commonExtension: CommonExtension<*, *, *, *, *, *>,
) {
    commonExtension.apply {
        buildFeatures {
            compose = true
        }

        dependencies {
            val bom = libs.findLibrary("androidx-compose-bom").get()
            "implementation"(platform(bom))
            "androidTestImplementation"(platform(bom))
            "implementation"(libs.findLibrary("androidx-compose-ui-tooling").get())
            "implementation"(libs.findLibrary("androidx-compose-ui-tooling-preview").get())
            "implementation"(libs.findLibrary("androidx-compose-runtime").get())
            "implementation"(libs.findLibrary("androidx-compose-foundation").get())
            "implementation"(libs.findLibrary("androidx-compose-material3").get())
            "debugImplementation"(libs.findLibrary("androidx-compose-ui-tooling").get())
        }
    }

    extensions.configure<ComposeCompilerGradlePluginExtension> {
        fun Provider<String>.onlyIfTrue() = flatMap { provider { it.takeIf(String::toBoolean) } }
        fun Provider<*>.relativeToRootProject(dir: String) = map {
            isolated.rootProject.projectDirectory
                .dir("build")
                .dir(projectDir.toRelativeString(rootDir))
        }.map { it.dir(dir) }

        project.providers.gradleProperty("enableComposeCompilerMetrics").onlyIfTrue()
            .relativeToRootProject("compose-metrics")
            .let(metricsDestination::set)

        project.providers.gradleProperty("enableComposeCompilerReports").onlyIfTrue()
            .relativeToRootProject("compose-reports")
            .let(reportsDestination::set)

        stabilityConfigurationFiles
            .add(isolated.rootProject.projectDirectory.file("compose_compiler_config.conf"))
    }
}

class AndroidLibraryComposeConventionPlugin : Plugin<Project> {
    override fun apply(target: Project) {
        with(target) {
            apply(plugin = "com.android.library")
            apply(plugin = "org.jetbrains.kotlin.plugin.compose")

            val extension = extensions.getByType<LibraryExtension>()
            configureAndroidCompose(extension)
        }
    }
}

解决方案

1. 修正CommonExtension泛型定义

AGP 9.0.0中CommonExtension不再是泛型接口,直接移除泛型参数:

internal fun Project.configureAndroidCompose(
    commonExtension: CommonExtension, // 移除<*, *, *, *, *, *>泛型
) {
    // ...
}

2. 修复接收器不匹配问题

将commonExtension.apply { ... }替换为commonExtension.run { ... },确保代码块能正确识别接收器类型:

commonExtension.run {
    buildFeatures {
        compose = true
    }
    // ...
}

3. 调整Compose Compiler配置中的rootProject获取方式

AGP 9.0.0中移除了isolated属性,直接使用rootProject即可:

fun Provider<*>.relativeToRootProject(dir: String) = map {
    rootProject.projectDirectory
        .dir("build")
        .dir(projectDir.toRelativeString(rootDir))
}.map { it.dir(dir) }

// ...

stabilityConfigurationFiles
    .add(rootProject.projectDirectory.file("compose_compiler_config.conf"))

4. 确保依赖版本兼容

检查gradle/libs.versions.toml中以下依赖版本与AGP 9.0.0匹配:

  • AGP版本设为9.0.0
  • Compose Compiler版本设为1.5.4或更高
  • Kotlin版本设为1.9.22或更高

修改后的完整代码

import com.android.build.api.dsl.CommonExtension
import com.android.build.api.dsl.LibraryExtension
import org.gradle.api.Project
import org.gradle.api.Plugin
import org.gradle.api.provider.Provider
import org.gradle.kotlin.dsl.configure
import org.gradle.kotlin.dsl.dependencies
import org.jetbrains.kotlin.compose.compiler.gradle.ComposeCompilerGradlePluginExtension

internal fun Project.configureAndroidCompose(
    commonExtension: CommonExtension,
) {
    commonExtension.run {
        buildFeatures {
            compose = true
        }

        dependencies {
            val bom = libs.findLibrary("androidx-compose-bom").get()
            implementation(platform(bom))
            androidTestImplementation(platform(bom))
            implementation(libs.findLibrary("androidx-compose-ui-tooling"))
            implementation(libs.findLibrary("androidx-compose-ui-tooling-preview"))
            implementation(libs.findLibrary("androidx-compose-runtime"))
            implementation(libs.findLibrary("androidx-compose-foundation"))
            implementation(libs.findLibrary("androidx-compose-material3"))
            debugImplementation(libs.findLibrary("androidx-compose-ui-tooling"))
        }
    }

    extensions.configure<ComposeCompilerGradlePluginExtension> {
        fun Provider<String>.onlyIfTrue() = flatMap { provider { it.takeIf(String::toBoolean) } }
        fun Provider<*>.relativeToRootProject(dir: String) = map {
            rootProject.projectDirectory
                .dir("build")
                .dir(projectDir.toRelativeString(rootDir))
        }.map { it.dir(dir) }

        project.providers.gradleProperty("enableComposeCompilerMetrics").onlyIfTrue()
            .relativeToRootProject("compose-metrics")
            .let(metricsDestination::set)

        project.providers.gradleProperty("enableComposeCompilerReports").onlyIfTrue()
            .relativeToRootProject("compose-reports")
            .let(reportsDestination::set)

        stabilityConfigurationFiles
            .add(rootProject.projectDirectory.file("compose_compiler_config.conf"))
    }
}

class AndroidLibraryComposeConventionPlugin : Plugin<Project> {
    override fun apply(target: Project) {
        with(target) {
            apply(plugin = "com.android.library")
            apply(plugin = "org.jetbrains.kotlin.plugin.compose")

            val extension = extensions.getByType<LibraryExtension>()
            configureAndroidCompose(extension)
        }
    }
}

内容的提问来源于stack exchange,提问作者Cuyer

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.11 15:34:53