Allow sealed inheritors for expect sealed classes in MPP submodules
KT-45842 Fixed KTIJ-7068
This commit is contained in:
committed by
TeamCityServer
parent
1633190478
commit
fe81078366
+11
-2
@@ -7,6 +7,7 @@ package org.jetbrains.kotlin.resolve.checkers
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.impl.ModuleDescriptorImpl
|
||||
import org.jetbrains.kotlin.descriptors.isSealed
|
||||
import org.jetbrains.kotlin.diagnostics.Errors
|
||||
import org.jetbrains.kotlin.psi.KtClassOrObject
|
||||
@@ -22,8 +23,16 @@ object SealedInheritorInSameModuleChecker : DeclarationChecker {
|
||||
val typeReference = superTypeListEntry.typeReference ?: continue
|
||||
val superType = typeReference.getAbbreviatedTypeOrType(context.trace.bindingContext)?.unwrap() ?: continue
|
||||
val superClass = superType.constructor.declarationDescriptor ?: continue
|
||||
if (superClass.isSealed() && superClass.module != currentModule) {
|
||||
context.trace.report(Errors.SEALED_INHERITOR_IN_DIFFERENT_MODULE.on(typeReference))
|
||||
if (superClass.isSealed()) {
|
||||
/*
|
||||
* It's allowed to declare inheritors of expect sealed class in any dependent module until actual
|
||||
* counterpart for this class will be declared. So if super class is resolved to expect sealed
|
||||
* class then its allowed to declare inheritor
|
||||
*/
|
||||
val inheritorAllowed = superClass.isExpect || superClass.module == currentModule
|
||||
if (!inheritorAllowed) {
|
||||
context.trace.report(Errors.SEALED_INHERITOR_IN_DIFFERENT_MODULE.on(typeReference))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+4
@@ -0,0 +1,4 @@
|
||||
package foo
|
||||
|
||||
expect sealed class <!LINE_MARKER("descr='Is subclassed by SealedWithPlatformActuals [common] SealedWithPlatformActuals [main] SimpleShared'"), LINE_MARKER("descr='Has actuals in JVM'")!>SealedWithSharedActual<!>()
|
||||
expect sealed class <!LINE_MARKER("descr='Is subclassed by SimpleShared'")!>SealedWithPlatformActuals<!> : SealedWithSharedActual
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
MODULE common { platform=[JVM, JS, Native]; root=common }
|
||||
MODULE intermediate { platform=[JVM]; root=intermediate }
|
||||
MODULE main { platform=[JVM]; root=main }
|
||||
|
||||
intermediate -> common { kind=DEPENDS_ON }
|
||||
main -> intermediate { kind=DEPENDS_ON }
|
||||
Vendored
+4
@@ -0,0 +1,4 @@
|
||||
package foo
|
||||
|
||||
actual sealed class <!LINE_MARKER("descr='Is subclassed by SealedWithPlatformActuals [main] SimpleShared'"), LINE_MARKER("descr='Has declaration in common module'")!>SealedWithSharedActual<!>
|
||||
class SimpleShared : SealedWithPlatformActuals<!NO_CONSTRUCTOR!>()<!>
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
package foo
|
||||
|
||||
actual sealed class SealedWithPlatformActuals <!ACTUAL_WITHOUT_EXPECT!>actual constructor()<!>: <!SEALED_INHERITOR_IN_DIFFERENT_MODULE!>SealedWithSharedActual<!>()
|
||||
+16
@@ -0,0 +1,16 @@
|
||||
package foo
|
||||
|
||||
/*
|
||||
* - Sealed1 [common], actualized in [main]
|
||||
* - Sealed2 [common], actualized in [intermediate]
|
||||
* - Derived11 [common]
|
||||
* - Derived12 [intermediate]
|
||||
* - Derived1 [common]
|
||||
* - Derived2 [intermediate]
|
||||
* - Derived3 [main]
|
||||
*/
|
||||
expect sealed class <!LINE_MARKER("descr='Has subclasses'")!>Sealed1<!>()
|
||||
expect sealed class <!LINE_MARKER("descr='Is subclassed by Derived11 Derived12 Derived13Error'"), LINE_MARKER("descr='Has actuals in JVM'")!>Sealed2<!>() : Sealed1
|
||||
|
||||
class Derived1 : Sealed1()
|
||||
class Derived11 : Sealed2()
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
MODULE common { platform=[JVM, JS, Native]; root=common }
|
||||
MODULE intermediate { platform=[JVM]; root=intermediate }
|
||||
MODULE main { platform=[JVM]; root=main }
|
||||
MODULE real-main { platform=[JVM]; root=real-main }
|
||||
|
||||
intermediate -> common { kind=DEPENDS_ON }
|
||||
main -> intermediate { kind=DEPENDS_ON }
|
||||
real-main -> main { kind=DEPENDS_ON }
|
||||
Vendored
+6
@@ -0,0 +1,6 @@
|
||||
package foo
|
||||
|
||||
actual sealed class <!LINE_MARKER("descr='Is subclassed by Derived12 Derived13Error'"), LINE_MARKER("descr='Has declaration in common module'")!>Sealed2<!> : Sealed1()
|
||||
|
||||
class Derived2 : Sealed1()
|
||||
class Derived12 : Sealed2()
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
package foo
|
||||
|
||||
actual sealed class <!LINE_MARKER("descr='Is subclassed by Derived2 Derived3Error'")!>Sealed1<!> actual constructor()
|
||||
|
||||
class Derived2 : Sealed1()
|
||||
class Derived13Error : <!SEALED_INHERITOR_IN_DIFFERENT_MODULE!>Sealed2<!>() // should be an error
|
||||
Vendored
+3
@@ -0,0 +1,3 @@
|
||||
package foo
|
||||
|
||||
class Derived3Error : <!SEALED_INHERITOR_IN_DIFFERENT_MODULE!>Sealed1<!>() // should be an error
|
||||
@@ -1 +1 @@
|
||||
class CommonAImplTestClass: <!SEALED_INHERITOR_IN_DIFFERENT_MODULE!>TestClass<!>()
|
||||
class CommonAImplTestClass: TestClass()
|
||||
|
||||
Generated
+10
@@ -229,6 +229,16 @@ public class MultiplatformAnalysisTestGenerated extends AbstractMultiplatformAna
|
||||
runTest("idea/testData/multiplatform/recursiveTypes/");
|
||||
}
|
||||
|
||||
@TestMetadata("sealedInheritorsInComplexModuleStructure1")
|
||||
public void testSealedInheritorsInComplexModuleStructure1() throws Exception {
|
||||
runTest("idea/testData/multiplatform/sealedInheritorsInComplexModuleStructure1/");
|
||||
}
|
||||
|
||||
@TestMetadata("sealedInheritorsInComplexModuleStructure2")
|
||||
public void testSealedInheritorsInComplexModuleStructure2() throws Exception {
|
||||
runTest("idea/testData/multiplatform/sealedInheritorsInComplexModuleStructure2/");
|
||||
}
|
||||
|
||||
@TestMetadata("simple")
|
||||
public void testSimple() throws Exception {
|
||||
runTest("idea/testData/multiplatform/simple/");
|
||||
|
||||
Reference in New Issue
Block a user