diff --git a/java/execution/impl/src/com/intellij/execution/junit/InheritorChooser.java b/java/execution/impl/src/com/intellij/execution/junit/InheritorChooser.java index 4463e3efef7c..d318ad47bb70 100644 --- a/java/execution/impl/src/com/intellij/execution/junit/InheritorChooser.java +++ b/java/execution/impl/src/com/intellij/execution/junit/InheritorChooser.java @@ -22,12 +22,11 @@ import com.intellij.execution.junit2.info.MethodLocation; import com.intellij.ide.util.PsiClassListCellRenderer; import com.intellij.openapi.actionSystem.PlatformDataKeys; import com.intellij.openapi.editor.Document; -import com.intellij.openapi.editor.Editor; -import com.intellij.openapi.fileEditor.FileDocumentManager; import com.intellij.openapi.fileEditor.FileEditor; import com.intellij.openapi.fileEditor.TextEditor; import com.intellij.openapi.progress.ProgressManager; import com.intellij.openapi.ui.popup.JBPopupFactory; +import com.intellij.openapi.util.Condition; import com.intellij.psi.*; import com.intellij.psi.search.searches.ClassInheritorsSearch; import com.intellij.psi.util.PsiClassUtil; @@ -37,7 +36,10 @@ import com.intellij.util.ArrayUtil; import com.intellij.util.Processor; import javax.swing.*; -import java.util.*; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collections; +import java.util.List; /** * User: anna @@ -57,7 +59,15 @@ public class InheritorChooser { final Runnable performRunnable, final PsiMethod psiMethod, final PsiClass containingClass) { - if (containingClass != null && containingClass.hasModifierProperty(PsiModifier.ABSTRACT)) { + return runMethodInAbstractClass(context, performRunnable, psiMethod, containingClass, Condition.TRUE); + } + + public boolean runMethodInAbstractClass(final ConfigurationContext context, + final Runnable performRunnable, + final PsiMethod psiMethod, + final PsiClass containingClass, + final Condition acceptAbstractCondition) { + if (containingClass != null && containingClass.hasModifierProperty(PsiModifier.ABSTRACT) && acceptAbstractCondition.value(containingClass)) { final Location location = context.getLocation(); if (location instanceof MethodLocation) { final PsiClass aClass = ((MethodLocation)location).getContainingClass(); diff --git a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/genericsHighlighting/TypeWithinItsWildcardBound.java b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/genericsHighlighting/TypeWithinItsWildcardBound.java index e85ae1288b9f..a7ada7896cfb 100644 --- a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/genericsHighlighting/TypeWithinItsWildcardBound.java +++ b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/genericsHighlighting/TypeWithinItsWildcardBound.java @@ -311,7 +311,7 @@ class WithingBounds { AA>> a3; A a4; - A<? super A> a5; + A<? super A> a5; A<A[]> a7; } } diff --git a/plugins/InspectionGadgets/InspectionGadgetsAnalysis/src/com/siyeh/ig/visibility/MethodOverloadsParentMethodInspectionBase.java b/plugins/InspectionGadgets/InspectionGadgetsAnalysis/src/com/siyeh/ig/visibility/MethodOverloadsParentMethodInspectionBase.java index 035593653df8..2795f75e6b8b 100644 --- a/plugins/InspectionGadgets/InspectionGadgetsAnalysis/src/com/siyeh/ig/visibility/MethodOverloadsParentMethodInspectionBase.java +++ b/plugins/InspectionGadgets/InspectionGadgetsAnalysis/src/com/siyeh/ig/visibility/MethodOverloadsParentMethodInspectionBase.java @@ -17,6 +17,7 @@ package com.siyeh.ig.visibility; import com.intellij.codeInspection.ui.SingleCheckboxOptionsPanel; import com.intellij.psi.*; +import com.intellij.psi.util.PsiUtil; import com.siyeh.InspectionGadgetsBundle; import com.siyeh.ig.BaseInspection; import com.siyeh.ig.BaseInspectionVisitor; @@ -85,18 +86,36 @@ public class MethodOverloadsParentMethodInspectionBase extends BaseInspection { if (MethodUtils.hasSuper(method)) { return; } - PsiClass ancestorClass = aClass.getSuperClass(); final Set visitedClasses = new HashSet(); - while (ancestorClass != null) { - if (!visitedClasses.add(ancestorClass)) { - return; - } - if (methodOverloads(method, ancestorClass)) { - registerMethodError(method); - return; - } - ancestorClass = ancestorClass.getSuperClass(); + processSupers(method, aClass, aClass, visitedClasses); + } + + private boolean processSupers(final PsiMethod method, + final PsiClass psiClass, + final PsiClass initialClass, + final Set visitedClasses) { + if (!visitedClasses.add(psiClass)) { + return false; } + if (initialClass != psiClass && methodOverloads(method, psiClass)) { + registerMethodError(method); + return true; + } + else { + if (PsiUtil.isLanguageLevel8OrHigher(method)) { + for (PsiClass superClass : psiClass.getSupers()) { + if (processSupers(method, superClass, initialClass, visitedClasses)) { + return true; + } + } + } else { + final PsiClass superClass = psiClass.getSuperClass(); + if (superClass != null) { + return processSupers(method, superClass, initialClass, visitedClasses); + } + } + } + return false; } private boolean methodOverloads(PsiMethod method, PsiClass ancestorClass) { @@ -107,6 +126,7 @@ public class MethodOverloadsParentMethodInspectionBase extends BaseInspection { for (final PsiMethod testMethod : methods) { if (!testMethod.hasModifierProperty(PsiModifier.PRIVATE) && !testMethod.hasModifierProperty(PsiModifier.STATIC) && + !testMethod.hasModifierProperty(PsiModifier.ABSTRACT) && !isOverriddenInClass(testMethod, method.getContainingClass())) { final PsiParameterList testParameterList = testMethod.getParameterList(); final PsiParameter[] testParameters = testParameterList.getParameters(); diff --git a/plugins/InspectionGadgets/test/com/siyeh/igtest/visibility/method_overloads_parent_method/MethodOverloadsParentMethod.java b/plugins/InspectionGadgets/test/com/siyeh/igtest/visibility/method_overloads_parent_method/MethodOverloadsParentMethod.java index 591f38d06ec4..47d8474f874f 100644 --- a/plugins/InspectionGadgets/test/com/siyeh/igtest/visibility/method_overloads_parent_method/MethodOverloadsParentMethod.java +++ b/plugins/InspectionGadgets/test/com/siyeh/igtest/visibility/method_overloads_parent_method/MethodOverloadsParentMethod.java @@ -24,4 +24,25 @@ class Parent { Object bla(double d) { return null; } +} + +class DefaultMethod { + public static interface IFoo { + default void foo(int i) { + System.out.println("IFoo.foo(int): " + i); + } + + void bar(int i); + + } + + public static class Foo implements IFoo { + public void foo(long l) { + System.out.println("Foo.foo(long): " + l); + } + + public void bar(long l) { + System.out.println("Foo.bar(long): " + l); + } + } } \ No newline at end of file diff --git a/plugins/InspectionGadgets/test/com/siyeh/igtest/visibility/method_overloads_parent_method/expected.xml b/plugins/InspectionGadgets/test/com/siyeh/igtest/visibility/method_overloads_parent_method/expected.xml index 5d8ab8b7374e..b5d00fce9a41 100644 --- a/plugins/InspectionGadgets/test/com/siyeh/igtest/visibility/method_overloads_parent_method/expected.xml +++ b/plugins/InspectionGadgets/test/com/siyeh/igtest/visibility/method_overloads_parent_method/expected.xml @@ -21,4 +21,11 @@ Method overloads method of superclass Method <code>bla()</code> overloads a compatible method of a superclass, when overriding might have been intended #loc + + + MethodOverloadsParentMethod.java + 40 + Method overloads method of superclass + Method <code>foo()</code> overloads a compatible method of a superclass, when overriding might have been intended #loc + \ No newline at end of file diff --git a/plugins/InspectionGadgets/testsrc/com/siyeh/ig/visibility/MethodOverloadsParentMethodInspectionTest.java b/plugins/InspectionGadgets/testsrc/com/siyeh/ig/visibility/MethodOverloadsParentMethodInspectionTest.java index 440e7cf993f0..0fe9f5d4c1c1 100644 --- a/plugins/InspectionGadgets/testsrc/com/siyeh/ig/visibility/MethodOverloadsParentMethodInspectionTest.java +++ b/plugins/InspectionGadgets/testsrc/com/siyeh/ig/visibility/MethodOverloadsParentMethodInspectionTest.java @@ -1,5 +1,9 @@ package com.siyeh.ig.visibility; +import com.intellij.openapi.projectRoots.Sdk; +import com.intellij.openapi.roots.LanguageLevelProjectExtension; +import com.intellij.pom.java.LanguageLevel; +import com.intellij.testFramework.IdeaTestUtil; import com.siyeh.ig.IGInspectionTestCase; public class MethodOverloadsParentMethodInspectionTest extends IGInspectionTestCase { @@ -7,4 +11,12 @@ public class MethodOverloadsParentMethodInspectionTest extends IGInspectionTestC public void test() throws Exception { doTest("com/siyeh/igtest/visibility/method_overloads_parent_method", new MethodOverloadsParentMethodInspection()); } + + @Override + protected Sdk getTestProjectSdk() { + final Sdk sdk = IdeaTestUtil.getMockJdk17(); + LanguageLevelProjectExtension.getInstance(getProject()).setLanguageLevel(LanguageLevel.HIGHEST); + return sdk; + } + } \ No newline at end of file diff --git a/plugins/testng/src/com/theoryinpractice/testng/configuration/TestNGInClassConfigurationProducer.java b/plugins/testng/src/com/theoryinpractice/testng/configuration/TestNGInClassConfigurationProducer.java index b613e1d721c0..381d72f63788 100644 --- a/plugins/testng/src/com/theoryinpractice/testng/configuration/TestNGInClassConfigurationProducer.java +++ b/plugins/testng/src/com/theoryinpractice/testng/configuration/TestNGInClassConfigurationProducer.java @@ -20,27 +20,21 @@ */ package com.theoryinpractice.testng.configuration; -import com.intellij.execution.JavaRunConfigurationExtensionManager; -import com.intellij.execution.Location; import com.intellij.execution.PsiLocation; import com.intellij.execution.RunnerAndConfigurationSettings; import com.intellij.execution.actions.ConfigurationContext; import com.intellij.execution.actions.ConfigurationFromContext; import com.intellij.execution.junit.InheritorChooser; -import com.intellij.execution.junit.JUnitUtil; -import com.intellij.execution.junit.JavaRuntimeConfigurationProducerBase; -import com.intellij.execution.junit2.info.LocationUtil; import com.intellij.execution.junit2.info.MethodLocation; import com.intellij.openapi.actionSystem.LangDataKeys; import com.intellij.openapi.module.Module; import com.intellij.openapi.project.Project; +import com.intellij.openapi.util.Condition; import com.intellij.openapi.util.Ref; import com.intellij.psi.*; import com.intellij.psi.util.PsiClassUtil; import com.intellij.psi.util.PsiTreeUtil; -import com.theoryinpractice.testng.model.TestData; import com.theoryinpractice.testng.util.TestNGUtil; -import org.jetbrains.annotations.Nullable; import java.util.List; @@ -88,7 +82,12 @@ public class TestNGInClassConfigurationProducer extends TestNGConfigurationProdu super.runForClass(aClass, psiMethod, context, performRunnable); } }; - if (inheritorChooser.runMethodInAbstractClass(fromContext, performRunnable, psiMethod, containingClass)) return; + if (inheritorChooser.runMethodInAbstractClass(fromContext, performRunnable, psiMethod, containingClass, new Condition() { + @Override + public boolean value(PsiClass aClass) { + return TestNGUtil.hasTest(aClass); + } + })) return; } super.onFirstRun(configuration, fromContext, performRunnable); }