change signature: convert method reference to lambda if SAM method signature was changed (IDEA-150138)

This commit is contained in:
Anna Kozlova
2016-01-13 16:54:58 +01:00
parent b56e7e0c20
commit 3fd8dfd38c
5 changed files with 66 additions and 4 deletions
@@ -113,9 +113,16 @@ public class JavaChangeSignatureUsageProcessor implements ChangeSignatureUsagePr
else if (usage instanceof FunctionalInterfaceChangedUsageInfo) {
final PsiElementFactory elementFactory = JavaPsiFacade.getElementFactory(usage.getProject());
final PsiElement element = usage.getElement();
final PsiMethod interfaceMethod = ((FunctionalInterfaceChangedUsageInfo)usage).getMethod();
if (element instanceof PsiLambdaExpression) {
processMethodParams((JavaChangeInfo)changeInfo, ((FunctionalInterfaceChangedUsageInfo)usage).getMethod(),
elementFactory, PsiSubstitutor.EMPTY, ((PsiLambdaExpression)element).getParameterList(), ((PsiLambdaExpression)element).getBody());
processMethodParams((JavaChangeInfo)changeInfo, interfaceMethod,
elementFactory, PsiSubstitutor.EMPTY, ((PsiLambdaExpression)element).getParameterList(), ((PsiLambdaExpression)element).getBody());
}
else if (element instanceof PsiMethodReferenceExpression) {
final PsiLambdaExpression lambdaExpression =
LambdaRefactoringUtil.convertMethodReferenceToLambda((PsiMethodReferenceExpression)element, false, true);
processMethodParams(((JavaChangeInfo)changeInfo), interfaceMethod, elementFactory, PsiSubstitutor.EMPTY,
lambdaExpression.getParameterList(), lambdaExpression.getBody());
}
return true;
}
@@ -981,7 +988,7 @@ public class JavaChangeSignatureUsageProcessor implements ChangeSignatureUsagePr
checkContract(conflictDescriptions, method);
}
else if (element instanceof PsiMethodReferenceExpression) {
conflictDescriptions.putValue(element, "Changed method is used in method reference");
conflictDescriptions.putValue(element, "Changed method is used in method reference. Proceeding would result in conversion to lambda expression");
}
}
@@ -0,0 +1,11 @@
interface I {
void m<caret>(int a, int b);
}
class Test {
{
I i = this::foo;
}
private void foo(int a, int b) {}
}
@@ -0,0 +1,11 @@
interface I {
void m(int b, int a);
}
class Test {
{
I i = (b, a) -> foo(a, b);
}
private void foo(int a, int b) {}
}
@@ -17,11 +17,13 @@ package com.intellij.refactoring;
import com.intellij.JavaTestUtil;
import com.intellij.codeInsight.TargetElementUtil;
import com.intellij.openapi.util.Ref;
import com.intellij.psi.*;
import com.intellij.refactoring.changeSignature.ChangeSignatureProcessor;
import com.intellij.refactoring.changeSignature.JavaThrownExceptionInfo;
import com.intellij.refactoring.changeSignature.ParameterInfoImpl;
import com.intellij.refactoring.changeSignature.ThrownExceptionInfo;
import com.intellij.usageView.UsageInfo;
import com.intellij.util.IncorrectOperationException;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
@@ -96,6 +98,16 @@ public abstract class ChangeSignatureBaseTest extends LightRefactoringTestCase {
GenParams genParams,
GenExceptions genExceptions,
boolean generateDelegate) {
doTest(newVisibility, newName, newReturnType, genParams, genExceptions, generateDelegate, false);
}
protected void doTest(@PsiModifier.ModifierConstant @Nullable String newVisibility,
@Nullable String newName,
@Nullable String newReturnType,
GenParams genParams,
GenExceptions genExceptions,
boolean generateDelegate,
boolean skipConflict) {
String basePath = getRelativePath() + getTestName(false);
configureByFile(basePath + ".java");
PsiElement targetElement = TargetElementUtil.findTargetElement(getEditor(), TargetElementUtil.ELEMENT_NAME_ACCEPTED);
@@ -104,7 +116,20 @@ public abstract class ChangeSignatureBaseTest extends LightRefactoringTestCase {
PsiType newType = newReturnType != null ? myFactory.createTypeFromText(newReturnType, method) : method.getReturnType();
new ChangeSignatureProcessor(getProject(), method, generateDelegate, newVisibility,
newName != null ? newName : method.getName(),
newType, genParams.genParams(method), genExceptions.genExceptions(method)).run();
newType, genParams.genParams(method), genExceptions.genExceptions(method)) {
@Override
protected boolean preprocessUsages(@NotNull Ref<UsageInfo[]> refUsages) {
try {
return super.preprocessUsages(refUsages);
}
catch (ConflictsInTestsException e) {
if (skipConflict) {
return true;
}
throw e;
}
}
}.run();
checkResultByFile(basePath + "_after.java");
}
@@ -340,6 +340,14 @@ public class ChangeSignatureTest extends ChangeSignatureBaseTest {
}, false);
}
public void testReorderParamsOfFunctionalInterfaceExpandMethodReference() {
GenParams genParams = method -> new ParameterInfoImpl[]{
new ParameterInfoImpl(1, "b", PsiType.INT),
new ParameterInfoImpl(0, "a", PsiType.INT)
};
doTest(null, null, null, genParams, new SimpleExceptionsGen(), false, true);
}
public void testMethodParametersAlignmentAfterMethodNameChange() {
getJavaSettings().ALIGN_MULTILINE_PARAMETERS = true;
getJavaSettings().ALIGN_MULTILINE_PARAMETERS_IN_CALLS = true;