mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
Merge branch 'master' of git.labs.intellij.net:idea/community
This commit is contained in:
@@ -302,7 +302,6 @@ def layoutFull(String home, String targetDirectory) {
|
||||
|
||||
|
||||
fileset(dir: "$home/plugins/groovy/resources/conf")
|
||||
fileset(dir: "${home}/plugins/groovy/lib")
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -18,15 +18,8 @@ package com.intellij.codeInspection.inferNullity;
|
||||
import com.intellij.codeInsight.AnnotationUtil;
|
||||
import com.intellij.codeInsight.NullableNotNullManager;
|
||||
import com.intellij.codeInsight.intention.AddAnnotationFix;
|
||||
import com.intellij.notification.Notification;
|
||||
import com.intellij.notification.NotificationDisplayType;
|
||||
import com.intellij.notification.NotificationType;
|
||||
import com.intellij.notification.Notifications;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.ui.Messages;
|
||||
import com.intellij.openapi.ui.popup.JBPopupFactory;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.search.LocalSearchScope;
|
||||
import com.intellij.psi.search.searches.OverridingMethodsSearch;
|
||||
@@ -43,16 +36,12 @@ import java.util.Collection;
|
||||
import java.util.HashSet;
|
||||
|
||||
public class NullityInferrer {
|
||||
private static final Logger LOG = Logger.getInstance("#" + NullityInferrer.class.getName());
|
||||
|
||||
private static final int MAX_PASSES = 10;
|
||||
private int numAnnotationsAdded = 0;
|
||||
private final HashSet<SmartPsiElementPointer<? extends PsiModifierListOwner>> myNotNullSet =
|
||||
new HashSet<SmartPsiElementPointer<? extends PsiModifierListOwner>>();
|
||||
private final HashSet<SmartPsiElementPointer<? extends PsiModifierListOwner>> myNullableSet =
|
||||
new HashSet<SmartPsiElementPointer<? extends PsiModifierListOwner>>();
|
||||
private boolean myAnnotateLocalVariables;
|
||||
private SmartPointerManager myPointerManager;
|
||||
private final HashSet<SmartPsiElementPointer<? extends PsiModifierListOwner>> myNotNullSet = new HashSet<SmartPsiElementPointer<? extends PsiModifierListOwner>>();
|
||||
private final HashSet<SmartPsiElementPointer<? extends PsiModifierListOwner>> myNullableSet = new HashSet<SmartPsiElementPointer<? extends PsiModifierListOwner>>();
|
||||
private final boolean myAnnotateLocalVariables;
|
||||
private final SmartPointerManager myPointerManager;
|
||||
|
||||
|
||||
public NullityInferrer(boolean annotateLocalVariables, Project project) {
|
||||
@@ -260,11 +249,7 @@ public class NullityInferrer {
|
||||
@Override
|
||||
public void visitMethodCallExpression(@NotNull PsiMethodCallExpression expression) {
|
||||
final PsiMethod method = expression.resolveMethod();
|
||||
if (method == null) {
|
||||
neverNull = false;
|
||||
} else {
|
||||
neverNull = isNotNull(method);
|
||||
}
|
||||
neverNull = method != null && isNotNull(method);
|
||||
}
|
||||
|
||||
private boolean isNeverNull() {
|
||||
|
||||
@@ -154,7 +154,7 @@ public class RefClassImpl extends RefJavaElementImpl implements RefClass {
|
||||
}
|
||||
}
|
||||
|
||||
if (getConstructors().size() == 0 && !isInterface() && !isAnonymous()) {
|
||||
if (getConstructors().isEmpty() && !isInterface() && !isAnonymous()) {
|
||||
RefImplicitConstructorImpl refImplicitConstructor = new RefImplicitConstructorImpl(this);
|
||||
setDefaultConstructor(refImplicitConstructor);
|
||||
addConstructor(refImplicitConstructor);
|
||||
@@ -173,7 +173,12 @@ public class RefClassImpl extends RefJavaElementImpl implements RefClass {
|
||||
final PsiClass applet = getRefJavaManager().getApplet();
|
||||
setApplet(applet != null && psiClass.isInheritor(applet, true));
|
||||
getRefManager().fireNodeInitialized(this);
|
||||
getRefManager().getPsiManager().dropResolveCaches();
|
||||
PsiManager psiManager = getRefManager().getPsiManager();
|
||||
psiManager.dropResolveCaches();
|
||||
PsiFile file = psiClass.getContainingFile();
|
||||
if (file != null) {
|
||||
psiManager.dropFileCaches(file);
|
||||
}
|
||||
}
|
||||
|
||||
private void initializeSuperReferences(PsiClass psiClass) {
|
||||
@@ -434,7 +439,7 @@ public class RefClassImpl extends RefJavaElementImpl implements RefClass {
|
||||
if (super.isReferenced()) return true;
|
||||
|
||||
if (isInterface() || isAbstract()) {
|
||||
if (getSubClasses().size() > 0) return true;
|
||||
if (!getSubClasses().isEmpty()) return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
@@ -444,7 +449,7 @@ public class RefClassImpl extends RefJavaElementImpl implements RefClass {
|
||||
if (super.hasSuspiciousCallers()) return true;
|
||||
|
||||
if (isInterface() || isAbstract()) {
|
||||
if (getSubClasses().size() > 0) return true;
|
||||
if (!getSubClasses().isEmpty()) return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
@@ -37,7 +37,7 @@ import com.intellij.psi.JavaDirectoryService;
|
||||
import com.intellij.psi.PsiClass;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.PsiJavaFile;
|
||||
import com.intellij.testFramework.IdeaTestUtil;
|
||||
import com.intellij.testFramework.PlatformTestUtil;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.io.IOException;
|
||||
@@ -56,16 +56,16 @@ public class NavigateFromSourceTest extends BaseProjectViewTestCase {
|
||||
|
||||
checkNavigateFromSourceBehaviour(psiClass, virtualFile, pane);
|
||||
|
||||
IdeaTestUtil.assertTreeEqual(pane.getTree(), "-Project\n" +
|
||||
" -PsiDirectory: showClassMembers\n" +
|
||||
" -PsiDirectory: src\n" +
|
||||
" -PsiDirectory: com\n" +
|
||||
" -PsiDirectory: package1\n" +
|
||||
" [Class1]\n" +
|
||||
" Class2\n" +
|
||||
getRootFiles() +
|
||||
" +External Libraries\n"
|
||||
, true);
|
||||
PlatformTestUtil.assertTreeEqual(pane.getTree(), "-Project\n" +
|
||||
" -PsiDirectory: showClassMembers\n" +
|
||||
" -PsiDirectory: src\n" +
|
||||
" -PsiDirectory: com\n" +
|
||||
" -PsiDirectory: package1\n" +
|
||||
" [Class1]\n" +
|
||||
" Class2\n" +
|
||||
getRootFiles() +
|
||||
" +External Libraries\n"
|
||||
, true);
|
||||
|
||||
changeClassTextAndTryToNavigate("class Class11 {}", (PsiJavaFile)containingFile, pane, "-Project\n" +
|
||||
" -PsiDirectory: showClassMembers\n" +
|
||||
@@ -102,19 +102,20 @@ public class NavigateFromSourceTest extends BaseProjectViewTestCase {
|
||||
assertEquals(1, tree.getSelectionCount());
|
||||
}
|
||||
|
||||
private void changeClassTextAndTryToNavigate(final String newClassString,
|
||||
PsiJavaFile psiFile,
|
||||
final AbstractProjectViewPSIPane pane,
|
||||
final String expected) throws IOException, InterruptedException {
|
||||
private static void changeClassTextAndTryToNavigate(final String newClassString,
|
||||
PsiJavaFile psiFile,
|
||||
final AbstractProjectViewPSIPane pane,
|
||||
final String expected) throws IOException, InterruptedException {
|
||||
PsiClass psiClass = psiFile.getClasses()[0];
|
||||
final VirtualFile virtualFile = psiClass.getContainingFile().getVirtualFile();
|
||||
final JTree tree = pane.getTree();
|
||||
writeToFile(virtualFile, newClassString.getBytes());
|
||||
|
||||
IdeaTestUtil.waitForAlarm(600);
|
||||
PlatformTestUtil.waitForAlarm(600);
|
||||
|
||||
psiClass = psiFile.getClasses()[0];
|
||||
pane.select(psiClass, virtualFile, true);
|
||||
IdeaTestUtil.assertTreeEqual(tree, expected, true);
|
||||
PlatformTestUtil.assertTreeEqual(tree, expected, true);
|
||||
}
|
||||
|
||||
private static void writeToFile(final VirtualFile virtualFile, final byte[] b) throws IOException {
|
||||
|
||||
+9
-1
@@ -19,6 +19,7 @@ import com.intellij.openapi.application.Result;
|
||||
import com.intellij.openapi.command.WriteCommandAction;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.impl.PsiModificationTrackerImpl;
|
||||
import com.intellij.psi.search.ProjectScope;
|
||||
import com.intellij.testFramework.fixtures.IdeaProjectTestFixture;
|
||||
import com.intellij.testFramework.fixtures.JavaCodeInsightTestFixture;
|
||||
@@ -51,7 +52,7 @@ public class JavaCodeInsightTestFixtureImpl extends CodeInsightTestFixtureImpl i
|
||||
return psiClass;
|
||||
}
|
||||
|
||||
private PsiClass addClass(@NonNls final String rootPath, @NotNull @NonNls final String classText) throws IOException {
|
||||
private PsiClass addClass(@NonNls final String rootPath, @NotNull @NonNls final String classText) {
|
||||
final PsiClass aClass = ((PsiJavaFile)PsiFileFactory.getInstance(getProject()).createFileFromText("a.java", classText)).getClasses()[0];
|
||||
final String qName = aClass.getQualifiedName();
|
||||
assert qName != null;
|
||||
@@ -65,6 +66,13 @@ public class JavaCodeInsightTestFixtureImpl extends CodeInsightTestFixtureImpl i
|
||||
return ((PsiJavaFile)psiFile).getClasses()[0];
|
||||
}
|
||||
|
||||
@Override
|
||||
protected PsiFile addFileToProject(String rootPath, String relativePath, String fileText) {
|
||||
PsiFile file = super.addFileToProject(rootPath, relativePath, fileText);
|
||||
((PsiModificationTrackerImpl)PsiManager.getInstance(getProject()).getModificationTracker()).incCounter();
|
||||
return file;
|
||||
}
|
||||
|
||||
@Override
|
||||
@NotNull
|
||||
public PsiClass findClass(@NotNull @NonNls final String name) {
|
||||
|
||||
+29
-33
@@ -125,22 +125,21 @@ public class ExtensionPointImpl<T> implements ExtensionPoint<T> {
|
||||
private void internalRegisterExtension(T extension, ExtensionComponentAdapter adapter, int index, boolean runNotifications) {
|
||||
if (myExtensions.contains(extension)) {
|
||||
myLogger.error("Extension was already added: " + extension);
|
||||
return;
|
||||
}
|
||||
else {
|
||||
myExtensions.add(index, extension);
|
||||
myLoadedAdapters.add(index, adapter);
|
||||
if (runNotifications) {
|
||||
if (extension instanceof Extension) {
|
||||
try {
|
||||
((Extension)extension).extensionAdded(this);
|
||||
}
|
||||
catch (Throwable e) {
|
||||
myLogger.error(e);
|
||||
}
|
||||
myExtensions.add(index, extension);
|
||||
myLoadedAdapters.add(index, adapter);
|
||||
if (runNotifications) {
|
||||
if (extension instanceof Extension) {
|
||||
try {
|
||||
((Extension)extension).extensionAdded(this);
|
||||
}
|
||||
catch (Throwable e) {
|
||||
myLogger.error(e);
|
||||
}
|
||||
|
||||
notifyListenersOnAdd(extension, adapter.getPluginDescriptor());
|
||||
}
|
||||
|
||||
notifyListenersOnAdd(extension, adapter.getPluginDescriptor());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -163,31 +162,28 @@ public class ExtensionPointImpl<T> implements ExtensionPoint<T> {
|
||||
result = myExtensionsCache;
|
||||
if (result == null) {
|
||||
processAdapters();
|
||||
List<T> extensions = new ArrayList<T>(myExtensions);
|
||||
|
||||
List<T> problemExtensions = new ArrayList<T>();
|
||||
|
||||
final Class<T> extensionClass = getExtensionClass();
|
||||
for (Iterator<T> iterator = extensions.iterator(); iterator.hasNext();) {
|
||||
T t = iterator.next();
|
||||
//noinspection unchecked
|
||||
result = myExtensions.toArray((T[])Array.newInstance(extensionClass, myExtensions.size()));
|
||||
|
||||
for (int i = result.length - 1; i >= 0; i--) {
|
||||
T t = result[i];
|
||||
if (i > 0 && result[i] == result[i - 1]) {
|
||||
LOG.error("Duplicate extension found: " + t + "; " +
|
||||
" Result: "+ Arrays.asList(result)+";\n" +
|
||||
" extensions: "+ myExtensions+";\n" +
|
||||
" getExtensionClass(): "+ extensionClass +";\n" +
|
||||
" size:"+myExtensions.size()+";"+result.length);
|
||||
}
|
||||
|
||||
if (!extensionClass.isAssignableFrom(t.getClass())) {
|
||||
problemExtensions.add(t);
|
||||
iterator.remove();
|
||||
LOG.error("Extension '" + t.getClass() + "' must be an instance of '" + extensionClass + "'",
|
||||
new ExtensionException(t.getClass()));
|
||||
result = ArrayUtil.remove(result, i); // we assume that usually all extensions are OK
|
||||
}
|
||||
}
|
||||
|
||||
for (T problemExtension : problemExtensions) {
|
||||
LOG.error("Extension '" + problemExtension.getClass() + "' should be instance of '" + extensionClass + "'", new ExtensionException(problemExtension.getClass()));
|
||||
}
|
||||
|
||||
//noinspection unchecked
|
||||
myExtensionsCache = result = extensions.toArray((T[])Array.newInstance(extensionClass, extensions.size()));
|
||||
for (int i = 1; i < result.length; i++) {
|
||||
assert result[i] != result[i - 1] : "Result: "+ Arrays.asList(result)+";\n" +
|
||||
" extensions: "+ extensions+";\n" +
|
||||
" getExtensionClass(): "+ extensionClass +";\n" +
|
||||
" size:"+extensions.size()+";"+result.length;
|
||||
}
|
||||
myExtensionsCache = result;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -341,18 +341,23 @@ public class AnalysisScope {
|
||||
if (needReadAction) {
|
||||
PsiDocumentManager.getInstance(psiManager.getProject()).commitAndRunReadAction(new Runnable(){
|
||||
public void run() {
|
||||
file.accept(visitor);
|
||||
psiManager.dropResolveCaches();
|
||||
doProcessFile(visitor, psiManager, file);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
file.accept(visitor);
|
||||
psiManager.dropResolveCaches();
|
||||
}
|
||||
else {
|
||||
doProcessFile(visitor, psiManager, file);
|
||||
}
|
||||
final ProgressIndicator indicator = ProgressManager.getInstance().getProgressIndicator();
|
||||
return indicator == null || !indicator.isCanceled();
|
||||
}
|
||||
|
||||
private static void doProcessFile(PsiElementVisitor visitor, PsiManager psiManager, PsiFile file) {
|
||||
file.accept(visitor);
|
||||
psiManager.dropResolveCaches();
|
||||
psiManager.dropFileCaches(file);
|
||||
}
|
||||
|
||||
protected void accept(@NotNull final PsiDirectory dir, @NotNull final PsiElementVisitor visitor, final boolean needReadAction) {
|
||||
final Project project = dir.getProject();
|
||||
final PsiManager psiManager = PsiManager.getInstance(project);
|
||||
|
||||
@@ -33,7 +33,6 @@ import org.jetbrains.annotations.Nullable;
|
||||
* The main entry point for accessing the PSI services for a project.
|
||||
*/
|
||||
public abstract class PsiManager extends UserDataHolderBase {
|
||||
|
||||
/**
|
||||
* Returns the PSI manager instance for the specified project.
|
||||
*
|
||||
@@ -239,4 +238,5 @@ public abstract class PsiManager extends UserDataHolderBase {
|
||||
|
||||
public abstract void unregisterLanguageInjector(@NotNull LanguageInjector injector);
|
||||
|
||||
public abstract void dropFileCaches(@NotNull PsiFile file);
|
||||
}
|
||||
|
||||
+4
-1
@@ -82,7 +82,7 @@ public class GlobalInspectionContextImpl implements GlobalInspectionContext {
|
||||
|
||||
private ProgressIndicator myProgressIndicator;
|
||||
public static final JobDescriptor BUILD_GRAPH = new JobDescriptor(InspectionsBundle.message("inspection.processing.job.descriptor"));
|
||||
public static final JobDescriptor[] BUILD_GRAPH_ONLY = new JobDescriptor[]{BUILD_GRAPH};
|
||||
public static final JobDescriptor[] BUILD_GRAPH_ONLY = {BUILD_GRAPH};
|
||||
public static final JobDescriptor FIND_EXTERNAL_USAGES =
|
||||
new JobDescriptor(InspectionsBundle.message("inspection.processing.job.descriptor1"));
|
||||
|
||||
@@ -557,6 +557,9 @@ public class GlobalInspectionContextImpl implements GlobalInspectionContext {
|
||||
catch (Exception e) {
|
||||
LOG.error(e);
|
||||
}
|
||||
finally {
|
||||
psiManager.dropFileCaches(file);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@@ -373,6 +373,7 @@ public class RefManagerImpl extends RefManager {
|
||||
visitElement(viewProvider.getPsi(language));
|
||||
}
|
||||
myPsiManager.dropResolveCaches();
|
||||
myPsiManager.dropFileCaches(file);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -362,7 +362,7 @@ public class FindUsagesManager implements JDOMExternalizable {
|
||||
return processor.process(UsageInfoToUsageConverter.convert(descriptor, usageInfo));
|
||||
}
|
||||
});
|
||||
List<? extends PsiElement> elements =
|
||||
final List<? extends PsiElement> elements =
|
||||
ApplicationManager.getApplication().runReadAction(new Computable<List<? extends PsiElement>>() {
|
||||
public List<? extends PsiElement> compute() {
|
||||
return descriptor.getAllElements();
|
||||
@@ -381,7 +381,12 @@ public class FindUsagesManager implements JDOMExternalizable {
|
||||
handler.processElementUsages(element, usageInfoProcessor, options);
|
||||
}
|
||||
|
||||
PsiManager.getInstance(handler.getProject()).getSearchHelper().processRequests(options.fastTrack, new ReadActionProcessor<PsiReference>() {
|
||||
Project project = ApplicationManager.getApplication().runReadAction(new Computable<Project>() {
|
||||
public Project compute() {
|
||||
return scopeFile != null ? scopeFile.getProject() : !elements.isEmpty() ? elements.get(0).getProject() : handler.getProject();
|
||||
}
|
||||
});
|
||||
PsiManager.getInstance(project).getSearchHelper().processRequests(options.fastTrack, new ReadActionProcessor<PsiReference>() {
|
||||
public boolean processInReadAction(final PsiReference ref) {
|
||||
TextRange rangeInElement = ref.getRangeInElement();
|
||||
return usageInfoProcessor.process(new UsageInfo(ref.getElement(), rangeInElement.getStartOffset(), rangeInElement.getEndOffset(), false));
|
||||
|
||||
@@ -269,12 +269,7 @@ public class FindInProjectUtil {
|
||||
String message = "<html><body>";
|
||||
if (largeFiles.size() == 1) {
|
||||
final VirtualFile vFile = largeFiles.iterator().next().getVirtualFile();
|
||||
message
|
||||
+= "File '"
|
||||
+ getPresentablePath(vFile)
|
||||
+ "' ("
|
||||
+ presentableSize(getFileLength(vFile))
|
||||
+ ") is ";
|
||||
message += "File " + presentableFileInfo(vFile) + " is ";
|
||||
}
|
||||
else {
|
||||
message += "Files<br> ";
|
||||
@@ -282,11 +277,7 @@ public class FindInProjectUtil {
|
||||
int counter = 0;
|
||||
for (PsiFile file : largeFiles) {
|
||||
final VirtualFile vFile = file.getVirtualFile();
|
||||
message +=
|
||||
getPresentablePath(vFile)
|
||||
+ " ("
|
||||
+ presentableSize(getFileLength(vFile))
|
||||
+ ")<br> ";
|
||||
message += presentableFileInfo(vFile) + "<br> ";
|
||||
if (counter++ > 10) break;
|
||||
}
|
||||
|
||||
@@ -312,6 +303,13 @@ public class FindInProjectUtil {
|
||||
}
|
||||
}
|
||||
|
||||
private static String presentableFileInfo(VirtualFile vFile) {
|
||||
return getPresentablePath(vFile)
|
||||
+ " ("
|
||||
+ presentableSize(getFileLength(vFile))
|
||||
+ ")";
|
||||
}
|
||||
|
||||
private static int processUsagesInFile(final PsiFile psiFile,
|
||||
final FindModel findModel,
|
||||
final Processor<UsageInfo> consumer) {
|
||||
@@ -339,11 +337,11 @@ public class FindInProjectUtil {
|
||||
}
|
||||
|
||||
private static String getPresentablePath(final VirtualFile virtualFile) {
|
||||
return ApplicationManager.getApplication().runReadAction(new Computable<String>() {
|
||||
return "'" + ApplicationManager.getApplication().runReadAction(new Computable<String>() {
|
||||
public String compute() {
|
||||
return virtualFile.getPresentableUrl();
|
||||
}
|
||||
});
|
||||
}) + "'";
|
||||
}
|
||||
|
||||
private static String presentableSize(long bytes) {
|
||||
@@ -434,9 +432,8 @@ public class FindInProjectUtil {
|
||||
final FileTypeManager fileTypeManager = FileTypeManager.getInstance();
|
||||
final VirtualFileFilter contentFilter = new VirtualFileFilter() {
|
||||
public boolean accept(final VirtualFile file) {
|
||||
if (file.isDirectory()) return true;
|
||||
if (fileTypeManager.isFileIgnored(file) || fileTypeManager.getFileTypeByFile(file).isBinary()) return false;
|
||||
return searchScope.contains(file);
|
||||
return file.isDirectory() ||
|
||||
!fileTypeManager.isFileIgnored(file) && !fileTypeManager.getFileTypeByFile(file).isBinary() && searchScope.contains(file);
|
||||
}
|
||||
};
|
||||
for (VirtualFile file : files) {
|
||||
@@ -567,8 +564,7 @@ public class FindInProjectUtil {
|
||||
|
||||
private static boolean canOptimizeForFastWordSearch(final FindModel findModel) {
|
||||
return !findModel.isRegularExpressions()
|
||||
&& (findModel.getCustomScope() == null || findModel.getCustomScope() instanceof GlobalSearchScope)
|
||||
;
|
||||
&& (findModel.getCustomScope() == null || findModel.getCustomScope() instanceof GlobalSearchScope);
|
||||
}
|
||||
|
||||
private static int addToUsages(@NotNull Document document, @NotNull Processor<UsageInfo> consumer, @NotNull FindModel findModel,
|
||||
@@ -588,7 +584,7 @@ public class FindInProjectUtil {
|
||||
if (!result.isStringFound()) break;
|
||||
|
||||
UsageInfo info = new UsageInfo(psiFile, result.getStartOffset(), result.getEndOffset());
|
||||
consumer.process(info);
|
||||
if (!consumer.process(info)) break;
|
||||
count++;
|
||||
|
||||
final int prevOffset = offset;
|
||||
|
||||
+9
-6
@@ -51,11 +51,15 @@ public class ScriptingLibraryMappings extends LanguagePerFileMappings<ScriptingL
|
||||
public ScriptingLibraryMappings(final Project project, final LibraryType libraryType) {
|
||||
super(project);
|
||||
myLibraryManager = new ScriptingLibraryManager(project, libraryType);
|
||||
registerLibraryTableListener(this, this);
|
||||
Disposer.register(project, this);
|
||||
}
|
||||
|
||||
public void registerLibraryTableListener(LibraryTable.Listener listener, Disposable parentDisposable) {
|
||||
if (myLibraryManager.ensureModel()) {
|
||||
LibraryTable libTable = myLibraryManager.getLibraryTable();
|
||||
if (libTable != null) libTable.addListener(this, this);
|
||||
if (libTable != null) libTable.addListener(listener, parentDisposable);
|
||||
}
|
||||
Disposer.register(project, this);
|
||||
}
|
||||
|
||||
protected String serialize(final ScriptingLibraryTable.LibraryModel library) {
|
||||
@@ -91,7 +95,6 @@ public class ScriptingLibraryMappings extends LanguagePerFileMappings<ScriptingL
|
||||
newContainer.addLibrary(libraryModel);
|
||||
}
|
||||
}
|
||||
newContainer.applyChanges();
|
||||
setMapping(file, newContainer.isEmpty() ? null : newContainer);
|
||||
if (!newContainer.isEmpty()) {
|
||||
if (file == null) {
|
||||
@@ -182,7 +185,7 @@ public class ScriptingLibraryMappings extends LanguagePerFileMappings<ScriptingL
|
||||
container = new CompoundLibrary();
|
||||
}
|
||||
if (!((CompoundLibrary)container).containsLibrary(libName)) {
|
||||
((CompoundLibrary)container).toggleLibrary(libraryModel);
|
||||
((CompoundLibrary)container).addLibrary(libraryModel);
|
||||
setMapping(file, container);
|
||||
}
|
||||
updateDependencies(getMappings());
|
||||
@@ -210,10 +213,9 @@ public class ScriptingLibraryMappings extends LanguagePerFileMappings<ScriptingL
|
||||
for (String libName : libNames) {
|
||||
ScriptingLibraryTable.LibraryModel libraryModel = myLibraryManager.getLibraryByName(libName.trim());
|
||||
if (libraryModel != null) {
|
||||
compoundLib.toggleLibrary(libraryModel);
|
||||
compoundLib.addLibrary(libraryModel);
|
||||
}
|
||||
}
|
||||
compoundLib.applyChanges();
|
||||
if (file == null) {
|
||||
myProjectLibs = compoundLib;
|
||||
}
|
||||
@@ -331,6 +333,7 @@ public class ScriptingLibraryMappings extends LanguagePerFileMappings<ScriptingL
|
||||
private void addLibrary(@NotNull ScriptingLibraryTable.LibraryModel library) {
|
||||
final String libName = library.getName();
|
||||
myLibraries.put(libName, library);
|
||||
applyChanges();
|
||||
}
|
||||
|
||||
public boolean containsLibrary(String libName) {
|
||||
|
||||
+31
-1
@@ -18,9 +18,13 @@ package com.intellij.ide.scriptingContext.ui;
|
||||
import com.intellij.ide.IdeBundle;
|
||||
import com.intellij.ide.scriptingContext.LangScriptingContextConfigurable;
|
||||
import com.intellij.ide.scriptingContext.ScriptingLibraryMappings;
|
||||
import com.intellij.openapi.Disposable;
|
||||
import com.intellij.openapi.options.ConfigurationException;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.roots.libraries.Library;
|
||||
import com.intellij.openapi.roots.libraries.LibraryTable;
|
||||
import com.intellij.openapi.roots.libraries.scripting.ScriptingLibraryTable;
|
||||
import com.intellij.openapi.util.Disposer;
|
||||
import com.intellij.openapi.util.IconLoader;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.util.ui.tree.LanguagePerFileConfigurable;
|
||||
@@ -33,7 +37,9 @@ import java.util.Map;
|
||||
/**
|
||||
* @author Rustam Vishnyakov
|
||||
*/
|
||||
public class ScriptingContextsConfigurable extends LanguagePerFileConfigurable<ScriptingLibraryTable.LibraryModel> {
|
||||
public class ScriptingContextsConfigurable extends LanguagePerFileConfigurable<ScriptingLibraryTable.LibraryModel>
|
||||
implements LibraryTable.Listener,
|
||||
Disposable {
|
||||
|
||||
private final ScriptingLibraryMappings myScriptingLibraryMappings;
|
||||
private final LangScriptingContextConfigurable myParent;
|
||||
@@ -46,6 +52,8 @@ public class ScriptingContextsConfigurable extends LanguagePerFileConfigurable<S
|
||||
IdeBundle.message("scripting.lib.usageScope.override.title"));
|
||||
myScriptingLibraryMappings = mappings;
|
||||
myParent = parent;
|
||||
mappings.registerLibraryTableListener(this, this);
|
||||
Disposer.register(project, this);
|
||||
}
|
||||
|
||||
public void resetMappings() {
|
||||
@@ -115,4 +123,26 @@ public class ScriptingContextsConfigurable extends LanguagePerFileConfigurable<S
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void dispose() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterLibraryAdded(Library newLibrary) {
|
||||
reset();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterLibraryRenamed(Library library) {
|
||||
reset();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void beforeLibraryRemoved(Library library) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterLibraryRemoved(Library library) {
|
||||
reset();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -109,20 +109,20 @@ public class EditorWindow extends UserDataHolderBase implements EditorEx {
|
||||
if (!editorWindow.isValid()/* || myDocumentWindow.intersects(editorWindow.myDocumentWindow)*/) {
|
||||
editorWindow.dispose();
|
||||
|
||||
InjectedLanguageUtil.clearCaches(editorWindow.getInjectedFile());
|
||||
InjectedLanguageUtil.clearCaches(editorWindow.myInjectedFile, editorWindow.getDocument());
|
||||
iterator.remove();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isValid() {
|
||||
return !isDisposed() && myInjectedFile.isValid() && myDocumentWindow.isValid();
|
||||
return !isDisposed() && !myInjectedFile.getProject().isDisposed() && myInjectedFile.isValid() && myDocumentWindow.isValid();
|
||||
}
|
||||
|
||||
public PsiFile getInjectedFile() {
|
||||
return myInjectedFile;
|
||||
}
|
||||
public LogicalPosition hostToInjected(LogicalPosition pos) {
|
||||
public LogicalPosition hostToInjected(@NotNull LogicalPosition pos) {
|
||||
assert isValid();
|
||||
int offsetInInjected = myDocumentWindow.hostToInjected(myDelegate.logicalPositionToOffset(pos));
|
||||
return offsetToLogicalPosition(offsetInInjected);
|
||||
|
||||
@@ -186,6 +186,10 @@ public class MockPsiManager extends PsiManagerEx {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void dropFileCaches(@NotNull PsiFile file) {
|
||||
}
|
||||
|
||||
public void postponeAutoFormattingInside(Runnable runnable) {
|
||||
PostprocessReformattingAspect.getInstance(getProject()).postponeFormattingInside(runnable);
|
||||
}
|
||||
@@ -222,9 +226,6 @@ public class MockPsiManager extends PsiManagerEx {
|
||||
public void registerRunnableToRunOnChange(@NotNull Runnable runnable) {
|
||||
}
|
||||
|
||||
public void registerWeakRunnableToRunOnChange(@NotNull Runnable runnable) {
|
||||
}
|
||||
|
||||
public void registerRunnableToRunOnAnyChange(@NotNull Runnable runnable) {
|
||||
}
|
||||
|
||||
|
||||
+1
@@ -113,6 +113,7 @@ public class BackwardDependenciesBuilder extends DependenciesBuilder {
|
||||
}
|
||||
}
|
||||
psiManager.dropResolveCaches();
|
||||
psiManager.dropFileCaches(file);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
+1
@@ -138,6 +138,7 @@ public class ForwardDependenciesBuilder extends DependenciesBuilder {
|
||||
collectedDeps.addAll(found);
|
||||
|
||||
psiManager.dropResolveCaches();
|
||||
psiManager.dropFileCaches(file);
|
||||
}
|
||||
}
|
||||
collectedDeps.removeAll(processed);
|
||||
|
||||
@@ -0,0 +1,21 @@
|
||||
/*
|
||||
* Copyright 2000-2011 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.psi.impl;
|
||||
|
||||
public interface AnyPsiChangeListener {
|
||||
void beforePsiChanged(boolean isPhysical);
|
||||
void afterPsiChanged(boolean isPhysical);
|
||||
}
|
||||
@@ -46,8 +46,6 @@ public abstract class PsiManagerEx extends PsiManager {
|
||||
*/
|
||||
public abstract void registerRunnableToRunOnChange(@NotNull Runnable runnable);
|
||||
|
||||
public abstract void registerWeakRunnableToRunOnChange(@NotNull Runnable runnable);
|
||||
|
||||
/**
|
||||
* @param runnable to be run before <b>physical</b> or <b>non-physical</b> PSI change
|
||||
*/
|
||||
|
||||
@@ -53,6 +53,7 @@ import com.intellij.psi.impl.source.PostprocessReformattingAspect;
|
||||
import com.intellij.psi.impl.source.PsiFileImpl;
|
||||
import com.intellij.psi.impl.source.resolve.ResolveCache;
|
||||
import com.intellij.psi.impl.source.tree.injected.InjectedLanguageManagerImpl;
|
||||
import com.intellij.psi.impl.source.tree.injected.InjectedLanguageUtil;
|
||||
import com.intellij.psi.search.PsiSearchHelper;
|
||||
import com.intellij.psi.util.CachedValuesManager;
|
||||
import com.intellij.psi.util.PsiModificationTracker;
|
||||
@@ -61,12 +62,13 @@ import com.intellij.testFramework.LightVirtualFile;
|
||||
import com.intellij.util.IncorrectOperationException;
|
||||
import com.intellij.util.ThrowableRunnable;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import com.intellij.util.messages.MessageBus;
|
||||
import com.intellij.util.messages.Topic;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.jetbrains.annotations.TestOnly;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.lang.ref.WeakReference;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.atomic.AtomicInteger;
|
||||
|
||||
@@ -76,6 +78,7 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
private static final Logger LOG = Logger.getInstance("#com.intellij.psi.impl.PsiManagerImpl");
|
||||
|
||||
private final Project myProject;
|
||||
private final MessageBus myMessageBus;
|
||||
|
||||
private final FileManager myFileManager;
|
||||
private final PsiSearchHelperImpl mySearchHelper;
|
||||
@@ -94,11 +97,6 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
private final List<PsiTreeChangeListener> myTreeChangeListeners = ContainerUtil.createEmptyCOWList();
|
||||
private boolean myTreeChangeEventIsFiring = false;
|
||||
|
||||
private final List<Runnable> myRunnablesOnChange = ContainerUtil.createEmptyCOWList();
|
||||
private final List<WeakReference<Runnable>> myWeakRunnablesOnChange = ContainerUtil.createEmptyCOWList();
|
||||
private final List<Runnable> myRunnablesOnAnyChange = ContainerUtil.createEmptyCOWList();
|
||||
private final List<Runnable> myRunnablesAfterAnyChange = ContainerUtil.createEmptyCOWList();
|
||||
|
||||
private boolean myIsDisposed;
|
||||
|
||||
private VirtualFileFilter myAssertOnFileLoadingFilter = VirtualFileFilter.NONE;
|
||||
@@ -106,6 +104,7 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
private final AtomicInteger myBatchFilesProcessingModeCount = new AtomicInteger(0);
|
||||
|
||||
private static final Key<PsiFile> CACHED_PSI_FILE_COPY_IN_FILECONTENT = Key.create("CACHED_PSI_FILE_COPY_IN_FILECONTENT");
|
||||
public static final Topic<AnyPsiChangeListener> ANY_PSI_CHANGE_TOPIC = Topic.create("PSI_CHANGE_TOPIC",AnyPsiChangeListener.class, Topic.BroadcastDirection.TO_PARENT);
|
||||
|
||||
private final List<LanguageInjector> myLanguageInjectors = ContainerUtil.createEmptyCOWList();
|
||||
|
||||
@@ -114,8 +113,9 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
StartupManager startupManager,
|
||||
FileTypeManager fileTypeManager,
|
||||
FileDocumentManager fileDocumentManager,
|
||||
PsiBuilderFactory psiBuilderFactory) {
|
||||
PsiBuilderFactory psiBuilderFactory, MessageBus messageBus) {
|
||||
myProject = project;
|
||||
myMessageBus = messageBus;
|
||||
|
||||
//We need to initialize PsiBuilderFactory service so it won't initialize under PsiLock from ChameleonTransform
|
||||
@SuppressWarnings({"UnusedDeclaration", "UnnecessaryLocalVariable"}) Object used = psiBuilderFactory;
|
||||
@@ -175,6 +175,11 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
nonPhysicalChange();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void dropFileCaches(@NotNull PsiFile file) {
|
||||
InjectedLanguageUtil.clearCachedInjectedFragmentsForFile(file);
|
||||
}
|
||||
|
||||
public boolean isInProject(@NotNull PsiElement element) {
|
||||
PsiFile file = element.getContainingFile();
|
||||
if (file instanceof PsiFileImpl && file.isPhysical() && file.getViewProvider().getVirtualFile() instanceof LightVirtualFile) return true;
|
||||
@@ -368,7 +373,7 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
|
||||
@TestOnly
|
||||
public void cleanupForNextTest() {
|
||||
//myFileManager.cleanupForNextTest();
|
||||
myFileManager.cleanupForNextTest();
|
||||
LOG.assertTrue(ApplicationManager.getApplication().isUnitTestMode());
|
||||
}
|
||||
|
||||
@@ -495,7 +500,7 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
}
|
||||
|
||||
public void childAdded(PsiTreeChangeEventImpl event) {
|
||||
onChange(true);
|
||||
beforeChange(true);
|
||||
event.setCode(CHILD_ADDED);
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug(
|
||||
@@ -504,11 +509,11 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
);
|
||||
}
|
||||
fireEvent(event);
|
||||
afterAnyChange();
|
||||
afterAnyChange(true);
|
||||
}
|
||||
|
||||
public void childRemoved(PsiTreeChangeEventImpl event) {
|
||||
onChange(true);
|
||||
beforeChange(true);
|
||||
event.setCode(CHILD_REMOVED);
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug(
|
||||
@@ -516,11 +521,11 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
);
|
||||
}
|
||||
fireEvent(event);
|
||||
afterAnyChange();
|
||||
afterAnyChange(true);
|
||||
}
|
||||
|
||||
public void childReplaced(PsiTreeChangeEventImpl event) {
|
||||
onChange(true);
|
||||
beforeChange(true);
|
||||
event.setCode(CHILD_REPLACED);
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug(
|
||||
@@ -530,11 +535,11 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
);
|
||||
}
|
||||
fireEvent(event);
|
||||
afterAnyChange();
|
||||
afterAnyChange(true);
|
||||
}
|
||||
|
||||
public void childMoved(PsiTreeChangeEventImpl event) {
|
||||
onChange(true);
|
||||
beforeChange(true);
|
||||
event.setCode(CHILD_MOVED);
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug(
|
||||
@@ -544,11 +549,11 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
);
|
||||
}
|
||||
fireEvent(event);
|
||||
afterAnyChange();
|
||||
afterAnyChange(true);
|
||||
}
|
||||
|
||||
public void childrenChanged(PsiTreeChangeEventImpl event) {
|
||||
onChange(true);
|
||||
beforeChange(true);
|
||||
event.setCode(CHILDREN_CHANGED);
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug(
|
||||
@@ -556,11 +561,11 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
);
|
||||
}
|
||||
fireEvent(event);
|
||||
afterAnyChange();
|
||||
afterAnyChange(true);
|
||||
}
|
||||
|
||||
public void propertyChanged(PsiTreeChangeEventImpl event) {
|
||||
onChange(true);
|
||||
beforeChange(true);
|
||||
event.setCode(PROPERTY_CHANGED);
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug(
|
||||
@@ -571,7 +576,7 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
);
|
||||
}
|
||||
fireEvent(event);
|
||||
afterAnyChange();
|
||||
afterAnyChange(true);
|
||||
}
|
||||
|
||||
public void addTreeChangePreprocessor(PsiTreeChangePreprocessor preprocessor) {
|
||||
@@ -658,57 +663,59 @@ public class PsiManagerImpl extends PsiManagerEx implements ProjectComponent {
|
||||
}
|
||||
}
|
||||
|
||||
public void registerRunnableToRunOnChange(@NotNull Runnable runnable) {
|
||||
myRunnablesOnChange.add(runnable);
|
||||
public void registerRunnableToRunOnChange(@NotNull final Runnable runnable) {
|
||||
myMessageBus.connect().subscribe(ANY_PSI_CHANGE_TOPIC, new AnyPsiChangeListener() {
|
||||
@Override
|
||||
public void beforePsiChanged(boolean isPhysical) {
|
||||
if (isPhysical) runnable.run();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterPsiChanged(boolean isPhysical) {
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void registerWeakRunnableToRunOnChange(@NotNull Runnable runnable) {
|
||||
myWeakRunnablesOnChange.add(new WeakReference<Runnable>(runnable));
|
||||
public void registerRunnableToRunOnAnyChange(@NotNull final Runnable runnable) { // includes non-physical changes
|
||||
myMessageBus.connect().subscribe(ANY_PSI_CHANGE_TOPIC, new AnyPsiChangeListener() {
|
||||
@Override
|
||||
public void beforePsiChanged(boolean isPhysical) {
|
||||
runnable.run();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterPsiChanged(boolean isPhysical) {
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void registerRunnableToRunOnAnyChange(@NotNull Runnable runnable) { // includes non-physical changes
|
||||
myRunnablesOnAnyChange.add(runnable);
|
||||
}
|
||||
public void registerRunnableToRunAfterAnyChange(@NotNull final Runnable runnable) { // includes non-physical changes
|
||||
myMessageBus.connect().subscribe(ANY_PSI_CHANGE_TOPIC, new AnyPsiChangeListener() {
|
||||
@Override
|
||||
public void beforePsiChanged(boolean isPhysical) {
|
||||
}
|
||||
|
||||
public void registerRunnableToRunAfterAnyChange(@NotNull Runnable runnable) { // includes non-physical changes
|
||||
myRunnablesAfterAnyChange.add(runnable);
|
||||
@Override
|
||||
public void afterPsiChanged(boolean isPhysical) {
|
||||
runnable.run();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void nonPhysicalChange() {
|
||||
onChange(false);
|
||||
beforeChange(false);
|
||||
}
|
||||
|
||||
public void physicalChange() {
|
||||
onChange(true);
|
||||
beforeChange(true);
|
||||
}
|
||||
|
||||
private void onChange(boolean isPhysical) {
|
||||
if (isPhysical) {
|
||||
runRunnables(myRunnablesOnChange);
|
||||
|
||||
WeakReference[] refs = myWeakRunnablesOnChange.toArray(new WeakReference[myWeakRunnablesOnChange.size()]);
|
||||
myWeakRunnablesOnChange.clear();
|
||||
for (WeakReference ref : refs) {
|
||||
Runnable runnable = ref != null ? (Runnable)ref.get() : null;
|
||||
if (runnable != null) {
|
||||
runnable.run();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
runRunnables(myRunnablesOnAnyChange);
|
||||
private void beforeChange(boolean isPhysical) {
|
||||
myMessageBus.syncPublisher(ANY_PSI_CHANGE_TOPIC).beforePsiChanged(isPhysical);
|
||||
}
|
||||
|
||||
private void afterAnyChange() {
|
||||
runRunnables(myRunnablesAfterAnyChange);
|
||||
}
|
||||
|
||||
private static void runRunnables(List<Runnable> runnables) {
|
||||
if (runnables.isEmpty()) return;
|
||||
//noinspection ForLoopReplaceableByForEach
|
||||
for (int i = 0; i < runnables.size(); i++) {
|
||||
runnables.get(i).run();
|
||||
}
|
||||
private void afterAnyChange(boolean isPhysical) {
|
||||
myMessageBus.syncPublisher(ANY_PSI_CHANGE_TOPIC).afterPsiChanged(isPhysical);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
+27
-1
@@ -288,12 +288,16 @@ public class InjectedLanguageUtil {
|
||||
private static final Key<List<RangeMarker>> INJECTED_REGIONS_KEY = Key.create("INJECTED_REGIONS_KEY");
|
||||
@NotNull
|
||||
public static List<DocumentWindow> getCachedInjectedDocuments(@NotNull PsiFile hostPsiFile) {
|
||||
// modification of cachedInjectedDocuments must be under PsiLock only
|
||||
List<DocumentWindow> injected = hostPsiFile.getUserData(INJECTED_DOCS_KEY);
|
||||
if (injected == null) {
|
||||
injected = ((UserDataHolderEx)hostPsiFile).putUserDataIfAbsent(INJECTED_DOCS_KEY, ContainerUtil.<DocumentWindow>createEmptyCOWList());
|
||||
}
|
||||
return injected;
|
||||
}
|
||||
public static void clearCachedInjectedFragmentsForFile(@NotNull PsiFile file) {
|
||||
file.putUserData(INJECTED_DOCS_KEY, null);
|
||||
}
|
||||
|
||||
public static void commitAllInjectedDocuments(Document hostDocument, Project project) {
|
||||
List<RangeMarker> injected = getCachedInjectedRegions(hostDocument);
|
||||
@@ -320,10 +324,32 @@ public class InjectedLanguageUtil {
|
||||
PsiDocumentManagerImpl.checkConsistency(hostPsiFile, hostDocument);
|
||||
}
|
||||
|
||||
public static void clearCaches(PsiFile injected) {
|
||||
public static void clearCaches(@NotNull PsiFile injected, @NotNull DocumentWindowImpl documentWindow) {
|
||||
VirtualFileWindow virtualFile = (VirtualFileWindow)injected.getVirtualFile();
|
||||
PsiManagerEx psiManagerEx = (PsiManagerEx)injected.getManager();
|
||||
if (psiManagerEx.isDisposed()) return;
|
||||
psiManagerEx.getFileManager().setViewProvider((VirtualFile)virtualFile, null);
|
||||
PsiElement context = injected.getContext();
|
||||
PsiFile hostFile;
|
||||
if (context != null) {
|
||||
hostFile = context.getContainingFile();
|
||||
}
|
||||
else {
|
||||
VirtualFile delegate = virtualFile.getDelegate();
|
||||
hostFile = delegate.isValid() ? psiManagerEx.findFile(delegate) : null;
|
||||
}
|
||||
if (hostFile != null) {
|
||||
// modification of cachedInjectedDocuments must be under PsiLock
|
||||
synchronized (PsiLock.LOCK) {
|
||||
List<DocumentWindow> cachedInjectedDocuments = getCachedInjectedDocuments(hostFile);
|
||||
for (int i = cachedInjectedDocuments.size() - 1; i >= 0; i--) {
|
||||
DocumentWindow cachedInjectedDocument = cachedInjectedDocuments.get(i);
|
||||
if (cachedInjectedDocument == documentWindow) {
|
||||
cachedInjectedDocuments.remove(i);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
+1
-1
@@ -235,7 +235,7 @@ public class MultiHostRegistrarImpl implements MultiHostRegistrar {
|
||||
PsiFile newFile = registerDocument(documentWindow, psiFile, place, myHostPsiFile, documentManager);
|
||||
boolean mergeHappened = newFile != psiFile;
|
||||
if (mergeHappened) {
|
||||
InjectedLanguageUtil.clearCaches(psiFile);
|
||||
InjectedLanguageUtil.clearCaches(psiFile, documentWindow);
|
||||
psiFile = newFile;
|
||||
viewProvider = (InjectedFileViewProvider)psiFile.getViewProvider();
|
||||
documentWindow = (DocumentWindowImpl)viewProvider.getDocument();
|
||||
|
||||
@@ -35,13 +35,13 @@ import java.util.Iterator;
|
||||
public class LazyRangeMarkerFactory extends AbstractProjectComponent {
|
||||
private final WeakList<LazyMarker> myMarkers = new WeakList<LazyMarker>();
|
||||
|
||||
public LazyRangeMarkerFactory(Project project, final FileDocumentManager fdm) {
|
||||
public LazyRangeMarkerFactory(Project project, final FileDocumentManager fileDocumentManager) {
|
||||
super(project);
|
||||
EditorFactory.getInstance().getEventMulticaster().addDocumentListener(new DocumentAdapter() {
|
||||
public void beforeDocumentChange(DocumentEvent e) {
|
||||
for (Iterator<LazyMarker> it = myMarkers.iterator(); it.hasNext();) {
|
||||
final LazyMarker marker = it.next();
|
||||
final VirtualFile docFile = fdm.getFile(e.getDocument());
|
||||
final VirtualFile docFile = fileDocumentManager.getFile(e.getDocument());
|
||||
if (marker.getFile() == docFile) {
|
||||
marker.ensureDelegate();
|
||||
it.remove();
|
||||
@@ -82,7 +82,7 @@ public class LazyRangeMarkerFactory extends AbstractProjectComponent {
|
||||
return marker;
|
||||
}
|
||||
|
||||
private static abstract class LazyMarker extends UserDataHolderBase implements RangeMarker{
|
||||
private abstract static class LazyMarker extends UserDataHolderBase implements RangeMarker{
|
||||
private RangeMarker myDelegate = null;
|
||||
private final VirtualFile myFile;
|
||||
protected final int myInitialOffset;
|
||||
|
||||
+1
@@ -203,6 +203,7 @@ public class ProgressIndicatorBase extends UserDataHolderBase implements Progres
|
||||
public void processFinish() {
|
||||
if (myOwnerTask != null) {
|
||||
finish(myOwnerTask);
|
||||
myOwnerTask = null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -93,7 +93,7 @@ public class FileWatcher {
|
||||
myManagingFS = ManagingFS.getInstance();
|
||||
try {
|
||||
if (!"true".equals(System.getProperty(PROPERTY_WATCHER_DISABLED))) {
|
||||
startupProcess();
|
||||
startupProcess(false);
|
||||
}
|
||||
}
|
||||
catch (IOException ignore) {
|
||||
@@ -236,7 +236,7 @@ public class FileWatcher {
|
||||
}
|
||||
|
||||
@SuppressWarnings({"IOResourceOpenedButNotSafelyClosed"})
|
||||
private void startupProcess() throws IOException {
|
||||
private void startupProcess(final boolean restart) throws IOException {
|
||||
if (isShuttingDown) return;
|
||||
|
||||
if (attemptCount++ > MAX_PROCESS_LAUNCH_ATTEMPT_COUNT) {
|
||||
@@ -260,10 +260,22 @@ public class FileWatcher {
|
||||
: PathManager.getBinPath() + File.separatorChar + executableName;
|
||||
if (!new File(pathToExecutable).canExecute()) return;
|
||||
|
||||
LOG.info("Starting file watcher: " + pathToExecutable);
|
||||
|
||||
notifierProcess = Runtime.getRuntime().exec(new String[]{pathToExecutable});
|
||||
|
||||
notifierReader = new BufferedReader(new InputStreamReader(notifierProcess.getInputStream()));
|
||||
notifierWriter = new BufferedWriter(new OutputStreamWriter(notifierProcess.getOutputStream()));
|
||||
|
||||
synchronized (LOCK) {
|
||||
if (restart && myRecursiveWatchRoots.size() + myFlatWatchRoots.size() > 0) {
|
||||
final List<String> recursiveWatchRoots = new ArrayList<String>(myRecursiveWatchRoots);
|
||||
final List<String> flatWatchRoots = new ArrayList<String>(myFlatWatchRoots);
|
||||
myRecursiveWatchRoots.clear();
|
||||
myFlatWatchRoots.clear();
|
||||
setWatchRoots(recursiveWatchRoots, flatWatchRoots);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void shutdownProcess() {
|
||||
@@ -301,7 +313,7 @@ public class FileWatcher {
|
||||
final String command = readLine();
|
||||
if (command == null) {
|
||||
// Unexpected process exit, relaunch attempt
|
||||
startupProcess();
|
||||
startupProcess(true);
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -352,7 +364,7 @@ public class FileWatcher {
|
||||
final String path = readLine();
|
||||
if (path == null) {
|
||||
// Unexpected process exit, relaunch attempt
|
||||
startupProcess();
|
||||
startupProcess(true);
|
||||
continue;
|
||||
}
|
||||
|
||||
|
||||
@@ -323,8 +323,6 @@ public class UsageViewManagerImpl extends UsageViewManager {
|
||||
if (usageView != null) {
|
||||
usageView.appendUsageLater(usage);
|
||||
}
|
||||
|
||||
if (usageCount % 100 == 0) System.out.println("usageCount = " + usageCount);
|
||||
}
|
||||
return indicator == null || !indicator.isCanceled();
|
||||
}
|
||||
|
||||
@@ -57,7 +57,7 @@ public class ModuleGroupingRule implements UsageGroupingRule {
|
||||
private static class LibraryUsageGroup implements UsageGroup {
|
||||
public static final Icon LIBRARY_ICON = IconLoader.getIcon("/nodes/ppLibOpen.png");
|
||||
|
||||
OrderEntry myEntry;
|
||||
private final OrderEntry myEntry;
|
||||
|
||||
public void update() {
|
||||
}
|
||||
|
||||
@@ -18,7 +18,6 @@ package com.intellij.util;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.Iterator;
|
||||
import java.util.Map;
|
||||
|
||||
public class EnvironmentUtil {
|
||||
@@ -27,7 +26,8 @@ public class EnvironmentUtil {
|
||||
private EnvironmentUtil() {
|
||||
}
|
||||
|
||||
public static @NonNls Map<String, String> getEnviromentProperties() {
|
||||
@NonNls
|
||||
public static Map<String, String> getEnviromentProperties() {
|
||||
return ourEnviromentProperties;
|
||||
}
|
||||
|
||||
@@ -39,8 +39,8 @@ public class EnvironmentUtil {
|
||||
Map enviroment = getEnviromentProperties();
|
||||
String[] envp = new String[enviroment.size()];
|
||||
int i = 0;
|
||||
for (Iterator iterator = enviroment.keySet().iterator(); iterator.hasNext();) {
|
||||
String name = (String)iterator.next();
|
||||
for (Object o : enviroment.keySet()) {
|
||||
String name = (String)o;
|
||||
String value = (String)enviroment.get(name);
|
||||
envp[i++] = name + "=" + value;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,26 @@
|
||||
/*
|
||||
* Created by IntelliJ IDEA.
|
||||
* User: mike
|
||||
* Date: Sep 19, 2002
|
||||
* Time: 3:27:12 PM
|
||||
* To change template for new class use
|
||||
* Code Style | Class Templates options (Tools | IDE Options).
|
||||
*/
|
||||
package com.intellij.util;
|
||||
|
||||
import com.intellij.util.EnvironmentUtil;
|
||||
import com.intellij.openapi.util.SystemInfo;
|
||||
import junit.framework.TestCase;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
public class EnvironmentUtilTest extends TestCase {
|
||||
public void test1() {
|
||||
Map enviromentProperties = EnvironmentUtil.getEnviromentProperties();
|
||||
assertNotNull(enviromentProperties);
|
||||
if(SystemInfo.isWindows)
|
||||
assertNotNull(enviromentProperties.get("Path"));
|
||||
else
|
||||
assertNotNull(enviromentProperties.get("PATH"));
|
||||
}
|
||||
}
|
||||
@@ -21,6 +21,9 @@ bigfile
|
||||
bigint
|
||||
binlog
|
||||
bool
|
||||
blog
|
||||
blogger
|
||||
blogging
|
||||
btree
|
||||
calc
|
||||
callee
|
||||
|
||||
Reference in New Issue
Block a user