Add warning on overriding java default by non @JvmDefault method
This commit is contained in:
+12
-4
@@ -7,13 +7,13 @@ package org.jetbrains.kotlin.resolve.jvm.checkers
|
||||
|
||||
import org.jetbrains.kotlin.config.AnalysisFlag
|
||||
import org.jetbrains.kotlin.config.JvmTarget
|
||||
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.PropertyAccessorDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.load.java.descriptors.JavaCallableMemberDescriptor
|
||||
import org.jetbrains.kotlin.load.java.descriptors.JavaMethodDescriptor
|
||||
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||
import org.jetbrains.kotlin.resolve.DescriptorToSourceUtils
|
||||
import org.jetbrains.kotlin.resolve.DescriptorUtils
|
||||
import org.jetbrains.kotlin.resolve.OverridingUtil
|
||||
import org.jetbrains.kotlin.resolve.annotations.JVM_DEFAULT_FQ_NAME
|
||||
import org.jetbrains.kotlin.resolve.annotations.hasJvmDefaultAnnotation
|
||||
import org.jetbrains.kotlin.resolve.checkers.DeclarationChecker
|
||||
@@ -55,6 +55,14 @@ class JvmDefaultChecker(val jvmTarget: JvmTarget) : DeclarationChecker {
|
||||
|
||||
if (memberDescriptor.overriddenDescriptors.any { it.annotations.hasAnnotation(JVM_DEFAULT_FQ_NAME) }) {
|
||||
context.trace.report(ErrorsJvm.JVM_DEFAULT_REQUIRED_FOR_OVERRIDE.on(declaration))
|
||||
} else if (enableJvmDefault) {
|
||||
descriptor.overriddenDescriptors.flatMap { OverridingUtil.getOverriddenDeclarations(it) }.toSet().let {
|
||||
for (realDescriptor in OverridingUtil.filterOutOverridden(it)) {
|
||||
if (realDescriptor is JavaMethodDescriptor && realDescriptor.modality != Modality.ABSTRACT) {
|
||||
return context.trace.report(ErrorsJvm.NON_JVM_DEFAULT_OVERRIDES_JAVA_DEFAULT.on(declaration))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+1
@@ -140,6 +140,7 @@ public class DefaultErrorMessagesJvm implements DefaultErrorMessages.Extension {
|
||||
MAP.put(JVM_DEFAULT_IN_DECLARATION, "Usage of '@JvmDefault' is only allowed if the flag -Xenable-jvm-default is enabled");
|
||||
MAP.put(JVM_DEFAULT_THROUGH_INHERITANCE, "Inheritance from an interface with '@JvmDefault' members is only allowed if the flag -Xenable-jvm-default is enabled");
|
||||
MAP.put(USAGE_OF_JVM_DEFAULT_THROUGH_SUPER_CALL, "Super calls of '@JvmDefault' members are only allowed if the flag -Xenable-jvm-default is enabled");
|
||||
MAP.put(NON_JVM_DEFAULT_OVERRIDES_JAVA_DEFAULT, "Non-@JvmDefault interface method cannot override default Java method. Please annotate this method with @JvmDefault");
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
@@ -121,6 +121,8 @@ public interface ErrorsJvm {
|
||||
DiagnosticFactory0<KtDeclaration> JVM_DEFAULT_THROUGH_INHERITANCE = DiagnosticFactory0.create(ERROR, DECLARATION_SIGNATURE);
|
||||
DiagnosticFactory0<PsiElement> USAGE_OF_JVM_DEFAULT_THROUGH_SUPER_CALL = DiagnosticFactory0.create(ERROR);
|
||||
|
||||
DiagnosticFactory0<KtDeclaration> NON_JVM_DEFAULT_OVERRIDES_JAVA_DEFAULT = DiagnosticFactory0.create(WARNING, DECLARATION_SIGNATURE);
|
||||
|
||||
enum NullabilityInformationSource {
|
||||
KOTLIN {
|
||||
@NotNull
|
||||
|
||||
+73
@@ -0,0 +1,73 @@
|
||||
// !API_VERSION: 1.3
|
||||
// !ENABLE_JVM_DEFAULT
|
||||
// !JVM_TARGET: 1.8
|
||||
|
||||
// FILE: JavaInterface.java
|
||||
public interface JavaInterface {
|
||||
default void test() {}
|
||||
|
||||
default void testForNonDefault() {}
|
||||
|
||||
void testAbstract();
|
||||
}
|
||||
|
||||
// FILE: 1.kt
|
||||
|
||||
interface KotlinInterface : JavaInterface {
|
||||
@JvmDefault
|
||||
override fun test() {}
|
||||
|
||||
<!NON_JVM_DEFAULT_OVERRIDES_JAVA_DEFAULT!>override fun testForNonDefault()<!> {}
|
||||
|
||||
override fun testAbstract() {}
|
||||
}
|
||||
|
||||
interface KotlinInterface2 : JavaInterface, KotlinInterface {
|
||||
@JvmDefault
|
||||
override fun test() {}
|
||||
|
||||
override fun testForNonDefault() {}
|
||||
|
||||
override fun testAbstract() {}
|
||||
}
|
||||
|
||||
|
||||
interface KotlinInterfaceForIndirect : JavaInterface {
|
||||
|
||||
}
|
||||
|
||||
interface KotlinInterfaceInderectInheritance : KotlinInterfaceForIndirect {
|
||||
|
||||
@JvmDefault
|
||||
override fun test() {}
|
||||
|
||||
<!NON_JVM_DEFAULT_OVERRIDES_JAVA_DEFAULT!>override fun testForNonDefault()<!> {}
|
||||
|
||||
override fun testAbstract() {}
|
||||
}
|
||||
|
||||
open class KotlinClass : JavaInterface {
|
||||
override fun test() {}
|
||||
|
||||
override fun testForNonDefault() {}
|
||||
|
||||
override fun testAbstract() {}
|
||||
}
|
||||
|
||||
interface KotlinInterfaceX {
|
||||
|
||||
fun test() {}
|
||||
|
||||
fun testForNonDefault() {}
|
||||
|
||||
fun testAbstract() {}
|
||||
}
|
||||
|
||||
interface KotlinInterfaceManySuper: JavaInterface, KotlinInterfaceX {
|
||||
@JvmDefault
|
||||
override fun test() {}
|
||||
|
||||
<!NON_JVM_DEFAULT_OVERRIDES_JAVA_DEFAULT!>override fun testForNonDefault()<!> {}
|
||||
|
||||
override fun testAbstract() {}
|
||||
}
|
||||
+58
@@ -0,0 +1,58 @@
|
||||
package
|
||||
|
||||
public interface JavaInterface {
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open fun test(): kotlin.Unit
|
||||
public open fun testForNonDefault(): kotlin.Unit
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public open class KotlinClass : JavaInterface {
|
||||
public constructor KotlinClass()
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ fun test(): kotlin.Unit
|
||||
public open override /*1*/ fun testForNonDefault(): kotlin.Unit
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public interface KotlinInterface : JavaInterface {
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
@kotlin.jvm.JvmDefault public open override /*1*/ fun test(): kotlin.Unit
|
||||
public open override /*1*/ fun testForNonDefault(): kotlin.Unit
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public interface KotlinInterfaceForIndirect : JavaInterface {
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun test(): kotlin.Unit
|
||||
public open override /*1*/ /*fake_override*/ fun testForNonDefault(): kotlin.Unit
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public interface KotlinInterfaceInderectInheritance : KotlinInterfaceForIndirect {
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
@kotlin.jvm.JvmDefault public open override /*1*/ fun test(): kotlin.Unit
|
||||
public open override /*1*/ fun testForNonDefault(): kotlin.Unit
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public interface KotlinInterfaceManySuper : JavaInterface, KotlinInterfaceX {
|
||||
public open override /*2*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*2*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
@kotlin.jvm.JvmDefault public open override /*2*/ fun test(): kotlin.Unit
|
||||
public open override /*2*/ fun testForNonDefault(): kotlin.Unit
|
||||
public open override /*2*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public interface KotlinInterfaceX {
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open fun test(): kotlin.Unit
|
||||
public open fun testForNonDefault(): kotlin.Unit
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
+6
@@ -482,6 +482,12 @@ public class DiagnosticsTestWithStdLibGenerated extends AbstractDiagnosticsTestW
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("javaOverride.kt")
|
||||
public void testJavaOverride() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/testsWithStdLib/annotations/jvmDefault/javaOverride.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("jvmDefaultInInheritance.kt")
|
||||
public void testJvmDefaultInInheritance() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/testsWithStdLib/annotations/jvmDefault/jvmDefaultInInheritance.kt");
|
||||
|
||||
compiler/tests/org/jetbrains/kotlin/checkers/javac/DiagnosticsTestWithStdLibUsingJavacGenerated.java
Generated
+6
@@ -482,6 +482,12 @@ public class DiagnosticsTestWithStdLibUsingJavacGenerated extends AbstractDiagno
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("javaOverride.kt")
|
||||
public void testJavaOverride() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/testsWithStdLib/annotations/jvmDefault/javaOverride.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("jvmDefaultInInheritance.kt")
|
||||
public void testJvmDefaultInInheritance() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/testsWithStdLib/annotations/jvmDefault/jvmDefaultInInheritance.kt");
|
||||
|
||||
Reference in New Issue
Block a user