Change Signature: Propagate parameters to chosen callers
#KT-7902 Fixed
This commit is contained in:
@@ -19,13 +19,14 @@ package org.jetbrains.kotlin.idea.refactoring.changeSignature
|
||||
import com.intellij.lang.Language
|
||||
import com.intellij.lang.java.JavaLanguage
|
||||
import com.intellij.psi.*
|
||||
import com.intellij.refactoring.changeSignature.ChangeInfo
|
||||
import com.intellij.refactoring.changeSignature.ChangeSignatureProcessor
|
||||
import com.intellij.refactoring.changeSignature.JavaChangeInfo
|
||||
import com.intellij.refactoring.changeSignature.ParameterInfoImpl
|
||||
import com.intellij.psi.search.searches.OverridingMethodsSearch
|
||||
import com.intellij.refactoring.changeSignature.*
|
||||
import com.intellij.refactoring.util.CanonicalTypes
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import com.intellij.util.VisibilityUtil
|
||||
import org.jetbrains.kotlin.asJava.getRepresentativeLightMethod
|
||||
import org.jetbrains.kotlin.asJava.toLightMethods
|
||||
import org.jetbrains.kotlin.asJava.unwrapped
|
||||
import org.jetbrains.kotlin.builtins.KotlinBuiltIns
|
||||
import org.jetbrains.kotlin.codegen.PropertyCodegen
|
||||
import org.jetbrains.kotlin.descriptors.CallableDescriptor
|
||||
@@ -37,16 +38,18 @@ import org.jetbrains.kotlin.idea.core.refactoring.j2k
|
||||
import org.jetbrains.kotlin.idea.project.ProjectStructureUtil
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetMethodDescriptor.Kind
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.usages.JetCallableDefinitionUsage
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.usages.KotlinCallerUsage
|
||||
import org.jetbrains.kotlin.idea.util.IdeDescriptorRenderers
|
||||
import org.jetbrains.kotlin.lexer.JetTokens
|
||||
import org.jetbrains.kotlin.load.java.JvmAbi
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
import org.jetbrains.kotlin.psi.*
|
||||
import org.jetbrains.kotlin.psi.psiUtil.parameterIndex
|
||||
import org.jetbrains.kotlin.resolve.DescriptorToSourceUtils
|
||||
import org.jetbrains.kotlin.types.JetType
|
||||
import org.jetbrains.kotlin.utils.addToStdlib.singletonOrEmptyList
|
||||
import java.util.*
|
||||
import java.util.ArrayList
|
||||
import java.util.HashMap
|
||||
import java.util.LinkedHashSet
|
||||
import kotlin.properties.Delegates
|
||||
|
||||
public class JetChangeInfo(
|
||||
@@ -57,7 +60,8 @@ public class JetChangeInfo(
|
||||
var newVisibility: Visibility = methodDescriptor.getVisibility(),
|
||||
parameterInfos: List<JetParameterInfo> = methodDescriptor.getParameters(),
|
||||
receiver: JetParameterInfo? = methodDescriptor.receiver,
|
||||
val context: PsiElement
|
||||
val context: PsiElement,
|
||||
primaryPropagationTargets: Collection<PsiElement> = emptyList()
|
||||
): ChangeInfo {
|
||||
var receiverParameterInfo: JetParameterInfo? = receiver
|
||||
set(value: JetParameterInfo?) {
|
||||
@@ -148,6 +152,42 @@ public class JetChangeInfo(
|
||||
|
||||
override fun getLanguage(): Language = JetLanguage.INSTANCE
|
||||
|
||||
public var propagationTargetUsageInfos: List<UsageInfo> = ArrayList()
|
||||
private set
|
||||
|
||||
public var primaryPropagationTargets: Collection<PsiElement> = emptyList()
|
||||
set(value: Collection<PsiElement>) {
|
||||
$primaryPropagationTargets = value
|
||||
|
||||
val result = LinkedHashSet<UsageInfo>()
|
||||
|
||||
fun add(element: PsiElement) {
|
||||
element.unwrapped?.let {
|
||||
val usageInfo = when (it) {
|
||||
is JetNamedFunction, is JetConstructor<*>, is JetClassOrObject ->
|
||||
KotlinCallerUsage(it as JetNamedDeclaration)
|
||||
is PsiMethod ->
|
||||
CallerUsageInfo(it, true, true)
|
||||
else ->
|
||||
return
|
||||
}
|
||||
|
||||
result.add(usageInfo)
|
||||
}
|
||||
}
|
||||
|
||||
for (caller in value) {
|
||||
add(caller)
|
||||
OverridingMethodsSearch.search(caller.getRepresentativeLightMethod() ?: continue).forEach { add(it) }
|
||||
}
|
||||
|
||||
propagationTargetUsageInfos = result.toList()
|
||||
}
|
||||
|
||||
init {
|
||||
this.primaryPropagationTargets = primaryPropagationTargets
|
||||
}
|
||||
|
||||
public fun getNewSignature(inheritedCallable: JetCallableDefinitionUsage<PsiElement>): String {
|
||||
val buffer = StringBuilder()
|
||||
|
||||
@@ -239,13 +279,22 @@ public class JetChangeInfo(
|
||||
VisibilityUtil.getVisibilityModifier(currentPsiMethod.getModifierList())
|
||||
else
|
||||
PsiModifier.PACKAGE_LOCAL
|
||||
val javaChangeInfo = ChangeSignatureProcessor(getMethod().getProject(),
|
||||
originalPsiMethod,
|
||||
false,
|
||||
newVisibility,
|
||||
newName,
|
||||
newReturnType ?: PsiType.VOID,
|
||||
newParameters).getChangeInfo()
|
||||
val propagationTargets = primaryPropagationTargets.asSequence()
|
||||
.map { it.getRepresentativeLightMethod() }
|
||||
.filterNotNull()
|
||||
.toSet()
|
||||
val javaChangeInfo = ChangeSignatureProcessor(
|
||||
getMethod().getProject(),
|
||||
originalPsiMethod,
|
||||
false,
|
||||
newVisibility,
|
||||
newName,
|
||||
CanonicalTypes.createTypeWrapper(newReturnType ?: PsiType.VOID),
|
||||
newParameters,
|
||||
arrayOf<ThrownExceptionInfo>(),
|
||||
propagationTargets,
|
||||
emptySet()
|
||||
).getChangeInfo()
|
||||
javaChangeInfo.updateMethod(currentPsiMethod)
|
||||
|
||||
return javaChangeInfo
|
||||
@@ -336,7 +385,7 @@ public val JetChangeInfo.kind: Kind get() = methodDescriptor.kind
|
||||
public val JetChangeInfo.oldName: String?
|
||||
get() = (methodDescriptor.getMethod() as? JetFunction)?.getName()
|
||||
|
||||
public val JetChangeInfo.affectedFunctions: Collection<UsageInfo> get() = methodDescriptor.affectedCallables
|
||||
public fun JetChangeInfo.getAffectedCallables(): Collection<UsageInfo> = methodDescriptor.affectedCallables + propagationTargetUsageInfos
|
||||
|
||||
public fun ChangeInfo.toJetChangeInfo(originalChangeSignatureDescriptor: JetMethodDescriptor): JetChangeInfo {
|
||||
val method = getMethod() as PsiMethod
|
||||
@@ -369,7 +418,7 @@ public fun ChangeInfo.toJetChangeInfo(originalChangeSignatureDescriptor: JetMeth
|
||||
name = info.getName(),
|
||||
type = if (oldIndex >= 0) originalParameterDescriptors[oldIndex].getType() else currentType,
|
||||
defaultValueForCall = defaultValueExpr)) {
|
||||
currentTypeText = IdeDescriptorRenderers.SOURCE_CODE.renderType(currentType)
|
||||
currentTypeText = IdeDescriptorRenderers.SOURCE_CODE_FOR_TYPE_ARGUMENTS.renderType(currentType)
|
||||
this
|
||||
}
|
||||
}
|
||||
|
||||
+2
-1
@@ -26,6 +26,7 @@ import com.intellij.refactoring.changeSignature.ChangeSignatureProcessorBase
|
||||
import com.intellij.refactoring.changeSignature.ChangeSignatureUsageProcessor
|
||||
import com.intellij.refactoring.changeSignature.JavaChangeSignatureUsageProcessor
|
||||
import com.intellij.refactoring.rename.RenameUtil
|
||||
import com.intellij.refactoring.rename.UnresolvableCollisionUsageInfo
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import com.intellij.usageView.UsageViewDescriptor
|
||||
import com.intellij.util.containers.MultiMap
|
||||
@@ -52,7 +53,7 @@ public class JetChangeSignatureProcessor(project: Project,
|
||||
KotlinWrapperForJavaUsageInfos(it, javaProcessor.findUsages(it), getChangeInfo().getMethod())
|
||||
}
|
||||
}
|
||||
super.findUsages().filterIsInstanceTo(allUsages, javaClass<JetUsageInfo<PsiElement>>())
|
||||
super.findUsages().filterTo(allUsages) { it is JetUsageInfo<*> || it is UnresolvableCollisionUsageInfo }
|
||||
|
||||
return allUsages.toTypedArray()
|
||||
}
|
||||
|
||||
+198
-28
@@ -28,6 +28,7 @@ import com.intellij.psi.search.searches.ReferencesSearch;
|
||||
import com.intellij.psi.util.PsiTreeUtil;
|
||||
import com.intellij.refactoring.changeSignature.*;
|
||||
import com.intellij.refactoring.rename.ResolveSnapshotProvider;
|
||||
import com.intellij.refactoring.rename.UnresolvableCollisionUsageInfo;
|
||||
import com.intellij.refactoring.util.CommonRefactoringUtil;
|
||||
import com.intellij.refactoring.util.MoveRenameUsageInfo;
|
||||
import com.intellij.refactoring.util.RefactoringUIUtil;
|
||||
@@ -54,6 +55,7 @@ import org.jetbrains.kotlin.idea.core.refactoring.RefactoringPackage;
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.usages.*;
|
||||
import org.jetbrains.kotlin.idea.references.JetSimpleNameReference;
|
||||
import org.jetbrains.kotlin.idea.search.usagesSearch.UsagesSearchPackage;
|
||||
import org.jetbrains.kotlin.idea.util.IdeDescriptorRenderers;
|
||||
import org.jetbrains.kotlin.kdoc.psi.impl.KDocName;
|
||||
import org.jetbrains.kotlin.load.java.descriptors.JavaClassDescriptor;
|
||||
import org.jetbrains.kotlin.name.Name;
|
||||
@@ -68,6 +70,7 @@ import org.jetbrains.kotlin.resolve.DescriptorUtils;
|
||||
import org.jetbrains.kotlin.resolve.calls.callUtil.CallUtilPackage;
|
||||
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall;
|
||||
import org.jetbrains.kotlin.resolve.calls.smartcasts.DataFlowInfo;
|
||||
import org.jetbrains.kotlin.resolve.calls.tasks.ExplicitReceiverKind;
|
||||
import org.jetbrains.kotlin.resolve.lazy.BodyResolveMode;
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScope;
|
||||
import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValue;
|
||||
@@ -80,6 +83,8 @@ import java.util.*;
|
||||
public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsageProcessor {
|
||||
@Override
|
||||
public UsageInfo[] findUsages(ChangeInfo info) {
|
||||
originalJavaMethodDescriptor = null;
|
||||
|
||||
Set<UsageInfo> result = new HashSet<UsageInfo>();
|
||||
|
||||
if (info instanceof JetChangeInfo) {
|
||||
@@ -89,19 +94,29 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
findSAMUsages(info, result);
|
||||
findConstructorDelegationUsages(info, result);
|
||||
findKotlinOverrides(info, result);
|
||||
if (info instanceof JavaChangeInfo) {
|
||||
findKotlinCallers((JavaChangeInfo) info, result);
|
||||
}
|
||||
}
|
||||
|
||||
return result.toArray(new UsageInfo[result.size()]);
|
||||
}
|
||||
|
||||
private static void findAllMethodUsages(JetChangeInfo changeInfo, Set<UsageInfo> result) {
|
||||
for (UsageInfo functionUsageInfo : ChangeSignaturePackage.getAffectedFunctions(changeInfo)) {
|
||||
for (UsageInfo functionUsageInfo : ChangeSignaturePackage.getAffectedCallables(changeInfo)) {
|
||||
if (functionUsageInfo instanceof JetCallableDefinitionUsage) {
|
||||
findOneMethodUsages((JetCallableDefinitionUsage) functionUsageInfo, changeInfo, result);
|
||||
}
|
||||
else if (functionUsageInfo instanceof KotlinCallerUsage) {
|
||||
findCallerUsages((KotlinCallerUsage) functionUsageInfo, changeInfo, result);
|
||||
}
|
||||
else {
|
||||
result.add(functionUsageInfo);
|
||||
|
||||
boolean propagationTarget = functionUsageInfo instanceof CallerUsageInfo
|
||||
|| (functionUsageInfo instanceof OverriderUsageInfo
|
||||
&& !((OverriderUsageInfo) functionUsageInfo).isOriginalOverrider());
|
||||
|
||||
PsiElement callee = functionUsageInfo.getElement();
|
||||
if (callee == null) continue;
|
||||
|
||||
@@ -115,13 +130,89 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
JetCallElement callElement = PsiTreeUtil.getParentOfType(element, JetCallElement.class);
|
||||
JetExpression calleeExpression = callElement != null ? callElement.getCalleeExpression() : null;
|
||||
if (calleeExpression != null && PsiTreeUtil.isAncestor(calleeExpression, element, false)) {
|
||||
result.add(new JetFunctionCallUsage(callElement, changeInfo.getMethodDescriptor().getOriginalPrimaryCallable()));
|
||||
result.add(propagationTarget
|
||||
? new KotlinCallerCallUsage(callElement)
|
||||
: new JetFunctionCallUsage(callElement, changeInfo.getMethodDescriptor().getOriginalPrimaryCallable()));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static void findCallerUsages(KotlinCallerUsage callerUsage, JetChangeInfo changeInfo, final Set<UsageInfo> result) {
|
||||
result.add(callerUsage);
|
||||
|
||||
JetNamedDeclaration element = callerUsage.getElement();
|
||||
if (element == null) return;
|
||||
|
||||
for (PsiReference ref : ReferencesSearch.search(element, element.getUseScope())) {
|
||||
PsiElement refElement = ref.getElement();
|
||||
JetCallElement callElement = PsiTreeUtil.getParentOfType(refElement, JetCallElement.class);
|
||||
if (callElement != null && PsiTreeUtil.isAncestor(callElement.getCalleeExpression(), refElement, false)) {
|
||||
result.add(new KotlinCallerCallUsage(callElement));
|
||||
}
|
||||
}
|
||||
|
||||
JetElement body = ChangeSignaturePackage.getDeclarationBody(element);
|
||||
final Set<String> newParameterNames = KotlinPackage.mapTo(
|
||||
changeInfo.getNonReceiverParameters(),
|
||||
new HashSet<String>(),
|
||||
new Function1<JetParameterInfo, String>() {
|
||||
@Override
|
||||
public String invoke(JetParameterInfo info) {
|
||||
return info.getName();
|
||||
}
|
||||
}
|
||||
);
|
||||
if (body != null) {
|
||||
final DeclarationDescriptor callerDescriptor = ResolvePackage.resolveToDescriptor(element);
|
||||
final BindingContext context = ResolvePackage.analyze(body);
|
||||
body.accept(
|
||||
new JetTreeVisitorVoid() {
|
||||
@Override
|
||||
public void visitSimpleNameExpression(@NotNull JetSimpleNameExpression expression) {
|
||||
final String currentName = expression.getReferencedName();
|
||||
if (!newParameterNames.contains(currentName)) return;
|
||||
|
||||
ResolvedCall<? extends CallableDescriptor> resolvedCall = CallUtilPackage.getResolvedCall(expression, context);
|
||||
if (resolvedCall == null) return;
|
||||
|
||||
if (resolvedCall.getExplicitReceiverKind() != ExplicitReceiverKind.NO_EXPLICIT_RECEIVER) return;
|
||||
|
||||
CallableDescriptor resultingDescriptor = resolvedCall.getResultingDescriptor();
|
||||
if (!(resultingDescriptor instanceof VariableDescriptor)) return;
|
||||
|
||||
// Do not report usages of duplicated parameter
|
||||
if (resultingDescriptor instanceof ValueParameterDescriptor
|
||||
&& resultingDescriptor.getContainingDeclaration() == callerDescriptor) return;
|
||||
|
||||
JetElement callElement = resolvedCall.getCall().getCallElement();
|
||||
|
||||
ReceiverValue receiver = resolvedCall.getExtensionReceiver();
|
||||
if (!(receiver instanceof ThisReceiver)) {
|
||||
receiver = resolvedCall.getDispatchReceiver();
|
||||
}
|
||||
if (receiver instanceof ThisReceiver) {
|
||||
result.add(new JetImplicitThisUsage(callElement, ((ThisReceiver) receiver).getDeclarationDescriptor()));
|
||||
}
|
||||
else if (!receiver.exists()) {
|
||||
result.add(
|
||||
new UnresolvableCollisionUsageInfo(callElement, null) {
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return "There is already a variable '" + currentName + "' in " +
|
||||
IdeDescriptorRenderers.SOURCE_CODE_SHORT_NAMES_IN_TYPES.render(callerDescriptor) +
|
||||
". It will conflict with the new parameter.";
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
private static void findOneMethodUsages(
|
||||
@NotNull JetCallableDefinitionUsage<?> functionUsageInfo,
|
||||
final JetChangeInfo changeInfo,
|
||||
@@ -269,7 +360,7 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
result.add(new JetImplicitThisToParameterUsage(callElement, originalReceiverInfo, functionUsageInfo));
|
||||
}
|
||||
else {
|
||||
result.add(new JetImplicitOuterThisToQualifiedThisUsage(callElement, targetDescriptor));
|
||||
result.add(new JetImplicitThisUsage(callElement, targetDescriptor));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -375,6 +466,25 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
}
|
||||
}
|
||||
|
||||
private static void findKotlinCallers(JavaChangeInfo changeInfo, Set<UsageInfo> result) {
|
||||
PsiElement method = changeInfo.getMethod();
|
||||
if (!RefactoringPackage.isTrueJavaMethod(method)) return;
|
||||
|
||||
for (PsiMethod primaryCaller : changeInfo.getMethodsToPropagateParameters()) {
|
||||
addDeferredCallerIfPossible(result, primaryCaller);
|
||||
for (PsiMethod overridingCaller : OverridingMethodsSearch.search(primaryCaller)) {
|
||||
addDeferredCallerIfPossible(result, overridingCaller);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static void addDeferredCallerIfPossible(Set<UsageInfo> result, PsiMethod overridingCaller) {
|
||||
PsiElement unwrappedElement = AsJavaPackage.getNamedUnwrappedElement(overridingCaller);
|
||||
if (unwrappedElement instanceof JetFunction || unwrappedElement instanceof JetClass) {
|
||||
result.add(new DeferredJavaMethodKotlinCallerUsage((JetNamedDeclaration) unwrappedElement));
|
||||
}
|
||||
}
|
||||
|
||||
private static void findDeferredUsagesOfParameters(
|
||||
ChangeInfo changeInfo,
|
||||
Set<UsageInfo> result,
|
||||
@@ -408,7 +518,7 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
javaMethodChangeInfo) {
|
||||
@NotNull
|
||||
@Override
|
||||
protected JetUsageInfo<JetElement> getDelegateUsage() {
|
||||
public JetUsageInfo<JetElement> getDelegateUsage() {
|
||||
return new JetParameterUsage((JetElement) element,
|
||||
getJavaMethodChangeInfo().getNewParameters()[paramIndex],
|
||||
functionInfoForParameters);
|
||||
@@ -428,16 +538,15 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
public MultiMap<PsiElement, String> findConflicts(ChangeInfo info, Ref<UsageInfo[]> refUsages) {
|
||||
MultiMap<PsiElement, String> result = new MultiMap<PsiElement, String>();
|
||||
|
||||
// Delete OverriderUsageInfo for Kotlin declarations since they can't be processed correctly
|
||||
// TODO: Drop when OverriderUsageInfo.getElement() gets deleted
|
||||
// Delete OverriderUsageInfo and CallerUsageInfo for Kotlin declarations since they can't be processed correctly
|
||||
// TODO (OverriderUsageInfo only): Drop when OverriderUsageInfo.getElement() gets deleted
|
||||
UsageInfo[] usageInfos = refUsages.get();
|
||||
List<UsageInfo> adjustedUsages = KotlinPackage.filterNot(
|
||||
usageInfos,
|
||||
new Function1<UsageInfo, Boolean>() {
|
||||
@Override
|
||||
public Boolean invoke(UsageInfo info) {
|
||||
return info instanceof OverriderUsageInfo &&
|
||||
((OverriderUsageInfo) info).getOverridingMethod() instanceof KotlinLightMethod;
|
||||
return getOverriderOrCaller(info) instanceof KotlinLightMethod;
|
||||
}
|
||||
}
|
||||
);
|
||||
@@ -519,9 +628,47 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
findThisLabelConflicts((JetChangeInfo) info, refUsages, result, changeInfo, function);
|
||||
}
|
||||
|
||||
for (UsageInfo usageInfo : usageInfos) {
|
||||
if (!(usageInfo instanceof KotlinCallerUsage)) continue;
|
||||
|
||||
JetNamedDeclaration caller = (JetNamedDeclaration) usageInfo.getElement();
|
||||
DeclarationDescriptor callerDescriptor = ResolvePackage.resolveToDescriptor(caller);
|
||||
|
||||
findParameterDuplicationInCaller(result, changeInfo, caller, callerDescriptor);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static void findParameterDuplicationInCaller(
|
||||
MultiMap<PsiElement, String> result,
|
||||
JetChangeInfo changeInfo,
|
||||
JetNamedDeclaration caller,
|
||||
DeclarationDescriptor callerDescriptor
|
||||
) {
|
||||
List<JetParameter> valueParameters = PsiUtilPackage.getValueParameters(caller);
|
||||
Map<String, JetParameter> existingParameters = KotlinPackage.toMap(
|
||||
valueParameters,
|
||||
new Function1<JetParameter, String>() {
|
||||
@Override
|
||||
public String invoke(JetParameter parameter) {
|
||||
return parameter.getName();
|
||||
}
|
||||
}
|
||||
);
|
||||
for (JetParameterInfo parameterInfo : changeInfo.getNonReceiverParameters()) {
|
||||
if (!(parameterInfo.getIsNewParameter())) continue;
|
||||
|
||||
String name = parameterInfo.getName();
|
||||
JetParameter parameter = existingParameters.get(name);
|
||||
if (parameter != null) {
|
||||
result.putValue(parameter, "There is already a parameter '" + name + "' in " +
|
||||
IdeDescriptorRenderers.SOURCE_CODE_SHORT_NAMES_IN_TYPES.render(callerDescriptor) +
|
||||
". It will conflict with the new parameter.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static void findThisLabelConflicts(
|
||||
JetChangeInfo info,
|
||||
Ref<UsageInfo[]> refUsages,
|
||||
@@ -666,21 +813,24 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
private JetMethodDescriptor originalJavaMethodDescriptor;
|
||||
|
||||
private static boolean isJavaMethodUsage(UsageInfo usageInfo) {
|
||||
if (usageInfo instanceof JavaMethodDeferredKotlinUsage) return true;
|
||||
|
||||
// MoveRenameUsageInfo corresponds to non-Java usage of Java method
|
||||
return usageInfo instanceof MoveRenameUsageInfo
|
||||
&& RefactoringPackage.isTrueJavaMethod(((MoveRenameUsageInfo) usageInfo).getReferencedElement());
|
||||
return usageInfo instanceof JavaMethodDeferredKotlinUsage || usageInfo instanceof MoveRenameUsageInfo;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private static UsageInfo createReplacementUsage(UsageInfo originalUsageInfo, JetChangeInfo javaMethodChangeInfo) {
|
||||
private static UsageInfo createReplacementUsage(UsageInfo originalUsageInfo, JetChangeInfo javaMethodChangeInfo, UsageInfo[] allUsages) {
|
||||
if (originalUsageInfo instanceof JavaMethodDeferredKotlinUsage) {
|
||||
return ((JavaMethodDeferredKotlinUsage<?>) originalUsageInfo).resolve(javaMethodChangeInfo);
|
||||
}
|
||||
|
||||
JetCallElement callElement = PsiTreeUtil.getParentOfType(originalUsageInfo.getElement(), JetCallElement.class);
|
||||
return callElement != null ? new JavaMethodKotlinCallUsage(callElement, javaMethodChangeInfo) : null;
|
||||
if (callElement == null) return null;
|
||||
|
||||
PsiReference ref = originalUsageInfo.getReference();
|
||||
PsiElement refTarget = ref != null ? ref.resolve() : null;
|
||||
return new JavaMethodKotlinCallUsage(callElement,
|
||||
javaMethodChangeInfo,
|
||||
refTarget != null && ChangeSignaturePackage.isCaller(refTarget, allUsages));
|
||||
}
|
||||
|
||||
private static class NullabilityPropagator {
|
||||
@@ -752,6 +902,20 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
}
|
||||
}
|
||||
|
||||
private static boolean isOverriderOrCaller(UsageInfo usage) {
|
||||
return usage instanceof OverriderUsageInfo || usage instanceof CallerUsageInfo;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private static PsiMethod getOverriderOrCaller(UsageInfo usage) {
|
||||
if (usage instanceof OverriderUsageInfo) return ((OverriderUsageInfo) usage).getOverridingMethod();
|
||||
if (usage instanceof CallerUsageInfo) {
|
||||
PsiElement element = usage.getElement();
|
||||
return element instanceof PsiMethod ? (PsiMethod) element : null;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean processUsage(ChangeInfo changeInfo, UsageInfo usageInfo, boolean beforeMethodChange, UsageInfo[] usages) {
|
||||
PsiElement method = changeInfo.getMethod();
|
||||
@@ -772,15 +936,15 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
NullabilityPropagator nullabilityPropagator = new NullabilityPropagator(javaChangeInfo.getMethod());
|
||||
|
||||
for (UsageInfo usage : javaUsageInfos) {
|
||||
if (usage instanceof OverriderUsageInfo && beforeMethodChange) continue;
|
||||
if (isOverriderOrCaller(usage) && beforeMethodChange) continue;
|
||||
for (ChangeSignatureUsageProcessor processor : processors) {
|
||||
if (processor instanceof JetChangeSignatureUsageProcessor) continue;
|
||||
if (usage instanceof OverriderUsageInfo) {
|
||||
if (isOverriderOrCaller(usage)) {
|
||||
processor.processUsage(javaChangeInfo, usage, true, javaUsageInfos);
|
||||
}
|
||||
if (processor.processUsage(javaChangeInfo, usage, beforeMethodChange, javaUsageInfos)) break;
|
||||
}
|
||||
if (usage instanceof OverriderUsageInfo) {
|
||||
if (usage instanceof OverriderUsageInfo && ((OverriderUsageInfo) usage).isOriginalOverrider()) {
|
||||
PsiMethod overridingMethod = ((OverriderUsageInfo) usage).getOverridingMethod();
|
||||
if (overridingMethod != null && !(overridingMethod instanceof KotlinLightMethod)) {
|
||||
nullabilityPropagator.processMethod(overridingMethod);
|
||||
@@ -791,23 +955,29 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
}
|
||||
|
||||
if (beforeMethodChange) {
|
||||
if (isJavaMethodUsage) {
|
||||
boolean startedFromJava = method instanceof PsiMethod;
|
||||
if (startedFromJava && originalJavaMethodDescriptor == null) {
|
||||
FunctionDescriptor methodDescriptor = ResolvePackage.getJavaMethodDescriptor((PsiMethod) method);
|
||||
JetChangeSignatureData changeSignatureData =
|
||||
new JetChangeSignatureData(methodDescriptor, method, Collections.singletonList(methodDescriptor));
|
||||
if (changeSignatureData != originalJavaMethodDescriptor) {
|
||||
originalJavaMethodDescriptor = changeSignatureData;
|
||||
}
|
||||
originalJavaMethodDescriptor =
|
||||
new JetChangeSignatureData(methodDescriptor, method, Collections.singletonList(methodDescriptor));;
|
||||
|
||||
// This change info is used as a placeholder before primary method update
|
||||
// It gets replaced with real change info afterwards
|
||||
JetChangeInfo dummyChangeInfo =
|
||||
new JetChangeInfo(originalJavaMethodDescriptor, "", null, "", Visibilities.INTERNAL, Collections.<JetParameterInfo>emptyList(), null, changeInfo.getMethod());
|
||||
new JetChangeInfo(originalJavaMethodDescriptor,
|
||||
"",
|
||||
null,
|
||||
"",
|
||||
Visibilities.INTERNAL,
|
||||
Collections.<JetParameterInfo>emptyList(),
|
||||
null,
|
||||
changeInfo.getMethod(),
|
||||
Collections.<PsiElement>emptyList());
|
||||
for (int i = 0; i < usages.length; i++) {
|
||||
UsageInfo oldUsageInfo = usages[i];
|
||||
if (!isJavaMethodUsage(oldUsageInfo)) continue;
|
||||
|
||||
UsageInfo newUsageInfo = createReplacementUsage(oldUsageInfo, dummyChangeInfo);
|
||||
UsageInfo newUsageInfo = createReplacementUsage(oldUsageInfo, dummyChangeInfo, usages);
|
||||
if (newUsageInfo != null) {
|
||||
usages[i] = newUsageInfo;
|
||||
}
|
||||
@@ -832,7 +1002,7 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
}
|
||||
|
||||
if (usageInfo instanceof JavaMethodKotlinUsageWithDelegate) {
|
||||
return ((JavaMethodKotlinUsageWithDelegate) usageInfo).processUsage();
|
||||
return ((JavaMethodKotlinUsageWithDelegate) usageInfo).processUsage(usages);
|
||||
}
|
||||
|
||||
if (usageInfo instanceof MoveRenameUsageInfo && isJavaMethodUsage) {
|
||||
@@ -846,7 +1016,7 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
return false;
|
||||
}
|
||||
|
||||
return usageInfo instanceof JetUsageInfo ? ((JetUsageInfo) usageInfo).processUsage((JetChangeInfo) changeInfo, element) : true;
|
||||
return usageInfo instanceof JetUsageInfo ? ((JetUsageInfo) usageInfo).processUsage((JetChangeInfo) changeInfo, element, usages) : true;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -855,7 +1025,7 @@ public class JetChangeSignatureUsageProcessor implements ChangeSignatureUsagePro
|
||||
|
||||
JetChangeInfo jetChangeInfo = (JetChangeInfo) changeInfo;
|
||||
for (JetCallableDefinitionUsage primaryFunction : jetChangeInfo.getMethodDescriptor().getPrimaryCallables()) {
|
||||
primaryFunction.processUsage(jetChangeInfo, primaryFunction.getDeclaration());
|
||||
primaryFunction.processUsage(jetChangeInfo, primaryFunction.getDeclaration(), UsageInfo.EMPTY_ARRAY);
|
||||
}
|
||||
jetChangeInfo.primaryMethodUpdated();
|
||||
return true;
|
||||
|
||||
+59
@@ -0,0 +1,59 @@
|
||||
/*
|
||||
* Copyright 2010-2015 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.idea.refactoring.changeSignature
|
||||
|
||||
import com.intellij.psi.PsiElement
|
||||
import com.intellij.refactoring.changeSignature.CallerUsageInfo
|
||||
import com.intellij.refactoring.changeSignature.OverriderUsageInfo
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.usages.DeferredJavaMethodKotlinCallerUsage
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.usages.JavaMethodKotlinUsageWithDelegate
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.usages.KotlinCallerUsage
|
||||
import org.jetbrains.kotlin.psi.*
|
||||
import org.jetbrains.kotlin.psi.psiUtil.parentsWithSelf
|
||||
|
||||
private fun JetNamedDeclaration.getDeclarationBody(): JetElement? {
|
||||
return when {
|
||||
this is JetClassOrObject -> getDelegationSpecifierList()
|
||||
this is JetPrimaryConstructor -> getContainingClassOrObject().getDelegationSpecifierList()
|
||||
this is JetSecondaryConstructor -> getDelegationCall()
|
||||
this is JetNamedFunction -> getBodyExpression()
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
|
||||
public fun PsiElement.isCaller(allUsages: Array<out UsageInfo>): Boolean {
|
||||
val elementToSearch = (this as? JetClass)?.getPrimaryConstructor() ?: this
|
||||
return allUsages
|
||||
.asSequence()
|
||||
.filter {
|
||||
val usage = (it as? JavaMethodKotlinUsageWithDelegate<*>)?.delegateUsage ?: it
|
||||
usage is KotlinCallerUsage
|
||||
|| usage is DeferredJavaMethodKotlinCallerUsage
|
||||
|| usage is CallerUsageInfo
|
||||
|| (usage is OverriderUsageInfo && !usage.isOriginalOverrider())
|
||||
}
|
||||
.any { it.getElement() == elementToSearch }
|
||||
}
|
||||
|
||||
public fun JetElement.isInsideOfCallerBody(allUsages: Array<out UsageInfo>): Boolean {
|
||||
val container = parentsWithSelf.firstOrNull {
|
||||
it is JetNamedFunction || it is JetConstructor<*> || it is JetClassOrObject
|
||||
} as? JetNamedDeclaration ?: return false
|
||||
val body = container.getDeclarationBody() ?: return false
|
||||
return body.getTextRange().contains(getTextRange()) && container.isCaller(allUsages)
|
||||
}
|
||||
+5
-4
@@ -20,7 +20,6 @@ import com.intellij.openapi.editor.colors.EditorColorsManager
|
||||
import com.intellij.openapi.editor.colors.EditorFontType
|
||||
import com.intellij.openapi.editor.event.DocumentAdapter
|
||||
import com.intellij.openapi.editor.event.DocumentEvent
|
||||
import com.intellij.openapi.fileTypes.LanguageFileType
|
||||
import com.intellij.openapi.options.ConfigurationException
|
||||
import com.intellij.openapi.project.Project
|
||||
import com.intellij.openapi.ui.VerticalFlowLayout
|
||||
@@ -30,18 +29,15 @@ import com.intellij.psi.PsiCodeFragment
|
||||
import com.intellij.psi.PsiDocumentManager
|
||||
import com.intellij.psi.PsiElement
|
||||
import com.intellij.refactoring.BaseRefactoringProcessor
|
||||
import com.intellij.refactoring.changeSignature.CallerChooserBase
|
||||
import com.intellij.refactoring.changeSignature.ChangeSignatureDialogBase
|
||||
import com.intellij.refactoring.changeSignature.MethodDescriptor
|
||||
import com.intellij.refactoring.changeSignature.ParameterTableModelItemBase
|
||||
import com.intellij.refactoring.ui.ComboBoxVisibilityPanel
|
||||
import com.intellij.refactoring.ui.VisibilityPanelBase
|
||||
import com.intellij.ui.DottedBorder
|
||||
import com.intellij.ui.EditorTextField
|
||||
import com.intellij.ui.components.JBLabel
|
||||
import com.intellij.ui.treeStructure.Tree
|
||||
import com.intellij.util.Consumer
|
||||
import com.intellij.util.Function
|
||||
import com.intellij.util.IJSwingUtilities
|
||||
import com.intellij.util.ui.UIUtil
|
||||
import com.intellij.util.ui.table.JBTableRow
|
||||
@@ -158,6 +154,10 @@ public class JetChangeSignatureDialog(
|
||||
override fun createCallerChooser(title: String, treeToReuse: Tree?, callback: Consumer<Set<PsiElement>>) =
|
||||
KotlinCallerChooser(myMethod.getMethod(), myProject, title, treeToReuse, callback)
|
||||
|
||||
// Forbid receiver propagation
|
||||
override fun mayPropagateParameters() =
|
||||
getParameters().any { it.isNewParameter && it != parametersTableModel.getReceiver() }
|
||||
|
||||
override fun getTableEditor(table: JTable, item: ParameterTableModelItemBase<JetParameterInfo>): JBTableRowEditor? {
|
||||
return object : JBTableRowEditor() {
|
||||
private val components = ArrayList<JComponent>()
|
||||
@@ -364,6 +364,7 @@ public class JetChangeSignatureDialog(
|
||||
getVisibility(),
|
||||
getMethodName(),
|
||||
myDefaultValueContext)
|
||||
changeInfo.primaryPropagationTargets = myMethodsToPropagateParameters ?: emptyList();
|
||||
return JetChangeSignatureProcessor(myProject, changeInfo, commandName ?: getTitle())
|
||||
}
|
||||
|
||||
|
||||
+23
-17
@@ -22,35 +22,41 @@ import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetChangeInfo
|
||||
import org.jetbrains.kotlin.psi.JetConstructorDelegationCall
|
||||
import org.jetbrains.kotlin.psi.JetFunction
|
||||
import org.jetbrains.kotlin.psi.JetNamedDeclaration
|
||||
import org.jetbrains.kotlin.types.JetType
|
||||
|
||||
public abstract class JavaMethodDeferredKotlinUsage<T: PsiElement>(element: T): UsageInfo(element) {
|
||||
abstract fun resolve(javaMethodChangeInfo: JetChangeInfo): JavaMethodKotlinUsageWithDelegate<T>
|
||||
public abstract class JavaMethodDeferredKotlinUsage<T : PsiElement>(element: T) : UsageInfo(element) {
|
||||
abstract fun resolve(javaMethodChangeInfo: JetChangeInfo): JavaMethodKotlinUsageWithDelegate<T>
|
||||
}
|
||||
|
||||
public class DeferredJavaMethodOverrideOrSAMUsage(
|
||||
val function: JetFunction,
|
||||
val functionDescriptor: FunctionDescriptor,
|
||||
val samCallType: JetType?
|
||||
): JavaMethodDeferredKotlinUsage<JetFunction>(function) {
|
||||
override fun resolve(javaMethodChangeInfo: JetChangeInfo): JavaMethodKotlinUsageWithDelegate<JetFunction> {
|
||||
return object : JavaMethodKotlinUsageWithDelegate<JetFunction>(function, javaMethodChangeInfo) {
|
||||
override val delegateUsage = JetCallableDefinitionUsage(
|
||||
function,
|
||||
functionDescriptor,
|
||||
javaMethodChangeInfo.methodDescriptor.originalPrimaryCallable,
|
||||
samCallType
|
||||
)
|
||||
}
|
||||
) : JavaMethodDeferredKotlinUsage<JetFunction>(function) {
|
||||
override fun resolve(javaMethodChangeInfo: JetChangeInfo): JavaMethodKotlinUsageWithDelegate<JetFunction> {
|
||||
return object : JavaMethodKotlinUsageWithDelegate<JetFunction>(function, javaMethodChangeInfo) {
|
||||
override val delegateUsage = JetCallableDefinitionUsage(function, functionDescriptor, javaMethodChangeInfo.methodDescriptor.originalPrimaryCallable, samCallType)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class DeferredJavaMethodKotlinCallerUsage(
|
||||
val declaration: JetNamedDeclaration
|
||||
) : JavaMethodDeferredKotlinUsage<JetNamedDeclaration>(declaration) {
|
||||
override fun resolve(javaMethodChangeInfo: JetChangeInfo): JavaMethodKotlinUsageWithDelegate<JetNamedDeclaration> {
|
||||
return object : JavaMethodKotlinUsageWithDelegate<JetNamedDeclaration>(declaration, javaMethodChangeInfo) {
|
||||
override val delegateUsage = KotlinCallerUsage(declaration)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class JavaConstructorDeferredUsageInDelegationCall(
|
||||
val delegationCall: JetConstructorDelegationCall
|
||||
): JavaMethodDeferredKotlinUsage<JetConstructorDelegationCall>(delegationCall) {
|
||||
override fun resolve(javaMethodChangeInfo: JetChangeInfo): JavaMethodKotlinUsageWithDelegate<JetConstructorDelegationCall> {
|
||||
return object : JavaMethodKotlinUsageWithDelegate<JetConstructorDelegationCall>(delegationCall, javaMethodChangeInfo) {
|
||||
override val delegateUsage = JetConstructorDelegationCallUsage(delegationCall, javaMethodChangeInfo)
|
||||
}
|
||||
) : JavaMethodDeferredKotlinUsage<JetConstructorDelegationCall>(delegationCall) {
|
||||
override fun resolve(javaMethodChangeInfo: JetChangeInfo): JavaMethodKotlinUsageWithDelegate<JetConstructorDelegationCall> {
|
||||
return object : JavaMethodKotlinUsageWithDelegate<JetConstructorDelegationCall>(delegationCall, javaMethodChangeInfo) {
|
||||
override val delegateUsage = JetConstructorDelegationCallUsage(delegationCall, javaMethodChangeInfo)
|
||||
}
|
||||
}
|
||||
}
|
||||
+9
-4
@@ -26,13 +26,18 @@ import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
||||
public abstract class JavaMethodKotlinUsageWithDelegate<T: PsiElement>(
|
||||
val psiElement: T,
|
||||
var javaMethodChangeInfo: JetChangeInfo): UsageInfo(psiElement) {
|
||||
protected abstract val delegateUsage: JetUsageInfo<T>
|
||||
abstract val delegateUsage: JetUsageInfo<T>
|
||||
|
||||
fun processUsage(): Boolean = delegateUsage.processUsage(javaMethodChangeInfo, psiElement)
|
||||
fun processUsage(allUsages: Array<UsageInfo>): Boolean = delegateUsage.processUsage(javaMethodChangeInfo, psiElement, allUsages)
|
||||
}
|
||||
|
||||
public class JavaMethodKotlinCallUsage(
|
||||
callElement: JetCallElement,
|
||||
javaMethodChangeInfo: JetChangeInfo): JavaMethodKotlinUsageWithDelegate<JetCallElement>(callElement, javaMethodChangeInfo) {
|
||||
override protected val delegateUsage = JetFunctionCallUsage(psiElement, javaMethodChangeInfo.methodDescriptor.originalPrimaryCallable)
|
||||
javaMethodChangeInfo: JetChangeInfo,
|
||||
propagationCall: Boolean): JavaMethodKotlinUsageWithDelegate<JetCallElement>(callElement, javaMethodChangeInfo) {
|
||||
override val delegateUsage = if (propagationCall) {
|
||||
KotlinCallerCallUsage(psiElement)
|
||||
} else {
|
||||
JetFunctionCallUsage(psiElement, javaMethodChangeInfo.methodDescriptor.originalPrimaryCallable)
|
||||
}
|
||||
}
|
||||
|
||||
+2
-1
@@ -21,6 +21,7 @@ import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiMethod;
|
||||
import com.intellij.psi.PsiWhiteSpace;
|
||||
import com.intellij.psi.util.PsiTreeUtil;
|
||||
import com.intellij.usageView.UsageInfo;
|
||||
import kotlin.KotlinPackage;
|
||||
import kotlin.Pair;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -165,7 +166,7 @@ public class JetCallableDefinitionUsage<T extends PsiElement> extends JetUsageIn
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean processUsage(@NotNull JetChangeInfo changeInfo, @NotNull PsiElement element) {
|
||||
public boolean processUsage(@NotNull JetChangeInfo changeInfo, @NotNull PsiElement element, @NotNull UsageInfo[] allUsages) {
|
||||
if (!(element instanceof JetNamedDeclaration)) return true;
|
||||
|
||||
JetPsiFactory psiFactory = JetPsiFactory(element.getProject());
|
||||
|
||||
+3
-2
@@ -16,6 +16,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.idea.refactoring.changeSignature.usages
|
||||
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetChangeInfo
|
||||
import org.jetbrains.kotlin.psi.JetConstructorDelegationCall
|
||||
import org.jetbrains.kotlin.psi.JetPsiFactory
|
||||
@@ -27,7 +28,7 @@ public class JetConstructorDelegationCallUsage(
|
||||
) : JetUsageInfo<JetConstructorDelegationCall>(call) {
|
||||
val delegate = JetFunctionCallUsage(call, changeInfo.methodDescriptor.originalPrimaryCallable)
|
||||
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetConstructorDelegationCall): Boolean {
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetConstructorDelegationCall, allUsages: Array<out UsageInfo>): Boolean {
|
||||
val isThisCall = element.isCallToThis()
|
||||
|
||||
var elementToWorkWith = element
|
||||
@@ -36,7 +37,7 @@ public class JetConstructorDelegationCallUsage(
|
||||
elementToWorkWith = constructor.replaceImplicitDelegationCallWithExplicit(isThisCall)
|
||||
}
|
||||
|
||||
val result = delegate.processUsage(changeInfo, elementToWorkWith)
|
||||
val result = delegate.processUsage(changeInfo, elementToWorkWith, allUsages)
|
||||
|
||||
if (changeInfo.getNewParametersCount() == 0 && !isThisCall && !elementToWorkWith.isImplicit()) {
|
||||
(elementToWorkWith.getParent() as? JetSecondaryConstructor)?.getColon()?.delete()
|
||||
|
||||
+3
-2
@@ -16,6 +16,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.idea.refactoring.changeSignature.usages
|
||||
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import org.jetbrains.kotlin.psi.JetEnumEntry
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetChangeInfo
|
||||
import org.jetbrains.kotlin.psi.JetPsiFactory
|
||||
@@ -24,7 +25,7 @@ import org.jetbrains.kotlin.psi.JetDelegatorToSuperCall
|
||||
import org.jetbrains.kotlin.psi.psiUtil.getStrictParentOfType
|
||||
|
||||
public class JetEnumEntryWithoutSuperCallUsage(enumEntry: JetEnumEntry) : JetUsageInfo<JetEnumEntry>(enumEntry) {
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetEnumEntry): Boolean {
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetEnumEntry, allUsages: Array<out UsageInfo>): Boolean {
|
||||
if (changeInfo.getNewParameters().size() > 0) {
|
||||
val psiFactory = JetPsiFactory(element)
|
||||
|
||||
@@ -36,7 +37,7 @@ public class JetEnumEntryWithoutSuperCallUsage(enumEntry: JetEnumEntry) : JetUsa
|
||||
element.addBefore(psiFactory.createColon(), delegatorToSuperCall)
|
||||
|
||||
return JetFunctionCallUsage(delegatorToSuperCall, changeInfo.methodDescriptor.originalPrimaryCallable)
|
||||
.processUsage(changeInfo, delegatorToSuperCall)
|
||||
.processUsage(changeInfo, delegatorToSuperCall, allUsages)
|
||||
}
|
||||
|
||||
return true
|
||||
|
||||
+17
-8
@@ -20,6 +20,7 @@ import com.intellij.openapi.util.Ref;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiReference;
|
||||
import com.intellij.psi.util.PsiTreeUtil;
|
||||
import com.intellij.usageView.UsageInfo;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import gnu.trove.TIntArrayList;
|
||||
import gnu.trove.TIntProcedure;
|
||||
@@ -34,6 +35,7 @@ import org.jetbrains.kotlin.descriptors.*;
|
||||
import org.jetbrains.kotlin.idea.caches.resolve.ResolvePackage;
|
||||
import org.jetbrains.kotlin.idea.codeInsight.shorten.ShortenPackage;
|
||||
import org.jetbrains.kotlin.idea.core.CorePackage;
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.ChangeSignaturePackage;
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetChangeInfo;
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetParameterInfo;
|
||||
import org.jetbrains.kotlin.idea.refactoring.introduce.extractionEngine.ExtractionEnginePackage;
|
||||
@@ -89,14 +91,14 @@ public class JetFunctionCallUsage extends JetUsageInfo<JetCallElement> {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean processUsage(JetChangeInfo changeInfo, JetCallElement element) {
|
||||
public boolean processUsage(@NotNull JetChangeInfo changeInfo, @NotNull JetCallElement element, @NotNull UsageInfo[] allUsages) {
|
||||
if (shouldSkipUsage(element)) return true;
|
||||
|
||||
changeNameIfNeeded(changeInfo, element);
|
||||
|
||||
if (element.getValueArgumentList() != null) {
|
||||
if (changeInfo.isParameterSetOrOrderChanged()) {
|
||||
updateArgumentsAndReceiver(changeInfo, element);
|
||||
updateArgumentsAndReceiver(changeInfo, element, allUsages);
|
||||
}
|
||||
else {
|
||||
changeArgumentNames(changeInfo, element);
|
||||
@@ -319,7 +321,7 @@ public class JetFunctionCallUsage extends JetUsageInfo<JetCallElement> {
|
||||
return newExpression;
|
||||
}
|
||||
|
||||
private void updateArgumentsAndReceiver(JetChangeInfo changeInfo, JetCallElement element) {
|
||||
private void updateArgumentsAndReceiver(JetChangeInfo changeInfo, JetCallElement element, @NotNull UsageInfo[] allUsages) {
|
||||
JetValueArgumentList arguments = element.getValueArgumentList();
|
||||
assert arguments != null : "Argument list is expected: " + element.getText();
|
||||
List<? extends ValueArgument> oldArguments = element.getValueArguments();
|
||||
@@ -347,11 +349,18 @@ public class JetFunctionCallUsage extends JetUsageInfo<JetCallElement> {
|
||||
}
|
||||
|
||||
JetExpression defaultValueForCall = parameterInfo.getDefaultValueForCall();
|
||||
String defaultValueText = defaultValueForCall != null
|
||||
? substituteReferences(defaultValueForCall,
|
||||
parameterInfo.getDefaultValueParameterReferences(),
|
||||
psiFactory).getText()
|
||||
: "";
|
||||
|
||||
String defaultValueText;
|
||||
if (ChangeSignaturePackage.isInsideOfCallerBody(element, allUsages)) {
|
||||
defaultValueText = parameterInfo.getName();
|
||||
}
|
||||
else {
|
||||
defaultValueText = defaultValueForCall != null
|
||||
? substituteReferences(defaultValueForCall,
|
||||
parameterInfo.getDefaultValueParameterReferences(),
|
||||
psiFactory).getText()
|
||||
: "";
|
||||
}
|
||||
|
||||
if (isNamedCall) {
|
||||
String newName = parameterInfo.getInheritedName(callee);
|
||||
|
||||
+3
-2
@@ -16,6 +16,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.idea.refactoring.changeSignature.usages
|
||||
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetChangeInfo
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetParameterInfo
|
||||
import org.jetbrains.kotlin.psi.JetPsiFactory
|
||||
@@ -32,7 +33,7 @@ public abstract class JetImplicitReceiverUsage(callElement: JetElement): JetUsag
|
||||
|
||||
}
|
||||
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetElement): Boolean {
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetElement, allUsages: Array<out UsageInfo>): Boolean {
|
||||
val newQualifiedCall = JetPsiFactory(element.getProject()).createExpression(
|
||||
"${getNewReceiverText()}.${element.getText()}"
|
||||
) as JetQualifiedExpression
|
||||
@@ -53,7 +54,7 @@ public class JetImplicitThisToParameterUsage(
|
||||
}
|
||||
}
|
||||
|
||||
public class JetImplicitOuterThisToQualifiedThisUsage(
|
||||
public class JetImplicitThisUsage(
|
||||
callElement: JetElement,
|
||||
val targetDescriptor: DeclarationDescriptor
|
||||
): JetImplicitReceiverUsage(callElement) {
|
||||
|
||||
+2
-1
@@ -16,6 +16,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.idea.refactoring.changeSignature.usages
|
||||
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import org.jetbrains.kotlin.psi.JetSimpleNameExpression
|
||||
import org.jetbrains.kotlin.psi.JetPsiFactory
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetChangeInfo
|
||||
@@ -35,7 +36,7 @@ public abstract class JetExplicitReferenceUsage<T: JetElement>(element: T) : Jet
|
||||
|
||||
}
|
||||
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: T): Boolean {
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: T, allUsages: Array<out UsageInfo>): Boolean {
|
||||
val newElement = JetPsiFactory(element.getProject()).createExpression(getReplacementText(changeInfo))
|
||||
val elementToReplace = (element.getParent() as? JetThisExpression) ?: element
|
||||
processReplacedElement(elementToReplace.replace(newElement) as JetElement)
|
||||
|
||||
+2
-1
@@ -16,6 +16,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.idea.refactoring.changeSignature.usages
|
||||
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import org.jetbrains.kotlin.idea.caches.resolve.analyze
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetChangeInfo
|
||||
import org.jetbrains.kotlin.psi.JetPsiFactory
|
||||
@@ -29,7 +30,7 @@ import org.jetbrains.kotlin.resolve.scopes.receivers.ExpressionReceiver
|
||||
public class JetPropertyCallUsage(element: JetSimpleNameExpression): JetUsageInfo<JetSimpleNameExpression>(element) {
|
||||
private val resolvedCall = element.getResolvedCall(element.analyze())
|
||||
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetSimpleNameExpression): Boolean {
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetSimpleNameExpression, allUsages: Array<out UsageInfo>): Boolean {
|
||||
updateName(changeInfo, element)
|
||||
updateReceiver(changeInfo, element)
|
||||
return true
|
||||
|
||||
+1
-1
@@ -28,5 +28,5 @@ public abstract class JetUsageInfo<T : PsiElement> : UsageInfo {
|
||||
@suppress("UNCHECKED_CAST")
|
||||
override fun getElement() = super.getElement() as T?
|
||||
|
||||
public abstract fun processUsage(changeInfo: JetChangeInfo, element: T): Boolean
|
||||
public abstract fun processUsage(changeInfo: JetChangeInfo, element: T, allUsages: Array<out UsageInfo>): Boolean
|
||||
}
|
||||
|
||||
+77
@@ -0,0 +1,77 @@
|
||||
/*
|
||||
* Copyright 2010-2015 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.idea.refactoring.changeSignature.usages
|
||||
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import org.jetbrains.kotlin.idea.codeInsight.shorten.addToShorteningWaitSet
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.JetChangeInfo
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.getAffectedCallables
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.isInsideOfCallerBody
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
import org.jetbrains.kotlin.psi.*
|
||||
import org.jetbrains.kotlin.psi.psiUtil.getValueParameterList
|
||||
|
||||
public class KotlinCallerUsage(element: JetNamedDeclaration): JetUsageInfo<JetNamedDeclaration>(element) {
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetNamedDeclaration, allUsages: Array<out UsageInfo>): Boolean {
|
||||
// Do not process function twice
|
||||
if (changeInfo.getAffectedCallables().any { it is JetCallableDefinitionUsage<*> && it.getElement() == element }) return true
|
||||
|
||||
val parameterList = when (element) {
|
||||
is JetFunction -> element.getValueParameterList()
|
||||
is JetClass -> element.createPrimaryConstructorParameterListIfAbsent()
|
||||
else -> null
|
||||
} ?: return true
|
||||
val psiFactory = JetPsiFactory(getProject())
|
||||
changeInfo.getNonReceiverParameters()
|
||||
.withIndex()
|
||||
.filter { it.value.isNewParameter }
|
||||
.forEach {
|
||||
val parameterText = it.value.getDeclarationSignature(it.index, changeInfo.methodDescriptor.originalPrimaryCallable)
|
||||
parameterList
|
||||
.addParameter(psiFactory.createParameter(parameterText))
|
||||
.addToShorteningWaitSet()
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
public class KotlinCallerCallUsage(element: JetCallElement): JetUsageInfo<JetCallElement>(element) {
|
||||
override fun processUsage(changeInfo: JetChangeInfo, element: JetCallElement, allUsages: Array<out UsageInfo>): Boolean {
|
||||
val argumentList = element.getValueArgumentList() ?: return true
|
||||
val psiFactory = JetPsiFactory(getProject())
|
||||
val isNamedCall = argumentList.getArguments().any { it.getArgumentName() != null }
|
||||
changeInfo.getNonReceiverParameters()
|
||||
.filter { it.isNewParameter }
|
||||
.forEach {
|
||||
val parameterName = it.getName()
|
||||
val argumentExpression = if (element.isInsideOfCallerBody(allUsages)) {
|
||||
psiFactory.createExpression(parameterName)
|
||||
}
|
||||
else {
|
||||
it.defaultValueForCall ?: psiFactory.createExpression("_")
|
||||
}
|
||||
val argument = psiFactory.createArgument(
|
||||
expression = argumentExpression,
|
||||
name = if (isNamedCall) Name.identifier(parameterName) else null
|
||||
)
|
||||
argumentList.addArgument(argument)
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
}
|
||||
+2
-2
@@ -100,7 +100,7 @@ public class KotlinIntroduceParameterMethodUsageProcessor : IntroduceParameterMe
|
||||
.map { it.unwrapped }
|
||||
.filterIsInstance<JetFunction>()
|
||||
return (kotlinFunctions + element).all {
|
||||
JetCallableDefinitionUsage(it, changeInfo.originalBaseFunctionDescriptor, null, null).processUsage(changeInfo, it)
|
||||
JetCallableDefinitionUsage(it, changeInfo.originalBaseFunctionDescriptor, null, null).processUsage(changeInfo, it, usages)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -116,7 +116,7 @@ public class KotlinIntroduceParameterMethodUsageProcessor : IntroduceParameterMe
|
||||
else {
|
||||
JetFunctionCallUsage(callElement, changeInfo.methodDescriptor.originalPrimaryCallable)
|
||||
}
|
||||
return delegateUsage.processUsage(changeInfo, callElement)
|
||||
return delegateUsage.processUsage(changeInfo, callElement, usages)
|
||||
}
|
||||
|
||||
override fun processAddSuperCall(data: IntroduceParameterData, usage: UsageInfo, usages: Array<out UsageInfo>): Boolean = true
|
||||
|
||||
+18
@@ -0,0 +1,18 @@
|
||||
open class C(n: Int) : A(n) {
|
||||
|
||||
}
|
||||
|
||||
open class D: A {
|
||||
constructor(n: Int): super(n)
|
||||
constructor(b: Boolean, n: Int) : super(n)
|
||||
}
|
||||
|
||||
fun test(n: Int) {
|
||||
A(n)
|
||||
A(false, n)
|
||||
B(n)
|
||||
B(false, n)
|
||||
C(n)
|
||||
D(n)
|
||||
D(false, n)
|
||||
}
|
||||
+32
@@ -0,0 +1,32 @@
|
||||
class A {
|
||||
public <caret>A(int n) {
|
||||
|
||||
}
|
||||
|
||||
public A(boolean b, int n) {
|
||||
this(n);
|
||||
}
|
||||
}
|
||||
|
||||
class B extends A {
|
||||
public B(int n) {
|
||||
|
||||
super(n);
|
||||
}
|
||||
|
||||
public B(boolean b, int n) {
|
||||
super(n);
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test(int n) {
|
||||
new A(n);
|
||||
new A(true, n);
|
||||
new B(n);
|
||||
new B(true, n);
|
||||
new C(n);
|
||||
new D(n);
|
||||
new D(true, n);
|
||||
}
|
||||
}
|
||||
+18
@@ -0,0 +1,18 @@
|
||||
open class C: A() {
|
||||
|
||||
}
|
||||
|
||||
open class D: A {
|
||||
constructor(): super()
|
||||
constructor(b: Boolean)
|
||||
}
|
||||
|
||||
fun test() {
|
||||
A()
|
||||
A(false)
|
||||
B()
|
||||
B(false)
|
||||
C()
|
||||
D()
|
||||
D(false)
|
||||
}
|
||||
+31
@@ -0,0 +1,31 @@
|
||||
class A {
|
||||
public <caret>A() {
|
||||
|
||||
}
|
||||
|
||||
public A(boolean b) {
|
||||
this();
|
||||
}
|
||||
}
|
||||
|
||||
class B extends A {
|
||||
public B() {
|
||||
|
||||
}
|
||||
|
||||
public B(boolean b) {
|
||||
super();
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test() {
|
||||
new A();
|
||||
new A(true);
|
||||
new B();
|
||||
new B(true);
|
||||
new C();
|
||||
new D();
|
||||
new D(true);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,28 @@
|
||||
open class C: A() {
|
||||
override fun foo(n: Int, s: String): Unit {
|
||||
|
||||
}
|
||||
|
||||
override fun bar(b: Boolean, n: Int, s: String) {
|
||||
foo(n, s)
|
||||
}
|
||||
|
||||
override fun baz() {
|
||||
foo(1, "abc")
|
||||
bar(false, 1, "abc")
|
||||
}
|
||||
}
|
||||
|
||||
fun test(n: Int, s: String) {
|
||||
A().foo(n, s)
|
||||
A().bar(true, n, s)
|
||||
A().baz()
|
||||
|
||||
B().foo(n, s)
|
||||
B().bar(true, n, s)
|
||||
B().baz()
|
||||
|
||||
C().foo(n, s)
|
||||
C().bar(true, n, s)
|
||||
C().baz()
|
||||
}
|
||||
@@ -0,0 +1,45 @@
|
||||
class A {
|
||||
public void foo(int n, String s) {
|
||||
|
||||
}
|
||||
|
||||
public void bar(boolean b, int n, String s) {
|
||||
foo(n, s);
|
||||
}
|
||||
|
||||
public void baz() {
|
||||
foo(1, "abc");
|
||||
bar(false, 1, "abc");
|
||||
}
|
||||
}
|
||||
|
||||
class B extends A {
|
||||
public void foo(int n, String s) {
|
||||
|
||||
}
|
||||
|
||||
public void bar(boolean b, int n, String s) {
|
||||
foo(1, "abc");
|
||||
}
|
||||
|
||||
public void baz() {
|
||||
foo(1, "abc");
|
||||
bar(false, 1, "abc");
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test() {
|
||||
new A().foo(1, "abc");
|
||||
new A().bar(true, 1, "abc");
|
||||
new A().baz();
|
||||
|
||||
new B().foo(1, "abc");
|
||||
new B().bar(true, 1, "abc");
|
||||
new B().baz();
|
||||
|
||||
new C().foo(1, "abc");
|
||||
new C().bar(true, 1, "abc");
|
||||
new C().baz();
|
||||
}
|
||||
}
|
||||
+28
@@ -0,0 +1,28 @@
|
||||
open class C: A() {
|
||||
override fun foo() {
|
||||
|
||||
}
|
||||
|
||||
override fun bar(b: Boolean) {
|
||||
foo()
|
||||
}
|
||||
|
||||
override fun baz() {
|
||||
foo()
|
||||
bar(false)
|
||||
}
|
||||
}
|
||||
|
||||
fun test() {
|
||||
A().foo()
|
||||
A().bar(true)
|
||||
A().baz()
|
||||
|
||||
B().foo()
|
||||
B().bar(true)
|
||||
B().baz()
|
||||
|
||||
C().foo()
|
||||
C().bar(true)
|
||||
C().baz()
|
||||
}
|
||||
+45
@@ -0,0 +1,45 @@
|
||||
class A {
|
||||
public void <caret>foo() {
|
||||
|
||||
}
|
||||
|
||||
public void bar(boolean b) {
|
||||
foo();
|
||||
}
|
||||
|
||||
public void baz() {
|
||||
foo();
|
||||
bar(false);
|
||||
}
|
||||
}
|
||||
|
||||
class B extends A {
|
||||
public void foo() {
|
||||
|
||||
}
|
||||
|
||||
public void bar(boolean b) {
|
||||
foo();
|
||||
}
|
||||
|
||||
public void baz() {
|
||||
foo();
|
||||
bar(false);
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test() {
|
||||
new A().foo();
|
||||
new A().bar(true);
|
||||
new A().baz();
|
||||
|
||||
new B().foo();
|
||||
new B().bar(true);
|
||||
new B().baz();
|
||||
|
||||
new C().foo();
|
||||
new C().bar(true);
|
||||
new C().baz();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
class J extends A {
|
||||
@Override
|
||||
public void foo(int n, @NotNull String s) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bar(boolean b, int n, String s) {
|
||||
foo(1, "abc"); // Propagated parameters are not passed to calles in overriding methods
|
||||
}
|
||||
|
||||
@Override
|
||||
public void baz() {
|
||||
foo(1, "abc");
|
||||
bar(false, 1, "abc");
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test() {
|
||||
new A().foo(1, "abc");
|
||||
new A().bar(true, 1, "abc");
|
||||
new A().baz();
|
||||
|
||||
new B().foo(1, "abc");
|
||||
new B().bar(true, 1, "abc");
|
||||
new B().baz();
|
||||
|
||||
new J().foo(1, "abc");
|
||||
new J().bar(true, 1, "abc");
|
||||
new J().baz();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,43 @@
|
||||
open class A {
|
||||
open fun <caret>foo(n: Int, s: String) {
|
||||
|
||||
}
|
||||
|
||||
open fun bar(b: Boolean, n: Int, s: String) {
|
||||
foo(n, s)
|
||||
}
|
||||
|
||||
open fun baz() {
|
||||
foo(1, "abc")
|
||||
bar(false, 1, "abc")
|
||||
}
|
||||
}
|
||||
|
||||
class B : A() {
|
||||
override fun foo(n: Int, s: String) {
|
||||
|
||||
}
|
||||
|
||||
override fun bar(b: Boolean, n: Int, s: String) {
|
||||
foo(n, s)
|
||||
}
|
||||
|
||||
override fun baz() {
|
||||
foo(1, "abc")
|
||||
bar(false, 1, "abc")
|
||||
}
|
||||
}
|
||||
|
||||
fun test(n: Int, s: String) {
|
||||
A().foo(n, s)
|
||||
A().bar(true, n, s)
|
||||
A().baz()
|
||||
|
||||
B().foo(n, s)
|
||||
B().bar(true, n, s)
|
||||
B().baz()
|
||||
|
||||
J().foo(n, s)
|
||||
J().bar(true, n, s)
|
||||
J().baz()
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
class J extends A {
|
||||
@Override
|
||||
public void foo() {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bar(boolean b) {
|
||||
foo(); // Propagated parameters are not passed to calles in overriding methods
|
||||
}
|
||||
|
||||
@Override
|
||||
public void baz() {
|
||||
foo();
|
||||
bar(false);
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test() {
|
||||
new A().foo();
|
||||
new A().bar(true);
|
||||
new A().baz();
|
||||
|
||||
new B().foo();
|
||||
new B().bar(true);
|
||||
new B().baz();
|
||||
|
||||
new J().foo();
|
||||
new J().bar(true);
|
||||
new J().baz();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,43 @@
|
||||
open class A {
|
||||
open fun <caret>foo() {
|
||||
|
||||
}
|
||||
|
||||
open fun bar(b: Boolean) {
|
||||
foo()
|
||||
}
|
||||
|
||||
open fun baz() {
|
||||
foo()
|
||||
bar(false)
|
||||
}
|
||||
}
|
||||
|
||||
class B : A() {
|
||||
override fun foo() {
|
||||
|
||||
}
|
||||
|
||||
override fun bar(b: Boolean) {
|
||||
foo()
|
||||
}
|
||||
|
||||
override fun baz() {
|
||||
foo()
|
||||
bar(false)
|
||||
}
|
||||
}
|
||||
|
||||
fun test() {
|
||||
A().foo()
|
||||
A().bar(true)
|
||||
A().baz()
|
||||
|
||||
B().foo()
|
||||
B().bar(true)
|
||||
B().baz()
|
||||
|
||||
J().foo()
|
||||
J().bar(true)
|
||||
J().baz()
|
||||
}
|
||||
Vendored
+22
@@ -0,0 +1,22 @@
|
||||
class J extends A {
|
||||
public J(int n) {
|
||||
|
||||
super(n);
|
||||
}
|
||||
|
||||
public J(boolean b, int n) {
|
||||
super(n);
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test(int n) {
|
||||
new A(n);
|
||||
new A(true, n);
|
||||
new B(n);
|
||||
new B(true, n);
|
||||
new C(true, n);
|
||||
new J(n);
|
||||
new J(true, n);
|
||||
}
|
||||
}
|
||||
+21
@@ -0,0 +1,21 @@
|
||||
open class <caret>A(n: Int) {
|
||||
constructor(b: Boolean, n: Int): this(n)
|
||||
}
|
||||
|
||||
open class B: A {
|
||||
constructor(n: Int) : super(n)
|
||||
|
||||
constructor(b: Boolean, n: Int): super(n)
|
||||
}
|
||||
|
||||
open class C(b: Boolean, n: Int): A(n)
|
||||
|
||||
fun test(n: Int) {
|
||||
A(n)
|
||||
A(false, n)
|
||||
B(n)
|
||||
B(false, n)
|
||||
C(false, n)
|
||||
J(n)
|
||||
J(false, n)
|
||||
}
|
||||
Vendored
+21
@@ -0,0 +1,21 @@
|
||||
class J extends A {
|
||||
public J() {
|
||||
|
||||
}
|
||||
|
||||
public J(boolean b) {
|
||||
super();
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test() {
|
||||
new A();
|
||||
new A(true);
|
||||
new B();
|
||||
new B(true);
|
||||
new C(true);
|
||||
new J();
|
||||
new J(true);
|
||||
}
|
||||
}
|
||||
+20
@@ -0,0 +1,20 @@
|
||||
open class <caret>A() {
|
||||
constructor(b: Boolean): this()
|
||||
}
|
||||
|
||||
open class B: A {
|
||||
constructor()
|
||||
constructor(b: Boolean): super()
|
||||
}
|
||||
|
||||
open class C(b: Boolean): A()
|
||||
|
||||
fun test() {
|
||||
A()
|
||||
A(false)
|
||||
B()
|
||||
B(false)
|
||||
C(false)
|
||||
J()
|
||||
J(false)
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
fun <caret>foo() = 1
|
||||
|
||||
fun bar(n: Int): Int {
|
||||
return foo() + n
|
||||
}
|
||||
+1
@@ -0,0 +1 @@
|
||||
There is already a parameter 'n' in fun bar(n: Int): Int. It will conflict with the new parameter.
|
||||
Vendored
+7
@@ -0,0 +1,7 @@
|
||||
fun <caret>foo(n: Int): Int = 1
|
||||
|
||||
class A(val n: Int) {
|
||||
fun bar(n: Int): Int {
|
||||
return foo(n) + this.n
|
||||
}
|
||||
}
|
||||
Vendored
+7
@@ -0,0 +1,7 @@
|
||||
fun <caret>foo(): Int = 1
|
||||
|
||||
class A(val n: Int) {
|
||||
fun bar(): Int {
|
||||
return foo() + n
|
||||
}
|
||||
}
|
||||
Vendored
+7
@@ -0,0 +1,7 @@
|
||||
fun <caret>foo(n: Int): Int = 1
|
||||
|
||||
class A(val n: Int)
|
||||
|
||||
fun A.bar(n: Int): Int {
|
||||
return foo(n) + this.n
|
||||
}
|
||||
Vendored
+7
@@ -0,0 +1,7 @@
|
||||
fun <caret>foo(): Int = 1
|
||||
|
||||
class A(val n: Int)
|
||||
|
||||
fun A.bar(): Int {
|
||||
return foo() + n
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
fun <caret>foo() = 1
|
||||
|
||||
val n = 1
|
||||
|
||||
fun bar(): Int {
|
||||
return foo() + n
|
||||
}
|
||||
+1
@@ -0,0 +1 @@
|
||||
There is already a variable 'n' in fun bar(): Int. It will conflict with the new parameter.
|
||||
Vendored
+22
@@ -0,0 +1,22 @@
|
||||
class J extends A {
|
||||
public J(int n) {
|
||||
|
||||
super(n);
|
||||
}
|
||||
|
||||
public J(boolean b, int n) {
|
||||
super(n);
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test(int n) {
|
||||
new A(n);
|
||||
new A(true, n);
|
||||
new B(n);
|
||||
new B(true, n);
|
||||
new C(true, n);
|
||||
new J(n);
|
||||
new J(true, n);
|
||||
}
|
||||
}
|
||||
+21
@@ -0,0 +1,21 @@
|
||||
open class A {
|
||||
<caret>constructor(n: Int)
|
||||
constructor(b: Boolean, n: Int): this(n)
|
||||
}
|
||||
|
||||
open class B: A {
|
||||
constructor(n: Int) : super(n)
|
||||
|
||||
constructor(b: Boolean, n: Int): super(n)
|
||||
}
|
||||
|
||||
open class C(b: Boolean, n: Int): A(n)
|
||||
|
||||
fun test(n: Int) {
|
||||
A(n)
|
||||
A(false, n)
|
||||
B(n)
|
||||
B(false, n)
|
||||
C(false, n)
|
||||
J(n)
|
||||
}
|
||||
Vendored
+21
@@ -0,0 +1,21 @@
|
||||
class J extends A {
|
||||
public J() {
|
||||
|
||||
}
|
||||
|
||||
public J(boolean b) {
|
||||
super();
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void test() {
|
||||
new A();
|
||||
new A(true);
|
||||
new B();
|
||||
new B(true);
|
||||
new C(true);
|
||||
new J();
|
||||
new J(true);
|
||||
}
|
||||
}
|
||||
Vendored
+20
@@ -0,0 +1,20 @@
|
||||
open class A {
|
||||
<caret>constructor()
|
||||
constructor(b: Boolean): this()
|
||||
}
|
||||
|
||||
open class B: A {
|
||||
constructor()
|
||||
constructor(b: Boolean): super()
|
||||
}
|
||||
|
||||
open class C(b: Boolean): A()
|
||||
|
||||
fun test() {
|
||||
A()
|
||||
A(false)
|
||||
B()
|
||||
B(false)
|
||||
C(false)
|
||||
J()
|
||||
}
|
||||
+252
-12
@@ -22,27 +22,32 @@ import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.projectRoots.Sdk;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.impl.java.stubs.index.JavaFullClassNameIndex;
|
||||
import com.intellij.psi.search.GlobalSearchScope;
|
||||
import com.intellij.refactoring.BaseRefactoringProcessor;
|
||||
import com.intellij.refactoring.changeSignature.ChangeSignatureProcessor;
|
||||
import com.intellij.refactoring.changeSignature.ParameterInfoImpl;
|
||||
import com.intellij.refactoring.changeSignature.ThrownExceptionInfo;
|
||||
import com.intellij.refactoring.util.CanonicalTypes;
|
||||
import com.intellij.refactoring.util.CommonRefactoringUtil;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import com.intellij.util.VisibilityUtil;
|
||||
import kotlin.KotlinPackage;
|
||||
import kotlin.jvm.functions.Function1;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.jetbrains.kotlin.asJava.AsJavaPackage;
|
||||
import org.jetbrains.kotlin.builtins.KotlinBuiltIns;
|
||||
import org.jetbrains.kotlin.descriptors.CallableDescriptor;
|
||||
import org.jetbrains.kotlin.descriptors.Visibilities;
|
||||
import org.jetbrains.kotlin.idea.caches.resolve.ResolvePackage;
|
||||
import org.jetbrains.kotlin.idea.refactoring.JetRefactoringBundle;
|
||||
import org.jetbrains.kotlin.idea.refactoring.changeSignature.ui.KotlinMethodNode;
|
||||
import org.jetbrains.kotlin.idea.stubindex.JetFullClassNameIndex;
|
||||
import org.jetbrains.kotlin.idea.stubindex.JetTopLevelFunctionFqnNameIndex;
|
||||
import org.jetbrains.kotlin.idea.test.DirectiveBasedActionUtils;
|
||||
import org.jetbrains.kotlin.idea.test.KotlinCodeInsightTestCase;
|
||||
import org.jetbrains.kotlin.idea.test.PluginTestCaseBase;
|
||||
import org.jetbrains.kotlin.psi.JetElement;
|
||||
import org.jetbrains.kotlin.psi.JetFile;
|
||||
import org.jetbrains.kotlin.psi.JetPsiFactory;
|
||||
import org.jetbrains.kotlin.psi.*;
|
||||
import org.jetbrains.kotlin.resolve.BindingContext;
|
||||
import org.jetbrains.kotlin.resolve.dataClassUtils.DataClassUtilsPackage;
|
||||
import org.jetbrains.kotlin.resolve.lazy.BodyResolveMode;
|
||||
@@ -544,7 +549,7 @@ public class JetChangeSignatureTest extends KotlinCodeInsightTestCase {
|
||||
public void testSAMChangeMethodReturnType() throws Exception {
|
||||
doJavaTest(
|
||||
new JavaRefactoringProvider() {
|
||||
@Nullable
|
||||
@NotNull
|
||||
@Override
|
||||
PsiType getNewReturnType(@NotNull PsiMethod method) {
|
||||
return PsiType.getJavaLangObject(getPsiManager(), GlobalSearchScope.allScope(getProject()));
|
||||
@@ -567,7 +572,7 @@ public class JetChangeSignatureTest extends KotlinCodeInsightTestCase {
|
||||
return newParameters;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@NotNull
|
||||
@Override
|
||||
PsiType getNewReturnType(@NotNull PsiMethod method) {
|
||||
return factory.createTypeFromText("X<java.util.List<A>>", method);
|
||||
@@ -978,7 +983,7 @@ public class JetChangeSignatureTest extends KotlinCodeInsightTestCase {
|
||||
public void testJavaMethodOverridesReplaceParam() throws Exception {
|
||||
doJavaTest(
|
||||
new JavaRefactoringProvider() {
|
||||
@Nullable
|
||||
@NotNull
|
||||
@Override
|
||||
PsiType getNewReturnType(@NotNull PsiMethod method) {
|
||||
return PsiType.getJavaLangString(getPsiManager(), GlobalSearchScope.allScope(getProject()));
|
||||
@@ -998,7 +1003,7 @@ public class JetChangeSignatureTest extends KotlinCodeInsightTestCase {
|
||||
public void testJavaMethodOverridesChangeParam() throws Exception {
|
||||
doJavaTest(
|
||||
new JavaRefactoringProvider() {
|
||||
@Nullable
|
||||
@NotNull
|
||||
@Override
|
||||
PsiType getNewReturnType(@NotNull PsiMethod method) {
|
||||
return PsiType.getJavaLangString(getPsiManager(), GlobalSearchScope.allScope(getProject()));
|
||||
@@ -1084,6 +1089,233 @@ public class JetChangeSignatureTest extends KotlinCodeInsightTestCase {
|
||||
doTest(changeInfo);
|
||||
}
|
||||
|
||||
public void testParameterPropagation() throws Exception {
|
||||
JetChangeInfo changeInfo = getChangeInfo();
|
||||
|
||||
JetParameterInfo newParameter1 = new JetParameterInfo(changeInfo.getMethodDescriptor().getBaseDescriptor(),
|
||||
-1, "n", null, null,
|
||||
new JetPsiFactory(getProject()).createExpression("1"), JetValVar.None, null);
|
||||
newParameter1.setCurrentTypeText("kotlin.Int");
|
||||
changeInfo.addParameter(newParameter1);
|
||||
|
||||
JetParameterInfo newParameter2 = new JetParameterInfo(changeInfo.getMethodDescriptor().getBaseDescriptor(),
|
||||
-1, "s", null, null,
|
||||
new JetPsiFactory(getProject()).createExpression("\"abc\""), JetValVar.None, null);
|
||||
newParameter2.setCurrentTypeText("kotlin.String");
|
||||
changeInfo.addParameter(newParameter2);
|
||||
|
||||
JetClassOrObject classA =
|
||||
JetFullClassNameIndex.getInstance().get("A", getProject(), GlobalSearchScope.allScope(getProject()))
|
||||
.iterator().next();
|
||||
JetDeclaration functionBar = KotlinPackage.first(
|
||||
classA.getDeclarations(),
|
||||
new Function1<JetDeclaration, Boolean>() {
|
||||
@Override
|
||||
public Boolean invoke(JetDeclaration declaration) {
|
||||
return declaration instanceof JetNamedFunction && "bar".equals(declaration.getName());
|
||||
}
|
||||
}
|
||||
);
|
||||
JetNamedFunction functionTest =
|
||||
JetTopLevelFunctionFqnNameIndex.getInstance().get("test", getProject(), GlobalSearchScope.allScope(getProject()))
|
||||
.iterator().next();
|
||||
|
||||
changeInfo.setPrimaryPropagationTargets(Arrays.asList(functionBar, functionTest));
|
||||
|
||||
doTest(changeInfo);
|
||||
}
|
||||
|
||||
public void testJavaParameterPropagation() throws Exception {
|
||||
doJavaTest(
|
||||
new JavaRefactoringProvider() {
|
||||
@NotNull
|
||||
@Override
|
||||
ParameterInfoImpl[] getNewParameters(@NotNull PsiMethod method) {
|
||||
return new ParameterInfoImpl[] {
|
||||
new ParameterInfoImpl(-1, "n", PsiType.INT, "1"),
|
||||
new ParameterInfoImpl(-1,
|
||||
"s",
|
||||
PsiType.getJavaLangString(getPsiManager(), GlobalSearchScope.allScope(getProject())),
|
||||
"\"abc\"")
|
||||
};
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
Set<PsiMethod> getParameterPropagationTargets(@NotNull PsiMethod method) {
|
||||
PsiClass classA = KotlinPackage.first(
|
||||
JavaFullClassNameIndex.getInstance()
|
||||
.get("A".hashCode(), getProject(), GlobalSearchScope.allScope(getProject())),
|
||||
new Function1<PsiClass, Boolean>() {
|
||||
@Override
|
||||
public Boolean invoke(PsiClass aClass) {
|
||||
return "A".equals(aClass.getName());
|
||||
}
|
||||
}
|
||||
);
|
||||
PsiMethod methodBar = KotlinPackage.first(
|
||||
classA.getMethods(),
|
||||
new Function1<PsiMethod, Boolean>() {
|
||||
@Override
|
||||
public Boolean invoke(PsiMethod method) {
|
||||
return "bar".equals(method.getName());
|
||||
}
|
||||
}
|
||||
);
|
||||
JetNamedFunction functionTest =
|
||||
JetTopLevelFunctionFqnNameIndex.getInstance().get("test", getProject(), GlobalSearchScope.allScope(getProject()))
|
||||
.iterator().next();
|
||||
|
||||
return KotlinPackage.setOf(methodBar, AsJavaPackage.getRepresentativeLightMethod(functionTest));
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public void testPropagateWithParameterDuplication() throws Exception {
|
||||
JetChangeInfo changeInfo = getChangeInfo();
|
||||
|
||||
JetParameterInfo newParameter = new JetParameterInfo(changeInfo.getMethodDescriptor().getBaseDescriptor(),
|
||||
-1, "n", KotlinBuiltIns.getInstance().getIntType(), null,
|
||||
new JetPsiFactory(getProject()).createExpression("1"), JetValVar.None, null);
|
||||
changeInfo.addParameter(newParameter);
|
||||
|
||||
JetNamedFunction functionBar =
|
||||
JetTopLevelFunctionFqnNameIndex.getInstance().get("bar", getProject(), GlobalSearchScope.allScope(getProject()))
|
||||
.iterator().next();
|
||||
|
||||
changeInfo.setPrimaryPropagationTargets(Collections.singletonList(functionBar));
|
||||
|
||||
doTestConflict(changeInfo);
|
||||
}
|
||||
|
||||
public void testPropagateWithVariableDuplication() throws Exception {
|
||||
JetChangeInfo changeInfo = getChangeInfo();
|
||||
|
||||
JetParameterInfo newParameter = new JetParameterInfo(changeInfo.getMethodDescriptor().getBaseDescriptor(),
|
||||
-1, "n", KotlinBuiltIns.getInstance().getIntType(), null,
|
||||
new JetPsiFactory(getProject()).createExpression("1"), JetValVar.None, null);
|
||||
changeInfo.addParameter(newParameter);
|
||||
|
||||
JetNamedFunction functionBar =
|
||||
JetTopLevelFunctionFqnNameIndex.getInstance().get("bar", getProject(), GlobalSearchScope.allScope(getProject()))
|
||||
.iterator().next();
|
||||
|
||||
changeInfo.setPrimaryPropagationTargets(Collections.singletonList(functionBar));
|
||||
|
||||
doTestConflict(changeInfo);
|
||||
}
|
||||
|
||||
public void testPropagateWithThisQualificationInClassMember() throws Exception {
|
||||
JetChangeInfo changeInfo = getChangeInfo();
|
||||
|
||||
JetParameterInfo newParameter = new JetParameterInfo(changeInfo.getMethodDescriptor().getBaseDescriptor(),
|
||||
-1, "n", KotlinBuiltIns.getInstance().getIntType(), null,
|
||||
new JetPsiFactory(getProject()).createExpression("1"), JetValVar.None, null);
|
||||
changeInfo.addParameter(newParameter);
|
||||
|
||||
JetClassOrObject classA =
|
||||
JetFullClassNameIndex.getInstance().get("A", getProject(), GlobalSearchScope.allScope(getProject()))
|
||||
.iterator().next();
|
||||
JetDeclaration functionBar = KotlinPackage.first(
|
||||
classA.getDeclarations(),
|
||||
new Function1<JetDeclaration, Boolean>() {
|
||||
@Override
|
||||
public Boolean invoke(JetDeclaration declaration) {
|
||||
return declaration instanceof JetNamedFunction && "bar".equals(declaration.getName());
|
||||
}
|
||||
}
|
||||
);
|
||||
changeInfo.setPrimaryPropagationTargets(Collections.singletonList(functionBar));
|
||||
|
||||
doTest(changeInfo);
|
||||
}
|
||||
|
||||
public void testPropagateWithThisQualificationInExtension() throws Exception {
|
||||
JetChangeInfo changeInfo = getChangeInfo();
|
||||
|
||||
JetParameterInfo newParameter = new JetParameterInfo(changeInfo.getMethodDescriptor().getBaseDescriptor(),
|
||||
-1, "n", KotlinBuiltIns.getInstance().getIntType(), null,
|
||||
new JetPsiFactory(getProject()).createExpression("1"), JetValVar.None, null);
|
||||
changeInfo.addParameter(newParameter);
|
||||
|
||||
JetNamedFunction functionBar =
|
||||
JetTopLevelFunctionFqnNameIndex.getInstance().get("bar", getProject(), GlobalSearchScope.allScope(getProject()))
|
||||
.iterator().next();
|
||||
|
||||
changeInfo.setPrimaryPropagationTargets(Collections.singletonList(functionBar));
|
||||
|
||||
doTest(changeInfo);
|
||||
}
|
||||
|
||||
public void testJavaConstructorParameterPropagation() throws Exception {
|
||||
doJavaTest(
|
||||
new JavaRefactoringProvider() {
|
||||
@NotNull
|
||||
@Override
|
||||
ParameterInfoImpl[] getNewParameters(@NotNull PsiMethod method) {
|
||||
return new ParameterInfoImpl[] { new ParameterInfoImpl(-1, "n", PsiType.INT, "1") };
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
Set<PsiMethod> getParameterPropagationTargets(@NotNull PsiMethod method) {
|
||||
return findCallers(method);
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public void testPrimaryConstructorParameterPropagation() throws Exception {
|
||||
JetChangeInfo changeInfo = getChangeInfo();
|
||||
|
||||
JetParameterInfo newParameter = new JetParameterInfo(changeInfo.getMethodDescriptor().getBaseDescriptor(),
|
||||
-1, "n", KotlinBuiltIns.getInstance().getIntType(), null,
|
||||
new JetPsiFactory(getProject()).createExpression("1"), JetValVar.None, null);
|
||||
changeInfo.addParameter(newParameter);
|
||||
|
||||
PsiMethod constructor = AsJavaPackage.getRepresentativeLightMethod(changeInfo.getMethod());
|
||||
assert constructor != null;
|
||||
changeInfo.setPrimaryPropagationTargets(findCallers(constructor));
|
||||
|
||||
doTest(changeInfo);
|
||||
}
|
||||
|
||||
public void testSecondaryConstructorParameterPropagation() throws Exception {
|
||||
JetChangeInfo changeInfo = getChangeInfo();
|
||||
|
||||
JetParameterInfo newParameter = new JetParameterInfo(changeInfo.getMethodDescriptor().getBaseDescriptor(),
|
||||
-1, "n", KotlinBuiltIns.getInstance().getIntType(), null,
|
||||
new JetPsiFactory(getProject()).createExpression("1"), JetValVar.None, null);
|
||||
changeInfo.addParameter(newParameter);
|
||||
|
||||
PsiMethod constructor = AsJavaPackage.getRepresentativeLightMethod(changeInfo.getMethod());
|
||||
assert constructor != null;
|
||||
changeInfo.setPrimaryPropagationTargets(findCallers(constructor));
|
||||
|
||||
doTest(changeInfo);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private LinkedHashSet<PsiMethod> findCallers(@NotNull PsiMethod method) {
|
||||
KotlinMethodNode rootNode =
|
||||
new KotlinMethodNode(method,
|
||||
new HashSet<PsiElement>(),
|
||||
getProject(),
|
||||
new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
}
|
||||
});
|
||||
LinkedHashSet<PsiMethod> callers = new LinkedHashSet<PsiMethod>();
|
||||
for (int i = 0; i < rootNode.getChildCount(); i++) {
|
||||
PsiElement element = ((KotlinMethodNode) rootNode.getChildAt(i)).getMethod();
|
||||
callers.addAll(AsJavaPackage.toLightMethods(element));
|
||||
}
|
||||
return callers;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
protected String getTestDataPath() {
|
||||
@@ -1142,9 +1374,10 @@ public class JetChangeSignatureTest extends KotlinCodeInsightTestCase {
|
||||
return method.getName();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@NotNull
|
||||
PsiType getNewReturnType(@NotNull PsiMethod method) {
|
||||
return method.getReturnType();
|
||||
PsiType type = method.getReturnType();
|
||||
return type != null ? type : PsiType.VOID;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@@ -1158,6 +1391,11 @@ public class JetChangeSignatureTest extends KotlinCodeInsightTestCase {
|
||||
return parameterInfos;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
Set<PsiMethod> getParameterPropagationTargets(@NotNull PsiMethod method) {
|
||||
return Collections.emptySet();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
final ChangeSignatureProcessor getProcessor(@NotNull PsiMethod method) {
|
||||
return new ChangeSignatureProcessor(
|
||||
@@ -1166,9 +1404,11 @@ public class JetChangeSignatureTest extends KotlinCodeInsightTestCase {
|
||||
false,
|
||||
VisibilityUtil.getVisibilityModifier(method.getModifierList()),
|
||||
getNewName(method),
|
||||
getNewReturnType(method),
|
||||
CanonicalTypes.createTypeWrapper(getNewReturnType(method)),
|
||||
getNewParameters(method),
|
||||
new ThrownExceptionInfo[0]);
|
||||
new ThrownExceptionInfo[0],
|
||||
getParameterPropagationTargets(method),
|
||||
Collections.<PsiMethod>emptySet());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user