Kotlin 2.1 的兼容性指南
Keeping the Language Modern and Comfortable Updates are among the fundamental principles in Kotlin Language Design. The former says that constructs which obstruct language evolution should be removed, and the latter says that this removal should be well-communicated beforehand to make code migration as smooth as possible.
While most of the language changes were already announced through other channels, like update changelogs or compiler warnings, this document summarizes them all, providing a complete reference for migration from Kotlin 2.0 to Kotlin 2.1.
Basic terms
In this document we introduce several kinds of compatibility:
- source: source-incompatible change stops code that used to compile fine (without errors or warnings) from compiling anymore
- binary: two binary artifacts are said to be binary-compatible if interchanging them doesn't lead to loading or linkage errors
- behavioral: a change is said to be behavioral-incompatible if the same program demonstrates different behavior before and after applying the change
Remember that those definitions are given only for pure Kotlin. Compatibility of Kotlin code from the other languages perspective (for example, from Java) is out of the scope of this document.
Language
Remove language versions 1.4 and 1.5
Issue: KT-60521
Component: Core language
Incompatible change type: source
Short summary: Kotlin 2.1 introduces language version 2.1 and removes support for language versions 1.4 and 1.5. Language versions 1.6 and 1.7 are deprecated.
Deprecation cycle:
- 1.6.0: report a warning for language version 1.4
- 1.9.0: report a warning for language version 1.5
- 2.1.0: report a warning for language versions 1.6 and 1.7; raise the warning to an error for language versions 1.4 and 1.5
Change the typeOf() function behavior on Kotlin/Native
Issue: KT-70754
Component: Core language
Incompatible change type: behavioral
Short summary: The behavior of the
typeOf()function on Kotlin/Native is aligned with Kotlin/JVM to ensure consistency across platforms.Deprecation cycle:
- 2.1.0: align the
typeOf()function behavior on Kotlin/Native
Prohibit exposing types through type parameters' bounds
Issue: KT-69653
Component: Core language
Incompatible change type: source
Short summary: Exposing types with lower visibility through type parameter bounds is now prohibited, addressing inconsistencies in type visibility rules. This change ensures that bounds on type parameters follow the same visibility rules as classes, preventing issues like IR validation errors in the JVM.
Deprecation cycle:
- 2.1.0: report a warning for exposing types via type parameter bounds with lower visibility
- 2.2.0: raise the warning to an error
Prohibit inheriting an abstract var property and a val property with the same name
Issue: KT-58659
Component: Core language
Incompatible change type: source
Short summary: If a class inherits an abstract
varproperty from an interface and avalproperty with the same name from a superclass, it now triggers a compilation error. This resolves runtime crashes caused by missing setters in such cases.Deprecation cycle:
- 2.1.0: report a warning (or an error in progressive mode) when a class inherits an abstract
varproperty from an interface and avalproperty with the same name from a superclass- 2.2.0: raise the warning to an error
Report error when accessing uninitialized enum entries
Issue: KT-68451
Component: Core language
Incompatible change type: source
Short summary: The compiler now reports an error when uninitialized enum entries are accessed during enum class or entry initialization. This aligns the behavior with member property initialization rules, preventing runtime exceptions and ensuring consistent logic.
Deprecation cycle:
- 2.1.0: report an error when accessing uninitialized enum entries
Changes in K2 smart cast propagation
Issue: KTLC-34
Component: Core language
Incompatible change type: behavioral
Short summary: The K2 compiler changes its behavior for smart cast propagation by introducing bidirectional propagation of type information for inferred variables, like
val x = y. Explicitly typed variables, such asval x: T = y, no longer propagate type information, ensuring stricter adherence to declared types.Deprecation cycle:
- 2.1.0: enable the new behavior
Correct the handling of member-extension property overrides in Java subclasses
Issue: KTLC-35
Component: Core language
Incompatible change type: behavioral
Short summary: The getter for member-extension properties overridden by Java subclasses is now hidden in the subclass's scope, aligning its behavior with that of regular Kotlin properties.
Deprecation cycle:
- 2.1.0: enable the new behavior
Correct visibility alignment for getters and setters of var properties overriding a protected val
Issue: KTLC-36
Component: Core language
Incompatible change type: binary
Short summary: The visibility of getters and setters for
varproperties overriding aprotected valproperty is now consistent, with both inheriting the visibility of the overriddenvalproperty.Deprecation cycle:
- 2.1.0: enforce consistent visibility for both getters and setters in K2; K1 remains unaffected
Raise severity of JSpecify nullability mismatch diagnostics to errors
Issue: KTLC-11
Component: Core language
Incompatible change type: source
Short summary: Nullability mismatches from
org.jspecify.annotations, such as@NonNull,@Nullable, and@NullMarkedare now treated as errors instead of warnings, enforcing stricter type safety for Java interoperability. To adjust the severity of these diagnostics, use the-Xnullability-annotationscompiler option.Deprecation cycle:
- 1.6.0: report warnings for potential nullability mismatches
- 1.8.20: expand warnings to specific JSpecify annotations, including:
@Nullable,@NullnessUnspecified,@NullMarked, and legacy annotations inorg.jspecify.nullness(JSpecify 0.2 and earlier)- 2.0.0: add support for the
@NonNullannotation- 2.1.0: change default mode to
strictfor JSpecify annotations, converting warnings into errors; use[email protected]:warningor[email protected]:ignoreto override the default behavior
Change overload resolution to prioritize extension functions over invoke calls in ambiguous cases
Issue: KTLC-37
Component: Core language
Incompatible change type: behavioral
Short summary: Overload resolution now consistently prioritizes extension functions over invoke calls in ambiguous cases. This resolves inconsistencies in the resolution logic for local functions and properties. The change applies only after recompilation, without affecting precompiled binaries.
Deprecation cycle:
- 2.1.0: change overload resolution to consistently prioritize extension functions over
invokecalls for extension functions with matching signatures; this change applies only after recompilation and does not affect precompiled binaries
Prohibit returning nullable values from lambdas in SAM constructors of JDK function interfaces
Issue: KTLC-42
Component: Core language
Incompatible change type: source
Short summary: Returning nullable values from lambdas in SAM constructors of JDK function interfaces now triggers a compilation error if the specified type argument is non-nullable. This resolves issues where nullability mismatches could lead to runtime exceptions, ensuring stricter type safety.
Deprecation cycle:
- 2.0.0: report a deprecation warning for nullable return values in SAM constructors of JDK function interfaces
- 2.1.0: enable the new behavior by default
Correct handling of private members conflicting with public members in Kotlin/Native
Issue: KTLC-43
Component: Core language
Incompatible change type: behavioral
Short summary: In Kotlin/Native, private members no longer override or conflict with public members in a superclass, aligning behavior with Kotlin/JVM. This resolves inconsistencies in override resolution and eliminates unexpected behavior caused by separate compilation.
Deprecation cycle:
- 2.1.0: private functions and properties in Kotlin/Native no longer override or affect public members in a superclass, aligning with JVM behavior
Forbid access to private operator functions in public inline functions
Issue: KTLC-71
Component: Core language
Incompatible change type: source
Short summary: Private operator functions such as
getValue(),setValue(),provideDelegate(),hasNext(), andnext()can no longer be accessed in public inline functions.Deprecation cycle:
- 2.0.0: report a deprecation warning for accessing private operator functions in public inline functions
- 2.1.0: raise the warning to an error
Prohibit passing invalid arguments to invariant parameters annotated with @UnsafeVariance
Issue: KTLC-72
Component: Core language
Incompatible change type: source
Short summary: The compiler now ignores
@UnsafeVarianceannotations during type checks, enforcing stricter type safety for invariant type parameters. This prevents invalid calls that rely on@UnsafeVarianceto bypass expected type checks.Deprecation cycle:
- 2.1.0: activate the new behavior
Report nullability errors for error-level nullable arguments of warning-level Java types
Issue: KTLC-100
Component: Core language
Incompatible change type: source
Short summary: The compiler now detects nullability mismatches in Java methods where a warning-level nullable type contains type arguments with stricter, error-level nullability. This ensures that previously ignored errors in type arguments are reported correctly.
Deprecation cycle:
- 2.0.0: report a deprecation warning for nullability mismatches in Java methods with stricter type arguments
- 2.1.0: raise the warning to an error
Report implicit usages of inaccessible types
Issue: KTLC-3
Component: Core language
Incompatible change type: source
Short summary: The compiler now reports usages of inaccessible types in function literals and type arguments, preventing compilation and runtime failures caused by incomplete type information.
Deprecation cycle:
- 2.0.0: report warnings for function literals with parameters or receivers of inaccessible non-generic types and for types with inaccessible type argument; report errors for function literals with parameters or receivers of inaccessible generic types and for types with inaccessible generic type arguments in specific scenarios
- 2.1.0: raise warnings to errors for function literals with parameters and receivers of inaccessible non-generic types
- 2.2.0: raise warnings to errors for types with inaccessible type arguments
Standard library
Deprecate locale-sensitive case conversion functions for Char and String
Issue: KT-43023
Component: kotlin-stdlib
Incompatible change type: source
Short summary: Among other Kotlin standard library APIs, locale-sensitive case conversion functions for
CharandString, such asChar.toUpperCase()andString.toLowerCase(), are deprecated. Replace them with locale-agnostic alternatives likeString.lowercase()or explicitly specify the locale for locale-sensitive behavior, such asString.lowercase(Locale.getDefault()).For a comprehensive list of deprecated Kotlin standard library APIs in Kotlin 2.1.0, see KT-71628.
Deprecation cycle:
- 1.4.30: introduce locale-agnostic alternatives as experimental API
- 1.5.0: deprecate locale-sensitive case conversion functions with a warning
- 2.1.0: raise the warning to an error
Remove kotlin-stdlib-common JAR artifact
Issue: KT-62159
Component: kotlin-stdlib
Incompatible change type: binary
Short summary: The
kotlin-stdlib-common.jarartifact, previously used for legacy multiplatform declarations metadata, is deprecated and replaced by.klibfiles as the standard format for common multiplatform declarations metadata. This change does not affect the mainkotlin-stdlib.jarorkotlin-stdlib-all.jarartifacts.Deprecation cycle:
- 2.1.0: deprecate and remove
kotlin-stdlib-common.jarartifact
Deprecate appendln() in favor of appendLine()
Issue: KTLC-27
Component: kotlin-stdlib
Incompatible change type: source
Short summary:
StringBuilder.appendln()is deprecated in favor ofStringBuilder.appendLine().Deprecation cycle:
- 1.4.0: the
appendln()function is deprecated; report a warning on use- 2.1.0: raise the warning to an error
Deprecate freezing-related APIs in Kotlin/Native
Issue: KT-69545
Component: kotlin-stdlib
Incompatible change type: source
Short summary: Freezing-related APIs in Kotlin/Native, previously marked with the
@FreezingIsDeprecatedannotation, are now deprecated. This aligns with the introduction of the new memory manager that removes the need for freezing objects for thread sharing. For migration details, see the Kotlin/Native migration guide.Deprecation cycle:
- 1.7.20: deprecate freezing-related APIs with a warning
- 2.1.0: raise the warning to an error
Change Map.Entry behavior to fail-fast on structural modification
Issue: KTLC-23
Component: kotlin-stdlib
Incompatible change type: behavioral
Short summary: Accessing a
Map.Entrykey-value pair after its associated map has been structurally modified now throws aConcurrentModificationException.Deprecation cycle:
- 2.1.0: throw an exception when a map structural modification is detected
Tools
Deprecate KotlinCompilationOutput#resourcesDirProvider
Issue: KT-69255
Component: Gradle
Incompatible change type: source
Short summary: The
KotlinCompilationOutput#resourcesDirProviderfield is deprecated. UseKotlinSourceSet.resourcesin your Gradle build script instead to add additional resource directories.Deprecation cycle:
- 2.1.0:
KotlinCompilationOutput#resourcesDirProvideris deprecated
Deprecate registerKotlinJvmCompileTask(taskName, moduleName) function
Issue: KT-69927
Component: Gradle
Incompatible change type: source
Short summary: The
registerKotlinJvmCompileTask(taskName, moduleName)function is deprecated in favor of the newregisterKotlinJvmCompileTask(taskName, compilerOptions, explicitApiMode)function, which now acceptsKotlinJvmCompilerOptions. This allows you to pass acompilerOptionsinstance, typically from an extension or target, with values used as conventions for the task's options.Deprecation cycle:
- 2.1.0: the
registerKotlinJvmCompileTask(taskName, moduleName)function is deprecated
Deprecate registerKaptGenerateStubsTask(taskName) function
Issue: KT-70383
Component: Gradle
Incompatible change type: source
Short summary: The
registerKaptGenerateStubsTask(taskName)function is deprecated. Use the newregisterKaptGenerateStubsTask(compileTask, kaptExtension, explicitApiMode)function instead. This new version allows you to link values as conventions from the relevantKotlinJvmCompiletask, ensuring both tasks are using the same set of options.Deprecation cycle:
- 2.1.0: the
registerKaptGenerateStubsTask(taskName)function is deprecated
Deprecate KotlinTopLevelExtension and KotlinTopLevelExtensionConfig interfaces
Issue: KT-71602
Component: Gradle
Incompatible change type: behavioral
Short summary:
KotlinTopLevelExtensionandKotlinTopLevelExtensionConfiginterfaces are deprecated in favor of a newKotlinTopLevelExtensioninterface. This interface mergesKotlinTopLevelExtensionConfig,KotlinTopLevelExtension, andKotlinProjectExtensionto streamline API hierarchy, and provide official access to the JVM toolchain and compiler properties.Deprecation cycle:
- 2.1.0: the
KotlinTopLevelExtensionandKotlinTopLevelExtensionConfiginterfaces are deprecated
Remove kotlin-compiler-embeddable from build runtime dependencies
Issue: KT-61706
Component: Gradle
Incompatible change type: source
Short summary: The
kotlin-compiler-embeddabledependency is removed from the runtime in Kotlin Gradle Plugin (KGP). Required modules are now included directly in KGP artifacts, with the Kotlin language version limited to 2.0 to support compatibility with Gradle Kotlin runtime in versions below 8.2.Deprecation cycle:
- 2.1.0: report a warning on using
kotlin-compiler-embeddable- 2.2.0: raise the warning to an error
Hide compiler symbols from the Kotlin Gradle Plugin API
Issue: KT-70251
Component: Gradle
Incompatible change type: source
Short summary: Compiler module symbols bundled within the Kotlin Gradle Plugin (KGP), such as
KotlinCompilerVersion, are hidden from the public API to prevent unintended access in build scripts.Deprecation cycle:
- 2.1.0: report a warning on accessing these symbols
- 2.2.0: raise the warning to an error
Add support for multiple stability configuration files
Issue: KT-68345
Component: Gradle
Incompatible change type: source
Short summary: The
stabilityConfigurationFileproperty in the Compose extension is deprecated in favor of a newstabilityConfigurationFilesproperty, which allows specifying multiple configuration files.Deprecation cycle:
- 2.1.0:
stabilityConfigurationFileproperty is deprecated
Remove deprecated platform plugin IDs
Issue: KT-65565
Component: Gradle
Incompatible change type: source
Short summary: Support for these platform plugin IDs have been removed:
kotlin-platform-commonorg.jetbrains.kotlin.platform.commonDeprecation cycle:
- 1.3: the platform plugin IDs are deprecated
- 2.1.0: the platform plugin IDs are no longer supported