mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
Merge remote-tracking branch 'origin/master'
This commit is contained in:
@@ -27,7 +27,7 @@ import com.intellij.refactoring.rename.PsiElementRenameHandler;
|
||||
* @author ven
|
||||
*/
|
||||
public class RenameFileAction extends AnAction implements DumbAware {
|
||||
public static final String RENAME_FILE = "Rename File";
|
||||
public static final String RENAME_FILE = "Rename File...";
|
||||
|
||||
public void actionPerformed(final AnActionEvent e) {
|
||||
final PsiFile file = e.getData(LangDataKeys.PSI_FILE);
|
||||
@@ -47,7 +47,7 @@ public class RenameFileAction extends AnAction implements DumbAware {
|
||||
presentation.setVisible(enabled);
|
||||
if (enabled) {
|
||||
presentation.setText(RENAME_FILE);
|
||||
presentation.setDescription(RENAME_FILE);
|
||||
presentation.setDescription("Rename selected file");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
package org.jetbrains.ether;
|
||||
|
||||
import com.intellij.openapi.application.PathManager;
|
||||
import com.intellij.openapi.application.ex.PathManagerEx;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.util.SystemInfo;
|
||||
@@ -31,7 +30,6 @@ import org.jetbrains.jps.Sdk;
|
||||
import org.jetbrains.jps.api.CanceledStatus;
|
||||
import org.jetbrains.jps.idea.IdeaProjectLoader;
|
||||
import org.jetbrains.jps.incremental.*;
|
||||
import org.jetbrains.jps.incremental.java.JavaBuilder;
|
||||
import org.jetbrains.jps.incremental.storage.BuildDataManager;
|
||||
import org.jetbrains.jps.incremental.storage.ProjectTimestamps;
|
||||
import org.jetbrains.jps.server.ClasspathBootstrap;
|
||||
@@ -154,8 +152,12 @@ public abstract class IncrementalTestCase extends TestCase {
|
||||
|
||||
@Override
|
||||
protected void tearDown() throws Exception {
|
||||
super.tearDown();
|
||||
delete(new File(workDir));
|
||||
try {
|
||||
super.tearDown();
|
||||
}
|
||||
finally {
|
||||
delete(new File(workDir));
|
||||
}
|
||||
}
|
||||
|
||||
private String getProjectName() {
|
||||
@@ -199,7 +201,7 @@ public abstract class IncrementalTestCase extends TestCase {
|
||||
|
||||
if (files != null) {
|
||||
for (File f : files) {
|
||||
copy(f, new File(output.getPath() + File.separator + f.getName()));
|
||||
copy(f, new File(output.getPath(), f.getName()));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -208,16 +210,26 @@ public abstract class IncrementalTestCase extends TestCase {
|
||||
}
|
||||
}
|
||||
else if (input.isFile()) {
|
||||
final FileReader in = new FileReader(input);
|
||||
final FileWriter out = new FileWriter(output);
|
||||
FileReader in = null;
|
||||
FileWriter out = null;
|
||||
|
||||
try {
|
||||
in = new FileReader(input);
|
||||
out = new FileWriter(output);
|
||||
int c;
|
||||
while ((c = in.read()) != -1) out.write(c);
|
||||
}
|
||||
finally {
|
||||
in.close();
|
||||
out.close();
|
||||
try {
|
||||
if (in != null) {
|
||||
in.close();
|
||||
}
|
||||
}
|
||||
finally {
|
||||
if (out != null) {
|
||||
out.close();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -241,7 +253,7 @@ public abstract class IncrementalTestCase extends TestCase {
|
||||
final String basename = pathSep == -1 ? postfix : postfix.substring(pathSep + 1);
|
||||
final String path =
|
||||
getWorkDir() + File.separator + (pathSep == -1 ? "src" : postfix.substring(0, pathSep).replace('-', File.separatorChar));
|
||||
final File output = new File(path + File.separator + basename);
|
||||
final File output = new File(path, basename);
|
||||
|
||||
if (copy) {
|
||||
copy(input, output);
|
||||
@@ -275,7 +287,7 @@ public abstract class IncrementalTestCase extends TestCase {
|
||||
|
||||
final Sdk jdk = project.createSdk("JavaSDK", "IDEA jdk", System.getProperty("java.home"), null);
|
||||
final List<String> paths = new LinkedList<String>();
|
||||
|
||||
|
||||
paths.add(FileUtil.toSystemIndependentName(ClasspathBootstrap.getResourcePath(Object.class).getCanonicalPath()));
|
||||
|
||||
jdk.setClasspath(paths);
|
||||
@@ -285,20 +297,32 @@ public abstract class IncrementalTestCase extends TestCase {
|
||||
final ProjectDescriptor projectDescriptor =
|
||||
new ProjectDescriptor(projectPath, project, new FSState(true), new ProjectTimestamps(projectName),
|
||||
new BuildDataManager(projectName, true));
|
||||
final IncProjectBuilder builder = new IncProjectBuilder(projectDescriptor, BuilderRegistry.getInstance(), CanceledStatus.NULL);
|
||||
try {
|
||||
|
||||
builder.build(new AllProjectScope(project, true), false, true);
|
||||
new IncProjectBuilder(
|
||||
projectDescriptor, BuilderRegistry.getInstance(), CanceledStatus.NULL
|
||||
).build(
|
||||
new AllProjectScope(project, true), false, true
|
||||
);
|
||||
|
||||
modify();
|
||||
modify();
|
||||
|
||||
if (SystemInfo.isUnix) {
|
||||
Thread.sleep(1000);
|
||||
if (SystemInfo.isUnix) {
|
||||
Thread.sleep(1000L);
|
||||
}
|
||||
|
||||
new IncProjectBuilder(
|
||||
projectDescriptor, BuilderRegistry.getInstance(), CanceledStatus.NULL
|
||||
).build(
|
||||
new AllProjectScope(project, false), true, false
|
||||
);
|
||||
|
||||
FileAssert.assertEquals(new File(getBaseDir() + ".log"), new File(getWorkDir() + ".log"));
|
||||
}
|
||||
finally {
|
||||
projectDescriptor.release();
|
||||
}
|
||||
|
||||
builder.build(new AllProjectScope(project, false), true, false);
|
||||
|
||||
projectDescriptor.release();
|
||||
|
||||
FileAssert.assertEquals(new File(getBaseDir() + ".log"), new File(getWorkDir() + ".log"));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -25,30 +25,40 @@ import java.util.Map;
|
||||
* @author yole
|
||||
*/
|
||||
public class CoreJarHandler extends JarHandlerBase {
|
||||
private final Map<String, VirtualFile> myFileMap = new HashMap<String, VirtualFile>();
|
||||
|
||||
private final CoreJarFileSystem myFileSystem;
|
||||
private final VirtualFile myRoot;
|
||||
|
||||
public CoreJarHandler(CoreJarFileSystem fileSystem, String path) {
|
||||
super(path);
|
||||
myFileSystem = fileSystem;
|
||||
|
||||
Map<EntryInfo, CoreJarVirtualFile> entries = new HashMap<EntryInfo, CoreJarVirtualFile>();
|
||||
|
||||
for (EntryInfo info : getEntriesMap().values()) {
|
||||
getOrCreateFile(info, entries);
|
||||
}
|
||||
|
||||
myRoot = getOrCreateFile(getEntryInfo(""), entries);
|
||||
}
|
||||
|
||||
private CoreJarVirtualFile getOrCreateFile(EntryInfo info, Map<EntryInfo, CoreJarVirtualFile> entries) {
|
||||
CoreJarVirtualFile answer = entries.get(info);
|
||||
if (answer == null) {
|
||||
EntryInfo parentEntry = info.parent;
|
||||
answer = new CoreJarVirtualFile(this, info, parentEntry != null ? getOrCreateFile(parentEntry, entries) : null);
|
||||
entries.put(info, answer);
|
||||
}
|
||||
|
||||
return answer;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public VirtualFile findFileByPath(String pathInJar) {
|
||||
if (getZip() == null) {
|
||||
return null;
|
||||
}
|
||||
VirtualFile file = myFileMap.get(pathInJar);
|
||||
if (file == null) {
|
||||
if (pathInJar.length() > 0) {
|
||||
EntryInfo entryInfo = getEntryInfo(pathInJar);
|
||||
if (entryInfo == null) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
file = new CoreJarVirtualFile(myFileSystem, this, pathInJar);
|
||||
myFileMap.put(pathInJar, file);
|
||||
}
|
||||
return file;
|
||||
return myRoot != null ? myRoot.findFileByRelativePath(pathInJar) : null;
|
||||
}
|
||||
|
||||
public CoreJarFileSystem getFileSystem() {
|
||||
return myFileSystem;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -23,44 +23,42 @@ import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.OutputStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author yole
|
||||
*/
|
||||
public class CoreJarVirtualFile extends VirtualFile {
|
||||
private final CoreJarFileSystem myFileSystem;
|
||||
private final CoreJarHandler myHandler;
|
||||
private final String myPathInJar;
|
||||
private final VirtualFile myParent;
|
||||
private VirtualFile[] myChildren;
|
||||
private final ArrayList<VirtualFile> myChildren = new ArrayList<VirtualFile>();
|
||||
private final JarHandlerBase.EntryInfo myEntry;
|
||||
|
||||
public CoreJarVirtualFile(CoreJarFileSystem fileSystem, CoreJarHandler handler, String pathInJar) {
|
||||
myFileSystem = fileSystem;
|
||||
public CoreJarVirtualFile(CoreJarHandler handler, JarHandlerBase.EntryInfo entry, CoreJarVirtualFile parent) {
|
||||
myHandler = handler;
|
||||
myPathInJar = pathInJar;
|
||||
myParent = calcParent();
|
||||
myParent = parent;
|
||||
myEntry = entry;
|
||||
|
||||
if (parent != null) {
|
||||
parent.myChildren.add(this);
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getName() {
|
||||
final int lastSlash = myPathInJar.lastIndexOf('/');
|
||||
if (lastSlash < 0) {
|
||||
return myPathInJar;
|
||||
}
|
||||
return myPathInJar.substring(lastSlash+1);
|
||||
return myEntry.shortName;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public VirtualFileSystem getFileSystem() {
|
||||
return myFileSystem;
|
||||
return myHandler.getFileSystem();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPath() {
|
||||
return myHandler.myBasePath + "!/" + myPathInJar;
|
||||
if (myParent == null) return myHandler.myBasePath + "!/";
|
||||
return myParent.getPath() + "/" + myEntry.shortName;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -70,7 +68,7 @@ public class CoreJarVirtualFile extends VirtualFile {
|
||||
|
||||
@Override
|
||||
public boolean isDirectory() {
|
||||
return myHandler.isDirectory(this);
|
||||
return myEntry.isDirectory;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -83,35 +81,9 @@ public class CoreJarVirtualFile extends VirtualFile {
|
||||
return myParent;
|
||||
}
|
||||
|
||||
private VirtualFile calcParent() {
|
||||
if (myPathInJar.length() == 0) {
|
||||
return null;
|
||||
}
|
||||
int lastSlash = myPathInJar.lastIndexOf('/');
|
||||
if (lastSlash < 0) {
|
||||
return myHandler.findFileByPath("");
|
||||
}
|
||||
return myHandler.findFileByPath(myPathInJar.substring(0, lastSlash));
|
||||
}
|
||||
|
||||
@Override
|
||||
public VirtualFile[] getChildren() {
|
||||
VirtualFile[] answer = myChildren;
|
||||
if (answer == null) {
|
||||
answer = calcChildren();
|
||||
myChildren = answer;
|
||||
}
|
||||
return answer;
|
||||
}
|
||||
|
||||
private VirtualFile[] calcChildren() {
|
||||
List<VirtualFile> result = new ArrayList<VirtualFile>();
|
||||
final String[] children = myHandler.list(this);
|
||||
for (String child : children) {
|
||||
final VirtualFile childFile = myPathInJar.isEmpty() ? myHandler.findFileByPath(child) : myHandler.findFileByPath(myPathInJar + "/" + child);
|
||||
result.add(childFile);
|
||||
}
|
||||
return result.toArray(new VirtualFile[result.size()]);
|
||||
return myChildren.toArray(new VirtualFile[myChildren.size()]);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
@@ -137,4 +137,6 @@ public interface ModifiableModuleModel {
|
||||
boolean hasModuleGroups();
|
||||
|
||||
void setModuleGroupPath(Module module, String[] groupPath);
|
||||
|
||||
void setModuleFilePath(Module module, String oldPath, String newFilePath);
|
||||
}
|
||||
|
||||
@@ -22,6 +22,10 @@ import com.intellij.openapi.actionSystem.DataContext;
|
||||
import com.intellij.openapi.actionSystem.LangDataKeys;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
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.editor.Editor;
|
||||
import com.intellij.openapi.module.ModifiableModuleModel;
|
||||
@@ -37,6 +41,7 @@ import com.intellij.psi.PsiFile;
|
||||
import com.intellij.refactoring.RefactoringBundle;
|
||||
import com.intellij.refactoring.rename.RenameHandler;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
/**
|
||||
* @author dsl
|
||||
@@ -86,6 +91,41 @@ public class RenameModuleHandler implements RenameHandler, TitledHandler {
|
||||
}
|
||||
|
||||
public boolean canClose(final String inputString) {
|
||||
final String oldName = myModule.getName();
|
||||
final ModifiableModuleModel modifiableModel = renameModule(inputString);
|
||||
if (modifiableModel == null) return false;
|
||||
final Ref<Boolean> success = Ref.create(Boolean.TRUE);
|
||||
CommandProcessor.getInstance().executeCommand(myProject, new Runnable() {
|
||||
public void run() {
|
||||
UndoableAction action = new BasicUndoableAction() {
|
||||
public void undo() throws UnexpectedUndoException {
|
||||
final ModifiableModuleModel modifiableModel = renameModule(oldName);
|
||||
if (modifiableModel != null) {
|
||||
modifiableModel.commit();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void redo() throws UnexpectedUndoException {
|
||||
final ModifiableModuleModel modifiableModel = renameModule(inputString);
|
||||
if (modifiableModel != null) {
|
||||
modifiableModel.commit();
|
||||
}
|
||||
}
|
||||
};
|
||||
UndoManager.getInstance(myProject).undoableActionPerformed(action);
|
||||
ApplicationManager.getApplication().runWriteAction(new Runnable() {
|
||||
public void run() {
|
||||
modifiableModel.commit();
|
||||
}
|
||||
});
|
||||
}
|
||||
}, IdeBundle.message("command.renaming.module", oldName), null);
|
||||
return success.get().booleanValue();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private ModifiableModuleModel renameModule(String inputString) {
|
||||
final ModifiableModuleModel modifiableModel = ModuleManager.getInstance(myProject).getModifiableModel();
|
||||
try {
|
||||
modifiableModel.renameModule(myModule, inputString);
|
||||
@@ -93,19 +133,9 @@ public class RenameModuleHandler implements RenameHandler, TitledHandler {
|
||||
catch (ModuleWithNameAlreadyExists moduleWithNameAlreadyExists) {
|
||||
Messages.showErrorDialog(myProject, IdeBundle.message("error.module.already.exists", inputString),
|
||||
IdeBundle.message("title.rename.module"));
|
||||
return false;
|
||||
return null;
|
||||
}
|
||||
final Ref<Boolean> success = Ref.create(Boolean.TRUE);
|
||||
CommandProcessor.getInstance().executeCommand(myProject, new Runnable() {
|
||||
public void run() {
|
||||
ApplicationManager.getApplication().runWriteAction(new Runnable() {
|
||||
public void run() {
|
||||
modifiableModel.commit();
|
||||
}
|
||||
});
|
||||
}
|
||||
}, IdeBundle.message("command.renaming.module", myModule.getName()), null);
|
||||
return success.get().booleanValue();
|
||||
return modifiableModel;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -29,6 +29,7 @@ import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.extensions.AreaInstance;
|
||||
import com.intellij.openapi.extensions.ExtensionPointName;
|
||||
import com.intellij.openapi.extensions.Extensions;
|
||||
import com.intellij.openapi.module.ModifiableModuleModel;
|
||||
import com.intellij.openapi.module.Module;
|
||||
import com.intellij.openapi.module.ModuleComponent;
|
||||
import com.intellij.openapi.module.impl.scopes.ModuleWithDependenciesScope;
|
||||
@@ -36,6 +37,7 @@ import com.intellij.openapi.module.impl.scopes.ModuleWithDependentsScope;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.roots.impl.storage.ClasspathStorage;
|
||||
import com.intellij.openapi.util.Comparing;
|
||||
import com.intellij.openapi.util.io.FileUtil;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.openapi.vfs.*;
|
||||
import com.intellij.psi.search.GlobalSearchScope;
|
||||
@@ -329,6 +331,20 @@ public class ModuleImpl extends ComponentManagerImpl implements Module {
|
||||
final Object requestor = event.getRequestor();
|
||||
if (MODULE_RENAMING_REQUESTOR.equals(requestor)) return;
|
||||
if (!VirtualFile.PROP_NAME.equals(event.getPropertyName())) return;
|
||||
|
||||
final VirtualFile parent = event.getParent();
|
||||
if (parent != null) {
|
||||
final String parentPath = parent.getPath();
|
||||
final String ancestorPath = parentPath + "/" + event.getOldValue();
|
||||
final String moduleFilePath = getModuleFilePath();
|
||||
if (VfsUtil.isAncestor(new File(ancestorPath), new File(moduleFilePath), true)) {
|
||||
final String newValue = (String)event.getNewValue();
|
||||
final String relativePath = FileUtil.getRelativePath(ancestorPath, moduleFilePath, '/');
|
||||
final String newFilePath = parentPath + "/" + newValue + "/" + relativePath;
|
||||
setModuleFilePath(moduleFilePath, newFilePath);
|
||||
}
|
||||
}
|
||||
|
||||
final VirtualFile moduleFile = getModuleFile();
|
||||
if (moduleFile == null) return;
|
||||
if (moduleFile.equals(event.getFile())) {
|
||||
@@ -336,6 +352,29 @@ public class ModuleImpl extends ComponentManagerImpl implements Module {
|
||||
ModuleManagerImpl.getInstanceImpl(getProject()).fireModuleRenamedByVfsEvent(ModuleImpl.this);
|
||||
}
|
||||
}
|
||||
|
||||
private void setModuleFilePath(String moduleFilePath, String newFilePath) {
|
||||
ClasspathStorage.modulePathChanged(ModuleImpl.this, newFilePath);
|
||||
|
||||
final ModifiableModuleModel modifiableModel = ModuleManagerImpl.getInstanceImpl(getProject()).getModifiableModel();
|
||||
modifiableModel.setModuleFilePath(ModuleImpl.this, moduleFilePath, newFilePath);
|
||||
modifiableModel.commit();
|
||||
|
||||
getStateStore().setModuleFilePath(newFilePath);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void fileMoved(VirtualFileMoveEvent event) {
|
||||
final VirtualFile oldParent = event.getOldParent();
|
||||
final VirtualFile newParent = event.getNewParent();
|
||||
final String dirName = event.getFileName();
|
||||
final String ancestorPath = oldParent.getPath() + "/" + dirName;
|
||||
final String moduleFilePath = getModuleFilePath();
|
||||
if (VfsUtil.isAncestor(new File(ancestorPath), new File(moduleFilePath), true)) {
|
||||
final String relativePath = FileUtil.getRelativePath(ancestorPath, moduleFilePath, '/');
|
||||
setModuleFilePath(moduleFilePath, newParent.getPath() + "/" + dirName + "/" + relativePath);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected MutablePicoContainer createPicoContainer() {
|
||||
|
||||
@@ -919,6 +919,12 @@ public class ModuleManagerImpl extends ModuleManager implements ProjectComponent
|
||||
myModuleGroupPath.put(module, groupPath);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setModuleFilePath(Module module, String oldPath, String newFilePath) {
|
||||
myPathToModule.remove(oldPath);
|
||||
myPathToModule.put(newFilePath, module);
|
||||
}
|
||||
}
|
||||
|
||||
private void commitModel(final ModuleModelImpl moduleModel, final Runnable runnable) {
|
||||
|
||||
@@ -328,6 +328,10 @@ public class ClasspathStorage implements StateStorage {
|
||||
getProvider(getStorageType(module)).moduleRenamed(module, newName);
|
||||
}
|
||||
|
||||
public static void modulePathChanged(Module module, String path) {
|
||||
getProvider(getStorageType(module)).modulePathChanged(module, path);
|
||||
}
|
||||
|
||||
private static class DefaultStorageProvider implements ClasspathStorageProvider {
|
||||
@NonNls
|
||||
public String getID() {
|
||||
@@ -356,6 +360,10 @@ public class ClasspathStorage implements StateStorage {
|
||||
public String getContentRoot(ModifiableRootModel model) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void modulePathChanged(Module module, String path) {
|
||||
}
|
||||
}
|
||||
|
||||
public static class UnsupportedStorageProvider implements ClasspathStorageProvider {
|
||||
@@ -406,5 +414,10 @@ public class ClasspathStorage implements StateStorage {
|
||||
public String getContentRoot(ModifiableRootModel model) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void modulePathChanged(Module module, String path) {
|
||||
throw new UnsupportedOperationException(getDescription());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+2
@@ -53,6 +53,8 @@ public interface ClasspathStorageProvider {
|
||||
|
||||
String getContentRoot(ModifiableRootModel model);
|
||||
|
||||
void modulePathChanged(Module module, String path);
|
||||
|
||||
interface ClasspathConverter {
|
||||
|
||||
FileSet getFileSet();
|
||||
|
||||
+5
@@ -20,6 +20,7 @@ import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.util.SystemInfo;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.openapi.vfs.impl.local.LocalFileSystemBase;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.io.FileNotFoundException;
|
||||
@@ -91,6 +92,10 @@ public class Win32LocalFileSystem extends LocalFileSystemBase {
|
||||
@NotNull
|
||||
@Override
|
||||
public String[] list(@NotNull VirtualFile file) {
|
||||
if (isInvalidSymLink(file)) {
|
||||
return ArrayUtil.EMPTY_STRING_ARRAY;
|
||||
}
|
||||
|
||||
try {
|
||||
String[] strings = myKernel.list(file.getPath());
|
||||
if (checkMe && !Arrays.asList(strings).equals(Arrays.asList(super.list(file)))) {
|
||||
|
||||
+4
-1
@@ -44,7 +44,10 @@ public class SymLinkHandlingTest extends LightPlatformLangTestCase {
|
||||
}
|
||||
|
||||
public void testBadLinksAreIgnored() throws Exception {
|
||||
if (!SystemInfo.areSymLinksSupported) return;
|
||||
if (!SystemInfo.areSymLinksSupported) {
|
||||
System.out.println("Test not passed");
|
||||
return;
|
||||
}
|
||||
|
||||
final File missingFile = new File(FileUtil.getTempDirectory(), "missing_file");
|
||||
assertTrue(missingFile.getAbsolutePath(), !missingFile.exists() || missingFile.delete());
|
||||
|
||||
@@ -152,7 +152,7 @@ public class UnixProcessManager {
|
||||
result = false;
|
||||
}
|
||||
|
||||
StringBuffer errorStr = new StringBuffer();
|
||||
StringBuilder errorStr = new StringBuilder();
|
||||
while ((s = stdError.readLine()) != null) {
|
||||
errorStr.append(s).append("\n");
|
||||
}
|
||||
@@ -172,24 +172,21 @@ public class UnixProcessManager {
|
||||
}
|
||||
|
||||
public static String[] getPSCmd(boolean commandLineOnly) {
|
||||
String psCommand = "/bin/ps";
|
||||
if (!new File(psCommand).isFile()) {
|
||||
psCommand = "ps";
|
||||
}
|
||||
if (SystemInfo.isLinux) {
|
||||
return new String[]{"ps", "-e", "e", "--format", commandLineOnly ? "%a" : "%P%p%a"};
|
||||
return new String[]{psCommand, "-e", "--format", commandLineOnly ? "%a" : "%P%p%a"};
|
||||
}
|
||||
else if (SystemInfo.isMac) {
|
||||
return new String[]{"ps", "-ax", "-E", "-o", commandLineOnly ? "command" : "ppid,pid,command"};
|
||||
}
|
||||
else if (SystemInfo.isFreeBSD) {
|
||||
return new String[]{"ps", "-ax", "-e", "-o", commandLineOnly ? "command" : "ppid,pid,command"};
|
||||
else if (SystemInfo.isMac || SystemInfo.isFreeBSD) {
|
||||
return new String[]{psCommand, "-ax", "-o", commandLineOnly ? "command" : "ppid,pid,command"};
|
||||
}
|
||||
else {
|
||||
throw new IllegalStateException(System.getProperty("os.name") + " is not supported.");
|
||||
}
|
||||
}
|
||||
|
||||
public static boolean containsMarker(@NotNull String environ, @NotNull String uid) {
|
||||
return environ.contains(uid);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static String readProcEnviron(int child_pid) throws FileNotFoundException {
|
||||
StringBuffer res = new StringBuffer();
|
||||
|
||||
@@ -322,4 +322,5 @@ android.lint.inspections.set.to.wrap.content=Replace size attribute with 'wrap_c
|
||||
android.lint.inspections.add.permission.attribute=Add 'permission' attribute
|
||||
android.lint.inspections.add.input.type.attribute=Add 'inputType' attribute
|
||||
android.lint.inspections.remove.unnecessary.view=Remove unnecessary view
|
||||
android.lint.inspections.replace.with.suggested.characters=Replace with suggested characters
|
||||
android.lint.inspections.replace.with.suggested.characters=Replace with suggested characters
|
||||
android.facet.settings.pack.test.sources=Include test code and resources into APK
|
||||
@@ -35,6 +35,7 @@ import com.intellij.openapi.project.DumbService;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.roots.*;
|
||||
import com.intellij.openapi.ui.Messages;
|
||||
import com.intellij.openapi.util.Computable;
|
||||
import com.intellij.openapi.util.Key;
|
||||
import com.intellij.openapi.util.Pair;
|
||||
import com.intellij.openapi.util.io.FileUtil;
|
||||
@@ -351,14 +352,24 @@ public class AndroidCompileUtil {
|
||||
}
|
||||
|
||||
public static void generate(final Module module, final GeneratingCompiler compiler) {
|
||||
module.getProject().getComponent(AndroidProjectComponent.class).runIfNotInCompilation(new Runnable() {
|
||||
final Project project = module.getProject();
|
||||
final AndroidProjectComponent component = ApplicationManager.getApplication().runReadAction(new Computable<AndroidProjectComponent>() {
|
||||
@Nullable
|
||||
@Override
|
||||
public AndroidProjectComponent compute() {
|
||||
return !project.isDisposed() ? project.getComponent(AndroidProjectComponent.class) : null;
|
||||
}
|
||||
});
|
||||
if (component == null) {
|
||||
return;
|
||||
}
|
||||
component.runIfNotInCompilation(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
assert !ApplicationManager.getApplication().isDispatchThread();
|
||||
final CompileContext[] contextWrapper = new CompileContext[1];
|
||||
ApplicationManager.getApplication().runReadAction(new Runnable() {
|
||||
public void run() {
|
||||
Project project = module.getProject();
|
||||
if (project.isDisposed()) return;
|
||||
CompilerTask task = new CompilerTask(project, true, "Android auto-generation", true);
|
||||
CompileScope scope = new ModuleCompileScope(module, false);
|
||||
|
||||
@@ -105,11 +105,6 @@ public class AndroidDexCompiler implements ClassPostProcessingCompiler {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static boolean shouldRunProguard(@NotNull AndroidFacet facet, @NotNull CompileContext context) {
|
||||
return AndroidCompileUtil.isReleaseBuild(context) &&
|
||||
AndroidCompileUtil.getProguardConfigFile(facet) != null;
|
||||
}
|
||||
|
||||
private static final class PrepareAction implements Computable<ProcessingItem[]> {
|
||||
private final CompileContext myContext;
|
||||
@@ -129,7 +124,10 @@ public class AndroidDexCompiler implements ClassPostProcessingCompiler {
|
||||
|
||||
Collection<VirtualFile> files;
|
||||
|
||||
if (shouldRunProguard(facet, myContext)) {
|
||||
final boolean shouldRunProguard = myContext.getCompileScope().
|
||||
getUserData(AndroidProguardCompiler.PROGUARD_CFG_PATH_KEY) != null;
|
||||
|
||||
if (shouldRunProguard) {
|
||||
final VirtualFile obfuscatedSourcesJar = dexOutputDir.findChild(AndroidProguardCompiler.PROGUARD_OUTPUT_JAR_NAME);
|
||||
if (obfuscatedSourcesJar == null) {
|
||||
myContext.addMessage(CompilerMessageCategory.INFORMATION, "Dex won't be launched for module " +
|
||||
@@ -166,10 +164,12 @@ public class AndroidDexCompiler implements ClassPostProcessingCompiler {
|
||||
}
|
||||
}
|
||||
|
||||
VirtualFile outputDirForTests = extension.getCompilerOutputPathForTests();
|
||||
if (facet.getConfiguration().PACK_TEST_CODE) {
|
||||
VirtualFile outputDirForTests = extension.getCompilerOutputPathForTests();
|
||||
|
||||
if (outputDirForTests != null) {
|
||||
addModuleOutputDir(files, outputDirForTests);
|
||||
if (outputDirForTests != null) {
|
||||
addModuleOutputDir(files, outputDirForTests);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -226,7 +226,7 @@ public class AndroidIdlCompiler implements SourceGeneratingCompiler {
|
||||
}
|
||||
|
||||
try {
|
||||
VirtualFile[] sourceRoots = AndroidPackagingCompiler.getSourceRootsForModuleAndDependencies(idlItem.myModule);
|
||||
VirtualFile[] sourceRoots = AndroidPackagingCompiler.getSourceRootsForModuleAndDependencies(idlItem.myModule, false);
|
||||
final String[] sourceRootPaths = AndroidCompileUtil.toOsPaths(sourceRoots);
|
||||
|
||||
final Map<CompilerMessageCategory, List<String>> messages = AndroidIdl
|
||||
|
||||
@@ -65,11 +65,14 @@ public class AndroidPackagingCompiler implements PackagingCompiler {
|
||||
return VirtualFile.EMPTY_ARRAY;
|
||||
}
|
||||
|
||||
private static void fillSourceRoots(@NotNull Module module, @NotNull Set<Module> visited, @NotNull Set<VirtualFile> result) {
|
||||
private static void fillSourceRoots(@NotNull Module module,
|
||||
@NotNull Set<Module> visited,
|
||||
@NotNull Set<VirtualFile> result,
|
||||
boolean includingTests) {
|
||||
visited.add(module);
|
||||
VirtualFile resDir = AndroidRootUtil.getResourceDir(module);
|
||||
ModuleRootManager manager = ModuleRootManager.getInstance(module);
|
||||
for (VirtualFile sourceRoot : manager.getSourceRoots()) {
|
||||
for (VirtualFile sourceRoot : manager.getSourceRoots(includingTests)) {
|
||||
if (resDir != sourceRoot) {
|
||||
result.add(sourceRoot);
|
||||
}
|
||||
@@ -78,10 +81,10 @@ public class AndroidPackagingCompiler implements PackagingCompiler {
|
||||
if (entry instanceof ModuleOrderEntry) {
|
||||
ModuleOrderEntry moduleOrderEntry = (ModuleOrderEntry)entry;
|
||||
DependencyScope scope = moduleOrderEntry.getScope();
|
||||
if (scope == DependencyScope.COMPILE || scope == DependencyScope.TEST) {
|
||||
if (scope == DependencyScope.COMPILE) {
|
||||
Module depModule = moduleOrderEntry.getModule();
|
||||
if (depModule != null && !visited.contains(depModule)) {
|
||||
fillSourceRoots(depModule, visited, result);
|
||||
fillSourceRoots(depModule, visited, result, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -89,9 +92,9 @@ public class AndroidPackagingCompiler implements PackagingCompiler {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static VirtualFile[] getSourceRootsForModuleAndDependencies(@NotNull Module module) {
|
||||
public static VirtualFile[] getSourceRootsForModuleAndDependencies(@NotNull Module module, boolean includingTests) {
|
||||
Set<VirtualFile> result = new HashSet<VirtualFile>();
|
||||
fillSourceRoots(module, new HashSet<Module>(), result);
|
||||
fillSourceRoots(module, new HashSet<Module>(), result, includingTests);
|
||||
return VfsUtil.toVirtualFileArray(result);
|
||||
}
|
||||
|
||||
@@ -102,7 +105,7 @@ public class AndroidPackagingCompiler implements PackagingCompiler {
|
||||
AndroidFacet facet = AndroidFacet.getInstance(module);
|
||||
if (facet != null && !facet.getConfiguration().LIBRARY_PROJECT) {
|
||||
VirtualFile manifestFile = AndroidRootUtil.getManifestFileForCompiler(facet);
|
||||
VirtualFile[] sourceRoots = getSourceRootsForModuleAndDependencies(module);
|
||||
VirtualFile[] sourceRoots = getSourceRootsForModuleAndDependencies(module, facet.getConfiguration().PACK_TEST_CODE);
|
||||
if (manifestFile != null) {
|
||||
AndroidFacetConfiguration configuration = facet.getConfiguration();
|
||||
VirtualFile outputDir = AndroidDexCompiler.getOutputDirectoryForDex(module);
|
||||
|
||||
+29
-4
@@ -21,6 +21,8 @@ import com.intellij.openapi.command.undo.UndoUtil;
|
||||
import com.intellij.openapi.components.ServiceManager;
|
||||
import com.intellij.openapi.module.Module;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.PsiReference;
|
||||
@@ -30,8 +32,8 @@ import com.intellij.psi.xml.XmlTag;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import com.intellij.util.PsiNavigateUtil;
|
||||
import com.intellij.util.xml.*;
|
||||
import org.jetbrains.android.dom.ResourceType;
|
||||
import org.jetbrains.android.dom.AdditionalConverter;
|
||||
import org.jetbrains.android.dom.ResourceType;
|
||||
import org.jetbrains.android.dom.resources.Item;
|
||||
import org.jetbrains.android.dom.resources.ResourceElement;
|
||||
import org.jetbrains.android.dom.resources.ResourceValue;
|
||||
@@ -110,7 +112,8 @@ public class ResourceReferenceConverter extends ResolvingConverter<ResourceValue
|
||||
if (module == null) return result;
|
||||
AndroidFacet facet = AndroidFacet.getInstance(module);
|
||||
if (facet == null) return result;
|
||||
Set<String> recommendedTypes = getResourceTypes(context);
|
||||
|
||||
final Set<String> recommendedTypes = getResourceTypes(context);
|
||||
|
||||
// hack to check if it is a real id attribute
|
||||
if (recommendedTypes.contains("id") && recommendedTypes.size() == 1) {
|
||||
@@ -122,7 +125,7 @@ public class ResourceReferenceConverter extends ResolvingConverter<ResourceValue
|
||||
String value = getValue(element);
|
||||
assert value != null;
|
||||
|
||||
if (!myQuiet || value.startsWith("@")) {
|
||||
if (!myQuiet || StringUtil.startsWithChar(value, '@')) {
|
||||
String resourcePackage = null;
|
||||
String systemPrefix = getPackagePrefix(SYSTEM_RESOURCE_PACKAGE);
|
||||
if (value.startsWith(systemPrefix)) {
|
||||
@@ -137,12 +140,17 @@ public class ResourceReferenceConverter extends ResolvingConverter<ResourceValue
|
||||
addResourceReferenceValues(facet, type, resourcePackage, result, explicitResourceType);
|
||||
}
|
||||
else {
|
||||
final Set<String> filteringSet = SYSTEM_RESOURCE_PACKAGE.equals(resourcePackage)
|
||||
? null
|
||||
: getResourceTypesInCurrentModule(facet);
|
||||
|
||||
for (String type : ResourceManager.REFERABLE_RESOURCE_TYPES) {
|
||||
String typePrefix = getTypePrefix(resourcePackage, type);
|
||||
if (value.startsWith(typePrefix)) {
|
||||
addResourceReferenceValues(facet, type, resourcePackage, result, true);
|
||||
}
|
||||
else if (recommendedTypes.contains(type)) {
|
||||
else if (recommendedTypes.contains(type) &&
|
||||
(filteringSet == null || filteringSet.contains(type))) {
|
||||
result.add(ResourceValue.literal(typePrefix));
|
||||
}
|
||||
}
|
||||
@@ -157,6 +165,23 @@ public class ResourceReferenceConverter extends ResolvingConverter<ResourceValue
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static Set<String> getResourceTypesInCurrentModule(@NotNull AndroidFacet facet) {
|
||||
final Set<String> result = new HashSet<String>();
|
||||
final LocalResourceManager manager = facet.getLocalResourceManager();
|
||||
|
||||
for (VirtualFile resSubdir : manager.getResourceSubdirs(null)) {
|
||||
final String resType = AndroidResourceUtil.getResourceTypeByDirName(resSubdir.getName());
|
||||
|
||||
if (resType != null && com.android.resources.ResourceType.getEnum(resType) != null) {
|
||||
result.add(resType);
|
||||
}
|
||||
}
|
||||
|
||||
result.addAll(manager.getValueResourceTypes());
|
||||
return result;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private String getTypePrefix(String resourcePackage, String type) {
|
||||
|
||||
@@ -81,6 +81,8 @@ public class AndroidFacetConfiguration implements FacetConfiguration {
|
||||
|
||||
public String CUSTOM_DEBUG_KEYSTORE_PATH = "";
|
||||
|
||||
public boolean PACK_TEST_CODE = false;
|
||||
|
||||
private AndroidFacet myFacet = null;
|
||||
|
||||
public void init(@NotNull Module module, @NotNull VirtualFile contentRoot) {
|
||||
|
||||
@@ -115,8 +115,8 @@
|
||||
</vspacer>
|
||||
</children>
|
||||
</grid>
|
||||
<grid id="84519" layout-manager="GridLayoutManager" row-count="4" column-count="1" same-size-horizontally="false" same-size-vertically="false" hgap="-1" vgap="-1">
|
||||
<margin top="0" left="0" bottom="0" right="0"/>
|
||||
<grid id="84519" layout-manager="GridLayoutManager" row-count="5" column-count="1" same-size-horizontally="false" same-size-vertically="false" hgap="-1" vgap="-1">
|
||||
<margin top="0" left="0" bottom="4" right="0"/>
|
||||
<constraints>
|
||||
<tabbedpane title="Compiler"/>
|
||||
</constraints>
|
||||
@@ -124,7 +124,7 @@
|
||||
<border type="none"/>
|
||||
<children>
|
||||
<grid id="3e085" layout-manager="GridLayoutManager" row-count="5" column-count="2" same-size-horizontally="false" same-size-vertically="false" hgap="-1" vgap="-1">
|
||||
<margin top="0" left="4" bottom="0" right="0"/>
|
||||
<margin top="0" left="0" bottom="0" right="0"/>
|
||||
<constraints>
|
||||
<grid row="2" column="0" row-span="1" col-span="1" vsize-policy="3" hsize-policy="3" anchor="0" fill="3" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
@@ -198,11 +198,11 @@
|
||||
</grid>
|
||||
<vspacer id="e716a">
|
||||
<constraints>
|
||||
<grid row="3" column="0" row-span="1" col-span="1" vsize-policy="6" hsize-policy="1" anchor="0" fill="2" indent="0" use-parent-layout="false"/>
|
||||
<grid row="4" column="0" row-span="1" col-span="1" vsize-policy="6" hsize-policy="1" anchor="0" fill="2" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
</vspacer>
|
||||
<grid id="4c810" layout-manager="GridLayoutManager" row-count="2" column-count="2" same-size-horizontally="false" same-size-vertically="false" hgap="-1" vgap="-1">
|
||||
<margin top="0" left="4" bottom="0" right="0"/>
|
||||
<margin top="0" left="0" bottom="0" right="0"/>
|
||||
<constraints>
|
||||
<grid row="0" column="0" row-span="1" col-span="1" vsize-policy="3" hsize-policy="3" anchor="0" fill="3" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
@@ -237,7 +237,7 @@
|
||||
</children>
|
||||
</grid>
|
||||
<grid id="c2a96" layout-manager="GridLayoutManager" row-count="3" column-count="1" same-size-horizontally="false" same-size-vertically="false" hgap="-1" vgap="-1">
|
||||
<margin top="0" left="4" bottom="0" right="0"/>
|
||||
<margin top="0" left="0" bottom="0" right="0"/>
|
||||
<constraints>
|
||||
<grid row="1" column="0" row-span="1" col-span="1" vsize-policy="3" hsize-policy="3" anchor="0" fill="3" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
@@ -297,6 +297,14 @@
|
||||
</component>
|
||||
</children>
|
||||
</grid>
|
||||
<component id="39707" class="javax.swing.JCheckBox" binding="myIncludeTestCodeAndCheckBox" default-binding="true">
|
||||
<constraints>
|
||||
<grid row="3" column="0" row-span="1" col-span="1" vsize-policy="0" hsize-policy="3" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<text resource-bundle="messages/AndroidBundle" key="android.facet.settings.pack.test.sources"/>
|
||||
</properties>
|
||||
</component>
|
||||
</children>
|
||||
</grid>
|
||||
</children>
|
||||
|
||||
@@ -93,6 +93,7 @@ public class AndroidFacetEditorTab extends FacetEditorTab {
|
||||
private JLabel myRGenPathLabel;
|
||||
private TextFieldWithBrowseButton myCustomDebugKeystoreField;
|
||||
private JBLabel myCustomKeystoreLabel;
|
||||
private JCheckBox myIncludeTestCodeAndCheckBox;
|
||||
|
||||
public AndroidFacetEditorTab(FacetEditorContext context, AndroidFacetConfiguration androidFacetConfiguration) {
|
||||
final Project project = context.getProject();
|
||||
@@ -282,6 +283,9 @@ public class AndroidFacetEditorTab extends FacetEditorTab {
|
||||
if (!myConfiguration.CUSTOM_DEBUG_KEYSTORE_PATH.equals(getSelectedCustomKeystorePath())) {
|
||||
return true;
|
||||
}
|
||||
if (myConfiguration.PACK_TEST_CODE != myIncludeTestCodeAndCheckBox.isSelected()) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -390,6 +394,8 @@ public class AndroidFacetEditorTab extends FacetEditorTab {
|
||||
myConfiguration.RUN_PROCESS_RESOURCES_MAVEN_TASK = myRunProcessResourcesRadio.isSelected();
|
||||
|
||||
myConfiguration.GENERATE_UNSIGNED_APK = myGenerateUnsignedApk.isSelected();
|
||||
|
||||
myConfiguration.PACK_TEST_CODE = myIncludeTestCodeAndCheckBox.isSelected();
|
||||
|
||||
boolean useCustomAptSrc = myUseCustomSourceDirectoryRadio.isSelected();
|
||||
|
||||
@@ -513,6 +519,7 @@ public class AndroidFacetEditorTab extends FacetEditorTab {
|
||||
myCompileResourcesByIdeRadio.setSelected(!myConfiguration.RUN_PROCESS_RESOURCES_MAVEN_TASK);
|
||||
|
||||
myGenerateUnsignedApk.setSelected(myConfiguration.GENERATE_UNSIGNED_APK);
|
||||
myIncludeTestCodeAndCheckBox.setSelected(myConfiguration.PACK_TEST_CODE);
|
||||
|
||||
updateAptPanel();
|
||||
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
|
||||
package org.jetbrains.android.facet;
|
||||
|
||||
import com.android.resources.ResourceFolderType;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.compiler.GeneratingCompiler;
|
||||
import com.intellij.openapi.module.Module;
|
||||
@@ -31,6 +32,7 @@ import org.jetbrains.android.compiler.*;
|
||||
import org.jetbrains.android.dom.manifest.Manifest;
|
||||
import org.jetbrains.android.fileTypes.AndroidIdlFileType;
|
||||
import org.jetbrains.android.fileTypes.AndroidRenderscriptFileType;
|
||||
import org.jetbrains.android.util.AndroidResourceUtil;
|
||||
import org.jetbrains.android.util.AndroidUtils;
|
||||
import org.jetbrains.android.util.ResourceEntry;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -147,7 +149,7 @@ class AndroidResourceFilesListener extends VirtualFileAdapter {
|
||||
final GeneratingCompiler compilerToRun = ApplicationManager.getApplication().runReadAction(new Computable<GeneratingCompiler>() {
|
||||
@Nullable
|
||||
public GeneratingCompiler compute() {
|
||||
return computeCompilerToRun();
|
||||
return computeCompilerToRunAndInvalidateLocalAttributesMap();
|
||||
}
|
||||
});
|
||||
|
||||
@@ -175,7 +177,7 @@ class AndroidResourceFilesListener extends VirtualFileAdapter {
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private GeneratingCompiler computeCompilerToRun() {
|
||||
private GeneratingCompiler computeCompilerToRunAndInvalidateLocalAttributesMap() {
|
||||
if (myFacet.isDisposed()) {
|
||||
return null;
|
||||
}
|
||||
@@ -197,10 +199,18 @@ class AndroidResourceFilesListener extends VirtualFileAdapter {
|
||||
return null;
|
||||
}
|
||||
|
||||
parent = parent.getParent();
|
||||
final VirtualFile gp = parent.getParent();
|
||||
|
||||
final VirtualFile resourceDir = AndroidRootUtil.getResourceDir(module);
|
||||
|
||||
if (gp == resourceDir &&
|
||||
ResourceFolderType.VALUES.getName().equals(AndroidResourceUtil.getResourceTypeByDirName(parent.getName()))) {
|
||||
myFacet.getLocalResourceManager().invalidateAttributeDefinitions();
|
||||
}
|
||||
|
||||
if (AndroidAptCompiler.isToCompileModule(module, myFacet.getConfiguration()) &&
|
||||
(myFacet.getConfiguration().REGENERATE_R_JAVA && parent == AndroidRootUtil.getResourceDir(module) ||
|
||||
AndroidRootUtil.getManifestFile(module) == file)) {
|
||||
(myFacet.getConfiguration().REGENERATE_R_JAVA && (gp == resourceDir ||
|
||||
AndroidRootUtil.getManifestFile(module) == file))) {
|
||||
final Manifest manifest = myFacet.getManifest();
|
||||
final String aPackage = manifest != null ? manifest.getPackage().getValue() : null;
|
||||
|
||||
@@ -209,8 +219,6 @@ class AndroidResourceFilesListener extends VirtualFileAdapter {
|
||||
AndroidCompileUtil.removeDuplicatingClasses(myModule, myCachedPackage, AndroidUtils.R_CLASS_NAME, null, aptGenDirPath);
|
||||
}
|
||||
myCachedPackage = aPackage;
|
||||
myFacet.getLocalResourceManager().invalidateAttributeDefinitions();
|
||||
|
||||
return new AndroidAptCompiler();
|
||||
}
|
||||
|
||||
|
||||
@@ -256,14 +256,9 @@ public class AndroidRootUtil {
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (!outputDirs.contains(classDir) && classDir != null && classDir.exists()) {
|
||||
outputDirs.add(classDir);
|
||||
}
|
||||
VirtualFile classDirForTests = extension.getCompilerOutputPathForTests();
|
||||
if (!outputDirs.contains(classDirForTests) && classDirForTests != null && classDirForTests.exists()) {
|
||||
outputDirs.add(classDirForTests);
|
||||
}
|
||||
// do not support android-app->android-app compile dependencies
|
||||
else if (facet == null && !outputDirs.contains(classDir) && classDir != null && classDir.exists()) {
|
||||
outputDirs.add(classDir);
|
||||
}
|
||||
}
|
||||
fillExternalLibrariesAndModules(depModule, outputDirs, libraries, visited, !libraryProject || exportedLibrariesOnly);
|
||||
|
||||
@@ -128,6 +128,7 @@ public class AndroidModuleBuilder extends JavaModuleBuilder {
|
||||
|
||||
if (myProjectType == ProjectType.TEST) {
|
||||
assert myTestedModule != null;
|
||||
facet.getConfiguration().PACK_TEST_CODE = true;
|
||||
ModuleOrderEntry entry = rootModel.addModuleOrderEntry(myTestedModule);
|
||||
entry.setScope(DependencyScope.PROVIDED);
|
||||
}
|
||||
|
||||
+44
-3
@@ -17,6 +17,7 @@
|
||||
package org.jetbrains.android.resourceManagers;
|
||||
|
||||
import com.android.AndroidConstants;
|
||||
import com.android.resources.ResourceType;
|
||||
import com.intellij.CommonBundle;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
@@ -27,10 +28,14 @@ import com.intellij.openapi.vfs.VfsUtil;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.search.GlobalSearchScope;
|
||||
import com.intellij.psi.xml.XmlFile;
|
||||
import com.intellij.util.IncorrectOperationException;
|
||||
import com.intellij.util.containers.HashMap;
|
||||
import com.intellij.util.containers.HashSet;
|
||||
import com.intellij.util.indexing.FileBasedIndex;
|
||||
import org.jetbrains.android.AndroidFileTemplateProvider;
|
||||
import org.jetbrains.android.AndroidValueResourcesIndex;
|
||||
import org.jetbrains.android.actions.CreateResourceFileAction;
|
||||
import org.jetbrains.android.dom.attrs.AttributeDefinitions;
|
||||
import org.jetbrains.android.dom.resources.Attr;
|
||||
@@ -42,13 +47,12 @@ import org.jetbrains.android.facet.AndroidRootUtil;
|
||||
import org.jetbrains.android.util.AndroidBundle;
|
||||
import org.jetbrains.android.util.AndroidResourceUtil;
|
||||
import org.jetbrains.android.util.AndroidUtils;
|
||||
import org.jetbrains.android.util.ResourceEntry;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.*;
|
||||
|
||||
import static org.jetbrains.android.util.AndroidUtils.loadDomElement;
|
||||
|
||||
@@ -135,6 +139,43 @@ public class LocalResourceManager extends ResourceManager {
|
||||
return facet != null ? facet.getLocalResourceManager() : null;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public Set<String> getValueResourceTypes() {
|
||||
final Map<VirtualFile, Set<String>> file2Types = new HashMap<VirtualFile, Set<String>>();
|
||||
final FileBasedIndex index = FileBasedIndex.getInstance();
|
||||
final GlobalSearchScope scope = GlobalSearchScope.projectScope(myModule.getProject());
|
||||
|
||||
for (String resourceType : ResourceType.getNames()) {
|
||||
final ResourceEntry typeMarkerEntry = AndroidValueResourcesIndex.createTypeMarkerEntry(resourceType);
|
||||
|
||||
for (Set<ResourceEntry> entrySet : index.getValues(AndroidValueResourcesIndex.INDEX_ID, typeMarkerEntry, scope)) {
|
||||
for (ResourceEntry entry : entrySet) {
|
||||
final Collection<VirtualFile> files = index.getContainingFiles(AndroidValueResourcesIndex.INDEX_ID, entry, scope);
|
||||
|
||||
for (VirtualFile file : files) {
|
||||
Set<String> resourcesInFile = file2Types.get(file);
|
||||
|
||||
if (resourcesInFile == null) {
|
||||
resourcesInFile = new HashSet<String>();
|
||||
file2Types.put(file, resourcesInFile);
|
||||
}
|
||||
resourcesInFile.add(entry.getType());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
final Set<String> result = new HashSet<String>();
|
||||
|
||||
for (VirtualFile file : getAllValueResourceFiles()) {
|
||||
final Set<String> types = file2Types.get(file);
|
||||
|
||||
if (types != null) {
|
||||
result.addAll(types);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public AttributeDefinitions getAttributeDefinitions() {
|
||||
if (myAttrDefs == null) {
|
||||
|
||||
@@ -92,11 +92,10 @@ public class AndroidRunConfiguration extends AndroidRunConfigurationBase impleme
|
||||
}
|
||||
|
||||
@Override
|
||||
public RunProfileState getState(@NotNull Executor executor, @NotNull ExecutionEnvironment env) throws ExecutionException {
|
||||
RunProfileState state = super.getState(executor, env);
|
||||
public AndroidRunningState getState(@NotNull Executor executor, @NotNull ExecutionEnvironment env) throws ExecutionException {
|
||||
AndroidRunningState state = super.getState(executor, env);
|
||||
if (state != null) {
|
||||
assert state instanceof AndroidRunningState;
|
||||
((AndroidRunningState)state).setDeploy(DEPLOY);
|
||||
state.setDeploy(DEPLOY);
|
||||
}
|
||||
return state;
|
||||
}
|
||||
|
||||
@@ -31,7 +31,6 @@ import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.module.Module;
|
||||
import com.intellij.openapi.module.ModuleManager;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.roots.DependencyScope;
|
||||
import com.intellij.openapi.roots.ModuleOrderEntry;
|
||||
import com.intellij.openapi.roots.ModuleRootManager;
|
||||
import com.intellij.openapi.roots.OrderEntry;
|
||||
@@ -158,7 +157,8 @@ public abstract class AndroidRunConfigurationBase extends ModuleBasedConfigurati
|
||||
TARGET_SELECTION_MODE = mode.name();
|
||||
}
|
||||
|
||||
private static boolean fillRuntimeAndTestDependencies(@NotNull Module module, @NotNull Map<AndroidFacet, String> module2PackageName) {
|
||||
private static boolean fillRuntimeAndTestDependencies(@NotNull Module module,
|
||||
@NotNull Map<AndroidFacet, String> module2PackageName) {
|
||||
for (OrderEntry entry : ModuleRootManager.getInstance(module).getOrderEntries()) {
|
||||
if (entry instanceof ModuleOrderEntry) {
|
||||
ModuleOrderEntry moduleOrderEntry = (ModuleOrderEntry)entry;
|
||||
@@ -167,8 +167,7 @@ public abstract class AndroidRunConfigurationBase extends ModuleBasedConfigurati
|
||||
AndroidFacet depFacet = AndroidFacet.getInstance(depModule);
|
||||
if (depFacet != null &&
|
||||
!module2PackageName.containsKey(depFacet) &&
|
||||
!depFacet.getConfiguration().LIBRARY_PROJECT &&
|
||||
moduleOrderEntry.getScope() != DependencyScope.COMPILE) {
|
||||
!depFacet.getConfiguration().LIBRARY_PROJECT) {
|
||||
String packageName = getPackageName(depFacet);
|
||||
if (packageName == null) {
|
||||
return false;
|
||||
@@ -184,7 +183,7 @@ public abstract class AndroidRunConfigurationBase extends ModuleBasedConfigurati
|
||||
return true;
|
||||
}
|
||||
|
||||
public RunProfileState getState(@NotNull final Executor executor, @NotNull ExecutionEnvironment env) throws ExecutionException {
|
||||
public AndroidRunningState getState(@NotNull final Executor executor, @NotNull ExecutionEnvironment env) throws ExecutionException {
|
||||
final Module module = getConfigurationModule().getModule();
|
||||
if (module == null) {
|
||||
throw new ExecutionException("Module is not found");
|
||||
|
||||
@@ -218,10 +218,6 @@ public abstract class AndroidRunningState implements RunProfileState, AndroidDeb
|
||||
return myLock;
|
||||
}
|
||||
|
||||
public AndroidFacet getAndroidFacet() {
|
||||
return myFacet;
|
||||
}
|
||||
|
||||
public String getPackageName() {
|
||||
return myPackageName;
|
||||
}
|
||||
@@ -230,6 +226,7 @@ public abstract class AndroidRunningState implements RunProfileState, AndroidDeb
|
||||
return myFacet.getModule();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public AndroidFacet getFacet() {
|
||||
return myFacet;
|
||||
}
|
||||
|
||||
+43
-1
@@ -28,6 +28,7 @@ import com.intellij.execution.Executor;
|
||||
import com.intellij.execution.configurations.*;
|
||||
import com.intellij.execution.junit.JUnitUtil;
|
||||
import com.intellij.execution.process.ProcessOutputTypes;
|
||||
import com.intellij.execution.runners.ExecutionEnvironment;
|
||||
import com.intellij.execution.testframework.sm.SMTestRunnerConnectionUtil;
|
||||
import com.intellij.execution.testframework.ui.BaseTestsOutputConsoleView;
|
||||
import com.intellij.execution.ui.ConsoleView;
|
||||
@@ -35,6 +36,8 @@ import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.module.Module;
|
||||
import com.intellij.openapi.options.SettingsEditor;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.roots.ModuleRootManager;
|
||||
import com.intellij.openapi.ui.Messages;
|
||||
import com.intellij.openapi.util.Disposer;
|
||||
import com.intellij.psi.JavaPsiFacade;
|
||||
import com.intellij.psi.PsiClass;
|
||||
@@ -43,6 +46,7 @@ import com.intellij.psi.PsiPackage;
|
||||
import org.jetbrains.android.dom.manifest.Instrumentation;
|
||||
import org.jetbrains.android.dom.manifest.Manifest;
|
||||
import org.jetbrains.android.facet.AndroidFacet;
|
||||
import org.jetbrains.android.facet.AndroidFacetConfiguration;
|
||||
import org.jetbrains.android.run.AndroidApplicationLauncher;
|
||||
import org.jetbrains.android.run.AndroidRunConfigurationBase;
|
||||
import org.jetbrains.android.run.AndroidRunConfigurationEditor;
|
||||
@@ -108,6 +112,44 @@ public class AndroidTestRunConfiguration extends AndroidRunConfigurationBase {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public AndroidRunningState getState(@NotNull Executor executor, @NotNull ExecutionEnvironment env) throws ExecutionException {
|
||||
final AndroidRunningState state = super.getState(executor, env);
|
||||
|
||||
if (state == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
final AndroidFacet facet = state.getFacet();
|
||||
final AndroidFacetConfiguration configuration = facet.getConfiguration();
|
||||
|
||||
if (!configuration.PACK_TEST_CODE) {
|
||||
final Module module = facet.getModule();
|
||||
final int count = getTestSourceRootCount(module);
|
||||
|
||||
if (count > 0) {
|
||||
final String message = "Code and resources under test source " + (count > 1 ? "roots" : "root") +
|
||||
" aren't included into debug APK.\nWould you like to include them and recompile " +
|
||||
module.getName() + " module?" + "\n(You may change this option in Android facet settings later)";
|
||||
final int result =
|
||||
Messages.showYesNoCancelDialog(getProject(), message, "Test code not included into APK", Messages.getQuestionIcon());
|
||||
|
||||
if (result == Messages.YES) {
|
||||
configuration.PACK_TEST_CODE = true;
|
||||
}
|
||||
else if (result == Messages.CANCEL) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
return state;
|
||||
}
|
||||
|
||||
private static int getTestSourceRootCount(@NotNull Module module) {
|
||||
final ModuleRootManager manager = ModuleRootManager.getInstance(module);
|
||||
return manager.getSourceRoots(true).length - manager.getSourceRoots(false).length;
|
||||
}
|
||||
|
||||
private void checkTestMethod() throws RuntimeConfigurationException {
|
||||
JavaRunConfigurationModule configurationModule = getConfigurationModule();
|
||||
final PsiClass testClass =
|
||||
@@ -166,7 +208,7 @@ public class AndroidTestRunConfiguration extends AndroidRunConfigurationBase {
|
||||
BaseTestsOutputConsoleView consoleView = SMTestRunnerConnectionUtil
|
||||
.createAndAttachConsole("Android", state.getProcessHandler(), properties, state.getRunnerSettings(), state.getConfigurationSettings()
|
||||
);
|
||||
Disposer.register(state.getAndroidFacet().getModule().getProject(), consoleView);
|
||||
Disposer.register(state.getFacet().getModule().getProject(), consoleView);
|
||||
return consoleView;
|
||||
}
|
||||
|
||||
|
||||
@@ -76,10 +76,17 @@ class AndroidSdkConfigurableForm {
|
||||
final IAndroidTarget target = (IAndroidTarget)e.getItem();
|
||||
|
||||
List<OrderRoot> roots = AndroidSdkUtils.getLibraryRootsForTarget(target, mySdkLocation);
|
||||
Map<OrderRootType, VirtualFile[]> configuredRoots = new HashMap<OrderRootType, VirtualFile[]>();
|
||||
Map<OrderRootType, String[]> configuredRoots = new HashMap<OrderRootType, String[]>();
|
||||
|
||||
for (OrderRootType type : OrderRootType.getAllTypes()) {
|
||||
configuredRoots.put(type, sdkModificator.getRoots(type));
|
||||
final VirtualFile[] oldRoots = sdkModificator.getRoots(type);
|
||||
final String[] oldRootPaths = new String[oldRoots.length];
|
||||
|
||||
for (int i = 0; i < oldRootPaths.length; i++) {
|
||||
oldRootPaths[i] = oldRoots[i].getPath();
|
||||
}
|
||||
|
||||
configuredRoots.put(type, oldRootPaths);
|
||||
}
|
||||
|
||||
for (OrderRoot root : roots) {
|
||||
@@ -87,8 +94,8 @@ class AndroidSdkConfigurableForm {
|
||||
sdkModificator.removeRoot(root.getFile(), root.getType());
|
||||
}
|
||||
else {
|
||||
VirtualFile[] configuredRootsForType = configuredRoots.get(root.getType());
|
||||
if (ArrayUtil.find(configuredRootsForType, root.getFile()) == -1) {
|
||||
String[] configuredRootsForType = configuredRoots.get(root.getType());
|
||||
if (ArrayUtil.find(configuredRootsForType, root.getFile().getPath()) == -1) {
|
||||
sdkModificator.addRoot(root.getFile(), root.getType());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -455,12 +455,15 @@ public class AndroidUtils {
|
||||
LOG.info(commandLine.getCommandLineString());
|
||||
OSProcessHandler handler = new OSProcessHandler(commandLine.createProcess(), "");
|
||||
|
||||
final StringBuffer buffer = new StringBuffer();
|
||||
final ProcessAdapter listener = new ProcessAdapter() {
|
||||
public void onTextAvailable(final ProcessEvent event, final Key outputType) {
|
||||
buffer.append(event.getText());
|
||||
}
|
||||
};
|
||||
|
||||
if (timeout == null || timeout > 0) {
|
||||
handler.addProcessListener(new ProcessAdapter() {
|
||||
public void onTextAvailable(final ProcessEvent event, final Key outputType) {
|
||||
messageBuilder.append(event.getText());
|
||||
}
|
||||
});
|
||||
handler.addProcessListener(listener);
|
||||
}
|
||||
|
||||
handler.startNotify();
|
||||
@@ -483,7 +486,9 @@ public class AndroidUtils {
|
||||
}
|
||||
|
||||
if (timeout == null || timeout > 0) {
|
||||
String message = messageBuilder.toString();
|
||||
handler.removeProcessListener(listener);
|
||||
final String message = buffer.toString();
|
||||
messageBuilder.append(message);
|
||||
LOG.info(message);
|
||||
}
|
||||
|
||||
|
||||
@@ -9,7 +9,6 @@ import com.intellij.openapi.util.Pair;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
@@ -116,9 +115,7 @@ public class AndroidLayoutDomTest extends AndroidDomTest {
|
||||
|
||||
public void testResourceCompletion() throws Throwable {
|
||||
doTestCompletionVariants("av3.xml", "@color/", "@android:", "@drawable/");
|
||||
List<String> list = getAllResources();
|
||||
list.add("@android:");
|
||||
doTestCompletionVariants("av8.xml", ArrayUtil.toStringArray(list));
|
||||
doTestCompletionVariants("av8.xml", "@android:", "@anim/", "@color/", "@dimen/", "@drawable/", "@id/", "@layout/", "@string/", "@style/");
|
||||
}
|
||||
|
||||
public void testLocalResourceCompletion1() throws Throwable {
|
||||
|
||||
@@ -1,11 +1,8 @@
|
||||
package org.jetbrains.android.dom;
|
||||
|
||||
import com.android.sdklib.SdkConstants;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import org.jetbrains.android.inspections.AndroidUnknownAttributeInspection;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author coyote
|
||||
*/
|
||||
@@ -73,9 +70,7 @@ public class AndroidManifestDomTest extends AndroidDomTest {
|
||||
}
|
||||
|
||||
public void testResourceCompletion3() throws Throwable {
|
||||
List<String> list = getAllResources();
|
||||
list.add("@android:");
|
||||
doTestCompletionVariants("av4.xml", ArrayUtil.toStringArray(list));
|
||||
doTestCompletionVariants("av4.xml", "@android:", "@anim/", "@color/", "@dimen/", "@drawable/", "@id/", "@string/", "@style/");
|
||||
}
|
||||
|
||||
public void testTagNameCompletion1() throws Throwable {
|
||||
|
||||
+8
@@ -103,6 +103,14 @@ public class EclipseClasspathStorageProvider implements ClasspathStorageProvider
|
||||
return model.getContentRoots()[0].getPath();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void modulePathChanged(Module module, String path) {
|
||||
final EclipseModuleManager moduleManager = EclipseModuleManager.getInstance(module);
|
||||
if (moduleManager != null) {
|
||||
moduleManager.setDocumentSet(null);
|
||||
}
|
||||
}
|
||||
|
||||
public static void registerFiles(final CachedXmlDocumentSet fileCache, final Module module, final String moduleRoot, final String storageRoot) {
|
||||
fileCache.register(EclipseXml.CLASSPATH_FILE, storageRoot);
|
||||
fileCache.register(EclipseXml.PROJECT_FILE, storageRoot);
|
||||
|
||||
+47
-35
@@ -89,12 +89,13 @@ public class MavenPluginConfigurationDomExtender extends DomExtender<MavenDomCon
|
||||
String name = eachParameter.getName().getStringValue();
|
||||
if (name == null) continue;
|
||||
|
||||
if (namesWithParameters.containsKey(name)) continue;
|
||||
|
||||
ParameterData data = new ParameterData(eachParameter);
|
||||
fillParameterData(name, data, eachMojo);
|
||||
|
||||
namesWithParameters.put(name, data);
|
||||
ParameterData oldParameter = namesWithParameters.get(name);
|
||||
if (oldParameter == null || hasMorePriority(data, oldParameter, executionElement != null)) {
|
||||
namesWithParameters.put(name, data);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -102,6 +103,16 @@ public class MavenPluginConfigurationDomExtender extends DomExtender<MavenDomCon
|
||||
return namesWithParameters.values();
|
||||
}
|
||||
|
||||
private static boolean hasMorePriority(ParameterData d1, ParameterData d2, boolean isForExecutionSection) {
|
||||
if (!isForExecutionSection) {
|
||||
if (StringUtil.isEmptyOrSpaces(d1.getMojo().getPhase().getStringValue())) return false;
|
||||
|
||||
if (StringUtil.isEmptyOrSpaces(d2.getMojo().getPhase().getStringValue())) return true;
|
||||
}
|
||||
|
||||
return d1.getRequiringLevel() > d2.getRequiringLevel();
|
||||
}
|
||||
|
||||
private static void fillParameterData(String name, ParameterData data, MavenDomMojo mojo) {
|
||||
XmlTag config = mojo.getConfiguration().getXmlTag();
|
||||
if (config == null) return;
|
||||
@@ -153,15 +164,27 @@ public class MavenPluginConfigurationDomExtender extends DomExtender<MavenDomCon
|
||||
}
|
||||
}
|
||||
|
||||
private static void addRequiredAnnotation(DomExtension e, ParameterData data) {
|
||||
if (!StringUtil.isEmptyOrSpaces(data.defaultValue)
|
||||
|| !StringUtil.isEmptyOrSpaces(data.expression)) {
|
||||
return;
|
||||
}
|
||||
private static void addRequiredAnnotation(DomExtension e, final ParameterData data) {
|
||||
if (Boolean.parseBoolean(data.parameter.getRequired().getStringValue())) {
|
||||
e.addCustomAnnotation(new Required(){
|
||||
@Override
|
||||
public boolean value() {
|
||||
return StringUtil.isEmptyOrSpaces(data.defaultValue) && StringUtil.isEmptyOrSpaces(data.expression);
|
||||
}
|
||||
|
||||
final String required = data.parameter.getRequired().getStringValue();
|
||||
if (!StringUtil.isEmptyOrSpaces(required)) {
|
||||
e.addCustomAnnotation(new MyRequired(required));
|
||||
@Override
|
||||
public boolean nonEmpty() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean identifier() {
|
||||
return false;
|
||||
}
|
||||
public Class<? extends Annotation> annotationType() {
|
||||
return Required.class;
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -181,43 +204,32 @@ public class MavenPluginConfigurationDomExtender extends DomExtender<MavenDomCon
|
||||
String type = parameter.getType().getStringValue();
|
||||
if (type.endsWith("[]")) return true;
|
||||
|
||||
List<String> collectionClasses = Arrays.asList("java.util.List",
|
||||
"java.util.Set",
|
||||
"java.util.Collection");
|
||||
return collectionClasses.contains(type);
|
||||
return type.equals("java.util.List") || type.equals("java.util.Set") || type.equals("java.util.Collection");
|
||||
}
|
||||
|
||||
public static class ParameterData {
|
||||
public MavenDomParameter parameter;
|
||||
public final MavenDomParameter parameter;
|
||||
public @Nullable String defaultValue;
|
||||
public @Nullable String expression;
|
||||
|
||||
private ParameterData(MavenDomParameter parameter) {
|
||||
this.parameter = parameter;
|
||||
}
|
||||
}
|
||||
|
||||
private static class MyRequired implements Required {
|
||||
private final String myRequired;
|
||||
|
||||
public MyRequired(String required) {
|
||||
myRequired = required;
|
||||
|
||||
@NotNull
|
||||
public MavenDomMojo getMojo() {
|
||||
return (MavenDomMojo)parameter.getParent().getParent();
|
||||
}
|
||||
|
||||
public boolean value() {
|
||||
return Boolean.valueOf(myRequired);
|
||||
}
|
||||
public int getRequiringLevel() {
|
||||
if (!Boolean.parseBoolean(parameter.getRequired().getStringValue())) return 0;
|
||||
|
||||
public boolean nonEmpty() {
|
||||
return false;
|
||||
}
|
||||
if (!StringUtil.isEmptyOrSpaces(defaultValue) || !StringUtil.isEmptyOrSpaces(expression)) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
public boolean identifier() {
|
||||
return false;
|
||||
}
|
||||
|
||||
public Class<? extends Annotation> annotationType() {
|
||||
return Required.class;
|
||||
return 2;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -23,6 +23,9 @@ public interface MavenDomMojo extends MavenDomElement {
|
||||
@NotNull
|
||||
GenericDomValue<String> getGoal();
|
||||
|
||||
@NotNull
|
||||
GenericDomValue<String> getPhase();
|
||||
|
||||
@NotNull
|
||||
MavenDomParameters getParameters();
|
||||
|
||||
|
||||
+2
-2
@@ -31,6 +31,7 @@ import com.intellij.util.ArrayUtil;
|
||||
import com.intellij.util.Function;
|
||||
import com.intellij.util.IncorrectOperationException;
|
||||
import com.intellij.util.PlatformIcons;
|
||||
import com.intellij.util.containers.CollectionFactory;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import com.intellij.util.xml.DomElement;
|
||||
import com.intellij.util.xml.DomUtil;
|
||||
@@ -51,13 +52,12 @@ import org.jetbrains.idea.maven.vfs.MavenPropertiesVirtualFileSystem;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
public class MavenPropertyPsiReference extends MavenPsiReference {
|
||||
private static final Set<String> BASEDIR_PROPS =
|
||||
new THashSet<String>(Arrays.asList("basedir", "project.basedir", "pom.basedir", "baseUri", "project.baseUri", "pom.baseUri"));
|
||||
CollectionFactory.newTroveSet("basedir", "project.basedir", "pom.basedir", "baseUri", "project.baseUri", "pom.baseUri");
|
||||
|
||||
private static final String TIMESTAMP_PROP = "maven.build.timestamp";
|
||||
|
||||
|
||||
@@ -896,25 +896,23 @@ public class MavenProject {
|
||||
|
||||
MavenProjectChanges result = new MavenProjectChanges();
|
||||
|
||||
result.packaging |= !Comparing.equal(myPackaging, other.myPackaging);
|
||||
result.packaging = !Comparing.equal(myPackaging, other.myPackaging);
|
||||
|
||||
result.output |= !Comparing.equal(myFinalName, other.myFinalName);
|
||||
result.output |= !Comparing.equal(myBuildDirectory, other.myBuildDirectory);
|
||||
result.output |= !Comparing.equal(myOutputDirectory, other.myOutputDirectory);
|
||||
result.output |= !Comparing.equal(myTestOutputDirectory, other.myTestOutputDirectory);
|
||||
result.output = !Comparing.equal(myFinalName, other.myFinalName)
|
||||
|| !Comparing.equal(myBuildDirectory, other.myBuildDirectory)
|
||||
|| !Comparing.equal(myOutputDirectory, other.myOutputDirectory)
|
||||
|| !Comparing.equal(myTestOutputDirectory, other.myTestOutputDirectory);
|
||||
|
||||
result.sources |= !Comparing.equal(mySources, other.mySources);
|
||||
result.sources |= !Comparing.equal(myTestSources, other.myTestSources);
|
||||
result.sources |= !Comparing.equal(myResources, other.myResources);
|
||||
result.sources |= !Comparing.equal(myTestResources, other.myTestResources);
|
||||
result.sources = !Comparing.equal(mySources, other.mySources)
|
||||
|| !Comparing.equal(myTestSources, other.myTestSources)
|
||||
|| !Comparing.equal(myResources, other.myResources)
|
||||
|| !Comparing.equal(myTestResources, other.myTestResources);
|
||||
|
||||
boolean repositoryChanged = !Comparing.equal(myLocalRepository, other.myLocalRepository);
|
||||
|
||||
result.dependencies |= repositoryChanged;
|
||||
result.dependencies |= !Comparing.equal(myDependencies, other.myDependencies);
|
||||
result.dependencies = repositoryChanged || !Comparing.equal(myDependencies, other.myDependencies);
|
||||
|
||||
result.plugins |= repositoryChanged;
|
||||
result.plugins |= !Comparing.equal(myPlugins, other.myPlugins);
|
||||
result.plugins = repositoryChanged || !Comparing.equal(myPlugins, other.myPlugins);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
+1
@@ -0,0 +1 @@
|
||||
4d0907396ac6a770e05c81f6e8ed6348740f86a0
|
||||
+203
@@ -0,0 +1,203 @@
|
||||
<?xml version='1.0' encoding='UTF-8'?>
|
||||
|
||||
<!--
|
||||
Licensed to the Apache Software Foundation (ASF) under one
|
||||
or more contributor license agreements. See the NOTICE file
|
||||
distributed with this work for additional information
|
||||
regarding copyright ownership. The ASF licenses this file
|
||||
to you 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.
|
||||
-->
|
||||
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<parent>
|
||||
<artifactId>maven-plugins</artifactId>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<version>19</version>
|
||||
<relativePath>../maven-plugins/pom.xml</relativePath>
|
||||
</parent>
|
||||
|
||||
<artifactId>maven-resources-plugin</artifactId>
|
||||
<version>2.5</version>
|
||||
<packaging>maven-plugin</packaging>
|
||||
|
||||
<name>Maven Resources Plugin</name>
|
||||
<description>
|
||||
The Resources Plugin handles the copying of project resources to the output
|
||||
directory. There are two different kinds of resources: main resources and test resources. The
|
||||
difference is that the main resources are the resources associated to the main
|
||||
source code while the test resources are associated to the test source code.
|
||||
Thus, this allows the separation of resources for the main source code and its
|
||||
unit tests.
|
||||
</description>
|
||||
<inceptionYear>2001</inceptionYear>
|
||||
|
||||
<prerequisites>
|
||||
<maven>${mavenVersion}</maven>
|
||||
</prerequisites>
|
||||
|
||||
<scm>
|
||||
<connection>scm:svn:http://svn.apache.org/repos/asf/maven/plugins/tags/maven-resources-plugin-2.5</connection>
|
||||
<developerConnection>scm:svn:https://svn.apache.org/repos/asf/maven/plugins/tags/maven-resources-plugin-2.5</developerConnection>
|
||||
<url>http://svn.apache.org/viewvc/maven/plugins/tags/maven-resources-plugin-2.5</url>
|
||||
</scm>
|
||||
<issueManagement>
|
||||
<system>JIRA</system>
|
||||
<url>http://jira.codehaus.org/browse/MRESOURCES</url>
|
||||
</issueManagement>
|
||||
|
||||
<properties>
|
||||
<mavenFilteringVersion>1.0</mavenFilteringVersion>
|
||||
<mavenVersion>2.0.6</mavenVersion>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.apache.maven</groupId>
|
||||
<artifactId>maven-plugin-api</artifactId>
|
||||
<version>${mavenVersion}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.maven</groupId>
|
||||
<artifactId>maven-project</artifactId>
|
||||
<version>${mavenVersion}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.maven</groupId>
|
||||
<artifactId>maven-core</artifactId>
|
||||
<version>${mavenVersion}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.maven</groupId>
|
||||
<artifactId>maven-artifact</artifactId>
|
||||
<version>${mavenVersion}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.maven</groupId>
|
||||
<artifactId>maven-settings</artifactId>
|
||||
<version>${mavenVersion}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.maven</groupId>
|
||||
<artifactId>maven-model</artifactId>
|
||||
<version>${mavenVersion}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.maven</groupId>
|
||||
<artifactId>maven-monitor</artifactId>
|
||||
<version>${mavenVersion}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.codehaus.plexus</groupId>
|
||||
<artifactId>plexus-container-default</artifactId>
|
||||
<version>1.0-alpha-9-stable-1</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.codehaus.plexus</groupId>
|
||||
<artifactId>plexus-utils</artifactId>
|
||||
<version>2.0.5</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.maven.shared</groupId>
|
||||
<artifactId>maven-filtering</artifactId>
|
||||
<version>${mavenFilteringVersion}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.codehaus.plexus</groupId>
|
||||
<artifactId>plexus-interpolation</artifactId>
|
||||
<version>1.13</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.maven.shared</groupId>
|
||||
<artifactId>maven-plugin-testing-harness</artifactId>
|
||||
<version>1.0-beta-1</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>commons-io</groupId>
|
||||
<artifactId>commons-io</artifactId>
|
||||
<version>1.4</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<profiles>
|
||||
<profile>
|
||||
<id>run-its</id>
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-jar-plugin</artifactId>
|
||||
<executions>
|
||||
<execution>
|
||||
<goals>
|
||||
<goal>test-jar</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.codehaus.plexus</groupId>
|
||||
<artifactId>plexus-maven-plugin</artifactId>
|
||||
<executions>
|
||||
<execution>
|
||||
<goals>
|
||||
<goal>test-descriptor</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-invoker-plugin</artifactId>
|
||||
<configuration>
|
||||
<debug>true</debug>
|
||||
<projectsDirectory>src/it</projectsDirectory>
|
||||
<pomIncludes>
|
||||
<pomInclude>**/pom.xml</pomInclude>
|
||||
</pomIncludes>
|
||||
<postBuildHookScript>verify</postBuildHookScript>
|
||||
<localRepositoryPath>${project.build.directory}/local-repo</localRepositoryPath>
|
||||
<goals>
|
||||
<goal>clean</goal>
|
||||
<goal>process-test-resources</goal>
|
||||
</goals>
|
||||
<settingsFile>src/it/settings.xml</settingsFile>
|
||||
<cloneProjectsTo>${project.build.directory}/it</cloneProjectsTo>
|
||||
<properties>
|
||||
<execProps>fromExecProps</execProps>
|
||||
</properties>
|
||||
</configuration>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>integration-test</id>
|
||||
<goals>
|
||||
<goal>install</goal>
|
||||
<goal>run</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</profile>
|
||||
</profiles>
|
||||
</project>
|
||||
+1
@@ -0,0 +1 @@
|
||||
2d44c4a29ea56775c87002edb5aa23aab47e71ac
|
||||
+2
-1
@@ -65,7 +65,7 @@ public class MavenExtensionCompletionAndResolutionTest extends MavenDomWithIndic
|
||||
" </extensions>" +
|
||||
"</build>");
|
||||
|
||||
assertCompletionVariants(myProjectPom, "maven-compiler-plugin", "maven-war-plugin", "maven-eclipse-plugin", "maven-surefire-plugin");
|
||||
assertCompletionVariants(myProjectPom, "maven-compiler-plugin", "maven-war-plugin", "maven-eclipse-plugin", "maven-surefire-plugin", "maven-resources-plugin");
|
||||
}
|
||||
|
||||
public void testArtifactWithoutGroupCompletion() throws Exception {
|
||||
@@ -86,6 +86,7 @@ public class MavenExtensionCompletionAndResolutionTest extends MavenDomWithIndic
|
||||
"maven-war-plugin",
|
||||
"maven-surefire-plugin",
|
||||
"build-helper-maven-plugin",
|
||||
"maven-resources-plugin",
|
||||
"maven-eclipse-plugin");
|
||||
}
|
||||
|
||||
|
||||
+57
-1
@@ -71,7 +71,7 @@ public class MavenPluginCompletionAndResolutionTest extends MavenDomWithIndicesT
|
||||
" </plugins>" +
|
||||
"</build>");
|
||||
|
||||
assertCompletionVariants(myProjectPom, "maven-compiler-plugin", "maven-war-plugin", "maven-surefire-plugin", "maven-eclipse-plugin");
|
||||
assertCompletionVariants(myProjectPom, "maven-compiler-plugin", "maven-war-plugin", "maven-surefire-plugin", "maven-eclipse-plugin", "maven-resources-plugin");
|
||||
}
|
||||
|
||||
public void testArtifactWithoutGroupCompletion() throws Exception {
|
||||
@@ -92,6 +92,7 @@ public class MavenPluginCompletionAndResolutionTest extends MavenDomWithIndicesT
|
||||
"maven-war-plugin",
|
||||
"build-helper-maven-plugin",
|
||||
"maven-surefire-plugin",
|
||||
"maven-resources-plugin",
|
||||
"maven-eclipse-plugin");
|
||||
}
|
||||
|
||||
@@ -902,4 +903,59 @@ public class MavenPluginCompletionAndResolutionTest extends MavenDomWithIndicesT
|
||||
|
||||
assertCompletionVariants(myProjectPom);
|
||||
}
|
||||
|
||||
public void testRequiringParameter() throws Throwable {
|
||||
createProjectPom("<groupId>test</groupId>" +
|
||||
"<artifactId>project</artifactId>" +
|
||||
"<version>1</version>" +
|
||||
|
||||
"<build>" +
|
||||
" <plugins>" +
|
||||
" <plugin>\n" +
|
||||
" <artifactId>maven-resources-plugin</artifactId>\n" +
|
||||
" <configuration>\n" +
|
||||
" <<error descr=\"Value must not be empty\">outputDirectory</error>/>\n" +
|
||||
" </configuration>\n" +
|
||||
" </plugin>\n" +
|
||||
|
||||
" <plugin>\n" +
|
||||
" <artifactId>maven-resources-plugin</artifactId>\n" +
|
||||
"" +
|
||||
" <configuration>\n" +
|
||||
" <outputDirectory>aaa</outputDirectory>\n" +
|
||||
" </configuration>\n" +
|
||||
" </plugin>\n" +
|
||||
|
||||
" <plugin>\n" +
|
||||
" <artifactId>maven-resources-plugin</artifactId>\n" +
|
||||
"" +
|
||||
" <configuration>\n" +
|
||||
" </configuration>\n" +
|
||||
" </plugin>\n" +
|
||||
|
||||
" <plugin>\n" +
|
||||
" <artifactId>maven-resources-plugin</artifactId>\n" +
|
||||
" <executions>" +
|
||||
" <execution>" +
|
||||
" <goals> " +
|
||||
" <goal>copy-resources</goal>" +
|
||||
" <goal>resources</goal>" +
|
||||
" </goals> " +
|
||||
" <<error descr=\"'outputDirectory' child tag should be defined\">configuration</error>>\n" +
|
||||
" </configuration>\n" +
|
||||
" " +
|
||||
" </execution>" +
|
||||
" </executions>" +
|
||||
"" +
|
||||
" <configuration>\n" +
|
||||
" </configuration>\n" +
|
||||
" </plugin>\n" +
|
||||
|
||||
|
||||
" </plugins>" +
|
||||
"</build>");
|
||||
|
||||
checkHighlighting();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -129,6 +129,7 @@ public final class GuiEditor extends JPanel implements DataProvider {
|
||||
private final Document myDocument;
|
||||
|
||||
final MainProcessor myProcessor;
|
||||
@NotNull private final JScrollPane myScrollPane;
|
||||
/**
|
||||
* This layered pane contains all layers to lay components out and to
|
||||
* show all necessary decoration items
|
||||
@@ -302,11 +303,12 @@ public final class GuiEditor extends JPanel implements DataProvider {
|
||||
gbc.gridy = 1;
|
||||
gbc.weightx = 1.0;
|
||||
gbc.weighty = 1.0;
|
||||
final JScrollPane scrollPane = ScrollPaneFactory.createScrollPane(myLayeredPane);
|
||||
scrollPane.setBackground(Color.WHITE);
|
||||
panel.add(scrollPane, gbc);
|
||||
myHorzCaptionPanel.attachToScrollPane(scrollPane);
|
||||
myVertCaptionPanel.attachToScrollPane(scrollPane);
|
||||
|
||||
myScrollPane = ScrollPaneFactory.createScrollPane(myLayeredPane);
|
||||
myScrollPane.setBackground(Color.WHITE);
|
||||
panel.add(myScrollPane, gbc);
|
||||
myHorzCaptionPanel.attachToScrollPane(myScrollPane);
|
||||
myVertCaptionPanel.attachToScrollPane(myScrollPane);
|
||||
|
||||
myValidCard.add(panel, BorderLayout.CENTER);
|
||||
|
||||
@@ -319,7 +321,7 @@ public final class GuiEditor extends JPanel implements DataProvider {
|
||||
myPsiTreeChangeListener = new MyPsiTreeChangeListener();
|
||||
PsiManager.getInstance(module.getProject()).addPsiTreeChangeListener(myPsiTreeChangeListener);
|
||||
|
||||
myQuickFixManager = new QuickFixManagerImpl(this, myGlassLayer, scrollPane.getViewport());
|
||||
myQuickFixManager = new QuickFixManagerImpl(this, myGlassLayer, myScrollPane.getViewport());
|
||||
|
||||
myDropTargetListener = new DesignDropTargetListener(this);
|
||||
if (!ApplicationManager.getApplication().isHeadlessEnvironment()) {
|
||||
@@ -987,7 +989,9 @@ public final class GuiEditor extends JPanel implements DataProvider {
|
||||
width += 50;
|
||||
height += 40;
|
||||
|
||||
return new Dimension(width, height);
|
||||
Rectangle bounds = myScrollPane.getViewport().getBounds();
|
||||
|
||||
return new Dimension(Math.max(width, bounds.width), Math.max(height, bounds.height));
|
||||
}
|
||||
|
||||
public Dimension getPreferredScrollableViewportSize() {
|
||||
|
||||
Reference in New Issue
Block a user