Kotlin 2.2.0 で Annotation use-site targets の新しいデフォルトルールが導入され、ビルド時に warning が表示されるようになりました。
Annotation use-site targets とは?
Annotation use-site targets は、
Kotlin のプロパティは一つの宣言で複数の Java 要素 (field、getter、コンストラクタのパラメータなど) にコンパイルされるため、単に Annotation を付けただけではコンパイラがどの要素に適用すればよいか判断できない場合があります。
それを解消するために Annotation use-site targets は Annotation をプロパティのどの要素に適用するかを明示的に指定するものとなっています。
class Example(
@field:ExampleAnnotation val foo, // annotate Java field
@get:ExampleAnnotation val bar, // annotate Java getter
@param:ExampleAnnotation val quux) // annotate Java constructor parameter
)
どうデフォルトが変わるのか
以前は Annotation に対してデフォルトで param、property、field のいずれか 1 つのみのターゲットが適用されていましたが、Kotlin 2.2.0 では Annotation に期待される内容に沿ったデフォルトのターゲットが適用される機能が追加されました。
-
paramが適用可能な場合は、paramターゲットが使用される -
propertyが適用可能な場合は、propertyターゲットが使用される -
fieldが適用可能でpropertyが適用不可能な場合は、fieldターゲットが使用される
例えば以下のようなコードの場合に、
data class User(
val username: String,
@Email val email: String
) {
@Email val secondaryEmail: String? = null
}
変更前はコンストラクタの @Email は param が適用されていました。
変更後は実体に合うように param と field が適用されるようになります。
フィールドの @Email は変更前後で変わりなく field が適用されます。
変更の背景
以前のデフォルトルールでは Annotation に対して開発者の意図したターゲットが適用されていないことがありました。
例えば以下のコードの場合、
data class User(
val username: String,
@Email var email: String
)
@Email は以前のルールの場合には param が適用されており、インスタンス生成時のみしか Annotation の検証がされておらず、プロパティの変更時には検証されていないという問題がありました。
プロジェクトでの対応
この新しいデフォルトルールを適用する場合は -Xannotation-default-target=param-property を設定します。
kotlin {
compilerOptions {
freeCompilerArgs.add("-Xannotation-default-target=param-property")
}
}
以前の動作を使用したい場合は、以下のどちらかで対応します。
-
@param:ExmapleAnnotationのように明示的にターゲットを設定 -
-Xannotation-default-target=first-onlyを適用してプロジェクト全体で変更前のルールを適用
もっと詳しく知りたい方は KEEP の提案も合わせて参照ください。