undo and rename/move class used in run configuration (IDEA-36423)

This commit is contained in:
anna
2011-03-30 14:01:35 +02:00
parent 676f00561e
commit 2946bdfeb3
32 changed files with 203 additions and 51 deletions

View File

@@ -24,6 +24,7 @@ import com.intellij.psi.search.GlobalSearchScope;
import com.intellij.psi.util.PsiTreeUtil;
import com.intellij.refactoring.listeners.RefactoringElementAdapter;
import com.intellij.refactoring.listeners.RefactoringElementListener;
import com.intellij.refactoring.listeners.UndoRefactoringElementListener;
import org.jetbrains.annotations.NotNull;
public class RefactoringListeners {
@@ -86,7 +87,8 @@ public class RefactoringListeners {
}
}
private static abstract class RenameElement<T extends PsiElement> extends RefactoringElementAdapter {
private static abstract class RenameElement<T extends PsiElement> extends RefactoringElementAdapter
implements UndoRefactoringElementListener{
private final Accessor<T> myAccessor;
private final String myPath;
@@ -113,6 +115,11 @@ public class RefactoringListeners {
protected abstract T findNewElement(T newParent, String qualifiedName);
protected abstract String getQualifiedName(T element);
@Override
public void undoElementMovedOrRenamed(@NotNull PsiElement newElement, @NotNull String oldQualifiedName) {
myAccessor.setName(oldQualifiedName);
}
}
private static class RefactorPackage extends RenameElement<PsiPackage> {

View File

@@ -1,6 +1,6 @@
public enum UserFlags {
Root("Has super administrative powers" ),
Blacklisted("Probably a spammer" );
Root("Has super administrative powers"),
Blacklisted("Probably a spammer");
public final String description;
public final int mask;

View File

@@ -1 +1 @@
class C<TC> extends A<TC>{}
class C<TC> extends A<TC> {}

View File

@@ -1,5 +1,5 @@
class Super {
void foo() {
}
}
}

View File

@@ -3,7 +3,7 @@ public class Super {
}
class Child extends Super {
}
}
class ChildChild extends Child {
}
}

View File

@@ -1,5 +1,5 @@
public class C2 extends C1 {
public void f(int a1) {
super.f(a1 );
super.f(a1);
}
}

View File

@@ -3,7 +3,7 @@ public class A {
bar();
}
}
}
class B extends A {
}
}

View File

@@ -1,5 +1,5 @@
public class C2 extends C1 {
public void f(int a1) {
super.f(a1 );
super.f(a1);
}
}

View File

@@ -21,7 +21,7 @@ import org.jetbrains.annotations.NotNull;
/**
* @author yole
*/
public abstract class RefactoringElementAdapter implements RefactoringElementListener {
public abstract class RefactoringElementAdapter implements RefactoringElementListener, UndoRefactoringElementListener {
@Override
public final void elementMoved(@NotNull PsiElement newElement) {
elementRenamedOrMoved(newElement);

View File

@@ -21,7 +21,7 @@ import org.jetbrains.annotations.NotNull;
import java.util.ArrayList;
public class RefactoringElementListenerComposite implements RefactoringElementListener {
public class RefactoringElementListenerComposite implements RefactoringElementListener, UndoRefactoringElementListener {
private final ArrayList<RefactoringElementListener> myListeners = new ArrayList<RefactoringElementListener>();
public void addListener(final RefactoringElementListener listener){
@@ -39,4 +39,13 @@ public class RefactoringElementListenerComposite implements RefactoringElementLi
myListener.elementRenamed(newElement);
}
}
@Override
public void undoElementMovedOrRenamed(@NotNull PsiElement newElement, @NotNull String oldQualifiedName) {
for (RefactoringElementListener listener : myListeners) {
if (listener instanceof UndoRefactoringElementListener) {
((UndoRefactoringElementListener)listener).undoElementMovedOrRenamed(newElement, oldQualifiedName);
}
}
}
}

View File

@@ -0,0 +1,27 @@
/*
* Copyright 2000-2011 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.listeners;
import com.intellij.psi.PsiElement;
import org.jetbrains.annotations.NotNull;
/**
* {@linkplain com.intellij.refactoring.listeners.RefactoringElementListenerProvider} receives a notification on undo.
* @author dsl
*/
public interface UndoRefactoringElementListener {
void undoElementMovedOrRenamed(@NotNull PsiElement newElement, @NotNull String oldQualifiedName);
}

View File

@@ -96,6 +96,22 @@ public class RefactoringScopeElementListenerProvider implements RefactoringEleme
catch (ParsingException ignore) {
}
}
@Override
public void undoElementMovedOrRenamed(@NotNull PsiElement newElement, @NotNull String oldQualifiedName) {
LOG.assertTrue(newElement instanceof PsiQualifiedNamedElement);
try {
final NamedScope[] currentScopes = descriptor.getHolder().getEditableScopes();
final String oldPattern = ((PatternBasedPackageSet)currentScopes[descriptor.getIdx()].getValue()).getPattern()
.replace(((PsiQualifiedNamedElement)newElement).getQualifiedName(), oldQualifiedName);
final PackageSet newSet = PackageSetFactory.getInstance().compile(oldPattern);
NamedScope newScope = new NamedScope(descriptor.getScope().getName(), newSet);
currentScopes[descriptor.getIdx()] = newScope;
descriptor.getHolder().setScopes(currentScopes);
}
catch (ParsingException ignore) {
}
}
});
}
return composite;

View File

@@ -23,8 +23,10 @@ import com.intellij.ide.DataManager;
import com.intellij.lang.Language;
import com.intellij.openapi.actionSystem.PlatformDataKeys;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.application.Result;
import com.intellij.openapi.command.CommandProcessor;
import com.intellij.openapi.command.UndoConfirmationPolicy;
import com.intellij.openapi.command.WriteCommandAction;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.extensions.Extensions;
import com.intellij.openapi.progress.ProcessCanceledException;
@@ -483,8 +485,9 @@ public abstract class BaseRefactoringProcessor {
UsageViewDescriptor descriptor = createUsageViewDescriptor(usages);
if (!ensureElementsWritable(usages, descriptor)) return;
ApplicationManager.getApplication().runWriteAction(new Runnable() {
public void run() {
new WriteCommandAction(myProject){
@Override
protected void run(Result result) throws Throwable {
RefactoringListenerManagerImpl listenerManager = (RefactoringListenerManagerImpl)RefactoringListenerManager.getInstance(myProject);
myTransaction = listenerManager.startTransaction();
Map<RefactoringHelper, Object> preparedData = new HashMap<RefactoringHelper, Object>();
@@ -499,7 +502,7 @@ public abstract class BaseRefactoringProcessor {
myTransaction.commit();
performPsiSpoilingRefactoring();
}
});
}.execute();
}
public static class ConflictsInTestsException extends RuntimeException {

View File

@@ -15,16 +15,25 @@
*/
package com.intellij.refactoring.changeSignature;
import com.intellij.ide.actions.CopyReferenceAction;
import com.intellij.openapi.command.CommandProcessor;
import com.intellij.openapi.command.undo.BasicUndoableAction;
import com.intellij.openapi.command.undo.UndoManager;
import com.intellij.openapi.command.undo.UndoableAction;
import com.intellij.openapi.command.undo.UnexpectedUndoException;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.project.Project;
import com.intellij.psi.PsiElement;
import com.intellij.psi.PsiManager;
import com.intellij.refactoring.BaseRefactoringProcessor;
import com.intellij.refactoring.RefactoringBundle;
import com.intellij.refactoring.listeners.RefactoringElementAdapter;
import com.intellij.refactoring.listeners.RefactoringElementListener;
import com.intellij.refactoring.listeners.UndoRefactoringElementListener;
import com.intellij.refactoring.util.MoveRenameUsageInfo;
import com.intellij.usageView.UsageInfo;
import com.intellij.usageView.UsageViewUtil;
import com.intellij.util.CommonProcessors;
import com.intellij.util.IncorrectOperationException;
import com.intellij.util.containers.ContainerUtil;
import com.intellij.util.containers.hash.HashMap;
@@ -105,6 +114,21 @@ public abstract class ChangeSignatureProcessorBase extends BaseRefactoringProces
protected void performRefactoring(UsageInfo[] usages) {
final RefactoringElementListener elementListener = getTransaction().getElementListener(myChangeInfo.getMethod());
final String fqn = CopyReferenceAction.elementToFqn(myChangeInfo.getMethod());
if (fqn != null) {
UndoableAction action = new BasicUndoableAction() {
public void undo() throws UnexpectedUndoException {
if (elementListener instanceof UndoRefactoringElementListener) {
((UndoRefactoringElementListener)elementListener).undoElementMovedOrRenamed(myChangeInfo.getMethod(), fqn);
}
}
@Override
public void redo() throws UnexpectedUndoException {
}
};
UndoManager.getInstance(myProject).undoableActionPerformed(action);
}
try {
final ChangeSignatureUsageProcessor[] processors = ChangeSignatureUsageProcessor.EP_NAME.getExtensions();

View File

@@ -19,6 +19,7 @@ package com.intellij.refactoring.listeners.impl.impl;
import com.intellij.psi.PsiElement;
import com.intellij.refactoring.listeners.RefactoringElementListener;
import com.intellij.refactoring.listeners.RefactoringElementListenerProvider;
import com.intellij.refactoring.listeners.UndoRefactoringElementListener;
import com.intellij.refactoring.listeners.impl.RefactoringTransaction;
import com.intellij.util.containers.HashMap;
import com.intellij.openapi.diagnostic.Logger;
@@ -74,7 +75,7 @@ public class RefactoringTransactionImpl implements RefactoringTransaction {
return listener;
}
private class MyRefactoringElementListener implements RefactoringElementListener {
private class MyRefactoringElementListener implements RefactoringElementListener, UndoRefactoringElementListener {
private final ArrayList<RefactoringElementListener> myListenerList;
private MyRefactoringElementListener(PsiElement oldElement) {
addAffectedElement(oldElement);
@@ -110,6 +111,15 @@ public class RefactoringTransactionImpl implements RefactoringTransaction {
}
});
}
@Override
public void undoElementMovedOrRenamed(@NotNull PsiElement newElement, @NotNull String oldQualifiedName) {
for (RefactoringElementListener listener : myListenerList) {
if (listener instanceof UndoRefactoringElementListener) {
((UndoRefactoringElementListener)listener).undoElementMovedOrRenamed(newElement, oldQualifiedName);
}
}
}
}
public void commit() {

View File

@@ -17,9 +17,14 @@
package com.intellij.refactoring.rename;
import com.intellij.codeInsight.CodeInsightUtilBase;
import com.intellij.ide.actions.CopyReferenceAction;
import com.intellij.lang.Language;
import com.intellij.lang.LanguageNamesValidation;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.command.undo.BasicUndoableAction;
import com.intellij.openapi.command.undo.UndoManager;
import com.intellij.openapi.command.undo.UndoableAction;
import com.intellij.openapi.command.undo.UnexpectedUndoException;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.editor.Document;
import com.intellij.openapi.project.Project;
@@ -36,6 +41,7 @@ import com.intellij.psi.meta.PsiWritableMetaData;
import com.intellij.psi.search.GlobalSearchScope;
import com.intellij.refactoring.RefactoringBundle;
import com.intellij.refactoring.listeners.RefactoringElementListener;
import com.intellij.refactoring.listeners.UndoRefactoringElementListener;
import com.intellij.refactoring.util.*;
import com.intellij.usageView.UsageInfo;
import com.intellij.util.IncorrectOperationException;
@@ -166,8 +172,23 @@ public class RenameUtil {
}
public static void doRename(final PsiElement element, String newName, UsageInfo[] usages, final Project project,
RefactoringElementListener listener) {
final RefactoringElementListener listener) {
final RenamePsiElementProcessor processor = RenamePsiElementProcessor.forElement(element);
final String fqn = element instanceof PsiFile ? ((PsiFile)element).getVirtualFile().getPath() : CopyReferenceAction.elementToFqn(element);
if (fqn != null) {
UndoableAction action = new BasicUndoableAction() {
public void undo() throws UnexpectedUndoException {
if (listener instanceof UndoRefactoringElementListener) {
((UndoRefactoringElementListener)listener).undoElementMovedOrRenamed(element, fqn);
}
}
@Override
public void redo() throws UnexpectedUndoException {
}
};
UndoManager.getInstance(project).undoableActionPerformed(action);
}
try {
processor.renameElement(element, newName, usages, listener);
}

View File

@@ -119,6 +119,11 @@ public class AndroidRunConfiguration extends AndroidRunConfigurationBase impleme
public void elementRenamedOrMoved(@NotNull PsiElement newElement) {
ACTIVITY_CLASS = ((PsiClass)newElement).getQualifiedName();
}
@Override
public void undoElementMovedOrRenamed(@NotNull PsiElement newElement, @NotNull String oldQualifiedName) {
ACTIVITY_CLASS = oldQualifiedName;
}
};
}
return null;

View File

@@ -1,6 +1,7 @@
enum E{
x(2), y(2)
def E(int a) {
def E(int a) {
}
}

View File

@@ -1,12 +1,12 @@
def foo(String s) throws IOException{
def foo(String s) throws IOException {
}
def bar() {
try{
foo("")
}catch(IOException e){
e.printStackTrace()
}
try {
foo("")
} catch (IOException e) {
e.printStackTrace()
}
}

View File

@@ -1,9 +1,9 @@
def foo(String s) throws IOException{}
def foo(String s) throws IOException {}
new Object().each {
try{
foo("")
}catch(IOException e){
e.printStackTrace()
}
try {
foo("")
} catch (IOException e) {
e.printStackTrace()
}
}

View File

@@ -7,7 +7,7 @@ class Foo {
this(s, 5);
}
def Foo() {
def Foo() {
this("a")
print new Foo("b");

View File

@@ -7,7 +7,7 @@ class X {
return foo(s, 2);
}
def main() {
def main() {
foo("a")
}
}

View File

@@ -1,4 +1,6 @@
class Z extends Foo {
Z() {
super(5);}}
Z() {
super(5);
}
}

View File

@@ -1,5 +1,6 @@
class Z extends Foo{
Z(){
super(5);}
super(5);
}
}

View File

@@ -1,5 +1,5 @@
class Foo {
public static void main(String[] args) {
new MoveVarArgParameters().foo(new String[]{"b","c"},"a" )
new MoveVarArgParameters().foo(new String[]{"b", "c"}, "a")
}
}

View File

@@ -1,6 +1,6 @@
def test=new Test()
try{
test.foo()
}catch(Exception e){
e.printStackTrace()
try {
test.foo()
} catch (Exception e) {
e.printStackTrace()
}

View File

@@ -1,6 +1,6 @@
class A extends C {
def A(int k) {
super(27)
int b = k;
super(27)
int b = k;
}
}

View File

@@ -28,6 +28,7 @@ import com.intellij.psi.PsiPackage;
import com.intellij.psi.search.GlobalSearchScope;
import com.intellij.refactoring.listeners.RefactoringElementAdapter;
import com.intellij.refactoring.listeners.RefactoringElementListener;
import com.intellij.refactoring.listeners.UndoRefactoringElementListener;
import com.intellij.rt.execution.junit.JUnitStarter;
import org.jetbrains.annotations.NotNull;
@@ -79,13 +80,23 @@ class TestMethod extends TestObject {
final PsiMethod method = (PsiMethod)element;
if (!method.getName().equals(configuration.getPersistentData().getMethodName())) return null;
if (!method.getContainingClass().equals(configuration.myClass.getPsiElement())) return null;
return new RefactoringElementAdapter() {
class Listener extends RefactoringElementAdapter implements UndoRefactoringElementListener {
public void elementRenamedOrMoved(@NotNull final PsiElement newElement) {
final boolean generatedName = configuration.isGeneratedName();
configuration.getPersistentData().setTestMethod(PsiLocation.fromPsiElement((PsiMethod)newElement));
if (generatedName) configuration.setGeneratedName();
}
};
@Override
public void undoElementMovedOrRenamed(@NotNull PsiElement newElement, @NotNull String oldQualifiedName) {
final int methodIdx = oldQualifiedName.indexOf("#") + 1;
if (methodIdx <= 0 || methodIdx >= oldQualifiedName.length()) return;
final boolean generatedName = configuration.isGeneratedName();
configuration.getPersistentData().METHOD_NAME = oldQualifiedName.substring(methodIdx);
if (generatedName) configuration.setGeneratedName();
}
}
return new Listener();
}
else {
return RefactoringListeners.getClassOrPackageListener(element, configuration.myClass);

View File

@@ -41,6 +41,7 @@ import com.intellij.psi.*;
import com.intellij.psi.search.GlobalSearchScope;
import com.intellij.refactoring.listeners.RefactoringElementAdapter;
import com.intellij.refactoring.listeners.RefactoringElementListener;
import com.intellij.refactoring.listeners.UndoRefactoringElementListener;
import com.theoryinpractice.testng.model.TestData;
import com.theoryinpractice.testng.model.TestType;
import org.jdom.Element;
@@ -396,14 +397,23 @@ public class TestNGConfiguration extends ModuleBasedConfiguration<JavaRunConfigu
final PsiMethod method = (PsiMethod)element;
if (!method.getName().equals(data.getMethodName())) return null;
if (!method.getContainingClass().equals(myClass.getPsiElement())) return null;
final RefactoringElementListener listener = new RefactoringElementAdapter() {
class Listener extends RefactoringElementAdapter implements UndoRefactoringElementListener {
public void elementRenamedOrMoved(@NotNull final PsiElement newElement) {
final boolean generatedName = isGeneratedName();
data.setTestMethod(PsiLocation.fromPsiElement((PsiMethod)newElement));
if (generatedName) setGeneratedName();
}
};
return RunConfigurationExtension.wrapRefactoringElementListener(element, this, listener);
@Override
public void undoElementMovedOrRenamed(@NotNull PsiElement newElement, @NotNull String oldQualifiedName) {
final int methodIdx = oldQualifiedName.indexOf("#") + 1;
if (methodIdx <= 0 || methodIdx >= oldQualifiedName.length()) return;
final boolean generatedName = isGeneratedName();
data.METHOD_NAME = oldQualifiedName.substring(methodIdx);
if (generatedName) setGeneratedName();
}
}
return RunConfigurationExtension.wrapRefactoringElementListener(element, this, new Listener());
}
return null;
}

View File

@@ -64,5 +64,11 @@ public class PaletteRefactoringListenerProvider implements RefactoringElementLis
myUiDesignerPaletteProvider.fireGroupsChanged();
}
}
@Override
public void undoElementMovedOrRenamed(@NotNull PsiElement newElement, @NotNull String oldQualifiedName) {
myItem.setClassName(oldQualifiedName);
myUiDesignerPaletteProvider.fireGroupsChanged();
}
}
}