Constructor usages are replaced too
This commit is contained in:
+30
-4
@@ -18,17 +18,19 @@ package org.jetbrains.kotlin.idea.quickfix.replaceWith
|
||||
|
||||
import org.jetbrains.kotlin.idea.core.replaced
|
||||
import org.jetbrains.kotlin.idea.util.ShortenReferences
|
||||
import org.jetbrains.kotlin.psi.JetElement
|
||||
import org.jetbrains.kotlin.psi.JetNameReferenceExpression
|
||||
import org.jetbrains.kotlin.psi.JetSimpleNameExpression
|
||||
import org.jetbrains.kotlin.psi.JetUserType
|
||||
import org.jetbrains.kotlin.psi.*
|
||||
import org.jetbrains.kotlin.psi.psiUtil.getQualifiedExpressionForSelectorOrThis
|
||||
|
||||
class ClassUsageReplacementStrategy(
|
||||
private val replacement: JetUserType
|
||||
) : UsageReplacementStrategy {
|
||||
|
||||
private val factory = JetPsiFactory(replacement)
|
||||
private val qualifierAsExpression = replacement.qualifier?.let { factory.createExpression(it.text) }
|
||||
|
||||
override fun createReplacer(usage: JetSimpleNameExpression): (() -> JetElement)? {
|
||||
if (usage !is JetNameReferenceExpression) return null
|
||||
if (replacement.referenceExpression == null) return null
|
||||
|
||||
val parent = usage.parent
|
||||
when (parent) {
|
||||
@@ -39,7 +41,31 @@ class ClassUsageReplacementStrategy(
|
||||
} //TODO: type arguments and type arguments of outer class are lost
|
||||
}
|
||||
|
||||
is JetCallExpression -> {
|
||||
if (usage != parent.calleeExpression) return null
|
||||
return { replaceConstructorCall(parent) }
|
||||
}
|
||||
|
||||
else -> return null //TODO
|
||||
}
|
||||
}
|
||||
|
||||
private fun replaceConstructorCall(callExpression: JetCallExpression): JetElement {
|
||||
callExpression.calleeExpression!!.replace(replacement.referenceExpression!!)
|
||||
|
||||
val expressionToReplace = callExpression.getQualifiedExpressionForSelectorOrThis()
|
||||
val newExpression = if (qualifierAsExpression != null)
|
||||
factory.createExpressionByPattern("$0.$1", qualifierAsExpression, callExpression)
|
||||
else
|
||||
callExpression
|
||||
|
||||
val result = if (expressionToReplace != newExpression) {
|
||||
expressionToReplace.replaced(newExpression)
|
||||
}
|
||||
else {
|
||||
expressionToReplace
|
||||
}
|
||||
|
||||
return ShortenReferences.DEFAULT.process(result)
|
||||
}
|
||||
}
|
||||
@@ -18,6 +18,7 @@ package org.jetbrains.kotlin.idea.quickfix.replaceWith
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.CallableDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.ConstructorDescriptor
|
||||
import org.jetbrains.kotlin.idea.caches.resolve.getResolutionFacade
|
||||
import org.jetbrains.kotlin.idea.references.mainReference
|
||||
import org.jetbrains.kotlin.psi.JetElement
|
||||
@@ -32,10 +33,16 @@ interface UsageReplacementStrategy {
|
||||
fun build(element: JetSimpleNameExpression, replaceWith: ReplaceWith): UsageReplacementStrategy? {
|
||||
val resolutionFacade = element.getResolutionFacade()
|
||||
val bindingContext = resolutionFacade.analyze(element, BodyResolveMode.PARTIAL)
|
||||
val target = element.mainReference.resolveToDescriptors(bindingContext).singleOrNull() ?: return null
|
||||
var target = element.mainReference.resolveToDescriptors(bindingContext).singleOrNull() ?: return null
|
||||
|
||||
var replacePatternFromSymbol = DeprecatedSymbolUsageFixBase.replaceWithPattern(target, resolutionFacade.project)
|
||||
if (replacePatternFromSymbol == null && target is ConstructorDescriptor) {
|
||||
target = target.containingDeclaration
|
||||
replacePatternFromSymbol = DeprecatedSymbolUsageFixBase.replaceWithPattern(target, resolutionFacade.project)
|
||||
}
|
||||
|
||||
// check that ReplaceWith hasn't changed
|
||||
if (DeprecatedSymbolUsageFixBase.replaceWithPattern(target, resolutionFacade.project) != replaceWith) return null
|
||||
if (replacePatternFromSymbol != replaceWith) return null
|
||||
|
||||
when (target) {
|
||||
is CallableDescriptor -> {
|
||||
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
// "Replace with 'NewClass'" "true"
|
||||
|
||||
@deprecated("", ReplaceWith("NewClass"))
|
||||
class OldClass(p: Int)
|
||||
|
||||
class NewClass(p: Int)
|
||||
|
||||
fun foo() {
|
||||
<caret>OldClass(1)
|
||||
}
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
// "Replace with 'NewClass'" "true"
|
||||
|
||||
@deprecated("", ReplaceWith("NewClass"))
|
||||
class OldClass(p: Int)
|
||||
|
||||
class NewClass(p: Int)
|
||||
|
||||
fun foo() {
|
||||
NewClass(1)
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
// "Replace with 'java.util.Random'" "true"
|
||||
|
||||
@deprecated("", ReplaceWith("java.util.Random"))
|
||||
class OldClass
|
||||
|
||||
fun foo() {
|
||||
<caret>OldClass(1)
|
||||
}
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
import java.util.Random
|
||||
|
||||
// "Replace with 'java.util.Random'" "true"
|
||||
|
||||
@deprecated("", ReplaceWith("java.util.Random"))
|
||||
class OldClass
|
||||
|
||||
fun foo() {
|
||||
Random(1)
|
||||
}
|
||||
+11
@@ -0,0 +1,11 @@
|
||||
// "Replace with 'NewClass'" "true"
|
||||
package ppp
|
||||
|
||||
@deprecated("", ReplaceWith("NewClass"))
|
||||
class OldClass(p: Int)
|
||||
|
||||
class NewClass(p: Int)
|
||||
|
||||
fun foo() {
|
||||
ppp.<caret>OldClass(1)
|
||||
}
|
||||
+11
@@ -0,0 +1,11 @@
|
||||
// "Replace with 'NewClass'" "true"
|
||||
package ppp
|
||||
|
||||
@deprecated("", ReplaceWith("NewClass"))
|
||||
class OldClass(p: Int)
|
||||
|
||||
class NewClass(p: Int)
|
||||
|
||||
fun foo() {
|
||||
NewClass(1)
|
||||
}
|
||||
@@ -3312,6 +3312,24 @@ public class QuickFixTestGenerated extends AbstractQuickFixTest {
|
||||
JetTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("idea/testData/quickfix/deprecatedSymbolUsage/classUsages"), Pattern.compile("^([\\w\\-_]+)\\.kt$"), true);
|
||||
}
|
||||
|
||||
@TestMetadata("constructorUsage1.kt")
|
||||
public void testConstructorUsage1() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/deprecatedSymbolUsage/classUsages/constructorUsage1.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("constructorUsage2.kt")
|
||||
public void testConstructorUsage2() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/deprecatedSymbolUsage/classUsages/constructorUsage2.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("constructorUsage3.kt")
|
||||
public void testConstructorUsage3() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/deprecatedSymbolUsage/classUsages/constructorUsage3.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("imports.kt")
|
||||
public void testImports() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/deprecatedSymbolUsage/classUsages/imports.kt");
|
||||
|
||||
Reference in New Issue
Block a user