Parcelize: Check @IgnoredOnParcel annotation usage (#KT-24459)

This commit is contained in:
Yan Zhulanow
2018-05-22 01:54:01 +03:00
parent ee37bcf14b
commit 3c1c776cdb
4 changed files with 43 additions and 1 deletions
@@ -18,6 +18,7 @@ package org.jetbrains.kotlin.android.parcel
import com.intellij.psi.PsiElement
import com.intellij.psi.util.PsiTreeUtil
import kotlinx.android.parcel.IgnoredOnParcel
import kotlinx.android.parcel.TypeParceler
import kotlinx.android.parcel.WriteWith
import org.jetbrains.kotlin.android.synthetic.diagnostic.DefaultErrorMessagesAndroid
@@ -44,6 +45,7 @@ class ParcelableAnnotationChecker : CallChecker {
companion object {
val TYPE_PARCELER_FQNAME = FqName(TypeParceler::class.java.name)
val WRITE_WITH_FQNAME = FqName(WriteWith::class.java.name)
val IGNORED_ON_PARCEL_FQNAME = FqName(IgnoredOnParcel::class.java.name)
}
override fun check(resolvedCall: ResolvedCall<*>, reportOn: PsiElement, context: CallCheckerContext) {
@@ -60,6 +62,21 @@ class ParcelableAnnotationChecker : CallChecker {
if (annotationClass.fqNameSafe == WRITE_WITH_FQNAME) {
checkWriteWithUsage(resolvedCall, annotationEntry, context, annotationOwner)
}
if (annotationClass.fqNameSafe == IGNORED_ON_PARCEL_FQNAME) {
checkIgnoredOnParcelUsage(annotationEntry, context, annotationOwner)
}
}
private fun checkIgnoredOnParcelUsage(annotationEntry: KtAnnotationEntry, context: CallCheckerContext, element: KtModifierListOwner) {
if (element is KtParameter && PsiTreeUtil.getParentOfType(element, KtDeclaration::class.java) is KtPrimaryConstructor) {
context.trace.reportFromPlugin(
ErrorsAndroid.INAPPLICABLE_IGNORED_ON_PARCEL_CONSTRUCTOR_PROPERTY.on(annotationEntry),
DefaultErrorMessagesAndroid
)
} else if (element !is KtProperty || PsiTreeUtil.getParentOfType(element, KtDeclaration::class.java) !is KtClass) {
context.trace.reportFromPlugin(ErrorsAndroid.INAPPLICABLE_IGNORED_ON_PARCEL.on(annotationEntry), DefaultErrorMessagesAndroid)
}
}
private fun checkTypeParcelerUsage(
@@ -101,5 +101,11 @@ object DefaultErrorMessagesAndroid : DefaultErrorMessages.Extension {
MAP.put(ErrorsAndroid.CLASS_SHOULD_BE_PARCELIZE,
"{0} should be annotated with ''@Parcelize''",
RENDER_CLASS_OR_OBJECT)
MAP.put(ErrorsAndroid.INAPPLICABLE_IGNORED_ON_PARCEL,
"'@IgnoredOnParcel' is only applicable to class properties")
MAP.put(ErrorsAndroid.INAPPLICABLE_IGNORED_ON_PARCEL_CONSTRUCTOR_PROPERTY,
"'@IgnoredOnParcel' is inapplicable to properties declared in the primary constructor")
}
}
@@ -56,6 +56,9 @@ public interface ErrorsAndroid {
DiagnosticFactory1<PsiElement, KtClassOrObject> REDUNDANT_TYPE_PARCELER = DiagnosticFactory1.create(WARNING);
DiagnosticFactory1<PsiElement, KtClassOrObject> CLASS_SHOULD_BE_PARCELIZE = DiagnosticFactory1.create(ERROR);
DiagnosticFactory0<PsiElement> INAPPLICABLE_IGNORED_ON_PARCEL = DiagnosticFactory0.create(WARNING);
DiagnosticFactory0<PsiElement> INAPPLICABLE_IGNORED_ON_PARCEL_CONSTRUCTOR_PROPERTY = DiagnosticFactory0.create(WARNING);
@SuppressWarnings("UnusedDeclaration")
Object _initializer = new Object() {
{
@@ -1,6 +1,6 @@
package test
import kotlinx.android.parcel.Parcelize
import kotlinx.android.parcel.*
import android.os.Parcelable
@Parcelize
@@ -18,3 +18,19 @@ class A(val firstName: String) : Parcelable {
get() = ""
set(<warning descr="[UNUSED_PARAMETER] Parameter 'v' is never used">v</warning>) {}
}
@Parcelize
@Suppress("WRONG_ANNOTATION_TARGET_WITH_USE_SITE_TARGET")
class B(<warning descr="[PLUGIN_WARNING] '@IgnoredOnParcel' is inapplicable to properties declared in the primary constructor">@IgnoredOnParcel</warning> val firstName: String) : Parcelable {
@IgnoredOnParcel
var a: String = ""
@field:IgnoredOnParcel
var <warning descr="[PLUGIN_WARNING] Property would not be serialized into a 'Parcel'. Add '@IgnoredOnParcel' annotation to remove the warning">b</warning>: String = ""
@get:IgnoredOnParcel
var <warning descr="[PLUGIN_WARNING] Property would not be serialized into a 'Parcel'. Add '@IgnoredOnParcel' annotation to remove the warning">c</warning>: String = ""
@set:IgnoredOnParcel
var <warning descr="[PLUGIN_WARNING] Property would not be serialized into a 'Parcel'. Add '@IgnoredOnParcel' annotation to remove the warning">d</warning>: String = ""
}