Uast: fix for creating an UClass for invalid object-literals (EA-122644, KT-20056)
This commit is contained in:
@@ -17,6 +17,7 @@
|
|||||||
package org.jetbrains.uast.kotlin
|
package org.jetbrains.uast.kotlin
|
||||||
|
|
||||||
import com.intellij.psi.*
|
import com.intellij.psi.*
|
||||||
|
import com.intellij.psi.impl.light.LightPsiClassBuilder
|
||||||
import org.jetbrains.kotlin.asJava.classes.KtLightClass
|
import org.jetbrains.kotlin.asJava.classes.KtLightClass
|
||||||
import org.jetbrains.kotlin.asJava.classes.KtLightClassForScript
|
import org.jetbrains.kotlin.asJava.classes.KtLightClassForScript
|
||||||
import org.jetbrains.kotlin.asJava.elements.KtLightMethod
|
import org.jetbrains.kotlin.asJava.elements.KtLightMethod
|
||||||
@@ -284,6 +285,37 @@ class KotlinScriptUClass(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* implementation of [UClass] for invalid code, when it is impossible to create a [KtLightClass]
|
||||||
|
*/
|
||||||
|
class KotlinInvalidUClass(
|
||||||
|
override val psi: PsiClass,
|
||||||
|
givenParent: UElement?
|
||||||
|
) : AbstractKotlinUClass(givenParent), PsiClass by psi {
|
||||||
|
|
||||||
|
constructor(name: String, context: PsiElement, givenParent: UElement?) : this(LightPsiClassBuilder(context, name), givenParent)
|
||||||
|
|
||||||
|
override fun getContainingFile(): PsiFile? = uastParent?.getContainingUFile()?.sourcePsi as? PsiFile
|
||||||
|
|
||||||
|
override val sourcePsi: PsiElement? get() = null
|
||||||
|
|
||||||
|
override val uastAnchor: UIdentifier? get() = null
|
||||||
|
|
||||||
|
override val javaPsi: PsiClass get() = psi
|
||||||
|
|
||||||
|
override fun getFields(): Array<UField> = emptyArray()
|
||||||
|
|
||||||
|
override fun getInitializers(): Array<UClassInitializer> = emptyArray()
|
||||||
|
|
||||||
|
override fun getInnerClasses(): Array<UClass> = emptyArray()
|
||||||
|
|
||||||
|
override fun getMethods(): Array<UMethod> = emptyArray()
|
||||||
|
|
||||||
|
override fun getSuperClass(): UClass? = null
|
||||||
|
|
||||||
|
override fun getOriginalElement(): PsiElement? = null
|
||||||
|
}
|
||||||
|
|
||||||
private fun reportConvertFailure(psiMethod: PsiMethod): Nothing {
|
private fun reportConvertFailure(psiMethod: PsiMethod): Nothing {
|
||||||
val isValid = psiMethod.isValid
|
val isValid = psiMethod.isValid
|
||||||
val report = KotlinExceptionWithAttachments(
|
val report = KotlinExceptionWithAttachments(
|
||||||
|
|||||||
@@ -17,6 +17,7 @@
|
|||||||
package org.jetbrains.uast.kotlin
|
package org.jetbrains.uast.kotlin
|
||||||
|
|
||||||
import com.intellij.psi.*
|
import com.intellij.psi.*
|
||||||
|
import com.intellij.psi.impl.light.LightPsiClassBuilder
|
||||||
import org.jetbrains.kotlin.asJava.classes.KtLightClass
|
import org.jetbrains.kotlin.asJava.classes.KtLightClass
|
||||||
import org.jetbrains.kotlin.asJava.classes.KtLightClassForScript
|
import org.jetbrains.kotlin.asJava.classes.KtLightClassForScript
|
||||||
import org.jetbrains.kotlin.asJava.elements.KtLightMethod
|
import org.jetbrains.kotlin.asJava.elements.KtLightMethod
|
||||||
@@ -274,6 +275,38 @@ class KotlinScriptUClass(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* implementation of [UClass] for invalid code, when it is impossible to create a [KtLightClass]
|
||||||
|
*/
|
||||||
|
class KotlinInvalidUClass(
|
||||||
|
override val psi: PsiClass,
|
||||||
|
givenParent: UElement?
|
||||||
|
) : AbstractKotlinUClass(givenParent), PsiClass by psi {
|
||||||
|
|
||||||
|
constructor(name: String, context: PsiElement, givenParent: UElement?) : this(LightPsiClassBuilder(context, name), givenParent)
|
||||||
|
|
||||||
|
override fun getContainingFile(): PsiFile? =
|
||||||
|
(uastParent?.getContainingUFile() as? JvmDeclarationUElementPlaceholder)?.sourcePsi as? PsiFile
|
||||||
|
|
||||||
|
override val sourcePsi: PsiElement? get() = null
|
||||||
|
|
||||||
|
override val uastAnchor: UIdentifier? get() = null
|
||||||
|
|
||||||
|
override val javaPsi: PsiClass get() = psi
|
||||||
|
|
||||||
|
override fun getFields(): Array<UField> = emptyArray()
|
||||||
|
|
||||||
|
override fun getInitializers(): Array<UClassInitializer> = emptyArray()
|
||||||
|
|
||||||
|
override fun getInnerClasses(): Array<UClass> = emptyArray()
|
||||||
|
|
||||||
|
override fun getMethods(): Array<UMethod> = emptyArray()
|
||||||
|
|
||||||
|
override fun getSuperClass(): UClass? = null
|
||||||
|
|
||||||
|
override fun getOriginalElement(): PsiElement? = null
|
||||||
|
}
|
||||||
|
|
||||||
private fun reportConvertFailure(psiMethod: PsiMethod): Nothing {
|
private fun reportConvertFailure(psiMethod: PsiMethod): Nothing {
|
||||||
val isValid = psiMethod.isValid
|
val isValid = psiMethod.isValid
|
||||||
val report = KotlinExceptionWithAttachments(
|
val report = KotlinExceptionWithAttachments(
|
||||||
|
|||||||
+3
-18
@@ -16,12 +16,8 @@
|
|||||||
|
|
||||||
package org.jetbrains.uast.kotlin
|
package org.jetbrains.uast.kotlin
|
||||||
|
|
||||||
import com.intellij.openapi.diagnostic.Attachment
|
|
||||||
import com.intellij.openapi.diagnostic.Logger
|
|
||||||
import com.intellij.psi.PsiMethod
|
import com.intellij.psi.PsiMethod
|
||||||
import com.intellij.psi.PsiType
|
import com.intellij.psi.PsiType
|
||||||
import com.intellij.psi.impl.light.LightPsiClassBuilder
|
|
||||||
import org.jetbrains.kotlin.asJava.classes.KtLightClass
|
|
||||||
import org.jetbrains.kotlin.asJava.toLightClass
|
import org.jetbrains.kotlin.asJava.toLightClass
|
||||||
import org.jetbrains.kotlin.psi.KtObjectLiteralExpression
|
import org.jetbrains.kotlin.psi.KtObjectLiteralExpression
|
||||||
import org.jetbrains.kotlin.psi.KtSuperTypeCallEntry
|
import org.jetbrains.kotlin.psi.KtSuperTypeCallEntry
|
||||||
@@ -34,17 +30,9 @@ class KotlinUObjectLiteralExpression(
|
|||||||
) : KotlinAbstractUExpression(givenParent), UObjectLiteralExpression, UCallExpressionEx, KotlinUElementWithType {
|
) : KotlinAbstractUExpression(givenParent), UObjectLiteralExpression, UCallExpressionEx, KotlinUElementWithType {
|
||||||
|
|
||||||
override val declaration: UClass by lz {
|
override val declaration: UClass by lz {
|
||||||
val lightClass: KtLightClass? = psi.objectDeclaration.toLightClass()
|
psi.objectDeclaration.toLightClass()
|
||||||
if (lightClass != null) {
|
?.let { getLanguagePlugin().convert<UClass>(it, this) }
|
||||||
getLanguagePlugin().convert<UClass>(lightClass, this)
|
?: KotlinInvalidUClass("<invalid object code>", psi, this)
|
||||||
} else {
|
|
||||||
logger.error(
|
|
||||||
"Failed to create light class for object declaration",
|
|
||||||
Attachment(psi.containingFile.virtualFile?.path ?: "<no path>", psi.containingFile.text)
|
|
||||||
)
|
|
||||||
|
|
||||||
getLanguagePlugin().convert(LightPsiClassBuilder(psi, "<unnamed>"), this)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun getExpressionType() = psi.objectDeclaration.toPsiType()
|
override fun getExpressionType() = psi.objectDeclaration.toPsiType()
|
||||||
@@ -96,7 +84,4 @@ class KotlinUObjectLiteralExpression(
|
|||||||
get() = psi.name ?: "<error>"
|
get() = psi.name ?: "<error>"
|
||||||
}
|
}
|
||||||
|
|
||||||
companion object {
|
|
||||||
val logger by lz { Logger.getInstance(KotlinUObjectLiteralExpression::class.java) }
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
+3
-18
@@ -16,12 +16,8 @@
|
|||||||
|
|
||||||
package org.jetbrains.uast.kotlin
|
package org.jetbrains.uast.kotlin
|
||||||
|
|
||||||
import com.intellij.openapi.diagnostic.Attachment
|
|
||||||
import com.intellij.openapi.diagnostic.Logger
|
|
||||||
import com.intellij.psi.PsiMethod
|
import com.intellij.psi.PsiMethod
|
||||||
import com.intellij.psi.PsiType
|
import com.intellij.psi.PsiType
|
||||||
import com.intellij.psi.impl.light.LightPsiClassBuilder
|
|
||||||
import org.jetbrains.kotlin.asJava.classes.KtLightClass
|
|
||||||
import org.jetbrains.kotlin.asJava.toLightClass
|
import org.jetbrains.kotlin.asJava.toLightClass
|
||||||
import org.jetbrains.kotlin.psi.KtObjectLiteralExpression
|
import org.jetbrains.kotlin.psi.KtObjectLiteralExpression
|
||||||
import org.jetbrains.kotlin.psi.KtSuperTypeCallEntry
|
import org.jetbrains.kotlin.psi.KtSuperTypeCallEntry
|
||||||
@@ -32,17 +28,9 @@ class KotlinUObjectLiteralExpression(
|
|||||||
givenParent: UElement?
|
givenParent: UElement?
|
||||||
) : KotlinAbstractUExpression(givenParent), UObjectLiteralExpression, KotlinUElementWithType {
|
) : KotlinAbstractUExpression(givenParent), UObjectLiteralExpression, KotlinUElementWithType {
|
||||||
override val declaration: UClass by lz {
|
override val declaration: UClass by lz {
|
||||||
val lightClass: KtLightClass? = psi.objectDeclaration.toLightClass()
|
psi.objectDeclaration.toLightClass()
|
||||||
if (lightClass != null) {
|
?.let { getLanguagePlugin().convert<UClass>(it, this) }
|
||||||
getLanguagePlugin().convert<UClass>(lightClass, this)
|
?: KotlinInvalidUClass("<invalid object code>", psi, this)
|
||||||
} else {
|
|
||||||
logger.error(
|
|
||||||
"Failed to create light class for object declaration",
|
|
||||||
Attachment(psi.containingFile.virtualFile?.path ?: "<no path>", psi.containingFile.text)
|
|
||||||
)
|
|
||||||
|
|
||||||
getLanguagePlugin().convert(LightPsiClassBuilder(psi, "<unnamed>"), this)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun getExpressionType() = psi.objectDeclaration.toPsiType()
|
override fun getExpressionType() = psi.objectDeclaration.toPsiType()
|
||||||
@@ -91,7 +79,4 @@ class KotlinUObjectLiteralExpression(
|
|||||||
get() = psi.name ?: "<error>"
|
get() = psi.name ?: "<error>"
|
||||||
}
|
}
|
||||||
|
|
||||||
companion object {
|
|
||||||
val logger by lz { Logger.getInstance(KotlinUObjectLiteralExpression::class.java) }
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
@@ -29,3 +29,7 @@ foo -> UAnnotationMethod (name = foo)
|
|||||||
read -> UAnnotationMethod (name = read)
|
read -> UAnnotationMethod (name = read)
|
||||||
Int -> USimpleNameReferenceExpression (identifier = Int)
|
Int -> USimpleNameReferenceExpression (identifier = Int)
|
||||||
run -> UAnnotationMethod (name = run)
|
run -> UAnnotationMethod (name = run)
|
||||||
|
withErr -> UAnnotationMethod (name = withErr)
|
||||||
|
runnable -> ULocalVariable (name = runnable)
|
||||||
|
object -> UastEmptyExpression
|
||||||
|
Runnable -> null
|
||||||
|
|||||||
+4
@@ -9,4 +9,8 @@ fun foo() {
|
|||||||
runnable2.run()
|
runnable2.run()
|
||||||
val closeableRunnable = object : Runnable, Closeable { override fun close() {} override fun run() {} }
|
val closeableRunnable = object : Runnable, Closeable { override fun close() {} override fun run() {} }
|
||||||
val runnableIs = object : InputStream(), Runnable { override fun read(): Int = 0; override fun run() {} }
|
val runnableIs = object : InputStream(), Runnable { override fun read(): Int = 0; override fun run() {} }
|
||||||
|
}
|
||||||
|
|
||||||
|
fun withErr() {
|
||||||
|
val runnable = object Runnable {} // EA-122644
|
||||||
}
|
}
|
||||||
@@ -51,3 +51,9 @@ UFile (package = )
|
|||||||
UAnnotationMethod (name = run)
|
UAnnotationMethod (name = run)
|
||||||
UBlockExpression
|
UBlockExpression
|
||||||
UAnnotationMethod (name = AnonymousKt$foo$runnableIs$1)
|
UAnnotationMethod (name = AnonymousKt$foo$runnableIs$1)
|
||||||
|
UAnnotationMethod (name = withErr)
|
||||||
|
UBlockExpression
|
||||||
|
UDeclarationsExpression
|
||||||
|
ULocalVariable (name = runnable)
|
||||||
|
UObjectLiteralExpression
|
||||||
|
UClass (name = <invalid object code>)
|
||||||
|
|||||||
@@ -12,4 +12,7 @@ public final class AnonymousKt {
|
|||||||
var closeableRunnable: <ErrorType> = anonymous object : Runnable, Closeable { override fun close() {} override fun run() {} }
|
var closeableRunnable: <ErrorType> = anonymous object : Runnable, Closeable { override fun close() {} override fun run() {} }
|
||||||
var runnableIs: <ErrorType> = anonymous object : InputStream(), Runnable { override fun read(): Int = 0; override fun run() {} }
|
var runnableIs: <ErrorType> = anonymous object : InputStream(), Runnable { override fun read(): Int = 0; override fun run() {} }
|
||||||
}
|
}
|
||||||
|
public static final fun withErr() : void {
|
||||||
|
var runnable: <ErrorType> = anonymous null
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user