Convert to anonymous function: do not suggest for suspend functions
#KT-37842 Fixed
This commit is contained in:
committed by
Yan Zhulanow
parent
ded996bdf7
commit
a4239afcb3
+13
-3
@@ -7,6 +7,7 @@ package org.jetbrains.kotlin.idea.intentions
|
|||||||
|
|
||||||
import com.intellij.codeInsight.intention.LowPriorityAction
|
import com.intellij.codeInsight.intention.LowPriorityAction
|
||||||
import com.intellij.openapi.editor.Editor
|
import com.intellij.openapi.editor.Editor
|
||||||
|
import org.jetbrains.kotlin.builtins.isSuspendFunctionType
|
||||||
import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
||||||
import org.jetbrains.kotlin.descriptors.impl.AnonymousFunctionDescriptor
|
import org.jetbrains.kotlin.descriptors.impl.AnonymousFunctionDescriptor
|
||||||
import org.jetbrains.kotlin.idea.KotlinBundle
|
import org.jetbrains.kotlin.idea.KotlinBundle
|
||||||
@@ -22,7 +23,10 @@ import org.jetbrains.kotlin.psi.*
|
|||||||
import org.jetbrains.kotlin.psi.psiUtil.collectDescendantsOfType
|
import org.jetbrains.kotlin.psi.psiUtil.collectDescendantsOfType
|
||||||
import org.jetbrains.kotlin.psi.psiUtil.endOffset
|
import org.jetbrains.kotlin.psi.psiUtil.endOffset
|
||||||
import org.jetbrains.kotlin.psi.psiUtil.getStrictParentOfType
|
import org.jetbrains.kotlin.psi.psiUtil.getStrictParentOfType
|
||||||
|
import org.jetbrains.kotlin.resolve.BindingContext
|
||||||
import org.jetbrains.kotlin.resolve.bindingContextUtil.getTargetFunctionDescriptor
|
import org.jetbrains.kotlin.resolve.bindingContextUtil.getTargetFunctionDescriptor
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.callUtil.getParameterForArgument
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.callUtil.getResolvedCall
|
||||||
import org.jetbrains.kotlin.resolve.lazy.BodyResolveMode
|
import org.jetbrains.kotlin.resolve.lazy.BodyResolveMode
|
||||||
import org.jetbrains.kotlin.types.isFlexible
|
import org.jetbrains.kotlin.types.isFlexible
|
||||||
import org.jetbrains.kotlin.types.typeUtil.isTypeParameter
|
import org.jetbrains.kotlin.types.typeUtil.isTypeParameter
|
||||||
@@ -35,10 +39,16 @@ class LambdaToAnonymousFunctionIntention : SelfTargetingIntention<KtLambdaExpres
|
|||||||
KotlinBundle.lazyMessage("convert.lambda.expression.to.anonymous.function")
|
KotlinBundle.lazyMessage("convert.lambda.expression.to.anonymous.function")
|
||||||
), LowPriorityAction {
|
), LowPriorityAction {
|
||||||
override fun isApplicableTo(element: KtLambdaExpression, caretOffset: Int): Boolean {
|
override fun isApplicableTo(element: KtLambdaExpression, caretOffset: Int): Boolean {
|
||||||
if (element.getStrictParentOfType<KtValueArgument>() == null) return false
|
val argument = element.getStrictParentOfType<KtValueArgument>() ?: return false
|
||||||
if (element.getStrictParentOfType<KtFunction>()?.hasModifier(KtTokens.INLINE_KEYWORD) == true) return false
|
val call = argument.getStrictParentOfType<KtCallElement>() ?: return false
|
||||||
val descriptor = element.functionLiteral.descriptor as? AnonymousFunctionDescriptor ?: return false
|
if (call.getStrictParentOfType<KtFunction>()?.hasModifier(KtTokens.INLINE_KEYWORD) == true) return false
|
||||||
|
|
||||||
|
val context = call.analyze(BodyResolveMode.PARTIAL)
|
||||||
|
if (call.getResolvedCall(context)?.getParameterForArgument(argument)?.type?.isSuspendFunctionType == true) return false
|
||||||
|
val descriptor =
|
||||||
|
context[BindingContext.DECLARATION_TO_DESCRIPTOR, element.functionLiteral] as? AnonymousFunctionDescriptor ?: return false
|
||||||
if (descriptor.valueParameters.any { it.name.isSpecial }) return false
|
if (descriptor.valueParameters.any { it.name.isSpecial }) return false
|
||||||
|
|
||||||
val lastElement = element.functionLiteral.arrow ?: element.functionLiteral.lBrace
|
val lastElement = element.functionLiteral.arrow ?: element.functionLiteral.lBrace
|
||||||
return caretOffset <= lastElement.endOffset
|
return caretOffset <= lastElement.endOffset
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,9 @@
|
|||||||
|
// IS_APPLICABLE: false
|
||||||
|
suspend fun sus(i: Int, block: suspend (Int) -> Unit) {
|
||||||
|
block(i)
|
||||||
|
}
|
||||||
|
|
||||||
|
suspend fun main() {
|
||||||
|
sus(1) {<caret>
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -10528,6 +10528,11 @@ public class IntentionTestGenerated extends AbstractIntentionTest {
|
|||||||
runTest("idea/testData/intentions/lambdaToAnonymousFunction/returnUnit.kt");
|
runTest("idea/testData/intentions/lambdaToAnonymousFunction/returnUnit.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("suspendFunction.kt")
|
||||||
|
public void testSuspendFunction() throws Exception {
|
||||||
|
runTest("idea/testData/intentions/lambdaToAnonymousFunction/suspendFunction.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("underscoreParameter.kt")
|
@TestMetadata("underscoreParameter.kt")
|
||||||
public void testUnderscoreParameter() throws Exception {
|
public void testUnderscoreParameter() throws Exception {
|
||||||
runTest("idea/testData/intentions/lambdaToAnonymousFunction/underscoreParameter.kt");
|
runTest("idea/testData/intentions/lambdaToAnonymousFunction/underscoreParameter.kt");
|
||||||
|
|||||||
Reference in New Issue
Block a user