DBE-8080 Introduce All Data Sources and per-Data Source search scopes

This commit is contained in:
Gregory.Shrago
2019-04-03 00:57:42 +03:00
parent cf9e6d9865
commit 0aabd53999
6 changed files with 151 additions and 69 deletions
@@ -2,15 +2,32 @@
package com.intellij.psi.search;
import com.intellij.openapi.extensions.ExtensionPointName;
import com.intellij.openapi.project.Project;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.Collections;
import java.util.List;
public interface SearchScopeProvider {
ExtensionPointName<SearchScopeProvider> EP = ExtensionPointName.create("com.intellij.searchScopesProvider");
ExtensionPointName<SearchScopeProvider> EP_NAME = ExtensionPointName.create("com.intellij.searchScopesProvider");
@Nullable
default String getDisplayName() {
return null;
}
@NotNull
default List<SearchScope> getSearchScopes(@NotNull Project project) {
return Collections.emptyList();
}
/**
* General project scopes are added after 'Project', 'Everything' but before 'Production', 'Tests', etc.
* @see PredefinedSearchScopeProvider
* @param project
*/
List<SearchScope> getGeneralProjectScopes();
default List<SearchScope> getGeneralSearchScopes(@NotNull Project project) {
return Collections.emptyList();
}
}
@@ -7,18 +7,18 @@ import com.intellij.openapi.actionSystem.DataContext;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.ui.ComboBox;
import com.intellij.openapi.util.Condition;
import com.intellij.packageDependencies.ChangeListsScopesProvider;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.packageDependencies.DependencyValidationManager;
import com.intellij.psi.search.GlobalSearchScope;
import com.intellij.psi.search.GlobalSearchScopesCore;
import com.intellij.psi.search.PredefinedSearchScopeProvider;
import com.intellij.psi.search.SearchScope;
import com.intellij.psi.search.SearchScopeProvider;
import com.intellij.psi.search.scope.packageSet.NamedScope;
import com.intellij.psi.search.scope.packageSet.NamedScopeManager;
import com.intellij.psi.search.scope.packageSet.NamedScopesHolder;
import com.intellij.ui.ComboboxSpeedSearch;
import com.intellij.ui.ComboboxWithBrowseButton;
import com.intellij.ui.ListCellRendererWrapper;
import com.intellij.util.containers.ContainerUtil;
import com.intellij.util.ui.JBUI;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -26,7 +26,7 @@ import org.jetbrains.annotations.Nullable;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
public class ScopeChooserCombo extends ComboboxWithBrowseButton implements Disposable {
@@ -156,35 +156,18 @@ public class ScopeChooserCombo extends ComboboxWithBrowseButton implements Dispo
@NotNull
private DefaultComboBoxModel<ScopeDescriptor> createModel() {
final DefaultComboBoxModel<ScopeDescriptor> model = new DefaultComboBoxModel<>();
DefaultComboBoxModel<ScopeDescriptor> model = new DefaultComboBoxModel<>();
createPredefinedScopeDescriptors(model);
final List<NamedScope> changeLists = ChangeListsScopesProvider.getInstance(myProject).getFilteredScopes();
if (!changeLists.isEmpty()) {
model.addElement(new ScopeSeparator("VCS Scopes"));
for (NamedScope changeListScope : changeLists) {
final GlobalSearchScope scope = GlobalSearchScopesCore.filterScope(myProject, changeListScope);
addScopeDescriptor(model, new ScopeDescriptor(scope));
for (SearchScopeProvider each : SearchScopeProvider.EP_NAME.getExtensions()) {
if (StringUtil.isEmpty(each.getDisplayName())) continue;
List<SearchScope> scopes = each.getSearchScopes(myProject);
if (scopes.isEmpty()) continue;
model.addElement(new ScopeSeparator(each.getDisplayName()));
for (SearchScope scope : ContainerUtil.sorted(scopes, Comparator.comparing(SearchScope::getDisplayName))) {
model.addElement(new ScopeDescriptor(scope));
}
}
final List<ScopeDescriptor> customScopes = new ArrayList<>();
final NamedScopesHolder[] holders = NamedScopesHolder.getAllNamedScopeHolders(myProject);
for (NamedScopesHolder holder : holders) {
final NamedScope[] scopes = holder.getEditableScopes(); // predefined scopes already included
for (NamedScope scope : scopes) {
final GlobalSearchScope searchScope = GlobalSearchScopesCore.filterScope(myProject, scope);
customScopes.add(new ScopeDescriptor(searchScope));
}
}
if (!customScopes.isEmpty()) {
model.addElement(new ScopeSeparator("Custom Scopes"));
for (ScopeDescriptor scope : customScopes) {
addScopeDescriptor(model, scope);
}
}
return model;
}
@@ -0,0 +1,112 @@
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.psi.search;
import com.intellij.ide.favoritesTreeView.FavoritesManager;
import com.intellij.ide.projectView.impl.AbstractUrl;
import com.intellij.openapi.application.ReadAction;
import com.intellij.openapi.module.Module;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.Pair;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.packageDependencies.ChangeListsScopesProvider;
import com.intellij.psi.search.scope.packageSet.NamedScope;
import com.intellij.psi.search.scope.packageSet.NamedScopesHolder;
import com.intellij.util.TreeItem;
import org.jetbrains.annotations.NotNull;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
/**
* @author gregsh
*/
public class DefaultSearchScopeProviders {
private DefaultSearchScopeProviders() {}
public static class Favorites implements SearchScopeProvider {
@Override
public String getDisplayName() {
return "Favorites";
}
@NotNull
@Override
public List<SearchScope> getSearchScopes(@NotNull Project project) {
FavoritesManager favoritesManager = FavoritesManager.getInstance(project);
if (favoritesManager == null) return Collections.emptyList();
List<SearchScope> result = new ArrayList<>();
for (String favorite : favoritesManager.getAvailableFavoritesListNames()) {
Collection<TreeItem<Pair<AbstractUrl, String>>> rootUrls = favoritesManager.getFavoritesListRootUrls(favorite);
if (rootUrls.isEmpty()) continue; // ignore unused root
result.add(new GlobalSearchScope(project) {
@NotNull
@Override
public String getDisplayName() {
return "Favorite \'" + favorite + "\'";
}
@Override
public boolean contains(@NotNull VirtualFile file) {
return ReadAction.compute(() -> favoritesManager.contains(favorite, file));
}
@Override
public boolean isSearchInModuleContent(@NotNull Module aModule) {
return true;
}
@Override
public boolean isSearchInLibraries() {
return true;
}
});
}
return result;
}
}
public static class ChangeLists implements SearchScopeProvider {
@Override
public String getDisplayName() {
return "Local Changes";
}
@NotNull
@Override
public List<SearchScope> getSearchScopes(@NotNull Project project) {
List<SearchScope> result = new ArrayList<>();
List<NamedScope> changeLists = ChangeListsScopesProvider.getInstance(project).getFilteredScopes();
if (!changeLists.isEmpty()) {
for (NamedScope changeListScope : changeLists) {
GlobalSearchScope scope = GlobalSearchScopesCore.filterScope(project, changeListScope);
result.add(scope);
}
}
return result;
}
}
public static class CustomNamed implements SearchScopeProvider {
@Override
public String getDisplayName() {
return "Other";
}
@NotNull
@Override
public List<SearchScope> getSearchScopes(@NotNull Project project) {
List<SearchScope> result = new ArrayList<>();
NamedScopesHolder[] holders = NamedScopesHolder.getAllNamedScopeHolders(project);
for (NamedScopesHolder holder : holders) {
NamedScope[] scopes = holder.getEditableScopes(); // predefined scopes already included
for (NamedScope scope : scopes) {
GlobalSearchScope searchScope = GlobalSearchScopesCore.filterScope(project, scope);
result.add(searchScope);
}
}
return result;
}
}
}
@@ -2,22 +2,18 @@
package com.intellij.psi.search;
import com.intellij.ide.IdeBundle;
import com.intellij.ide.favoritesTreeView.FavoritesManager;
import com.intellij.ide.hierarchy.HierarchyBrowserBase;
import com.intellij.ide.projectView.impl.AbstractUrl;
import com.intellij.ide.scratch.ScratchesSearchScope;
import com.intellij.openapi.actionSystem.CommonDataKeys;
import com.intellij.openapi.actionSystem.DataContext;
import com.intellij.openapi.actionSystem.LangDataKeys;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.application.ReadAction;
import com.intellij.openapi.editor.Editor;
import com.intellij.openapi.editor.SelectionModel;
import com.intellij.openapi.fileEditor.FileEditorManager;
import com.intellij.openapi.module.*;
import com.intellij.openapi.project.DumbUnawareHider;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.Pair;
import com.intellij.openapi.util.TextRange;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.openapi.wm.ToolWindow;
@@ -36,7 +32,6 @@ import com.intellij.usages.UsageView;
import com.intellij.usages.UsageViewManager;
import com.intellij.usages.rules.PsiElementUsage;
import com.intellij.util.PlatformUtils;
import com.intellij.util.TreeItem;
import com.intellij.util.containers.ContainerUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -62,8 +57,8 @@ public class PredefinedSearchScopeProviderImpl extends PredefinedSearchScopeProv
result.add(GlobalSearchScope.allScope(project));
}
for (SearchScopeProvider each : SearchScopeProvider.EP.getExtensions(project)) {
result.addAll(each.getGeneralProjectScopes());
for (SearchScopeProvider each : SearchScopeProvider.EP_NAME.getExtensions()) {
result.addAll(each.getGeneralSearchScopes(project));
}
if (ModuleUtil.hasTestSourceRoots(project)) {
@@ -207,36 +202,6 @@ public class PredefinedSearchScopeProviderImpl extends PredefinedSearchScopeProv
}
}
final FavoritesManager favoritesManager = FavoritesManager.getInstance(project);
if (favoritesManager != null) {
for (final String favorite : favoritesManager.getAvailableFavoritesListNames()) {
final Collection<TreeItem<Pair<AbstractUrl, String>>> rootUrls = favoritesManager.getFavoritesListRootUrls(favorite);
if (rootUrls.isEmpty()) continue; // ignore unused root
result.add(new GlobalSearchScope(project) {
@NotNull
@Override
public String getDisplayName() {
return "Favorite \'" + favorite + "\'";
}
@Override
public boolean contains(@NotNull final VirtualFile file) {
return ReadAction.compute(() -> favoritesManager.contains(favorite, file));
}
@Override
public boolean isSearchInModuleContent(@NotNull final Module aModule) {
return true;
}
@Override
public boolean isSearchInLibraries() {
return true;
}
});
}
}
ContainerUtil.addIfNotNull(result, getSelectedFilesScope(project, dataContext));
return ContainerUtil.newArrayList(result);
@@ -267,7 +267,7 @@
<extensionPoint name="definitionsSearch" interface="com.intellij.util.QueryExecutor"/>
<extensionPoint name="definitionsScopedSearch" interface="com.intellij.util.QueryExecutor"/>
<extensionPoint name="searchScopesProvider" interface="com.intellij.psi.search.SearchScopeProvider" area="IDEA_PROJECT"/>
<extensionPoint name="searchScopesProvider" interface="com.intellij.psi.search.SearchScopeProvider"/>
<extensionPoint name="searchScopeEnlarger" interface="com.intellij.psi.search.SearchScopeEnlarger"/>
<extensionPoint name="useScopeEnlarger" interface="com.intellij.psi.search.UseScopeEnlarger"/>
<extensionPoint name="resolveScopeEnlarger" interface="com.intellij.psi.ResolveScopeEnlarger"/>
@@ -502,6 +502,11 @@
<customScopesProvider implementation="com.intellij.packageDependencies.DefaultScopesProvider" id="default" order="first"/>
<customScopesProvider implementation="com.intellij.psi.search.scope.ProblemsScope$Provider" order="last"/>
<customScopesProvider implementation="com.intellij.packageDependencies.ChangeListsScopesProvider" order="last"/>
<searchScopesProvider implementation="com.intellij.psi.search.DefaultSearchScopeProviders$Favorites"/>
<searchScopesProvider implementation="com.intellij.psi.search.DefaultSearchScopeProviders$ChangeLists"/>
<searchScopesProvider implementation="com.intellij.psi.search.DefaultSearchScopeProviders$CustomNamed" order="last"/>
<refactoring.elementListenerProvider implementation="com.intellij.packageDependencies.ui.RefactoringScopeElementListenerProvider"/>
<highlightVisitor implementation="com.intellij.codeInsight.daemon.impl.DefaultHighlightVisitor"/>