Uast: making AbstractKotlinUClass not inherit from AbstractJavaUClass
This commit is contained in:
committed by
Nikolay Krasko
parent
084da3665a
commit
e22e466485
@@ -18,6 +18,7 @@ package org.jetbrains.uast.kotlin
|
||||
|
||||
import com.intellij.psi.PsiElement
|
||||
import org.jetbrains.kotlin.asJava.LightClassUtil
|
||||
import org.jetbrains.kotlin.asJava.classes.KtLightClassForLocalDeclaration
|
||||
import org.jetbrains.kotlin.asJava.toLightGetter
|
||||
import org.jetbrains.kotlin.asJava.toLightSetter
|
||||
import org.jetbrains.kotlin.descriptors.annotations.AnnotationUseSiteTarget
|
||||
@@ -40,6 +41,14 @@ abstract class KotlinAbstractUElement(private val givenParent: UElement?) : UEle
|
||||
val psi = psi
|
||||
var parent = psi?.parent ?: psi?.containingFile
|
||||
|
||||
if (psi is KtLightClassForLocalDeclaration) {
|
||||
val originParent = psi.kotlinOrigin.parent
|
||||
parent = when (originParent) {
|
||||
is KtClassBody -> originParent.parent
|
||||
else -> originParent
|
||||
}
|
||||
}
|
||||
|
||||
if (psi is KtAnnotationEntry) {
|
||||
val parentUnwrapped = KotlinConverter.unwrapElements(parent) ?: return null
|
||||
val target = psi.useSiteTarget?.getAnnotationUseSiteTarget()
|
||||
|
||||
@@ -18,7 +18,6 @@ package org.jetbrains.uast.kotlin
|
||||
|
||||
import com.intellij.psi.*
|
||||
import org.jetbrains.kotlin.asJava.classes.KtLightClass
|
||||
import org.jetbrains.kotlin.asJava.classes.KtLightClassForLocalDeclaration
|
||||
import org.jetbrains.kotlin.asJava.classes.KtLightClassForScript
|
||||
import org.jetbrains.kotlin.asJava.elements.KtLightMethod
|
||||
import org.jetbrains.kotlin.load.java.JvmAbi
|
||||
@@ -27,21 +26,38 @@ import org.jetbrains.kotlin.utils.SmartList
|
||||
import org.jetbrains.kotlin.utils.addIfNotNull
|
||||
import org.jetbrains.kotlin.utils.addToStdlib.firstIsInstanceOrNull
|
||||
import org.jetbrains.uast.*
|
||||
import org.jetbrains.uast.java.AbstractJavaUClass
|
||||
import org.jetbrains.uast.kotlin.declarations.KotlinUMethod
|
||||
import org.jetbrains.uast.kotlin.declarations.UastLightIdentifier
|
||||
|
||||
abstract class AbstractKotlinUClass(private val givenParent: UElement?) : AbstractJavaUClass(), JvmDeclarationUElement {
|
||||
override val uastParent: UElement? by lz { givenParent ?: convertParent() }
|
||||
abstract class AbstractKotlinUClass(givenParent: UElement?) : KotlinAbstractUElement(givenParent), UClass, JvmDeclarationUElement {
|
||||
|
||||
override val uastDeclarations by lz {
|
||||
mutableListOf<UDeclaration>().apply {
|
||||
addAll(fields)
|
||||
addAll(initializers)
|
||||
addAll(methods)
|
||||
addAll(innerClasses)
|
||||
}
|
||||
}
|
||||
|
||||
override val uastSuperTypes: List<UTypeReferenceExpression>
|
||||
get() {
|
||||
val ktClass = (psi as? KtLightClass)?.kotlinOrigin ?: return emptyList()
|
||||
return ktClass.superTypeListEntries.mapNotNull { it.typeReference }.map {
|
||||
LazyKotlinUTypeReferenceExpression(it, this)
|
||||
}
|
||||
}
|
||||
|
||||
override val uastAnchor: UElement?
|
||||
get() = UIdentifier(psi.nameIdentifier, this)
|
||||
|
||||
override val annotations: List<UAnnotation> by lz {
|
||||
(sourcePsi as? KtModifierListOwner)?.annotationEntries.orEmpty().map { KotlinUAnnotation(it, this) }
|
||||
}
|
||||
|
||||
override fun equals(other: Any?) = other is AbstractKotlinUClass && psi == other.psi
|
||||
override fun hashCode() = psi.hashCode()
|
||||
|
||||
//TODO: should be merged with KotlinAbstractUElement.convertParent() after detaching from AbstractJavaUClass
|
||||
override fun convertParent(): UElement? =
|
||||
(this.psi as? KtLightClassForLocalDeclaration)?.kotlinOrigin?.parent?.let {
|
||||
when (it) {
|
||||
is KtClassBody -> it.parent.toUElement() // TODO: it seems that `class_body`-s are never created in kotlin uast in top-down walk, probably they should be completely skipped and always unwrapped
|
||||
else -> it.toUElement()
|
||||
}
|
||||
} ?: (psi.parent ?: psi.containingFile).toUElement()
|
||||
}
|
||||
|
||||
open class KotlinUClass private constructor(
|
||||
@@ -63,9 +79,6 @@ open class KotlinUClass private constructor(
|
||||
|
||||
override fun getContainingFile(): PsiFile? = unwrapFakeFileForLightClass(psi.containingFile)
|
||||
|
||||
override val annotations: List<UAnnotation>
|
||||
get() = ktClass?.annotationEntries?.map { KotlinUAnnotation(it, this) } ?: emptyList()
|
||||
|
||||
override val uastAnchor: UElement
|
||||
get() = UIdentifier(nameIdentifier, this)
|
||||
|
||||
@@ -209,8 +222,8 @@ class KotlinUAnonymousClass(
|
||||
|
||||
class KotlinScriptUClass(
|
||||
psi: KtLightClassForScript,
|
||||
override val uastParent: UElement?
|
||||
) : AbstractJavaUClass(), PsiClass by psi {
|
||||
givenParent: UElement?
|
||||
) : AbstractKotlinUClass(givenParent), PsiClass by psi {
|
||||
override fun getContainingFile(): PsiFile = unwrapFakeFileForLightClass(psi.containingFile)
|
||||
|
||||
override fun getNameIdentifier(): PsiIdentifier? = UastLightIdentifier(psi, psi.kotlinOrigin)
|
||||
|
||||
+22
@@ -0,0 +1,22 @@
|
||||
@Test
|
||||
class A
|
||||
|
||||
annotation class MyAnnotation(val text: String)
|
||||
|
||||
@MyAnnotation("class")
|
||||
class B {
|
||||
|
||||
@MyAnnotation("inB class")
|
||||
class InB {
|
||||
|
||||
}
|
||||
|
||||
@MyAnnotation("companion")
|
||||
companion object {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@MyAnnotation("object")
|
||||
object Obj
|
||||
@@ -0,0 +1,30 @@
|
||||
UFile (package = )
|
||||
UClass (name = A)
|
||||
UAnnotation (fqName = null)
|
||||
UAnnotationMethod (name = A)
|
||||
UClass (name = MyAnnotation)
|
||||
UAnnotationMethod (name = text)
|
||||
UClass (name = B)
|
||||
UAnnotation (fqName = MyAnnotation)
|
||||
UNamedExpression (name = text)
|
||||
ULiteralExpression (value = "class")
|
||||
UField (name = Companion)
|
||||
UAnnotation (fqName = null)
|
||||
UAnnotationMethod (name = B)
|
||||
UClass (name = InB)
|
||||
UAnnotation (fqName = MyAnnotation)
|
||||
UNamedExpression (name = text)
|
||||
ULiteralExpression (value = "inB class")
|
||||
UAnnotationMethod (name = InB)
|
||||
UClass (name = Companion)
|
||||
UAnnotation (fqName = MyAnnotation)
|
||||
UNamedExpression (name = text)
|
||||
ULiteralExpression (value = "companion")
|
||||
UAnnotationMethod (name = Companion)
|
||||
UClass (name = Obj)
|
||||
UAnnotation (fqName = MyAnnotation)
|
||||
UNamedExpression (name = text)
|
||||
ULiteralExpression (value = "object")
|
||||
UField (name = INSTANCE)
|
||||
UAnnotation (fqName = null)
|
||||
UAnnotationMethod (name = Obj)
|
||||
@@ -0,0 +1,23 @@
|
||||
public final class A {
|
||||
public fun A() = UastEmptyExpression
|
||||
}
|
||||
|
||||
public abstract annotation MyAnnotation {
|
||||
public abstract fun text() : java.lang.String = UastEmptyExpression
|
||||
}
|
||||
|
||||
public final class B {
|
||||
@null public static final var Companion: B.Companion
|
||||
public fun B() = UastEmptyExpression
|
||||
public static final class InB {
|
||||
public fun InB() = UastEmptyExpression
|
||||
}
|
||||
public static final class Companion {
|
||||
private fun Companion() = UastEmptyExpression
|
||||
}
|
||||
}
|
||||
|
||||
public final class Obj {
|
||||
@null public static final var INSTANCE: Obj
|
||||
private fun Obj() = UastEmptyExpression
|
||||
}
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
public class SimpleScript : kotlin.script.templates.standard.ScriptTemplateWithArgs {
|
||||
public class SimpleScript {
|
||||
public final fun getBarOrNull(@org.jetbrains.annotations.NotNull flag: boolean) : SimpleScript.Bar {
|
||||
return if (flag) <init>(42) else null
|
||||
}
|
||||
|
||||
@@ -26,7 +26,7 @@ UFile (package = ) [public abstract interface Callback {...]
|
||||
ULambdaExpression [{ ...}] : PsiType:<ErrorType>
|
||||
UBlockExpression [{...}]
|
||||
UObjectLiteralExpression [anonymous object : Callback {... }] : PsiType:Callback
|
||||
UClass (name = null) [final class null {...}]
|
||||
UClass (name = null) [final class null : Callback {...}]
|
||||
UAnnotationMethod (name = onError) [public fun onError(@org.jetbrains.annotations.NotNull throwable: java.lang.Throwable) : void {...}]
|
||||
UParameter (name = throwable) [@org.jetbrains.annotations.NotNull var throwable: java.lang.Throwable]
|
||||
UAnnotation (fqName = org.jetbrains.annotations.NotNull) [@org.jetbrains.annotations.NotNull]
|
||||
|
||||
@@ -61,4 +61,7 @@ class SimpleKotlinRenderLogTest : AbstractKotlinRenderLogTest() {
|
||||
|
||||
@Test
|
||||
fun testConstructors() = doTest("Constructors")
|
||||
|
||||
@Test
|
||||
fun testClassAnnotation() = doTest("ClassAnnotation")
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user