"Convert put to assignment": Fix false positive inside elvis expression
So #KT-22072 Fixed
This commit is contained in:
committed by
Mikhail Glukhikh
parent
1b1e503716
commit
1ac6f18a47
@@ -23,9 +23,11 @@ import org.jetbrains.kotlin.builtins.DefaultBuiltIns
|
|||||||
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||||
import org.jetbrains.kotlin.idea.caches.resolve.analyze
|
import org.jetbrains.kotlin.idea.caches.resolve.analyze
|
||||||
import org.jetbrains.kotlin.idea.intentions.callExpression
|
import org.jetbrains.kotlin.idea.intentions.callExpression
|
||||||
|
import org.jetbrains.kotlin.lexer.KtTokens
|
||||||
import org.jetbrains.kotlin.psi.*
|
import org.jetbrains.kotlin.psi.*
|
||||||
import org.jetbrains.kotlin.psi.psiUtil.findDescendantOfType
|
import org.jetbrains.kotlin.psi.psiUtil.findDescendantOfType
|
||||||
import org.jetbrains.kotlin.psi.psiUtil.getParentOfType
|
import org.jetbrains.kotlin.psi.psiUtil.getParentOfType
|
||||||
|
import org.jetbrains.kotlin.psi.psiUtil.getStrictParentOfType
|
||||||
import org.jetbrains.kotlin.resolve.bindingContextUtil.isUsedAsExpression
|
import org.jetbrains.kotlin.resolve.bindingContextUtil.isUsedAsExpression
|
||||||
import org.jetbrains.kotlin.resolve.calls.callUtil.getResolvedCall
|
import org.jetbrains.kotlin.resolve.calls.callUtil.getResolvedCall
|
||||||
import org.jetbrains.kotlin.resolve.calls.resolvedCallUtil.getExplicitReceiverValue
|
import org.jetbrains.kotlin.resolve.calls.resolvedCallUtil.getExplicitReceiverValue
|
||||||
@@ -44,6 +46,15 @@ class ReplacePutWithAssignmentInspection : AbstractApplicabilityBasedInspection<
|
|||||||
|
|
||||||
val context = element.analyze()
|
val context = element.analyze()
|
||||||
if (element.isUsedAsExpression(context)) return false
|
if (element.isUsedAsExpression(context)) return false
|
||||||
|
|
||||||
|
// This fragment had to be added because of incorrect behaviour of isUsesAsExpression
|
||||||
|
// TODO: remove it after fix of KT-25682
|
||||||
|
val binaryExpression = element.getStrictParentOfType<KtBinaryExpression>()
|
||||||
|
val right = binaryExpression?.right
|
||||||
|
if (binaryExpression?.operationToken == KtTokens.ELVIS &&
|
||||||
|
right != null && (right == element || KtPsiUtil.deparenthesize(right) == element)
|
||||||
|
) return false
|
||||||
|
|
||||||
val resolvedCall = element.getResolvedCall(context)
|
val resolvedCall = element.getResolvedCall(context)
|
||||||
val receiverType = resolvedCall?.getExplicitReceiverValue()?.type ?: return false
|
val receiverType = resolvedCall?.getExplicitReceiverValue()?.type ?: return false
|
||||||
val receiverClass = receiverType.constructor.declarationDescriptor as? ClassDescriptor ?: return false
|
val receiverClass = receiverType.constructor.declarationDescriptor as? ClassDescriptor ?: return false
|
||||||
|
|||||||
@@ -0,0 +1,6 @@
|
|||||||
|
// PROBLEM: none
|
||||||
|
// WITH_RUNTIME
|
||||||
|
|
||||||
|
fun test(i: Int?, m: MutableMap<String, Int>) {
|
||||||
|
i ?: m.<caret>put("", 1)
|
||||||
|
}
|
||||||
@@ -0,0 +1,6 @@
|
|||||||
|
// PROBLEM: none
|
||||||
|
// WITH_RUNTIME
|
||||||
|
|
||||||
|
fun test(i: Int?, m: MutableMap<String, Int>) {
|
||||||
|
i ?: ((m.<caret>put("", 1)))
|
||||||
|
}
|
||||||
@@ -0,0 +1,6 @@
|
|||||||
|
// PROBLEM: none
|
||||||
|
// WITH_RUNTIME
|
||||||
|
|
||||||
|
fun test(i: Int?, m: MutableMap<String, Int>) {
|
||||||
|
m.<caret>put("", 1) ?: i
|
||||||
|
}
|
||||||
+15
@@ -4188,10 +4188,25 @@ public class LocalInspectionTestGenerated extends AbstractLocalInspectionTest {
|
|||||||
KotlinTestUtils.runTest(this::doTest, TargetBackend.ANY, testDataFilePath);
|
KotlinTestUtils.runTest(this::doTest, TargetBackend.ANY, testDataFilePath);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("afterElvis.kt")
|
||||||
|
public void testAfterElvis() throws Exception {
|
||||||
|
runTest("idea/testData/inspectionsLocal/replacePutWithAssignment/afterElvis.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("afterElvis2.kt")
|
||||||
|
public void testAfterElvis2() throws Exception {
|
||||||
|
runTest("idea/testData/inspectionsLocal/replacePutWithAssignment/afterElvis2.kt");
|
||||||
|
}
|
||||||
|
|
||||||
public void testAllFilesPresentInReplacePutWithAssignment() throws Exception {
|
public void testAllFilesPresentInReplacePutWithAssignment() throws Exception {
|
||||||
KotlinTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("idea/testData/inspectionsLocal/replacePutWithAssignment"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), TargetBackend.ANY, true);
|
KotlinTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("idea/testData/inspectionsLocal/replacePutWithAssignment"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), TargetBackend.ANY, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("beforeElvis.kt")
|
||||||
|
public void testBeforeElvis() throws Exception {
|
||||||
|
runTest("idea/testData/inspectionsLocal/replacePutWithAssignment/beforeElvis.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("nonMap.kt")
|
@TestMetadata("nonMap.kt")
|
||||||
public void testNonMap() throws Exception {
|
public void testNonMap() throws Exception {
|
||||||
runTest("idea/testData/inspectionsLocal/replacePutWithAssignment/nonMap.kt");
|
runTest("idea/testData/inspectionsLocal/replacePutWithAssignment/nonMap.kt");
|
||||||
|
|||||||
Reference in New Issue
Block a user