Uast: process catch parameters and finally blocks (KT-35804)

This commit is contained in:
Nicolay Mitropolsky
2020-03-22 17:23:51 +03:00
parent f1d5570ca1
commit 2eb6f1988d
8 changed files with 165 additions and 3 deletions
@@ -43,6 +43,7 @@ import org.jetbrains.kotlin.psi.psiUtil.containingClassOrObject
import org.jetbrains.kotlin.psi.psiUtil.getParentOfType
import org.jetbrains.kotlin.resolve.BindingContext
import org.jetbrains.kotlin.resolve.calls.callUtil.getResolvedCall
import org.jetbrains.kotlin.utils.addToStdlib.safeAs
import org.jetbrains.uast.*
import org.jetbrains.uast.expressions.UInjectionHost
import org.jetbrains.uast.kotlin.KotlinConverter.convertDeclaration
@@ -195,6 +196,7 @@ internal object KotlinConverter {
is KtLightParameterList -> unwrapElements(element.parent)
is KtTypeElement -> unwrapElements(element.parent)
is KtSuperTypeList -> unwrapElements(element.parent)
is KtFinallySection -> unwrapElements(element.parent)
else -> element
}
@@ -626,6 +628,10 @@ internal object KotlinConverter {
val lightParameter = lightMethod.parameterList.parameters.find { it.name == element.name } ?: return@uParam null
KotlinUParameter(lightParameter, element, givenParent)
},
alternative catch@{
val uCatchClause = element.parent?.parent?.safeAs<KtCatchClause>()?.toUElementOfType<UCatchClause>() ?: return@catch null
uCatchClause.parameters.firstOrNull { it.sourcePsi == element }
},
*convertToPropertyAlternatives(LightClassUtil.getLightClassPropertyMethods(element), givenParent)
)
@@ -199,6 +199,7 @@ open class KotlinUParameter(
override fun acceptsAnnotationTarget(target: AnnotationUseSiteTarget?): Boolean {
if (sourcePsi !is KtParameter) return false
if (isKtConstructorParam == isLightConstructorParam && target == null) return true
if (sourcePsi.parent.parent is KtCatchClause && target == null) return true
when (target) {
AnnotationUseSiteTarget.CONSTRUCTOR_PARAMETER -> return isLightConstructorParam == true
AnnotationUseSiteTarget.SETTER_PARAMETER -> return isLightConstructorParam != true
@@ -22,7 +22,9 @@ import org.jetbrains.uast.UCatchClause
import org.jetbrains.uast.UElement
import org.jetbrains.uast.UParameter
import org.jetbrains.uast.UTypeReferenceExpression
import org.jetbrains.uast.internal.acceptList
import org.jetbrains.uast.kotlin.psi.UastKotlinPsiParameter
import org.jetbrains.uast.visitor.UastVisitor
class KotlinUCatchClause(
override val sourcePsi: KtCatchClause,
@@ -34,15 +36,27 @@ class KotlinUCatchClause(
override val javaPsi: PsiElement? get() = null
override val body by lz { KotlinConverter.convertOrEmpty(sourcePsi.catchBody, this) }
override val parameters by lz {
val parameter = sourcePsi.catchParameter ?: return@lz emptyList<UParameter>()
listOf(KotlinUParameter(UastKotlinPsiParameter.create(parameter, sourcePsi, this, 0), sourcePsi, this))
listOf(KotlinUParameter(UastKotlinPsiParameter.create(parameter, sourcePsi, this, 0), parameter, this))
}
override val typeReferences by lz {
val parameter = sourcePsi.catchParameter ?: return@lz emptyList<UTypeReferenceExpression>()
val typeReference = parameter.typeReference ?: return@lz emptyList<UTypeReferenceExpression>()
listOf(LazyKotlinUTypeReferenceExpression(typeReference, this) { typeReference.toPsiType(this, boxed = true) } )
listOf(LazyKotlinUTypeReferenceExpression(typeReference, this) { typeReference.toPsiType(this, boxed = true) })
}
// equal to IDEA 202 implementation
override fun accept(visitor: UastVisitor) {
if (visitor.visitCatchClause(this)) return
parameters.acceptList(visitor)
body.accept(visitor)
visitor.afterVisitCatchClause(this)
}
// equal to IDEA 202 implementation
override fun asRenderString(): String = "catch (${parameters.joinToString { it.asRenderString() }}) ${body.asRenderString()}"
}
+32
View File
@@ -0,0 +1,32 @@
class TryCatch {
fun catches() {
try {
body()
} catch (e: Throwable) {
catcher()
} finally {
finalizer()
}
}
fun body() {}
fun catcher() {}
fun finalizer() {}
}
class TryCatchAnnotations {
@java.lang.SuppressWarnings("Something")
fun catches() {
try {
body()
} catch (@java.lang.SuppressWarnings("Something") e: Throwable) {
catcher()
} finally {
finalizer()
}
}
fun body() {}
fun catcher() {}
fun finalizer() {}
}
+61
View File
@@ -0,0 +1,61 @@
UFile (package = )
UClass (name = TryCatch)
UMethod (name = catches)
UBlockExpression
UTryExpression
UBlockExpression
UCallExpression (kind = UastCallKind(name='method_call'), argCount = 0))
UIdentifier (Identifier (body))
USimpleNameReferenceExpression (identifier = body, resolvesTo = null)
UCatchClause (e)
UParameter (name = e)
UAnnotation (fqName = org.jetbrains.annotations.NotNull)
UBlockExpression
UCallExpression (kind = UastCallKind(name='method_call'), argCount = 0))
UIdentifier (Identifier (catcher))
USimpleNameReferenceExpression (identifier = catcher, resolvesTo = null)
UBlockExpression
UCallExpression (kind = UastCallKind(name='method_call'), argCount = 0))
UIdentifier (Identifier (finalizer))
USimpleNameReferenceExpression (identifier = finalizer, resolvesTo = null)
UMethod (name = body)
UBlockExpression
UMethod (name = catcher)
UBlockExpression
UMethod (name = finalizer)
UBlockExpression
UMethod (name = TryCatch)
UClass (name = TryCatchAnnotations)
UMethod (name = catches)
UAnnotation (fqName = java.lang.SuppressWarnings)
UNamedExpression (name = value)
UPolyadicExpression (operator = +)
ULiteralExpression (value = "Something")
UBlockExpression
UTryExpression
UBlockExpression
UCallExpression (kind = UastCallKind(name='method_call'), argCount = 0))
UIdentifier (Identifier (body))
USimpleNameReferenceExpression (identifier = body, resolvesTo = null)
UCatchClause (e)
UParameter (name = e)
UAnnotation (fqName = org.jetbrains.annotations.NotNull)
UAnnotation (fqName = java.lang.SuppressWarnings)
UNamedExpression (name = value)
UPolyadicExpression (operator = +)
ULiteralExpression (value = "Something")
UBlockExpression
UCallExpression (kind = UastCallKind(name='method_call'), argCount = 0))
UIdentifier (Identifier (catcher))
USimpleNameReferenceExpression (identifier = catcher, resolvesTo = null)
UBlockExpression
UCallExpression (kind = UastCallKind(name='method_call'), argCount = 0))
UIdentifier (Identifier (finalizer))
USimpleNameReferenceExpression (identifier = finalizer, resolvesTo = null)
UMethod (name = body)
UBlockExpression
UMethod (name = catcher)
UBlockExpression
UMethod (name = finalizer)
UBlockExpression
UMethod (name = TryCatchAnnotations)
+42
View File
@@ -0,0 +1,42 @@
public final class TryCatch {
public final fun catches() : void {
try {
body()
}
catch (@org.jetbrains.annotations.NotNull var e: java.lang.Throwable) {
catcher()
}
finally {
finalizer()
}
}
public final fun body() : void {
}
public final fun catcher() : void {
}
public final fun finalizer() : void {
}
public fun TryCatch() = UastEmptyExpression
}
public final class TryCatchAnnotations {
@java.lang.SuppressWarnings(value = "Something")
public final fun catches() : void {
try {
body()
}
catch (@org.jetbrains.annotations.NotNull @java.lang.SuppressWarnings(value = "Something") var e: java.lang.Throwable) {
catcher()
}
finally {
finalizer()
}
}
public final fun body() : void {
}
public final fun catcher() : void {
}
public final fun finalizer() : void {
}
public fun TryCatchAnnotations() = UastEmptyExpression
}
@@ -163,4 +163,7 @@ class KotlinIDERenderLogTest : AbstractKotlinUastLightCodeInsightFixtureTest(),
@Test
fun testDeprecatedHidden() = doTest("DeprecatedHidden")
@Test
fun testTryCatch() = doTest("TryCatch")
}
@@ -141,6 +141,9 @@ class SimpleKotlinRenderLogTest : AbstractKotlinUastTest(), AbstractKotlinRender
@Test
fun testDeprecatedHidden() = doTest("DeprecatedHidden")
@Test
fun testTryCatch() = doTest("TryCatch")
}
fun withForceUInjectionHostValue(call: () -> Unit) {