diff --git a/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/parcel/ParcelableAnnotationChecker.kt b/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/parcel/ParcelableAnnotationChecker.kt index 77a286156fd..b7eebb01b88 100644 --- a/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/parcel/ParcelableAnnotationChecker.kt +++ b/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/parcel/ParcelableAnnotationChecker.kt @@ -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( diff --git a/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/synthetic/diagnostic/DefaultErrorMessagesAndroid.kt b/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/synthetic/diagnostic/DefaultErrorMessagesAndroid.kt index 9d3450dccde..c58f228badc 100644 --- a/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/synthetic/diagnostic/DefaultErrorMessagesAndroid.kt +++ b/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/synthetic/diagnostic/DefaultErrorMessagesAndroid.kt @@ -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") } } diff --git a/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/synthetic/diagnostic/ErrorsAndroid.java b/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/synthetic/diagnostic/ErrorsAndroid.java index 28829f1c233..08244bcdeee 100644 --- a/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/synthetic/diagnostic/ErrorsAndroid.java +++ b/plugins/android-extensions/android-extensions-compiler/src/org/jetbrains/kotlin/android/synthetic/diagnostic/ErrorsAndroid.java @@ -56,6 +56,9 @@ public interface ErrorsAndroid { DiagnosticFactory1 REDUNDANT_TYPE_PARCELER = DiagnosticFactory1.create(WARNING); DiagnosticFactory1 CLASS_SHOULD_BE_PARCELIZE = DiagnosticFactory1.create(ERROR); + DiagnosticFactory0 INAPPLICABLE_IGNORED_ON_PARCEL = DiagnosticFactory0.create(WARNING); + DiagnosticFactory0 INAPPLICABLE_IGNORED_ON_PARCEL_CONSTRUCTOR_PROPERTY = DiagnosticFactory0.create(WARNING); + @SuppressWarnings("UnusedDeclaration") Object _initializer = new Object() { { diff --git a/plugins/android-extensions/android-extensions-idea/testData/android/parcel/checker/properties.kt b/plugins/android-extensions/android-extensions-idea/testData/android/parcel/checker/properties.kt index e12e0ae1158..8baef1a0b26 100644 --- a/plugins/android-extensions/android-extensions-idea/testData/android/parcel/checker/properties.kt +++ b/plugins/android-extensions/android-extensions-idea/testData/android/parcel/checker/properties.kt @@ -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(v) {} } + +@Parcelize +@Suppress("WRONG_ANNOTATION_TARGET_WITH_USE_SITE_TARGET") +class B(@IgnoredOnParcel val firstName: String) : Parcelable { + @IgnoredOnParcel + var a: String = "" + + @field:IgnoredOnParcel + var b: String = "" + + @get:IgnoredOnParcel + var c: String = "" + + @set:IgnoredOnParcel + var d: String = "" +} \ No newline at end of file