Skip to content

Kotlin Gradle 插件中的编译器选项

每个 Kotlin 版本都包含针对受支持目标平台(JVM、JavaScript 和适用于受支持平台的原生二进制文件)的编译器。

这些编译器由以下组件使用:

  • IDE,当您点击 Kotlin 项目的 CompileRun 按钮时。
  • Gradle,当您在控制台或 IDE 中调用 gradle build 时。
  • Maven,当您在控制台或 IDE 中调用 mvn compilemvn test-compile 时。

您也可以按照使用命令行编译器教程中的说明,从命令行手动运行 Kotlin 编译器。

如何定义选项

Kotlin 编译器提供了许多选项,用于定制编译过程。

Gradle DSL 允许对编译器选项进行全面配置。它适用于 Kotlin MultiplatformJVM/Android 项目。

使用 Gradle DSL,您可以在构建脚本中通过三个级别配置编译器选项:

Kotlin compiler options levels

较高级别的设置会作为较低级别的约定(默认值):

  • 在扩展级别设置的编译器选项是目标级别选项的默认值,包括 commonMainnativeMaincommonTest 等共享源代码集。
  • 在目标级别设置的编译器选项是编译单元(任务)级别选项的默认值,例如 compileKotlinJvmcompileTestKotlinJvm 任务。

反之,在较低级别进行的配置会覆盖较高级别的相关设置:

  • 任务级别的编译器选项会覆盖目标级别或扩展级别的相关配置。
  • 目标级别的编译器选项会覆盖扩展级别的相关配置。

要查明哪个级别的编译器实参应用于编译项,请使用 Gradle 日志记录DEBUG 级别。 对于 JVM 和 JS/WASM 任务,在日志中搜索 "Kotlin compiler args:" 字符串;对于 Native 任务,搜索 "Arguments =" 字符串。

如果您是第三方插件作者,最好在项目级别应用配置,以避免出现覆盖问题。您可以为此使用新的 Kotlin 插件 DSL 扩展类型。建议您在您的文档中显式说明此配置。

扩展级别

您可以在顶层的 compilerOptions {} 代码块中为所有目标平台和共享源代码集配置通用编译器选项:

kotlin
kotlin {
    compilerOptions {
        optIn.add("kotlin.RequiresOptIn")
    }
}

目标级别

您可以在 target {} 代码块内部的 compilerOptions {} 代码块中为 JVM/Android 目标平台配置编译器选项:

kotlin
kotlin {
    target { 
        compilerOptions {
            optIn.add("kotlin.RequiresOptIn")
        }
    }
}

在 Kotlin Multiplatform 项目中,您可以在特定目标平台内部配置编译器选项。例如,jvm { compilerOptions {}}。关于更多信息,请参见 Multiplatform Gradle DSL 参考

编译单元级别

您可以在任务配置内部的 compilerOptions {} 代码块中为特定编译单元或任务配置编译器选项:

Kotlin
tasks.named<KotlinJvmCompile>("compileKotlin"){
    compilerOptions {
        optIn.add("kotlin.RequiresOptIn")
    }
}

您还可以通过 KotlinCompilation 在编译单元级别访问并配置编译器选项:

Kotlin
kotlin {
    target {
        val main by compilations.getting {
            compileTaskProvider.configure {
                compilerOptions {
                    optIn.add("kotlin.RequiresOptIn")
                }
            }
        }
    }
}

如果您想配置与 JVM/Android 和 Kotlin Multiplatform 目标平台不同的插件,请使用相应 Kotlin 编译任务的 compilerOptions {} 属性。以下示例展示了如何在 Kotlin 和 Groovy DSL 中设置此配置:

kotlin
tasks.named("compileKotlin", org.jetbrains.kotlin.gradle.tasks.KotlinCompilationTask::class.java) {
    compilerOptions {
        apiVersion.set(org.jetbrains.kotlin.gradle.dsl.KotlinVersion.KOTLIN_2_0)
    }
}
groovy
tasks.named('compileKotlin', org.jetbrains.kotlin.gradle.tasks.KotlinCompilationTask.class) {
    compilerOptions {
        apiVersion.set(org.jetbrains.kotlin.gradle.dsl.KotlinVersion.KOTLIN_2_0)
    }
}

kotlinOptions {} 迁移到 compilerOptions {}

在 Kotlin 2.2.0 之前,您可以使用 kotlinOptions {} 代码块配置编译器选项。由于 kotlinOptions {} 代码块自 Kotlin 2.0.0 起已弃用,本节提供了关于将构建脚本迁移到使用 compilerOptions {} 代码块的指导和建议:

集中管理编译器选项并使用类型

尽可能在扩展级别配置编译器选项,并针对特定任务在编译单元级别覆盖它们。

您不能在 compilerOptions {} 代码块中使用原始字符串,因此请将它们转换为类型化值。例如,如果您有以下代码:

kotlin
plugins {
    kotlin("jvm") version "2.2.10"
}

tasks.withType<KotlinCompile>().configureEach {
    kotlinOptions {
        jvmTarget = "17"
        languageVersion = "2.1"
        apiVersion = "2.1"
    }
}
kotlin
plugins {
    id 'org.jetbrains.kotlin.jvm' version '2.2.10'
}

tasks.withType(KotlinCompile).configureEach {
    kotlinOptions {
        jvmTarget = '17'
        languageVersion = '2.1'
        apiVersion = '2.1'
    }
}

迁移后,应变为:

kotlin
plugins {
    kotlin("jvm") version "2.2.10"
}

kotlin {
    // Extension level
    compilerOptions {
        jvmTarget = JvmTarget.fromTarget("17")
        languageVersion = KotlinVersion.fromVersion("2.1")
        apiVersion = KotlinVersion.fromVersion("2.1")
    }
}

// Example of overriding at compilation unit level
tasks.named<KotlinJvmCompile>("compileKotlin"){
    compilerOptions {
        apiVersion = KotlinVersion.fromVersion("2.1")
    }
}
kotlin
plugins {
    id 'org.jetbrains.kotlin.jvm' version '2.2.10'
}

kotlin {
  // Extension level
    compilerOptions {
        jvmTarget = JvmTarget.fromTarget("17")
        languageVersion = KotlinVersion.fromVersion("2.1")
        apiVersion = KotlinVersion.fromVersion("2.1")
    }
}

// Example of overriding at compilation unit level
tasks.named("compileKotlin", KotlinJvmCompile).configure {
    compilerOptions {
        apiVersion = KotlinVersion.fromVersion("2.1")
    }
}

放弃使用 android.kotlinOptions

如果您的构建脚本之前使用了 android.kotlinOptions,请转而迁移到 kotlin.compilerOptions。这可以在扩展级别或目标级别进行。

例如,如果您有一个 Android 项目:

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

android {
    kotlinOptions {
        jvmTarget = "17"
    }
}
kotlin
plugins {
    id 'com.android.application'
    id 'org.jetbrains.kotlin.android'
}

android {
    kotlinOptions {
        jvmTarget = '17'
    }
}

将其更新为:

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

kotlin {
    compilerOptions {
        jvmTarget = JvmTarget.fromTarget("17")
    }
}
kotlin
plugins {
    id 'com.android.application'
    id 'org.jetbrains.kotlin.android'
}

kotlin {
    compilerOptions {
        jvmTarget = JvmTarget.fromTarget("17")
    }
}

再例如,如果您有一个带 Android 目标平台的 Kotlin Multiplatform 项目:

kotlin
plugins {
    kotlin("multiplatform")
    id("com.android.application")
}

kotlin {
    androidTarget {
        compilations.all {
            kotlinOptions.jvmTarget = "17"
        }
    }
}
kotlin
plugins {
    id 'org.jetbrains.kotlin.multiplatform'
    id 'com.android.application'
}

kotlin {
    androidTarget {
        compilations.all {
            kotlinOptions {
                jvmTarget = '17'
            }
        }
    }
}

将其更新为:

kotlin
plugins {
    kotlin("multiplatform")
    id("com.android.application")
}

kotlin {
    androidTarget {
        compilerOptions {
            jvmTarget = JvmTarget.fromTarget("17")
        }
    }
}
kotlin
plugins {
    id 'org.jetbrains.kotlin.multiplatform'
    id 'com.android.application'
}

kotlin {
    androidTarget {
        compilerOptions {
            jvmTarget = JvmTarget.fromTarget("17")
        }
    }
}

迁移 freeCompilerArgs

  • 将所有 += 操作替换为 add()addAll() 函数。

  • 如果您使用 -opt-in 编译器选项,请检查 KGP API 参考中是否已有专用 DSL,并转而使用它。

  • 迁移任何 -progressive 编译器选项的使用,转而使用专用 DSL:progressiveMode.set(true)

  • 迁移任何 -Xjvm-default 编译器选项的使用,转而使用专用 DSLjvmDefault.set()。使用以下选项映射:

    BeforeAfter
    -Xjvm-default=all-compatibilityjvmDefault.set(JvmDefaultMode.ENABLE)
    -Xjvm-default=alljvmDefault.set(JvmDefaultMode.NO_COMPATIBILITY)
    -Xjvm-default=disablejvmDefault.set(JvmDefaultMode.DISABLE)

例如,如果您有以下代码:

kotlin
kotlinOptions {
    freeCompilerArgs += "-opt-in=kotlin.RequiresOptIn"
    freeCompilerArgs += listOf("-Xcontext-receivers", "-Xinline-classes", "-progressive", "-Xjvm-default=all")
}
kotlin
kotlinOptions {
    freeCompilerArgs += "-opt-in=kotlin.RequiresOptIn"
    freeCompilerArgs += ["-Xcontext-receivers", "-Xinline-classes", "-progressive", "-Xjvm-default=all"]
}

迁移到:

kotlin
kotlin {
    compilerOptions {
        optIn.add("kotlin.RequiresOptIn")
        freeCompilerArgs.addAll(listOf("-Xcontext-receivers", "-Xinline-classes"))
        progressiveMode.set(true)
        jvmDefault.set(JvmDefaultMode.NO_COMPATIBILITY)
    }
}
kotlin
kotlin {
    compilerOptions {
        optIn.add("kotlin.RequiresOptIn")
        freeCompilerArgs.addAll(["-Xcontext-receivers", "-Xinline-classes"])
        progressiveMode.set(true)
        jvmDefault.set(JvmDefaultMode.NO_COMPATIBILITY)
    }
}

面向 JVM 目标平台

如前所述,您可以为 JVM/Android 项目在扩展、目标和编译单元级别(任务)定义编译器选项。

默认的 JVM 编译任务是用于生产代码的 compileKotlin 和用于测试代码的 compileTestKotlin。自定义源代码集的任务则根据其 compile<Name>Kotlin 模式命名。

您可以通过在终端中运行 gradlew tasks --all 命令,并在 Other tasks 组中搜索 compile*Kotlin 任务名称来查看 Android 编译任务列表。

一些需要注意的重要细节:

  • kotlin.compilerOptions 配置项目中的每个 Kotlin 编译任务。
  • 您可以使用 tasks.named<KotlinJvmCompile>("compileKotlin") { }(或 tasks.withType<KotlinJvmCompile>().configureEach { })方法,覆盖由 kotlin.compilerOptions DSL 应用的配置。

面向 JavaScript 目标平台

JavaScript 编译任务是用于生产代码的 compileKotlinJs、用于测试代码的 compileTestKotlinJs,以及用于自定义源代码集的 compile<Name>KotlinJs

要配置单个任务,请使用其名称:

kotlin
import org.jetbrains.kotlin.gradle.tasks.KotlinCompilationTask
// ...

val compileKotlin: KotlinCompilationTask<*> by tasks

compileKotlin.compilerOptions.suppressWarnings.set(true)
groovy
import org.jetbrains.kotlin.gradle.tasks.KotlinCompilationTask
// ...

tasks.named('compileKotlin', KotlinCompilationTask) {
    compilerOptions {
        suppressWarnings = true
    }
}

请注意,使用 Gradle Kotlin DSL 时,您应该首先从项目的 tasks 获取任务。

对于 JS 和公共目标平台,请分别使用 Kotlin2JsCompileKotlinCompileCommon 类型。

您可以通过在终端中运行 gradlew tasks --all 命令,并在 Other tasks 组中搜索 compile*KotlinJS 任务名称来查看 JavaScript 编译任务列表。

所有 Kotlin 编译任务

还可以配置项目中的所有 Kotlin 编译任务:

kotlin
import org.jetbrains.kotlin.gradle.tasks.KotlinCompilationTask
// ...

tasks.named<KotlinCompilationTask<*>>("compileKotlin").configure {
    compilerOptions { /*...*/ }
}
groovy
import org.jetbrains.kotlin.gradle.tasks.KotlinCompilationTask
// ...

tasks.named('compileKotlin', KotlinCompilationTask) {
    compilerOptions { /*...*/ }
}

所有编译器选项

以下是 Gradle 编译器的完整选项列表:

通用属性

名称描述可能值默认值
optIn用于配置 opt-in 编译器实参列表的属性listOf( /* opt-ins */ )emptyList()
progressiveMode启用渐进式编译模式true, falsefalse
extraWarnings启用额外的声明、表达式和类型编译器检测,如果为 true 则发出警告true, falsefalse

JVM 特有的属性

名称描述可能值默认值
javaParameters为 Java 1.8 方法形参的反射生成元数据false
jvmTarget生成的 JVM 字节码的目标版本"1.8", "9", "10", ..., "23", "24"。另外,关于编译器选项的类型请参见相关内容"1.8"
noJdk不要自动将 Java 运行时包含到类路径中false
jvmTargetValidationModeWARNING, ERROR, IGNOREERROR
jvmDefault控制在接口中声明的函数如何在 JVM 上编译为默认方法ENABLE, NO_COMPATIBILITY, DISABLEENABLE

JVM 和 JavaScript 通用的属性

名称描述可能值默认值
allWarningsAsErrors如果有任何警告则报告错误false
suppressWarnings不生成警告false
verbose启用详细日志输出。仅当启用 Gradle 调试日志级别时有效false
freeCompilerArgs额外的编译器实参列表。您也可以在此处使用实验性的 -X 实参。关于示例请参见通过 freeCompilerArgs 使用额外实参的示例[]
apiVersion将声明的使用限制为来自指定版本捆绑库中的声明"1.8", "1.9", "2.0", "2.1", "2.2" (实验性的)
languageVersion提供与指定版本 Kotlin 的源代码兼容性"1.8", "1.9", "2.0", "2.1", "2.2" (实验性的)

我们将在未来版本中弃用 freeCompilerArgs 属性。如果您发现 Kotlin Gradle DSL 中缺少某些选项,请提交一个问题

通过 freeCompilerArgs 使用额外实参的示例

使用 freeCompilerArgs 属性提供额外(包括实验性)的编译器实参。您可以向此属性添加单个实参或实参列表:

kotlin
import org.jetbrains.kotlin.gradle.tasks.KotlinCompilationTask
// ...

kotlin {
    compilerOptions {
        // Specifies the version of the Kotlin API and the JVM target
        apiVersion.set(KotlinVersion.KOTLIN_2_1)
        jvmTarget.set(JvmTarget.JVM_1_8)
        
        // Single experimental argument
        freeCompilerArgs.add("-Xexport-kdoc")

        // Single additional argument
        freeCompilerArgs.add("-Xno-param-assertions")

        // List of arguments
        freeCompilerArgs.addAll(
            listOf(
                "-Xno-receiver-assertions",
                "-Xno-call-assertions"
            )
        ) 
    }
}
groovy
import org.jetbrains.kotlin.gradle.tasks.KotlinCompilationTask
// ...

tasks.named('compileKotlin', KotlinCompilationTask) {
    compilerOptions {
        // Specifies the version of the Kotlin API and the JVM target
        apiVersion = KotlinVersion.KOTLIN_2_1
        jvmTarget = JvmTarget.JVM_1_8
        
        // Single experimental argument
        freeCompilerArgs.add("-Xexport-kdoc")
        
        // Single additional argument, can be a key-value pair
        freeCompilerArgs.add("-Xno-param-assertions")
        
        // List of arguments
        freeCompilerArgs.addAll(["-Xno-receiver-assertions", "-Xno-call-assertions"])
    }
}

freeCompilerArgs 属性可在扩展目标编译单元(任务)级别使用。

设置 languageVersion 的示例

要设置语言版本,请使用以下语法:

kotlin
kotlin {
    compilerOptions {
        languageVersion.set(org.jetbrains.kotlin.gradle.dsl.KotlinVersion.KOTLIN_2_1)
    }
}
groovy
tasks
    .withType(org.jetbrains.kotlin.gradle.tasks.KotlinCompilationTask.class)
    .configureEach {
        compilerOptions.languageVersion =
            org.jetbrains.kotlin.gradle.dsl.KotlinVersion.KOTLIN_2_1
    }

另外,关于编译器选项的类型请参见相关内容。

JavaScript 特有的属性

名称描述可能值默认值
friendModulesDisabled禁用内部声明导出false
main指定在执行时是否应调用 main 函数JsMainFunctionExecutionMode.CALL, JsMainFunctionExecutionMode.NO_CALLJsMainFunctionExecutionMode.CALL
moduleKind编译器生成的 JS 模块类型JsModuleKind.MODULE_AMD, JsModuleKind.MODULE_PLAIN, JsModuleKind.MODULE_ES, JsModuleKind.MODULE_COMMONJS, JsModuleKind.MODULE_UMDnull
sourceMap生成源映射false
sourceMapEmbedSources将源文件嵌入到源映射中JsSourceMapEmbedMode.SOURCE_MAP_SOURCE_CONTENT_INLINING, JsSourceMapEmbedMode.SOURCE_MAP_SOURCE_CONTENT_NEVER, JsSourceMapEmbedMode.SOURCE_MAP_SOURCE_CONTENT_ALWAYSnull
sourceMapNamesPolicy将您在 Kotlin 代码中声明的变量和函数名称添加到源映射中。关于行为的更多信息,请参见我们的编译器参考JsSourceMapNamesPolicy.SOURCE_MAP_NAMES_POLICY_FQ_NAMES, JsSourceMapNamesPolicy.SOURCE_MAP_NAMES_POLICY_SIMPLE_NAMES, JsSourceMapNamesPolicy.SOURCE_MAP_NAMES_POLICY_NOnull
sourceMapPrefix将指定的前缀添加到源映射中的路径null
target为特定 ECMA 版本生成 JS 文件"es5", "es2015""es5"
useEsClasses让生成的 JavaScript 代码使用 ES2015 类。在 ES2015 目标平台使用的情况下默认启用null

编译器选项的类型

compilerOptions 中的一些选项使用新类型而不是 String 类型:

选项类型示例
jvmTargetJvmTargetcompilerOptions.jvmTarget.set(JvmTarget.JVM_11)
apiVersionlanguageVersionKotlinVersioncompilerOptions.languageVersion.set(KotlinVersion.KOTLIN_2_1)
mainJsMainFunctionExecutionModecompilerOptions.main.set(JsMainFunctionExecutionMode.NO_CALL)
moduleKindJsModuleKindcompilerOptions.moduleKind.set(JsModuleKind.MODULE_ES)
sourceMapEmbedSourcesJsSourceMapEmbedModecompilerOptions.sourceMapEmbedSources.set(JsSourceMapEmbedMode.SOURCE_MAP_SOURCE_CONTENT_INLINING)
sourceMapNamesPolicyJsSourceMapNamesPolicycompilerOptions.sourceMapNamesPolicy.set(JsSourceMapNamesPolicy.SOURCE_MAP_NAMES_POLICY_FQ_NAMES)

接下来是什么?

了解更多关于: