ae13e0c2725862261103fd70fcf81061871bff9f
[idea/community.git] / java / java-tests / testSrc / com / intellij / java / execution / ConfigurationRefactoringsTest.java
1 /*
2  * Copyright 2000-2017 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
3  */
4 package com.intellij.java.execution;
5
6 import com.intellij.execution.RunManager;
7 import com.intellij.execution.application.ApplicationConfiguration;
8 import com.intellij.execution.configurations.RunConfiguration;
9 import com.intellij.execution.configurations.RuntimeConfigurationException;
10 import com.intellij.execution.impl.RunManagerImpl;
11 import com.intellij.execution.impl.RunnerAndConfigurationSettingsImpl;
12 import com.intellij.execution.junit.AllInPackageConfigurationProducer;
13 import com.intellij.execution.junit.JUnitConfiguration;
14 import com.intellij.execution.junit.JUnitConfigurationType;
15 import com.intellij.execution.testframework.AbstractJavaTestConfigurationProducer;
16 import com.intellij.openapi.vfs.VirtualFile;
17 import com.intellij.psi.*;
18 import com.intellij.refactoring.PackageWrapper;
19 import com.intellij.refactoring.move.moveClassesOrPackages.MoveClassesOrPackagesProcessor;
20 import com.intellij.refactoring.move.moveClassesOrPackages.SingleSourceRootMoveDestination;
21 import com.intellij.refactoring.move.moveMembers.MockMoveMembersOptions;
22 import com.intellij.refactoring.move.moveMembers.MoveMembersProcessor;
23 import com.intellij.refactoring.rename.RenameProcessor;
24 import com.intellij.testFramework.MapDataContext;
25 import java.util.HashSet;
26 import org.jetbrains.annotations.NotNull;
27
28 import java.io.IOException;
29
30 public class ConfigurationRefactoringsTest extends BaseConfigurationTestCase {
31   private static final String APPLICATION_CODE = "public class Application {" +
32                                                  "  public static void main(String[] args) {\n" +
33                                                  "  }" +
34                                                  "}";
35   private static final String TEST_CODE = "import junit.framework.TestCase;" +
36                                           "public class ATest extends TestCase {" +
37                                           "public void test() {}" +
38                                           "private void otherMethod() {}" +
39                                           "}";
40   private TestSources mySource;
41   private static final String NOT_A_TEST = "public class NotATest {" +
42                                            "public void test() {}" +
43                                            "}";
44   public void testRenameApplication() throws IOException {
45     PsiClass psiClass = mySource.createClass("Application", APPLICATION_CODE);
46     assertNotNull(psiClass);
47     ApplicationConfiguration configuration = createConfiguration(psiClass);
48     assertNotNull(configuration);
49     rename(psiClass, "NewName");
50     try {
51       configuration.checkConfiguration();
52     }
53     catch (RuntimeConfigurationException e) {
54       fail("Unexpected ConfigurationException: " + e);
55     }
56     assertEquals("NewName", configuration.getMainClassName());
57   }
58
59   public void testMoveApplication() throws IOException {
60     PsiClass psiClass = mySource.createClass("Application", APPLICATION_CODE);
61     assertNotNull(psiClass);
62     ApplicationConfiguration configuration = createConfiguration(psiClass);
63     move(psiClass, "pkg");
64     try {
65       configuration.checkConfiguration();
66     }
67     catch (RuntimeConfigurationException e) {
68       fail("Unexpected ConfigurationException: " + e);
69     }
70
71     assertEquals("pkg.Application", configuration.getMainClassName());
72     rename(JavaPsiFacade.getInstance(myProject).findPackage("pkg"), "pkg2");
73     assertEquals("pkg2.Application", configuration.getMainClassName());
74   }
75
76   public void testRenameJUnitPackage() {
77     PsiPackage psiPackage = mySource.createPackage("pkg");
78     JUnitConfiguration configuration = createJUnitConfiguration(psiPackage, AllInPackageConfigurationProducer.class, new MapDataContext());
79     rename(psiPackage, "pkg2");
80     checkPackage("pkg2", configuration);
81     PsiPackage outer = mySource.createPackage("outerPkg");
82     move(JavaPsiFacade.getInstance(myProject).findPackage("pkg2"), outer.getQualifiedName());
83     checkPackage("outerPkg.pkg2", configuration);
84     rename(outer, "outer2");
85     checkPackage("outer2.pkg2", configuration);
86   }
87
88   public void testRenameJUnitContainingPackage() throws IOException {
89     PsiClass psiClass = mySource.createClass("ATest", TEST_CODE);
90     assertNotNull(psiClass);
91     JUnitConfiguration configuration = createConfiguration(psiClass);
92     PsiPackage psiPackage = mySource.createPackage("pkg");
93     move(psiClass, "pkg");
94     checkClassName("pkg.ATest", configuration);
95     rename(psiPackage, "newPkg");
96     checkClassName("newPkg.ATest", configuration);
97     psiPackage = mySource.findPackage("newPkg");
98
99     mySource.createPackage("pkg2");
100     move(psiPackage, "pkg2");
101     checkClassName("pkg2.newPkg.ATest", configuration);
102   }
103
104   public void testRefactorTestMethod() throws IOException {
105     PsiClass psiClass = mySource.createClass("ATest", TEST_CODE);
106     assertNotNull(psiClass);
107     PsiMethod testMethod = psiClass.findMethodsByName("test", false)[0];
108     JUnitConfiguration configuration = createConfiguration(testMethod);
109     rename(testMethod, "test1");
110     checkMethodName("test1", configuration);
111     checkClassName("ATest", configuration);
112     assertEquals("ATest.test1", configuration.getName());
113     move(psiClass, "pkg");
114     checkClassName("pkg.ATest", configuration);
115     psiClass = configuration.getConfigurationModule().findClass(configuration.getPersistentData().getMainClassName());
116     rename(psiClass, "TestClassName");
117     assertEquals("TestClassName.test1", configuration.getName());
118     psiClass = configuration.getConfigurationModule().findClass(configuration.getPersistentData().getMainClassName());
119
120     PsiClass otherTest = mySource.createClass("ATest", TEST_CODE);
121     HashSet<PsiMember> members = new HashSet<>();
122     assertNotNull(psiClass);
123     members.add(psiClass.findMethodsByName("test1", false)[0]);
124     moveMembers(otherTest, members);
125     psiClass = configuration.getConfigurationModule().findClass(configuration.getPersistentData().getMainClassName());
126     checkMethodName("test1", configuration);
127     checkClassName("ATest", configuration);
128     assertEquals("ATest.test1", configuration.getName());
129
130     assertNotNull(psiClass);
131     PsiMethod otherMethod = psiClass.findMethodsByName("otherMethod", false)[0];
132     rename(otherMethod, "newName");
133     checkMethodName("test1", configuration);
134   }
135
136   public void testRenameBadTestClass() throws IOException {
137     PsiClass psiClass = mySource.createClass("NotATest", NOT_A_TEST);
138     assertNotNull(psiClass);
139     JUnitConfigurationType instance = JUnitConfigurationType.getInstance();
140     assertNotNull(instance);
141     JUnitConfiguration configuration = new JUnitConfiguration("notATest", myProject, instance.getConfigurationFactories()[0]);
142     configuration.setMainClass(psiClass);
143     configuration.setModule(configuration.getValidModules().iterator().next());
144
145     checkConfigurationException("NotATest isn't test class", configuration);
146
147     RunManagerImpl runManager = (RunManagerImpl)RunManager.getInstance(myProject);
148     runManager.setTemporaryConfiguration(new RunnerAndConfigurationSettingsImpl(runManager, configuration, false));
149     rename(psiClass, "NotATest2");
150     JUnitConfiguration.Data data = configuration.getPersistentData();
151     assertEquals("NotATest2", data.getMainClassName());
152
153     data.METHOD_NAME = "test";
154     data.TEST_OBJECT = JUnitConfiguration.TEST_METHOD;
155     checkConfigurationException("Test method 'test' doesn't exist", configuration);
156     rename(psiClass.findMethodsByName("test", false)[0], "test2");
157     assertEquals("NotATest2", data.getMainClassName());
158     assertEquals("test2", data.getMethodName());
159   }
160
161   private static void checkConfigurationException(String expectedExceptionMessage, JUnitConfiguration configuration) {
162     try {
163       configuration.checkConfiguration();
164     }
165     catch (RuntimeConfigurationException e) {
166       assertEquals(expectedExceptionMessage, e.getLocalizedMessage());
167       return;
168     }
169     fail("ConfigurationException expected");
170   }
171
172   public void testRefactorOtherClass() throws IOException {
173     PsiClass psiClass = mySource.createClass("ATest", TEST_CODE);
174     assertNotNull(psiClass);
175     JUnitConfiguration configuration = createConfiguration(psiClass);
176
177     psiClass = mySource.createClass("Application", APPLICATION_CODE);
178     assertNotNull(psiClass);
179     rename(psiClass, "NewName");
180     checkClassName("ATest", configuration);
181     mySource.createPackage("pkg");
182
183     psiClass = mySource.findClass("NewName");
184     assertNotNull(psiClass);
185     move(psiClass, "pkg");
186     checkClassName("ATest", configuration);
187   }
188
189   private void moveMembers(final PsiClass otherTest, final HashSet<PsiMember> members) {
190     MockMoveMembersOptions options = new MockMoveMembersOptions(otherTest.getQualifiedName(), members);
191     new MoveMembersProcessor(myProject, null, options).run();
192   }
193
194   private void initModule() {
195     mySource.initModule();
196     mySource.copyJdkFrom(myModule);
197     mySource.addLibrary(findFile(MOCK_JUNIT));
198   }
199
200   private void move(final PsiElement psiElement, String packageName) {
201     VirtualFile pkgFile = mySource.createPackageDir(packageName);
202     final PsiDirectory toDir = PsiManager.getInstance(myProject).findDirectory(pkgFile);
203     assertNotNull(toDir);
204     PackageWrapper wrapper = PackageWrapper.create(JavaDirectoryService.getInstance().getPackage(toDir));
205     new MoveClassesOrPackagesProcessor(myProject, new PsiElement[]{psiElement},
206                                        new SingleSourceRootMoveDestination(wrapper, toDir),
207                                        false, false, null).run();
208   }
209
210   private void rename(final PsiElement psiElement, final String newName) {
211     new RenameProcessor(myProject, psiElement, newName, false, false).run();
212   }
213
214   @Override
215   protected void setUp() throws Exception {
216     super.setUp();
217
218     mySource = new TestSources(myProject, myFilesToDelete);
219     initModule();
220   }
221
222   @Override
223   protected void tearDown() throws Exception {
224     try {
225       mySource.tearDown();
226       mySource = null;
227     }
228     finally {
229       super.tearDown();
230     }
231   }
232
233   @Override
234   protected <T extends RunConfiguration> T createConfiguration(@NotNull PsiElement psiClass, @NotNull MapDataContext dataContext) {
235     T configuration = super.createConfiguration(psiClass, dataContext);
236     RunManagerImpl manager = (RunManagerImpl)RunManager.getInstance(myProject);
237     manager.setTemporaryConfiguration(new RunnerAndConfigurationSettingsImpl(manager, configuration, false));
238     return configuration;
239   }
240
241   @Override
242   protected JUnitConfiguration createJUnitConfiguration(@NotNull PsiElement psiElement,
243                                                         @NotNull Class<? extends AbstractJavaTestConfigurationProducer> producerClass,
244                                                         @NotNull MapDataContext dataContext) {
245     final JUnitConfiguration configuration = super.createJUnitConfiguration(psiElement, producerClass, dataContext);
246     RunManagerImpl manager = (RunManagerImpl)RunManager.getInstance(myProject);
247     manager.setTemporaryConfiguration(new RunnerAndConfigurationSettingsImpl(manager, configuration));
248     return configuration;
249   }
250 }