mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
batch inspections: don't remove refs on parameter multiple times (IDEA-175665)
base RefManager#removeRefElement removes also references on children, thus processing parameters separately is redundant
This commit is contained in:
+1
-9
@@ -246,15 +246,7 @@ public class RefJavaManagerImpl extends RefJavaManager {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeReference(@NotNull final RefElement refElement) {
|
||||
if (refElement instanceof RefMethod) {
|
||||
RefMethod refMethod = (RefMethod)refElement;
|
||||
RefParameter[] params = refMethod.getParameters();
|
||||
for (RefParameter param : params) {
|
||||
myRefManager.removeReference(param);
|
||||
}
|
||||
}
|
||||
}
|
||||
public void removeReference(@NotNull final RefElement refElement) { }
|
||||
|
||||
@Override
|
||||
@Nullable
|
||||
|
||||
@@ -490,11 +490,6 @@ public class RefMethodImpl extends RefJavaElementImpl implements RefMethod {
|
||||
for (RefMethod subMethod : getDerivedMethods()) {
|
||||
subMethod.getSuperMethods().remove(this);
|
||||
}
|
||||
|
||||
ArrayList<RefElement> deletedRefs = new ArrayList<>();
|
||||
for (RefParameter parameter : getParameters()) {
|
||||
getRefManager().removeRefElement(parameter, deletedRefs);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
+34
-10
@@ -54,6 +54,7 @@ import com.intellij.util.text.CharArrayUtil;
|
||||
import com.intellij.util.text.DateFormatUtil;
|
||||
import com.intellij.util.ui.JBUI;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import gnu.trove.THashSet;
|
||||
import org.jdom.Element;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -234,20 +235,43 @@ public class UnusedDeclarationPresentation extends DefaultInspectionToolPresenta
|
||||
@Override
|
||||
protected boolean applyFix(@NotNull final RefEntity[] refElements) {
|
||||
if (!super.applyFix(refElements)) return false;
|
||||
final PsiElement[] psiElements = Arrays
|
||||
.stream(refElements)
|
||||
.filter((obj) -> obj instanceof RefJavaElement && getFilter().accepts((RefJavaElement)obj))
|
||||
.map(e -> ((RefElement) e).getElement())
|
||||
.filter(e -> e != null)
|
||||
.toArray(PsiElement[]::new);
|
||||
if (psiElements.length == 0) return false;
|
||||
|
||||
//filter only elements applicable to be deleted (exclude entry points)
|
||||
RefElement[] filteredRefElements = Arrays.stream(refElements)
|
||||
.filter(entry -> entry instanceof RefJavaElement && getFilter().accepts((RefJavaElement)entry))
|
||||
.toArray(RefElement[]::new);
|
||||
|
||||
ApplicationManager.getApplication().invokeLater(() -> {
|
||||
final Project project = getContext().getProject();
|
||||
if (isDisposed() || project.isDisposed()) return;
|
||||
SafeDeleteHandler.invoke(project, psiElements, false,
|
||||
List<PsiElement> psiElements = new ArrayList<>();
|
||||
Set<PsiClass> classes = new THashSet<>();
|
||||
for (RefEntity obj : filteredRefElements) {
|
||||
PsiElement e = ((RefElement)obj).getElement();
|
||||
if (e != null) {
|
||||
psiElements.add(e);
|
||||
if (e instanceof PsiClass) {
|
||||
classes.add((PsiClass)e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (psiElements.size() == 0) return;
|
||||
|
||||
//filter out elements inside classes to be deleted
|
||||
PsiElement[] elements = psiElements.stream().filter(e -> {
|
||||
if (e instanceof PsiMember) {
|
||||
PsiClass containingClass = ((PsiMember)e).getContainingClass();
|
||||
if (containingClass != null && classes.contains(containingClass)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}).toArray(PsiElement[]::new);
|
||||
SafeDeleteHandler.invoke(project, elements, false,
|
||||
() -> {
|
||||
removeElements(refElements, project, myToolWrapper);
|
||||
for (RefEntity ref : refElements) {
|
||||
removeElements(filteredRefElements, project, myToolWrapper);
|
||||
for (RefEntity ref : filteredRefElements) {
|
||||
myFixedElements.put(ref, UnusedDeclarationHint.DELETE);
|
||||
}
|
||||
});
|
||||
|
||||
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Copyright 2000-2017 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.java.codeInspection;
|
||||
|
||||
import com.intellij.analysis.AnalysisScope;
|
||||
import com.intellij.codeInspection.InspectionManager;
|
||||
import com.intellij.codeInspection.reference.RefElement;
|
||||
import com.intellij.codeInspection.reference.RefEntity;
|
||||
import com.intellij.codeInspection.reference.RefManagerImpl;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.psi.PsiClass;
|
||||
import com.intellij.testFramework.fixtures.LightCodeInsightFixtureTestCase;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class BatchModeInspectionTest extends LightCodeInsightFixtureTestCase {
|
||||
public void testEnsureReferencesAreRemoved() throws Exception {
|
||||
PsiClass aClass = myFixture.addClass("class Foo {public void bar(int i){}}");
|
||||
Project project = myFixture.getProject();
|
||||
RefManagerImpl refManager = new RefManagerImpl(project, new AnalysisScope(aClass.getContainingFile()), InspectionManager.getInstance(
|
||||
project).createNewGlobalContext(false));
|
||||
refManager.findAllDeclarations();
|
||||
List<RefElement> sortedElements = refManager.getSortedElements();
|
||||
|
||||
RefElement refMethod = refManager.getReference(aClass.getMethods()[0]);
|
||||
List<RefEntity> children = refMethod.getChildren();
|
||||
ArrayList<RefElement> deletedRefs = new ArrayList<>();
|
||||
refManager.removeRefElement(refMethod, deletedRefs);
|
||||
assertTrue(deletedRefs.containsAll(children));
|
||||
assertTrue(deletedRefs.contains(refMethod));
|
||||
|
||||
//check that table was not reinitialized due to full table traversal
|
||||
assertTrue(sortedElements == refManager.getSortedElements());
|
||||
}
|
||||
}
|
||||
+7
-2
@@ -381,7 +381,7 @@ public class RefManagerImpl extends RefManager {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
List<RefElement> getSortedElements() {
|
||||
public List<RefElement> getSortedElements() {
|
||||
List<RefElement> answer = myCachedSortedRefs;
|
||||
if (answer != null) return answer;
|
||||
|
||||
@@ -682,7 +682,12 @@ public class RefManagerImpl extends RefManager {
|
||||
|
||||
((RefManagerImpl)refElement.getRefManager()).removeReference(refElement);
|
||||
((RefElementImpl)refElement).referenceRemoved();
|
||||
if (!deletedRefs.contains(refElement)) deletedRefs.add(refElement);
|
||||
if (!deletedRefs.contains(refElement)) {
|
||||
deletedRefs.add(refElement);
|
||||
}
|
||||
else {
|
||||
LOG.error("deleted second time");
|
||||
}
|
||||
}
|
||||
|
||||
boolean isValidPointForReference() {
|
||||
|
||||
Reference in New Issue
Block a user