Do not insert returns before Nothing in "Replace return with 'if'"

So #KT-22159 Fixed
This commit is contained in:
Toshiaki Kameyama
2018-01-17 16:52:19 +03:00
committed by Mikhail Glukhikh
parent f28bec0db1
commit 3a81be6cfb
23 changed files with 269 additions and 11 deletions
@@ -19,15 +19,16 @@ package org.jetbrains.kotlin.idea.intentions.branchedTransformations.intentions
import com.intellij.codeInsight.intention.LowPriorityAction
import com.intellij.openapi.editor.Editor
import com.intellij.openapi.util.TextRange
import org.jetbrains.kotlin.idea.caches.resolve.analyze
import org.jetbrains.kotlin.idea.core.copied
import org.jetbrains.kotlin.idea.intentions.SelfTargetingRangeIntention
import org.jetbrains.kotlin.psi.KtIfExpression
import org.jetbrains.kotlin.psi.KtPsiFactory
import org.jetbrains.kotlin.psi.KtReturnExpression
import org.jetbrains.kotlin.psi.createExpressionByPattern
import org.jetbrains.kotlin.psi.*
import org.jetbrains.kotlin.psi.psiUtil.endOffset
import org.jetbrains.kotlin.psi.psiUtil.lastBlockStatementOrThis
import org.jetbrains.kotlin.psi.psiUtil.startOffset
import org.jetbrains.kotlin.resolve.BindingContext
import org.jetbrains.kotlin.resolve.calls.callUtil.getResolvedCall
import org.jetbrains.kotlin.types.typeUtil.isNothing
class UnfoldReturnToIfIntention : SelfTargetingRangeIntention<KtReturnExpression>(KtReturnExpression::class.java, "Replace return with 'if' expression"), LowPriorityAction {
override fun applicabilityRange(element: KtReturnExpression): TextRange? {
@@ -37,14 +38,29 @@ class UnfoldReturnToIfIntention : SelfTargetingRangeIntention<KtReturnExpression
override fun applyTo(element: KtReturnExpression, editor: Editor?) {
val ifExpression = element.returnedExpression as KtIfExpression
val thenExpr = ifExpression.then!!.lastBlockStatementOrThis()
val elseExpr = ifExpression.`else`!!.lastBlockStatementOrThis()
val newIfExpression = ifExpression.copied()
val thenExpr = newIfExpression.then!!.lastBlockStatementOrThis()
val elseExpr = newIfExpression.`else`!!.lastBlockStatementOrThis()
val newThenExpr = newIfExpression.then!!.lastBlockStatementOrThis()
val newElseExpr = newIfExpression.`else`!!.lastBlockStatementOrThis()
val psiFactory = KtPsiFactory(element)
thenExpr.replace(psiFactory.createExpressionByPattern("return $0", thenExpr))
elseExpr.replace(psiFactory.createExpressionByPattern("return $0", elseExpr))
val context = element.analyze()
newThenExpr.replace(createReturnExpression(thenExpr, psiFactory, context))
newElseExpr.replace(createReturnExpression(elseExpr, psiFactory, context))
element.replace(newIfExpression)
}
companion object {
fun createReturnExpression(expr: KtExpression, psiFactory: KtPsiFactory, context: BindingContext): KtExpression {
val returnText = when (expr) {
is KtBreakExpression, is KtContinueExpression, is KtReturnExpression, is KtThrowExpression -> ""
else -> if (expr.getResolvedCall(context)?.resultingDescriptor?.returnType?.isNothing() == true) "" else "return "
}
return psiFactory.createExpressionByPattern("$returnText$0", expr)
}
}
}
@@ -19,6 +19,7 @@ package org.jetbrains.kotlin.idea.intentions.branchedTransformations.intentions
import com.intellij.codeInsight.intention.LowPriorityAction
import com.intellij.openapi.editor.Editor
import com.intellij.openapi.util.TextRange
import org.jetbrains.kotlin.idea.caches.resolve.analyze
import org.jetbrains.kotlin.idea.core.copied
import org.jetbrains.kotlin.idea.intentions.SelfTargetingRangeIntention
import org.jetbrains.kotlin.psi.*
@@ -35,14 +36,17 @@ class UnfoldReturnToWhenIntention : SelfTargetingRangeIntention<KtReturnExpressi
}
override fun applyTo(element: KtReturnExpression, editor: Editor?) {
val psiFactory = KtPsiFactory(element)
val context = element.analyze()
val whenExpression = element.returnedExpression as KtWhenExpression
val newWhenExpression = whenExpression.copied()
for (entry in newWhenExpression.entries) {
whenExpression.entries.zip(newWhenExpression.entries).forEach { (entry, newEntry) ->
val expr = entry.expression!!.lastBlockStatementOrThis()
expr.replace(KtPsiFactory(element).createExpressionByPattern("return $0", expr))
val newExpr = newEntry.expression!!.lastBlockStatementOrThis()
newExpr.replace(UnfoldReturnToIfIntention.createReturnExpression(expr, psiFactory, context))
}
element.replace(newWhenExpression)
}
}