ability to change name of method to any string constant. Detection of incorrect usages
authorMaxim Medvedev <maxim.medvedev@jetbrains.com>
Mon, 31 May 2010 15:18:30 +0000 (19:18 +0400)
committerMaxim Medvedev <maxim.medvedev@jetbrains.com>
Mon, 31 May 2010 15:18:30 +0000 (19:18 +0400)
18 files changed:
java/java-impl/src/com/intellij/refactoring/actions/ChangeSignatureAction.java
java/java-impl/src/com/intellij/refactoring/changeSignature/ChangeSignatureProcessor.java
java/java-impl/src/com/intellij/refactoring/changeSignature/JavaChangeSignatureHandler.java
java/java-impl/src/com/intellij/refactoring/changeSignature/JavaChangeSignatureUsageProcessor.java
java/java-impl/src/com/intellij/refactoring/changeSignature/PossiblyIncorrectUsage.java [new file with mode: 0644]
java/java-tests/testSrc/com/intellij/refactoring/ChangeSignatureTargetTest.java
platform/lang-api/src/com/intellij/refactoring/changeSignature/ChangeSignatureHandler.java
platform/lang-api/src/com/intellij/refactoring/changeSignature/ChangeSignatureUsageProcessor.java
platform/platform-resources-en/src/messages/RefactoringBundle.properties
plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/changeSignature/GrChageSignatureUsageSearcher.java
plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/changeSignature/GrChangeInfoImpl.java
plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/changeSignature/GrChangeSignatureDialog.java
plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/changeSignature/GrChangeSignatureHandler.java
plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/changeSignature/GrChangeSignatureProcessor.java
plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/changeSignature/GrChangeSignatureUsageProcessor.java
plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/changeSignature/GrMethodCallUsageInfo.java
plugins/groovy/testdata/refactoring/changeSignature/ReplaceVarargWithArray.groovy
plugins/groovy/testdata/refactoring/changeSignature/ReplaceVarargWithArray_after.groovy

index 382cc4adb1ed328e2dd4e5509859c60332a539d2..4c21639f963a1e19f811beab862a2b3b9355ad13 100644 (file)
@@ -21,9 +21,12 @@ import com.intellij.openapi.actionSystem.DataContext;
 import com.intellij.openapi.actionSystem.LangDataKeys;
 import com.intellij.openapi.editor.Document;
 import com.intellij.openapi.editor.Editor;
+import com.intellij.openapi.editor.ScrollType;
+import com.intellij.openapi.project.Project;
 import com.intellij.psi.*;
 import com.intellij.refactoring.RefactoringActionHandler;
 import com.intellij.refactoring.changeSignature.ChangeSignatureHandler;
+import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 
 public class ChangeSignatureAction extends BaseRefactoringAction {
@@ -38,18 +41,60 @@ public class ChangeSignatureAction extends BaseRefactoringAction {
   protected boolean isAvailableOnElementInEditor(final PsiElement element, final Editor editor) {
     final Document document = editor.getDocument();
     final PsiFile file = PsiDocumentManager.getInstance(element.getProject()).getPsiFile(document);
-    final ChangeSignatureHandler handler = getChangeSignatureHandler(element.getLanguage());
-    if (handler == null) return false;
-    if (file != null && handler.findTargetMember(file, editor) != null) {
-      return true;
+    if (file == null) return false;
+    PsiElement targetMember = findTargetMember(file, editor);
+    if (targetMember == null) return false;
+    final ChangeSignatureHandler targetHandler = getChangeSignatureHandler(targetMember.getLanguage());
+    if (targetHandler == null) return false;
+    return true;
+  }
+
+  @Nullable
+  private static PsiElement findTargetMember(PsiFile file, Editor editor) {
+    final PsiElement element = file.findElementAt(editor.getCaretModel().getOffset());
+    final PsiElement targetMember = findTargetMember(element);
+    if (targetMember != null) return targetMember;
+
+    final PsiReference reference = file.findReferenceAt(editor.getCaretModel().getOffset());
+    if (reference == null) return null;
+    return reference.resolve();
+  }
+
+  @Nullable
+  private static PsiElement findTargetMember(@Nullable PsiElement element) {
+    if (element == null) return null;
+    final ChangeSignatureHandler fileHandler = getChangeSignatureHandler(element.getLanguage());
+    if (fileHandler != null) {
+      final PsiElement targetMember = fileHandler.findTargetMember(element);
+      if (targetMember != null) return targetMember;
     }
-    return element instanceof PsiMethod || element instanceof PsiClass;
+    final PsiReference reference = element.getReference();
+    if (reference == null) return null;
+    return reference.resolve();
   }
 
   public RefactoringActionHandler getHandler(DataContext dataContext) {
     final Language language = LangDataKeys.LANGUAGE.getData(dataContext);
     if (language != null) {
-      return getChangeSignatureHandler(language);
+      return new RefactoringActionHandler() {
+        public void invoke(@NotNull Project project, Editor editor, PsiFile file, DataContext dataContext) {
+          editor.getScrollingModel().scrollToCaret(ScrollType.MAKE_VISIBLE);
+          final PsiElement targetMember = findTargetMember(file, editor);
+          if (targetMember == null) return;
+          final ChangeSignatureHandler handler = getChangeSignatureHandler(targetMember.getLanguage());
+          if (handler == null) return;
+          handler.invoke(project, new PsiElement[]{targetMember}, dataContext);
+        }
+
+        public void invoke(@NotNull Project project, @NotNull PsiElement[] elements, DataContext dataContext) {
+          if (elements.length != 1) return;
+          final PsiElement targetMember = findTargetMember(elements[0]);
+          if (targetMember == null) return;
+          final ChangeSignatureHandler handler = getChangeSignatureHandler(targetMember.getLanguage());
+          if (handler == null) return;
+          handler.invoke(project, new PsiElement[]{targetMember}, dataContext);
+        }
+      };
     }
     return null;
   }
index c543d4ee7b8b9b143f9d53bbb4823249364d097f..286ad737555a9a6aa88679038fd8bf8ba16da712 100644 (file)
@@ -204,6 +204,14 @@ public class ChangeSignatureProcessor extends BaseRefactoringProcessor {
   protected void preprocessCovariantOverriders(final List<UsageInfo> covariantOverriderInfos) {
   }
 
+  @Override
+  protected boolean isPreviewUsages(UsageInfo[] usages) {
+    for (ChangeSignatureUsageProcessor processor : ChangeSignatureUsageProcessor.EP_NAME.getExtensions()) {
+      if (processor.shouldPreviewUsages(myChangeInfo, usages)) return true;
+    }
+    return super.isPreviewUsages(usages);
+  }
+
   protected boolean isProcessCovariantOverriders() {
     return Messages
              .showYesNoDialog(myProject, RefactoringBundle.message("do.you.want.to.process.overriding.methods.with.covariant.return.type"),
index 0a40702708d580392990f7b4e2d5aaa22d439ef5..dc627dc1d0685b2eeab20e3246de954d79270844 100644 (file)
@@ -97,12 +97,20 @@ public class JavaChangeSignatureHandler implements ChangeSignatureHandler {
   }
 
   @Nullable
-  public PsiMember findTargetMember(PsiFile file, Editor editor) {
+  public PsiElement findTargetMember(PsiFile file, Editor editor) {
     PsiElement element = file.findElementAt(editor.getCaretModel().getOffset());
+    return findTargetMember(element);
+  }
+
+  public PsiElement findTargetMember(PsiElement element) {
     if (PsiTreeUtil.getParentOfType(element, PsiParameterList.class) != null) {
       return PsiTreeUtil.getParentOfType(element, PsiMethod.class);
     }
 
+    if (element.getParent() instanceof PsiMethod && ((PsiMethod)element.getParent()).getNameIdentifier()==element) {
+      return element.getParent();
+    }
+
     final PsiMethodCallExpression expression = PsiTreeUtil.getParentOfType(element, PsiMethodCallExpression.class);
     if (expression != null) {
       assert element != null;
@@ -133,10 +141,10 @@ public class JavaChangeSignatureHandler implements ChangeSignatureHandler {
       if (referenceElement != null) {
         final PsiElement resolved = referenceElement.resolve();
         if (resolved instanceof PsiClass) {
-          return (PsiMember)resolved;
+          return resolved;
         }
         else if (resolved instanceof PsiMethod) {
-          return (PsiMember)resolved;
+          return resolved;
         }
       }
     }
index 08ea1f00f740d24f9a09f15998696da776cb6d3b..907cb41ccb74bfba0dc6e8f0b4eb6007ba366c52 100644 (file)
@@ -524,6 +524,10 @@ public class JavaChangeSignatureUsageProcessor implements ChangeSignatureUsagePr
     return true;
   }
 
+  public boolean shouldPreviewUsages(ChangeInfo changeInfo, UsageInfo[] usages) {
+    return false;
+  }
+
   private static void generateDelegate(JavaChangeInfo changeInfo) throws IncorrectOperationException {
     final PsiMethod delegate = (PsiMethod)changeInfo.getMethod().copy();
     final PsiClass targetClass = changeInfo.getMethod().getContainingClass();
@@ -854,6 +858,7 @@ public class JavaChangeSignatureUsageProcessor implements ChangeSignatureUsagePr
       try {
         PsiMethod prototype;
         final PsiMethod method = myChangeInfo.getMethod();
+        if (!StdLanguages.JAVA.equals(method.getLanguage())) return;
         PsiManager manager = PsiManager.getInstance(method.getProject());
         PsiElementFactory factory = JavaPsiFacade.getInstance(manager.getProject()).getElementFactory();
         final CanonicalTypes.Type returnType = myChangeInfo.getNewReturnType();
diff --git a/java/java-impl/src/com/intellij/refactoring/changeSignature/PossiblyIncorrectUsage.java b/java/java-impl/src/com/intellij/refactoring/changeSignature/PossiblyIncorrectUsage.java
new file mode 100644 (file)
index 0000000..68c2fd1
--- /dev/null
@@ -0,0 +1,24 @@
+/*
+ * Copyright 2000-2010 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 com.intellij.refactoring.changeSignature;
+
+/**
+ * All Usages that may be incorrect must implement this interface. In other case incorrect usages will be processed by default processor  
+ * @author Maxim.Medvedev
+ */
+public interface PossiblyIncorrectUsage {
+  boolean isCorrect();
+}
index c2161d9179ce9b9be48ca7f1bb8f8a25a1f466d7..e27c45a45726aef0b015ecb474efb6fde4257a0c 100644 (file)
@@ -7,6 +7,7 @@ package com.intellij.refactoring;
 import com.intellij.JavaTestUtil;
 import com.intellij.openapi.projectRoots.Sdk;
 import com.intellij.openapi.projectRoots.impl.JavaSdkImpl;
+import com.intellij.psi.PsiElement;
 import com.intellij.psi.PsiMember;
 import com.intellij.refactoring.changeSignature.JavaChangeSignatureHandler;
 import com.intellij.testFramework.LightCodeInsightTestCase;
@@ -43,8 +44,8 @@ public class ChangeSignatureTargetTest extends LightCodeInsightTestCase {
     String basePath = "/refactoring/changeSignatureTarget/" + getTestName(true);
     @NonNls final String filePath = basePath + ".java";
     configureByFile(filePath);
-    final PsiMember member = new JavaChangeSignatureHandler().findTargetMember(getFile(), getEditor());
+    final PsiElement member = new JavaChangeSignatureHandler().findTargetMember(getFile(), getEditor());
     assertNotNull(member);
-    assertEquals(expectedMemberName, member.getName());
+    assertEquals(expectedMemberName, ((PsiMember)member).getName());
   }
 }
index 00a88165b80279e39874651419683f5e76506257..4a1dc6b870fb79f2ec23b867d323e5200afb0c22 100644 (file)
@@ -25,9 +25,12 @@ import org.jetbrains.annotations.Nullable;
 /**
  * @author Maxim.Medvedev
  */
-public interface ChangeSignatureHandler extends RefactoringActionHandler{
+public interface ChangeSignatureHandler extends RefactoringActionHandler {
   String REFACTORING_NAME = RefactoringBundle.message("changeSignature.refactoring.name");
 
   @Nullable
   PsiElement findTargetMember(PsiFile file, Editor editor);
+
+  @Nullable
+  PsiElement findTargetMember(PsiElement element);
 }
index 3857afd60dda990f25efb1227cb5853c44361398..240c05f885f846a37c0704bbd30994635953d8d6 100644 (file)
@@ -35,4 +35,6 @@ public interface ChangeSignatureUsageProcessor {
   boolean processUsage(ChangeInfo changeInfo, UsageInfo usageInfo, boolean beforeMethodChange, UsageInfo[] usages);
 
   boolean processPrimaryMethod(ChangeInfo changeInfo);
+
+  boolean shouldPreviewUsages(ChangeInfo changeInfo, UsageInfo[] usages);
 }
index 97799609dd07c23db1db91a4e254d4cf3002d0a5..34e5f971a7ed90e6a17ca829af42ac96225b6db2 100644 (file)
@@ -261,6 +261,7 @@ do.you.want.to.process.overriding.methods.with.covariant.return.type=Do you want
 changing.signature.of.0=Changing signature of {0}
 there.is.already.a.0.in.1.it.will.conflict.with.the.new.parameter=There is already a {0} in {1}. It will conflict with the new parameter.
 0.to.change.signature={0} to change signature
+New.name.of.method.is.not.java.identifier=New name of method is not Java identifier
 references.to.be.changed=References to be changed {0}
 source.folder.0.has.package.prefix.1=Source folder {0} has package prefix ''{1}''\nPackage ''{2}'' cannot be created there.
 javadoc.as.is=&As is
index 01a4d03ea1f679301841b5632ffd05bdf9a423cc..4404a611603b14f82a2c9baf3bc8353ba9fe2668 100644 (file)
@@ -34,10 +34,8 @@ import com.intellij.usageView.UsageViewUtil;
 import com.intellij.util.containers.HashSet;
 import org.jetbrains.plugins.groovy.GroovyFileType;
 import org.jetbrains.plugins.groovy.lang.groovydoc.psi.api.GrDocTagValueToken;
-import org.jetbrains.plugins.groovy.lang.psi.api.statements.arguments.GrArgumentList;
 import org.jetbrains.plugins.groovy.lang.psi.api.statements.blocks.GrOpenBlock;
 import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.GrAnonymousClassDefinition;
-import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrEnumConstant;
 import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrMethod;
 import org.jetbrains.plugins.groovy.lang.psi.util.PsiUtil;
 
@@ -206,16 +204,7 @@ class GrChageSignatureUsageSearcher {
 
         boolean isToCatchExceptions = isToThrowExceptions && needToCatchExceptions(RefactoringUtil.getEnclosingMethod(element));
         if (PsiUtil.isMethodUsage(element)) {
-          final GrArgumentList argList = PsiUtil.getArgumentsList(element);
-          //enum constant may not have argList
-          if (argList == null) {
-            if (element instanceof GrEnumConstant) {
-              result.add(new GrMethodCallUsageInfo(element, isToModifyArgs, isToCatchExceptions));
-            }
-          }
-          else {
-            result.add(new GrMethodCallUsageInfo(element, isToModifyArgs,isToCatchExceptions));
-          }
+          result.add(new GrMethodCallUsageInfo(element, isToModifyArgs, isToCatchExceptions, method));
         }
         else if (element instanceof GrDocTagValueToken) {
           result.add(new UsageInfo(ref.getElement()));
@@ -229,7 +218,7 @@ class GrChageSignatureUsageSearcher {
           LOG.assertTrue(method.isConstructor());
           final PsiClass psiClass = (PsiClass)element;
           if (psiClass instanceof GrAnonymousClassDefinition) {
-            result.add(new GrMethodCallUsageInfo(element, isToModifyArgs, isToCatchExceptions));
+            result.add(new GrMethodCallUsageInfo(element, isToModifyArgs, isToCatchExceptions, method));
             continue;
           }
           /*if (!(myChangeInfo instanceof JavaChangeInfoImpl)) continue; todo propagate methods
@@ -274,6 +263,8 @@ class GrChageSignatureUsageSearcher {
     return overridingMethods;
   }
 
+
+
   private static void addParameterUsages(PsiParameter parameter, ArrayList<UsageInfo> results, ParameterInfo info) {
     PsiManager manager = parameter.getManager();
     GlobalSearchScope projectScope = GlobalSearchScope.projectScope(manager.getProject());
index 935fb50e6100cde33a6d744479451c265deddcda..a7ab92d8f41aa7a6d98a8c0a4266a789d15a9191 100644 (file)
@@ -16,6 +16,7 @@
 package org.jetbrains.plugins.groovy.refactoring.changeSignature;
 
 import com.intellij.lang.Language;
+import com.intellij.openapi.util.text.StringUtil;
 import com.intellij.psi.*;
 import com.intellij.refactoring.changeSignature.JavaChangeInfo;
 import com.intellij.refactoring.changeSignature.JavaParameterInfo;
@@ -151,7 +152,11 @@ class GrChangeInfoImpl implements JavaChangeInfo {
     }
 
     if (myIsNameChanged) {
-      myNewNameIdentifier = JavaPsiFacade.getElementFactory(getMethod().getProject()).createIdentifier(newName);
+      if (StringUtil.isJavaIdentifier(newName)) {
+        myNewNameIdentifier = JavaPsiFacade.getElementFactory(getMethod().getProject()).createIdentifier(newName);
+      } else {
+        myNewNameIdentifier = getMethod().getNameIdentifier();
+      }
     }
 
     PsiElementFactory factory = JavaPsiFacade.getInstance(method.getProject()).getElementFactory();
@@ -189,8 +194,6 @@ class GrChangeInfoImpl implements JavaChangeInfo {
         }
       }
     }
-
-
   }
 
   @NotNull
index a395ba7e7e53f9c44d084023431de36be7bb8185..7d6a6378fc11a0f24d7a8230826b3b8da44171e5 100644 (file)
@@ -35,6 +35,7 @@ import com.intellij.util.Function;
 import com.intellij.util.containers.ContainerUtil;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.plugins.groovy.debugger.fragments.GroovyCodeFragment;
+import org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElementFactory;
 import org.jetbrains.plugins.groovy.lang.psi.api.auxiliary.modifiers.GrModifier;
 import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrMethod;
 import org.jetbrains.plugins.groovy.lang.psi.api.types.GrTypeElement;
@@ -313,8 +314,19 @@ public class GrChangeSignatureDialog extends RefactoringDialog {
     CommonRefactoringUtil.showErrorHint(myProject, null, hint, GroovyRefactoringBundle.message("incorrect.data"), HelpID.CHANGE_SIGNATURE);
   }
 
+  private boolean isGroovyMethodName(String name) {
+    String methodText = "def " + name + "(){}";
+    try {
+      final GrMethod method = GroovyPsiElementFactory.getInstance(getProject()).createMethodFromText(methodText);
+      return method != null;
+    }
+    catch (Throwable e) {
+      return false;
+    }
+  }
+
   private boolean validateInputData() {
-    if (!StringUtil.isJavaIdentifier(getNewName())) {
+    if (!isGroovyMethodName(getNewName())) {
       showErrorHint(message("name.is.wrong", getNewName()));
       return false;
     }
@@ -327,6 +339,7 @@ public class GrChangeSignatureDialog extends RefactoringDialog {
     for (GrTableParameterInfo info : myParameterModel.getParameterInfos()) {
       if (!StringUtil.isJavaIdentifier(info.getName())) {
         showErrorHint(message("name.is.wrong", info.getName()));
+        return false;
       }
       if (!checkType(info.getTypeFragment())) {
         showErrorHint(message("type.for.parameter.is.incorrect", info.getName()));
index 0ff6bf70226f397fe1031b929d67f88a284ceed7..72f9b39c5bea192a3d95bf27811321657e079da0 100644 (file)
@@ -25,6 +25,7 @@ import com.intellij.openapi.project.Project;
 import com.intellij.psi.PsiElement;
 import com.intellij.psi.PsiFile;
 import com.intellij.psi.PsiMethod;
+import com.intellij.psi.PsiReference;
 import com.intellij.psi.util.PsiTreeUtil;
 import com.intellij.refactoring.HelpID;
 import com.intellij.refactoring.RefactoringBundle;
@@ -87,15 +88,36 @@ public class GrChangeSignatureHandler implements ChangeSignatureHandler {
   }
 
   @Nullable
-  public PsiMethod findTargetMember(PsiFile file, Editor editor) {
+  public PsiElement findTargetMember(PsiFile file, Editor editor) {
     final PsiElement element = file.findElementAt(editor.getCaretModel().getOffset());
+    final PsiElement targetMember = findTargetMember(element);
+    if (targetMember != null) return targetMember;
+
+    final PsiReference reference = file.findReferenceAt(editor.getCaretModel().getOffset());
+    if (reference != null) {
+      return reference.resolve();
+    }
+    return null;
+  }
+
+  @Nullable
+  public PsiElement findTargetMember(PsiElement element) {
     final GrParameterList parameterList = PsiTreeUtil.getParentOfType(element, GrParameterList.class);
     if (parameterList != null) {
       final PsiElement parent = parameterList.getParent();
-      if (parent instanceof PsiMethod) return (PsiMethod)parent;
+      if (parent instanceof PsiMethod) return parent;
+    }
+
+    if (element.getParent() instanceof GrMethod && ((GrMethod)element.getParent()).getNameIdentifierGroovy() == element) {
+      return element.getParent();
     }
     final GrMethodCallExpression expression = PsiTreeUtil.getParentOfType(element, GrMethodCallExpression.class);
-    if (expression == null) return null;
-    return expression.resolveMethod();
+    if (expression != null) {
+      return expression.resolveMethod();
+    }
+
+    final PsiReference ref = element.getReference();
+    if (ref == null) return null;
+    return ref.resolve();
   }
 }
index b18e4fafe209beb3f42439fa0e2e3b70f6284583..901ce677d63c567aaa48d4c1541f2ddc746caac8 100644 (file)
@@ -23,6 +23,7 @@ import com.intellij.psi.PsiMethod;
 import com.intellij.refactoring.BaseRefactoringProcessor;
 import com.intellij.refactoring.changeSignature.ChangeSignatureUsageProcessor;
 import com.intellij.refactoring.changeSignature.ChangeSignatureViewDescriptor;
+import com.intellij.refactoring.changeSignature.PossiblyIncorrectUsage;
 import com.intellij.refactoring.rename.RenameUtil;
 import com.intellij.refactoring.ui.ConflictsDialog;
 import com.intellij.refactoring.util.MoveRenameUsageInfo;
@@ -85,7 +86,9 @@ public class GrChangeSignatureProcessor extends BaseRefactoringProcessor {
       else {
         moveRenameInfos.remove(element);
         usedElements.add(element);
-        result.add(info);
+        if (!(info instanceof PossiblyIncorrectUsage) || ((PossiblyIncorrectUsage)info).isCorrect()) {
+          result.add(info);
+        }
       }
     }
     result.addAll(moveRenameInfos.values());
@@ -158,4 +161,12 @@ public class GrChangeSignatureProcessor extends BaseRefactoringProcessor {
     prepareSuccessful();
     return true;
   }
+
+  @Override
+  protected boolean isPreviewUsages(UsageInfo[] usages) {
+    for (ChangeSignatureUsageProcessor processor : ChangeSignatureUsageProcessor.EP_NAME.getExtensions()) {
+      if (processor.shouldPreviewUsages(myChangeInfo, usages)) return true;
+    }
+    return super.isPreviewUsages(usages);
+  }
 }
index dc01b03df1b5deaaad7c4142ef7ade74deffd2ab..67b5a8dabe0646f5ec2ef593e86a486a44818b09 100644 (file)
@@ -106,6 +106,17 @@ public class GrChangeSignatureUsageProcessor implements ChangeSignatureUsageProc
     return processPrimaryMethodInner(grInfo, method, null);
   }
 
+  public boolean shouldPreviewUsages(ChangeInfo changeInfo, UsageInfo[] usages) {
+    if (!StringUtil.isJavaIdentifier(changeInfo.getNewName())) return true;
+
+    for (UsageInfo usage : usages) {
+      if (usage instanceof GrMethodCallUsageInfo) {
+        if (((GrMethodCallUsageInfo)usage).isPossibleUsage()) return true;
+      }
+    }
+    return false;
+  }
+
   private static boolean generateDelegate(GrChangeInfoImpl grInfo) {
     final GrMethod method = grInfo.getMethod();
     final PsiClass psiClass = method.getContainingClass();
index a92476e6e3c13399bb0e5a6f9c31c285270740c0..86c5adeb6848ea8f43b9313b0c3c07b9eadbce54 100644 (file)
@@ -18,6 +18,8 @@ package org.jetbrains.plugins.groovy.refactoring.changeSignature;
 import com.intellij.psi.PsiElement;
 import com.intellij.psi.PsiMethod;
 import com.intellij.psi.PsiSubstitutor;
+import com.intellij.psi.search.GlobalSearchScope;
+import com.intellij.refactoring.changeSignature.PossiblyIncorrectUsage;
 import com.intellij.usageView.UsageInfo;
 import org.jetbrains.annotations.Nullable;
 import org.jetbrains.plugins.groovy.lang.psi.api.GroovyResolveResult;
@@ -35,10 +37,9 @@ import org.jetbrains.plugins.groovy.lang.psi.util.PsiUtil;
 /**
  * @author Maxim.Medvedev
  */
-public class GrMethodCallUsageInfo extends UsageInfo {
+public class GrMethodCallUsageInfo extends UsageInfo implements PossiblyIncorrectUsage {
   private final boolean myToChangeArguments;
   private final boolean myToCatchExceptions;
-  private final PsiMethod myReferencedMethod;
   private GrClosureSignatureUtil.ArgInfo[] myMapToArguments;
   private PsiSubstitutor mySubstitutor;
 
@@ -50,30 +51,35 @@ public class GrMethodCallUsageInfo extends UsageInfo {
     return myToChangeArguments;
   }
 
-  public GrMethodCallUsageInfo(PsiElement element, boolean isToChangeArguments, boolean isToCatchExceptions) {
+  public GrMethodCallUsageInfo(PsiElement element, boolean isToChangeArguments, boolean isToCatchExceptions, PsiMethod method) {
     super(element);
+    final GroovyResolveResult resolveResult = resolveMethod(element);
+    if (resolveResult == null || resolveResult.getElement() == null) {
+      mySubstitutor = PsiSubstitutor.EMPTY;
+    }
+    else {
+      mySubstitutor = resolveResult.getSubstitutor();
+    }
+    GrClosureSignature signature = GrClosureSignatureUtil.createSignature(method, mySubstitutor);
     myToChangeArguments = isToChangeArguments;
     myToCatchExceptions = isToCatchExceptions;
-    final GroovyResolveResult resolveResult = resolveMethod(element);
-    myReferencedMethod = (PsiMethod)resolveResult.getElement();
-    mySubstitutor = resolveResult.getSubstitutor();
     final GrArgumentList list = PsiUtil.getArgumentsList(element);
     if (list == null) {
       myMapToArguments = GrClosureSignatureUtil.ArgInfo.EMPTY_ARRAY;
     }
     else {
-      final GrClosureSignature signature = GrClosureSignatureUtil.createSignature(myReferencedMethod, mySubstitutor);
       myMapToArguments =
-        GrClosureSignatureUtil.mapParametersToArguments(signature, list, element.getManager(), myReferencedMethod.getResolveScope());
+        GrClosureSignatureUtil.mapParametersToArguments(signature, list, element.getManager(), GlobalSearchScope.allScope(getProject()));
     }
   }
 
   @Nullable
-  private static GroovyResolveResult resolveMethod(final PsiElement ref) {
+  public static GroovyResolveResult resolveMethod(final PsiElement ref) {
     if (ref instanceof GrEnumConstant) return ((GrEnumConstant)ref).resolveConstructorGenerics();
     PsiElement parent = ref.getParent();
     if (parent instanceof GrCallExpression) {
-      return ((GrCallExpression)parent).getMethodVariants()[0];
+      final GroovyResolveResult[] variants = ((GrCallExpression)parent).getMethodVariants();
+      return variants.length == 1 ? variants[0] : null;
     }
     else if (parent instanceof GrApplicationStatement) {
       final GrExpression expression = ((GrApplicationStatement)parent).getFunExpression();
@@ -88,9 +94,6 @@ public class GrMethodCallUsageInfo extends UsageInfo {
     return null;
   }
 
-  public PsiMethod getReferencedMethod() {
-    return myReferencedMethod;
-  }
 
   public GrClosureSignatureUtil.ArgInfo[] getMapToArguments() {
     return myMapToArguments;
@@ -99,4 +102,13 @@ public class GrMethodCallUsageInfo extends UsageInfo {
   public PsiSubstitutor getSubstitutor() {
     return mySubstitutor;
   }
+
+  public boolean isPossibleUsage() {
+    final GroovyResolveResult resolveResult = resolveMethod(getElement());
+    return resolveResult == null || resolveResult.getElement() == null;
+  }
+
+  public boolean isCorrect() {
+    return myMapToArguments != null;
+  }
 }
index d47669e10e5a01bcafced7ca5712ae4199c46858..474f03f2e63e974faa32cf69cd0228bafc0cc899 100644 (file)
@@ -1,14 +1,14 @@
 class List<T> {}
 
 class Base<T> {
-  void fo<caret>o(String s, List<T>... l) {}
+  def fo<caret>o(String s, List<T>... l) {}
 }
 
 class Inheritor extends Base<Integer> {
-  void foo(String s, List<Integer>... l) {}
+  def foo(String s, List<Integer>... l) {}
 
   {
-    new Inheritor().foo("a", new ArrayList<Integer>());
+    new Inheritor().foo("a", new List<Integer>());
   }
 }
 
index be83d989534c72ac1203ddf9afc9b60235496fee..dcd4a35fed33f8739d325d5841ab97fccea7c849 100644 (file)
@@ -1,11 +1,11 @@
 class List<T> {}
 
 class Base<T> {
-  void foo(List<T>[] l, String s) {}
+  def foo(List<T>[] l, String s) {}
 }
 
 class Inheritor extends Base<Integer> {
-  void foo(List<Integer>[] l, String s) {}
+  def foo(List<Integer>[] l, String s) {}
 
   {
     new Inheritor().foo([new List<Integer>()] as List<Integer>[], "a");