Skip to content

Kotlin 1.9 兼容性指南

保持语言现代化舒适的更新 是 Kotlin 语言设计的核心原则。前者指出,阻碍语言演进的构造应被移除;后者指出,此移除应提前充分沟通,以使代码迁移尽可能顺畅。

虽然大多数语言更改已通过其他渠道(例如更新日志或编译器警告)公布,但本文档将它们全部汇总,为从 Kotlin 1.8 迁移到 Kotlin 1.9 提供完整的参考。

基本术语

本文档介绍了几种兼容性:

  • sourcesource(源代码)不兼容性变更会使原本可以正常编译(无错误或警告)的代码不再能够编译
  • binary:如果两个二进制 artifact 相互替换不会导致加载或链接错误,则称它们是 binary(二进制)兼容的
  • behavioral:如果同一程序在应用更改前后表现出不同行为,则称该更改是 behavioral(行为)不兼容的

请记住,这些定义仅适用于纯 Kotlin。从其他语言视角(例如 Java)看 Kotlin 代码的兼容性不在本文档的作用域内。

语言

移除语言版本 1.3

Issue: KT-61111

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.9 引入了语言版本 1.9 并移除了对语言版本 1.3 的支持。

Deprecation cycle:

  • 1.6.0: 报告警告
  • 1.9.0: 将警告提升为错误

禁止当超接口类型为函数字面值时调用超类构造函数

Issue: KT-46344

Component: Core language

Incompatible change type: source

Short summary: 如果接口继承自函数字面值类型,Kotlin 1.9 会禁止调用超类构造函数,因为不存在此类构造函数。

Deprecation cycle:

  • 1.7.0: 报告警告(或在渐进模式下报告错误)
  • 1.9.0: 将警告提升为错误

禁止注解形参类型中的循环

Issue: KT-47932

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.9 禁止注解的类型直接或间接地用作其 parameter 类型之一。这可以防止创建循环。但是,允许 parameter 类型为该注解类型的 Arrayvararg

Deprecation cycle:

  • 1.7.0: 报告关于注解 parameter 类型中循环的警告(或在渐进模式下报告错误)
  • 1.9.0: 将警告提升为错误,可以使用 -XXLanguage:-ProhibitCyclesInAnnotations 暂时恢复到 1.9 之前的行为

禁止在无形参的函数类型上使用 @ExtensionFunctionType 注解

Issue: KT-43527

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.9 禁止在无形参函数类型上,或在非函数类型上使用 @ExtensionFunctionType 注解。

Deprecation cycle:

  • 1.7.0: 报告关于非函数类型注解的警告,报告关于函数类型的注解的错误
  • 1.9.0: 将关于函数类型的警告提升为错误

禁止 Java 字段类型在赋值时不匹配

Issue: KT-48994

Component: Kotlin/JVM

Incompatible change type: source

Short summary: 如果检测到赋值给 Java field 的值的类型与 Java field 的投影类型不匹配,Kotlin 1.9 会报告编译器错误。

Deprecation cycle:

  • 1.6.0: 当投影的 Java field 类型与赋值的值类型不匹配时,报告警告(或在渐进模式下报告错误)
  • 1.9.0: 将警告提升为错误,可以使用 -XXLanguage:-RefineTypeCheckingOnAssignmentsToJavaFields 暂时恢复到 1.9 之前的行为

平台类型空安全断言异常中不包含源代码摘录

Issue: KT-57570

Component: Kotlin/JVM

Incompatible change type: behavioral

Short summary: 在 Kotlin 1.9 中,表达式空检测的异常消息不包含源代码摘录。取而代之的是,会显示方法字段的名称。如果表达式不是方法字段,则消息中不提供额外信息。

Deprecation cycle:

  • < 1.9.0: 表达式空检测生成的异常消息包含源代码摘录
  • 1.9.0: 表达式空检测生成的异常消息仅包含方法字段名称,可以使用 -XXLanguage:-NoSourceCodeInNotNullAssertionExceptions 暂时恢复到 1.9 之前的行为

禁止将超类调用委托给抽象超类成员

Issues: KT-45508, KT-49017, KT-38078

Component: Core language

Incompatible change type: source

Short summary: Kotlin 将报告编译错误,当显式或隐式超类调用委托给超类的 抽象 成员时,即使超接口中存在默认实现。

Deprecation cycle:

  • 1.5.20: 引入警告,当使用未覆盖所有抽象成员的非抽象类时
  • 1.7.0: 如果超类调用实际上访问了超类中的抽象成员,则报告警告
  • 1.7.0: 如果启用了 -Xjvm-default=all-Xjvm-default=all-compatibility 兼容模式,则在所有受影响的情况下报告错误;在渐进模式下报告错误
  • 1.8.0: 报告在声明具有超类中未覆盖的抽象方法的具象类,以及超类中 Any 方法的超类调用被覆盖为抽象的情况下的错误
  • 1.9.0: 在所有受影响的情况下报告错误,包括对超类中抽象方法的显式超类调用

废弃 when 表达式中令人混淆的语法

Issue: KT-48385

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.6 废弃when 条件表达式中几个令人混淆的语法构造。

Deprecation cycle:

  • 1.6.20: 对受影响的表达式引入废弃警告
  • 1.8.0: 将此警告提升为错误,-XXLanguage:-ProhibitConfusingSyntaxInWhenBranches 可用于暂时恢复到 1.8 之前的行为
  • = 2.1: 将一些废弃的构造重新用于新的语言特性

阻止不同数字类型之间的隐式强制转换

Issue: KT-48645

Component: Kotlin/JVM

Incompatible change type: behavioral

Short summary: Kotlin 将避免将数字值自动转换为原语数字类型,而仅在语义上需要向下转型为该类型的情况下才进行转换。

Deprecation cycle:

  • < 1.5.30: 在所有受影响的情况下的旧行为
  • 1.5.30: 构建的属性委托访问器中向下转型行为的修复,-Xuse-old-backend 可用于暂时恢复到 1.5.30 修复之前的行为
  • = 2.0: 在其他受影响的情况下修复向下转型行为

禁止泛型类型别名使用中的上界违例(在别名类型的类型实参的泛型类型实参中使用的类型形参

Issue: KT-54066

Component: Core language

Incompatible change type: source

Short summary: Kotlin 将禁止使用带有类型实参的类型别名,这些实参违反了别名类型相应类型形参上界限制,当类型别名类型形参用作别名类型的类型实参的泛型类型实参时,例如 typealias Alias<T> = Base<List<T>>

Deprecation cycle:

  • 1.8.0: 当泛型类型别名使用中的类型实参违反了别名类型相应类型形参上界约束时,报告警告
  • 2.0.0: 将警告提升为错误

在公共签名中近似局部类型时保持可空性

Issue: KT-53982

Component: Core language

Incompatible change type: source, binary

Short summary: 当局部或匿名类型从没有显式指定返回类型的表达式函数返回时,Kotlin 编译器会使用该类型的已知超类型来推断(或近似)返回类型。在此过程中,编译器可能会推断非空的类型,而实际上可能返回 null 值。

Deprecation cycle:

  • 1.8.0: 通过 flexible 超类型近似 flexible 类型
  • 1.8.0: 当声明推断为应可空却为非空类型时,报告警告,提示用户显式指定类型
  • 2.0.0: 通过可空超类型近似可空类型,-XXLanguage:-KeepNullabilityWhenApproximatingLocalType 可用于暂时恢复到 2.0 之前的行为

不通过覆盖传播废弃状态

Issue: KT-47902

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.9 将不再将废弃状态从超类中已废弃的成员传播到子类中其覆盖的成员,从而为废弃超类成员同时使其在子类中不被废弃提供了显式机制。

Deprecation cycle:

  • 1.6.20: 报告带有未来行为更改消息的警告,并提示要么抑制此警告,要么在已废弃成员的覆盖处显式写入 @Deprecated 注解
  • 1.9.0: 停止向被覆盖的成员传播废弃状态。此更改也会立即在渐进模式下生效

禁止在注解类中除其形参``声明之外的任何地方使用集合字面值

Issue: KT-39041

Component: Core language

Incompatible change type: source

Short summary: Kotlin 允许以受限方式使用集合字面值——用于将数组传递给注解类的形参或为此类形参指定默认值。然而除此之外,Kotlin 允许在注解类内部的任何其他地方使用集合字面值,例如在其嵌套对象中。Kotlin 1.9 将禁止在注解类中除其形参的默认值之外的任何地方使用集合字面值。

Deprecation cycle:

  • 1.7.0: 报告关于注解类中嵌套对象中数组字面值的警告(或在渐进模式下报告错误)
  • 1.9.0: 将警告提升为错误

禁止在默认值表达式中向前引用形参

Issue: KT-25694

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.9 将禁止在其他形参的默认值表达式中向前引用形参。这确保了在形参被默认值表达式访问时,它已经通过函数传递了值或通过其自身的默认值表达式初始化了值。

Deprecation cycle:

  • 1.7.0: 当带有默认值的形参在它之前的另一个形参的默认值中被引用时,报告警告(或在渐进模式下报告错误)
  • 1.9.0: 将警告提升为错误,-XXLanguage:-ProhibitIllegalValueParameterUsageInDefaultArguments 可用于暂时恢复到 1.9 之前的行为

禁止对内联函数``形参进行扩展调用

Issue: KT-52502

Component: Core language

Incompatible change type: source

Short summary: 尽管 Kotlin 允许将内联函数``形参作为接收者传递给另一个内联函数,但编译此类代码块时总是导致编译器异常。Kotlin 1.9 将禁止此行为,从而报告错误而不是导致编译器崩溃。

Deprecation cycle:

  • 1.7.20: 报告关于内联函数``形参上的内联扩展调用的警告(或在渐进模式下报告错误)
  • 1.9.0: 将警告提升为错误

禁止调用名为 suspend 且带有匿名函数``实参中缀函数

Issue: KT-49264

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.9 将不再允许调用名为 suspend 且带有一个作为匿名函数字面值传递的函数``类型``实参中缀函数

Deprecation cycle:

  • 1.7.20: 报告关于 suspend 中缀函数调用(带匿名函数字面值)的警告
  • 1.9.0: 将警告提升为错误,-XXLanguage:-ModifierNonBuiltinSuspendFunError 可用于暂时恢复到 1.9 之前的行为
  • TODO: 更改解析器解释 suspend fun 令牌序列的方式

禁止在内部类中违背型变规则使用捕获的类型形参

Issue: KT-50947

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.9 将禁止在该类的内部类中,在违反该类型形参``声明型变规则的位置使用具有 inout 型变的外部类的类型形参

Deprecation cycle:

  • 1.7.0: 当外部类的类型形参使用位置违反该形参型变规则时,报告警告(或在渐进模式下报告错误)
  • 1.9.0: 将警告提升为错误,-XXLanguage:-ReportTypeVarianceConflictOnQualifierArguments 可用于暂时恢复到 1.9 之前的行为

禁止在复合赋值操作符中递归调用无显式返回类型的函数

Issue: KT-48546

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.9 将禁止在函数体内部的复合赋值``操作符``实参中调用无显式返回类型的函数,就像它目前在该函数体内部的其他表达式中那样。

Deprecation cycle:

  • 1.7.0: 当无显式返回类型的函数在该函数体内部的复合赋值``操作符``实参中被递归调用时,报告警告(或在渐进模式下报告错误)
  • 1.9.0: 将警告提升为错误

禁止 expected @NotNull Tgiven Kotlin generic parameter with nullable bound 之间不健全的调用

Issue: KT-36770

Component: Kotlin/JVM

Incompatible change type: source

Short summary: Kotlin 1.9 将禁止方法调用,当将潜在可空泛型类型的值传递给 Java 方法@NotNull 注解形参时。

Deprecation cycle:

  • 1.5.20: 当将无约束的泛型类型形参传递给预期为非空类型的位置时,报告警告
  • 1.9.0: 报告类型不匹配错误而非上述警告,-XXLanguage:-ProhibitUsingNullableTypeParameterAgainstNotNullAnnotated 可用于暂时恢复到 1.8 之前的行为

禁止在枚举类的条目初始化器中访问枚举伴生对象成员

Issue: KT-49110

Component: Core language

Incompatible change type: source

Short summary: Kotlin 1.9 将禁止从枚举条目初始化器中对枚举``伴生对象的所有类型访问。

Deprecation cycle:

  • 1.6.20: 报告关于此类伴生对象成员访问的警告(或在渐进模式下报告错误)
  • 1.9.0: 将警告提升为错误,-XXLanguage:-ProhibitAccessToEnumCompanionMembersInEnumConstructorCall 可用于暂时恢复到 1.8 之前的行为

废弃并移除 Enum.declaringClass 合成属性

Issue: KT-49653

Component: Kotlin/JVM

Incompatible change type: source

Short summary: Kotlin 允许对从底层 Java 类 java.lang.EnumgetDeclaringClass() 方法生成的 Enum 值使用合成属性 declaringClass,即使此方法对 Kotlin Enum 类型不可用。Kotlin 1.9 将禁止使用此属性,建议迁移到扩展属性 declaringJavaClass

Deprecation cycle:

  • 1.7.0: 报告关于 declaringClass 属性用法的警告(或在渐进模式下报告错误),建议迁移到 declaringJavaClass 扩展
  • 1.9.0: 将警告提升为错误,-XXLanguage:-ProhibitEnumDeclaringClass 可用于暂时恢复到 1.9 之前的行为
  • 2.0.0: 移除 declaringClass 合成属性

废弃 编译器选项 -Xjvm-defaultenablecompatibility 模式

Issues: KT-46329, KT-54746

Component: Kotlin/JVM

Incompatible change type: source

Short summary: Kotlin 1.9 禁止使用 编译器选项 -Xjvm-defaultenablecompatibility 模式。

Deprecation cycle:

  • 1.6.20: 对 编译器选项 -Xjvm-defaultenablecompatibility 模式引入警告
  • 1.9.0: 将此警告提升为错误

禁止在构建器``推断上下文的上界中隐式推断类型变量

Issue: KT-47986

Component: Core language

Incompatible change type: source

Short summary: Kotlin 2.0 将禁止在构建器``推断 lambda 表达式作用域中,在没有任何使用点类型信息的情况下,将类型变量推断为相应类型形参上界,其方式与当前在其他上下文中的方式相同。

Deprecation cycle:

  • 1.7.20: 当在没有使用点类型信息的情况下,类型形参推断声明上界时,报告警告(或在渐进模式下报告错误)
  • 2.0.0: 将警告提升为错误

标准库

Range/Progression 实现 Collection 时警告潜在的重载决议更改

Issue: KT-49276

Component: Core language / kotlin-stdlib

Incompatible change type: source

Short summary: 计划在 Kotlin 1.9 中在标准数列和从它们继承的具体区间中实现 Collection 接口。如果某个方法有两个重载,一个接受元素,另一个接受集合,这可能会导致在重载决议中选择不同的重载。当使用区间数列``实参调用此类重载``方法时,Kotlin 将通过报告警告或错误来使这种情况可见。

Deprecation cycle:

  • 1.6.20: 当重载``方法以标准数列或其区间``继承者作为实参调用时,如果此数列/区间实现 Collection 接口导致将来在此调用中选择另一个重载,则报告警告
  • 1.8.0: 将此警告提升为错误
  • 2.1.0: 停止报告错误,在数列中实现 Collection 接口,从而更改受影响情况下的重载决议结果

kotlin.domkotlin.browser 包中的声明迁移到 kotlinx.*

Issue: KT-39330

Component: kotlin-stdlib (JS)

Incompatible change type: source

Short summary: kotlin.domkotlin.browser 包中的声明已移至相应的 kotlinx.* 包,以准备将其从标准库中提取。

Deprecation cycle:

  • 1.4.0: 在 kotlinx.domkotlinx.browser 包中引入替代 API
  • 1.4.0: 废弃 kotlin.domkotlin.browser 包中的 API 并建议使用上述新 API 作为替代
  • 1.6.0: 将废弃级别提升为错误
  • 1.8.20: 为 JS-IR target 从标准库中移除废弃函数
  • = 2.0: 将 kotlinx.* 包中的 API 移至单独的库

废弃一些仅限 JS 的 API

Issue: KT-48587

Component: kotlin-stdlib (JS)

Incompatible change type: source

Short summary: 标准库中一些仅限 JS 的函数废弃以备移除。它们包括:String.concat(String)String.match(regex: String)String.matches(regex: String),以及接受比较函数的数组排序函数,例如 Array<out T>.sort(comparison: (a: T, b: T) -> Int)

Deprecation cycle:

  • 1.6.0: 废弃受影响的函数并发出警告
  • 1.9.0: 将废弃级别提升为错误
  • =2.0: 从公共 API 中移除废弃函数

工具

从 Gradle 设置中移除 enableEndorsedLibs 标志

Issue: KT-54098

Component: Gradle

Incompatible change type: source

Short summary: Gradle 设置不再支持 enableEndorsedLibs 标志。

Deprecation cycle:

  • < 1.9.0: Gradle 设置支持 enableEndorsedLibs 标志
  • 1.9.0: Gradle 设置支持 enableEndorsedLibs 标志

移除 Gradle 约定

Issue: KT-52976

Component: Gradle

Incompatible change type: source

Short summary: Gradle 约定已在 Gradle 7.1 中废弃,并已在 Gradle 8 中移除。

Deprecation cycle:

  • 1.7.20: Gradle 约定已废弃
  • 1.9.0: Gradle 约定已移除

移除 KotlinCompile 任务classpath 属性

Issue: KT-53748

Component: Gradle

Incompatible change type: source

Short summary: KotlinCompile 任务classpath 属性已移除。

Deprecation cycle:

  • 1.7.0: classpath 属性已废弃
  • 1.8.0: 将废弃级别提升为错误
  • 1.9.0: 从公共 API 中移除废弃函数

废弃 kotlin.internal.single.build.metrics.file 属性

Issue: KT-53357

Component: Gradle

Incompatible change type: source

Short summary: 废弃用于定义单个文件构建报告的 kotlin.internal.single.build.metrics.file 属性。请改用 kotlin.build.report.single_file 属性并设置 kotlin.build.report.output=single_file

Deprecation cycle:

  • 1.8.0: 将废弃级别提升为警告
  • = 1.9: 删除该属性