[LC] add isEquivalentTo implementation so LC can be referenced from java
otherwise references from java to ktElements won't be treated as references, cause java references resolve to light elements and search can/should be called on ktElements
This commit is contained in:
+5
-2
@@ -154,8 +154,11 @@ abstract class SymbolLightClassForClassLike<SType : KtClassOrObjectSymbol> prote
|
||||
override fun getNavigationElement(): PsiElement = classOrObjectDeclaration ?: this
|
||||
|
||||
override fun isEquivalentTo(another: PsiElement?): Boolean =
|
||||
basicIsEquivalentTo(this, another) ||
|
||||
another is PsiClass && qualifiedName != null && another.qualifiedName == qualifiedName
|
||||
isEquivalentToByName(another) ||
|
||||
isOriginEquivalentTo(another)
|
||||
|
||||
protected fun isEquivalentToByName(another: PsiElement?): Boolean = basicIsEquivalentTo(this, another) ||
|
||||
another is PsiClass && qualifiedName != null && another.qualifiedName == qualifiedName
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (this === other) return true
|
||||
|
||||
+5
@@ -15,6 +15,7 @@ import org.jetbrains.kotlin.asJava.elements.KtLightIdentifier
|
||||
import org.jetbrains.kotlin.asJava.elements.KtLightMethod
|
||||
import org.jetbrains.kotlin.light.classes.symbol.codeReferences.SymbolLightPsiJavaCodeReferenceElementWithNoReference
|
||||
import org.jetbrains.kotlin.light.classes.symbol.fields.SymbolLightFieldForEnumEntry
|
||||
import org.jetbrains.kotlin.light.classes.symbol.isOriginEquivalentTo
|
||||
import org.jetbrains.kotlin.light.classes.symbol.modifierLists.SymbolLightClassModifierList
|
||||
import org.jetbrains.kotlin.load.java.structure.LightClassOriginKind
|
||||
import org.jetbrains.kotlin.psi.KtEnumEntry
|
||||
@@ -44,6 +45,10 @@ internal class SymbolLightClassForEnumEntry(
|
||||
|
||||
override fun toString(): String = "SymbolLightClassForEnumEntry:$name"
|
||||
|
||||
override fun isEquivalentTo(another: PsiElement?): Boolean {
|
||||
return super.isEquivalentTo(another) || isOriginEquivalentTo(another)
|
||||
}
|
||||
|
||||
private val _modifierList: PsiModifierList by lazyPub {
|
||||
SymbolLightClassModifierList(
|
||||
containingDeclaration = this,
|
||||
|
||||
+4
@@ -24,6 +24,10 @@ internal class SymbolLightClassForInterfaceDefaultImpls(private val containingCl
|
||||
|
||||
override fun copy() = SymbolLightClassForInterfaceDefaultImpls(containingClass)
|
||||
|
||||
override fun isEquivalentTo(another: PsiElement?): Boolean {
|
||||
return isEquivalentToByName(another)
|
||||
}
|
||||
|
||||
override fun equals(other: Any?): Boolean = this === other ||
|
||||
other is SymbolLightClassForInterfaceDefaultImpls && other.containingClass == containingClass
|
||||
|
||||
|
||||
+4
@@ -62,6 +62,10 @@ internal class SymbolLightClassForRepeatableAnnotationContainer(private val cont
|
||||
|
||||
override fun copy(): SymbolLightClassForRepeatableAnnotationContainer = SymbolLightClassForRepeatableAnnotationContainer(containerOwner)
|
||||
|
||||
override fun isEquivalentTo(another: PsiElement?): Boolean {
|
||||
return isEquivalentToByName(another)
|
||||
}
|
||||
|
||||
override fun equals(other: Any?): Boolean = this === other ||
|
||||
other is SymbolLightClassForRepeatableAnnotationContainer && other.containerOwner == containerOwner
|
||||
|
||||
|
||||
+5
@@ -16,6 +16,7 @@ import org.jetbrains.kotlin.light.classes.symbol.analyzeForLightClasses
|
||||
import org.jetbrains.kotlin.light.classes.symbol.annotations.computeAnnotations
|
||||
import org.jetbrains.kotlin.light.classes.symbol.classes.SymbolLightClassForClassOrObject
|
||||
import org.jetbrains.kotlin.light.classes.symbol.classes.SymbolLightClassForEnumEntry
|
||||
import org.jetbrains.kotlin.light.classes.symbol.isOriginEquivalentTo
|
||||
import org.jetbrains.kotlin.light.classes.symbol.modifierLists.SymbolLightMemberModifierList
|
||||
import org.jetbrains.kotlin.light.classes.symbol.nonExistentType
|
||||
import org.jetbrains.kotlin.psi.KtEnumEntry
|
||||
@@ -46,6 +47,10 @@ internal class SymbolLightFieldForEnumEntry(
|
||||
}
|
||||
}
|
||||
|
||||
override fun isEquivalentTo(another: PsiElement?): Boolean {
|
||||
return super.isEquivalentTo(another) || isOriginEquivalentTo(another)
|
||||
}
|
||||
|
||||
override fun getModifierList(): PsiModifierList = _modifierList
|
||||
|
||||
override val kotlinOrigin: KtEnumEntry = enumEntry
|
||||
|
||||
+5
-4
@@ -5,10 +5,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.light.classes.symbol.fields
|
||||
|
||||
import com.intellij.psi.PsiExpression
|
||||
import com.intellij.psi.PsiModifier
|
||||
import com.intellij.psi.PsiModifierList
|
||||
import com.intellij.psi.PsiType
|
||||
import com.intellij.psi.*
|
||||
import org.jetbrains.kotlin.analysis.api.KtAnalysisSession
|
||||
import org.jetbrains.kotlin.analysis.api.KtConstantInitializerValue
|
||||
import org.jetbrains.kotlin.analysis.api.annotations.hasAnnotation
|
||||
@@ -87,6 +84,10 @@ internal class SymbolLightFieldForProperty private constructor(
|
||||
}
|
||||
}
|
||||
|
||||
override fun isEquivalentTo(another: PsiElement?): Boolean {
|
||||
return super.isEquivalentTo(another) || isOriginEquivalentTo(another)
|
||||
}
|
||||
|
||||
override fun isDeprecated(): Boolean = _isDeprecated
|
||||
|
||||
override fun getType(): PsiType = _returnedType
|
||||
|
||||
+8
@@ -5,6 +5,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.light.classes.symbol.methods
|
||||
|
||||
import com.intellij.psi.PsiElement
|
||||
import com.intellij.psi.PsiIdentifier
|
||||
import com.intellij.psi.PsiParameterList
|
||||
import com.intellij.psi.impl.light.LightReferenceListBuilder
|
||||
@@ -21,6 +22,7 @@ import org.jetbrains.kotlin.light.classes.symbol.annotations.computeThrowsList
|
||||
import org.jetbrains.kotlin.light.classes.symbol.annotations.hasDeprecatedAnnotation
|
||||
import org.jetbrains.kotlin.light.classes.symbol.classes.SymbolLightClassBase
|
||||
import org.jetbrains.kotlin.light.classes.symbol.compareSymbolPointers
|
||||
import org.jetbrains.kotlin.light.classes.symbol.isOriginEquivalentTo
|
||||
import org.jetbrains.kotlin.light.classes.symbol.isValid
|
||||
import org.jetbrains.kotlin.light.classes.symbol.parameters.SymbolLightParameter
|
||||
import org.jetbrains.kotlin.light.classes.symbol.parameters.SymbolLightParameterList
|
||||
@@ -135,6 +137,12 @@ internal abstract class SymbolLightMethod<FType : KtFunctionLikeSymbol> private
|
||||
|
||||
override fun isValid(): Boolean = super.isValid() && functionDeclaration?.isValid ?: functionSymbolPointer.isValid(ktModule)
|
||||
|
||||
override fun isOverride(): Boolean = withFunctionSymbol { it.getDirectlyOverriddenSymbols().isNotEmpty() }
|
||||
|
||||
override fun isEquivalentTo(another: PsiElement?): Boolean {
|
||||
return super.isEquivalentTo(another) || isOriginEquivalentTo(another)
|
||||
}
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (this === other) return true
|
||||
if (other !is SymbolLightMethod<*> ||
|
||||
|
||||
+3
-1
@@ -186,7 +186,9 @@ internal class SymbolLightTypeParameter private constructor(
|
||||
}
|
||||
|
||||
override fun hashCode(): Int = typeParameterDeclaration?.hashCode() ?: name.hashCode()
|
||||
override fun isEquivalentTo(another: PsiElement): Boolean = basicIsEquivalentTo(this, another)
|
||||
override fun isEquivalentTo(another: PsiElement): Boolean {
|
||||
return basicIsEquivalentTo(this, another) || isOriginEquivalentTo(another)
|
||||
}
|
||||
|
||||
override fun getText(): String? = typeParameterDeclaration?.text
|
||||
override fun getTextRange(): TextRange? = typeParameterDeclaration?.textRange
|
||||
|
||||
+5
@@ -22,6 +22,7 @@ import org.jetbrains.kotlin.analysis.api.symbols.pointers.KtSymbolPointer
|
||||
import org.jetbrains.kotlin.analysis.api.types.*
|
||||
import org.jetbrains.kotlin.analysis.project.structure.KtModule
|
||||
import org.jetbrains.kotlin.asJava.elements.KtLightElement
|
||||
import org.jetbrains.kotlin.asJava.elements.KtLightElementBase
|
||||
import org.jetbrains.kotlin.asJava.elements.KtLightMember
|
||||
import org.jetbrains.kotlin.asJava.elements.psiType
|
||||
import org.jetbrains.kotlin.descriptors.Modality
|
||||
@@ -115,6 +116,10 @@ internal fun basicIsEquivalentTo(`this`: PsiElement?, that: PsiElement?): Boolea
|
||||
return thisMemberOrigin.isEquivalentTo(thatMemberOrigin)
|
||||
}
|
||||
|
||||
internal fun KtLightElement<*, *>.isOriginEquivalentTo(that: PsiElement?): Boolean {
|
||||
return kotlinOrigin?.isEquivalentTo(that) == true
|
||||
}
|
||||
|
||||
internal fun KtAnalysisSession.getTypeNullability(ktType: KtType): NullabilityType {
|
||||
if (ktType.nullabilityType != NullabilityType.NotNull) return ktType.nullabilityType
|
||||
|
||||
|
||||
@@ -0,0 +1,2 @@
|
||||
// org.jetbrains.kotlin.light.classes.symbol.classes.SymbolLightClassForAnnotationClass
|
||||
annotation class Fo<caret>oBar
|
||||
@@ -0,0 +1,4 @@
|
||||
// org.jetbrains.kotlin.light.classes.symbol.classes.SymbolLightClassForAnonymousObject
|
||||
val f = obje<caret>ct : I {}
|
||||
|
||||
interface I {}
|
||||
@@ -0,0 +1,6 @@
|
||||
// org.jetbrains.kotlin.light.classes.symbol.fields.SymbolLightFieldForProperty
|
||||
class FooBar {
|
||||
companion object {
|
||||
var f<caret>oo : String = ""
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
// org.jetbrains.kotlin.light.classes.symbol.methods.SymbolLightConstructor
|
||||
class FooBar {
|
||||
cons<caret>tructor() {
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
// org.jetbrains.kotlin.light.classes.symbol.classes.SymbolLightClassForEnumEntry
|
||||
enum class FooBar {
|
||||
EnumClass<caret>Entry {
|
||||
fun foo() {
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,2 @@
|
||||
// org.jetbrains.kotlin.light.classes.symbol.methods.SymbolLightSimpleMethod
|
||||
fun foo<caret>Bar() {}
|
||||
@@ -0,0 +1,2 @@
|
||||
// org.jetbrains.kotlin.light.classes.symbol.classes.SymbolLightClassForInterface
|
||||
interface Fo<caret>oBar
|
||||
@@ -0,0 +1,2 @@
|
||||
// org.jetbrains.kotlin.light.classes.symbol.classes.SymbolLightClassForClassOrObject
|
||||
cl<caret>ass FooBar
|
||||
@@ -0,0 +1,2 @@
|
||||
// org.jetbrains.kotlin.light.classes.symbol.parameters.SymbolLightTypeParameter
|
||||
interface FooBar<<caret>T>
|
||||
+34
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||
* Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.light.classes.symbol.base
|
||||
|
||||
import org.jetbrains.kotlin.analysis.low.level.api.fir.test.configurators.AnalysisApiFirSourceTestConfigurator
|
||||
import org.jetbrains.kotlin.analysis.test.framework.base.AbstractAnalysisApiBasedSingleModuleTest
|
||||
import org.jetbrains.kotlin.analysis.test.framework.services.expressionMarkerProvider
|
||||
import org.jetbrains.kotlin.analysis.test.framework.test.configurators.AnalysisApiTestConfigurator
|
||||
import org.jetbrains.kotlin.asJava.LightClassTestCommon
|
||||
import org.jetbrains.kotlin.asJava.toLightElements
|
||||
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||
import org.jetbrains.kotlin.psi.KtFile
|
||||
import org.jetbrains.kotlin.test.model.TestModule
|
||||
import org.jetbrains.kotlin.test.services.TestServices
|
||||
import org.jetbrains.kotlin.test.services.assertions
|
||||
|
||||
abstract class AbstractSymbolLightClassesEqualityTest : AbstractAnalysisApiBasedSingleModuleTest() {
|
||||
override fun doTestByFileStructure(ktFiles: List<KtFile>, module: TestModule, testServices: TestServices) {
|
||||
val lightQName = LightClassTestCommon.fqNameInTestDataFile(testDataPath.toFile())
|
||||
val ktFile = ktFiles.first()
|
||||
val declaration = testServices.expressionMarkerProvider.getElementOfTypeAtCaret<KtDeclaration>(ktFile)
|
||||
val lightElements = declaration.toLightElements()
|
||||
testServices.assertions.assertFalse(lightElements.isEmpty())
|
||||
val lightElement = lightElements.find { it.javaClass.name == lightQName }
|
||||
testServices.assertions.assertNotNull(lightElement) { "Expected $lightQName, got: " + lightElements.joinToString { it::class.java.name } }
|
||||
testServices.assertions.assertTrue(lightElement!!.isEquivalentTo(declaration)) { "Light element is not equivalent to the corresponding ktElement" }
|
||||
}
|
||||
|
||||
override val configurator: AnalysisApiTestConfigurator
|
||||
get() = AnalysisApiFirSourceTestConfigurator(analyseInDependentSession = false)
|
||||
}
|
||||
+80
@@ -0,0 +1,80 @@
|
||||
/*
|
||||
* Copyright 2010-2023 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||
* Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.light.classes.symbol.base;
|
||||
|
||||
import com.intellij.testFramework.TestDataPath;
|
||||
import org.jetbrains.kotlin.test.util.KtTestUtil;
|
||||
import org.jetbrains.kotlin.test.TestMetadata;
|
||||
import org.junit.jupiter.api.Nested;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
/** This class is generated by {@link org.jetbrains.kotlin.generators.tests.analysis.api.GenerateAnalysisApiTestsKt}. DO NOT MODIFY MANUALLY */
|
||||
@SuppressWarnings("all")
|
||||
@TestMetadata("analysis/symbol-light-classes/testData/equivalentTo")
|
||||
@TestDataPath("$PROJECT_ROOT")
|
||||
public class SymbolLightClassesEqualityTestGenerated extends AbstractSymbolLightClassesEqualityTest {
|
||||
@Test
|
||||
public void testAllFilesPresentInEquivalentTo() throws Exception {
|
||||
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("analysis/symbol-light-classes/testData/equivalentTo"), Pattern.compile("^(.+)\\.(kt)$"), null, true);
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("AnnotationClass.kt")
|
||||
public void testAnnotationClass() throws Exception {
|
||||
runTest("analysis/symbol-light-classes/testData/equivalentTo/AnnotationClass.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("AnonymousClass.kt")
|
||||
public void testAnonymousClass() throws Exception {
|
||||
runTest("analysis/symbol-light-classes/testData/equivalentTo/AnonymousClass.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("CompanionProperty.kt")
|
||||
public void testCompanionProperty() throws Exception {
|
||||
runTest("analysis/symbol-light-classes/testData/equivalentTo/CompanionProperty.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("Constructor.kt")
|
||||
public void testConstructor() throws Exception {
|
||||
runTest("analysis/symbol-light-classes/testData/equivalentTo/Constructor.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("EnumClassEntry.kt")
|
||||
public void testEnumClassEntry() throws Exception {
|
||||
runTest("analysis/symbol-light-classes/testData/equivalentTo/EnumClassEntry.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("Function.kt")
|
||||
public void testFunction() throws Exception {
|
||||
runTest("analysis/symbol-light-classes/testData/equivalentTo/Function.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("Interface.kt")
|
||||
public void testInterface() throws Exception {
|
||||
runTest("analysis/symbol-light-classes/testData/equivalentTo/Interface.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("Klass.kt")
|
||||
public void testKlass() throws Exception {
|
||||
runTest("analysis/symbol-light-classes/testData/equivalentTo/Klass.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("TypeParameter.kt")
|
||||
public void testTypeParameter() throws Exception {
|
||||
runTest("analysis/symbol-light-classes/testData/equivalentTo/TypeParameter.kt");
|
||||
}
|
||||
}
|
||||
+7
@@ -7,6 +7,7 @@ package org.jetbrains.kotlin.generators.tests.analysis.api
|
||||
|
||||
import org.jetbrains.kotlin.generators.TestGroupSuite
|
||||
import org.jetbrains.kotlin.generators.util.TestGeneratorUtil
|
||||
import org.jetbrains.kotlin.light.classes.symbol.base.AbstractSymbolLightClassesEqualityTest
|
||||
import org.jetbrains.kotlin.light.classes.symbol.decompiled.*
|
||||
import org.jetbrains.kotlin.light.classes.symbol.source.*
|
||||
|
||||
@@ -81,5 +82,11 @@ internal fun TestGroupSuite.generateSymbolLightClassesTests() {
|
||||
model("structureByFqName", pattern = TestGeneratorUtil.KT)
|
||||
}
|
||||
}
|
||||
|
||||
run {
|
||||
testClass<AbstractSymbolLightClassesEqualityTest> {
|
||||
model("equivalentTo", pattern = TestGeneratorUtil.KT)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user