mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-18 09:34:34 +07:00
[java] for service implementations, checks a provider first (IDEA-169447)
This commit is contained in:
+12
-15
@@ -378,14 +378,24 @@ public class ModuleHighlightUtil {
|
||||
PsiElement implTarget = implRef.resolve();
|
||||
if (implTarget instanceof PsiClass) {
|
||||
PsiClass implClass = (PsiClass)implTarget;
|
||||
PsiMethod provider;
|
||||
|
||||
if (findModule(statement) != findModule(implClass)) {
|
||||
String message = JavaErrorMessages.message("module.service.alien");
|
||||
results.add(HighlightInfo.newHighlightInfo(HighlightInfoType.ERROR).range(range(implRef)).descriptionAndTooltip(message).create());
|
||||
}
|
||||
|
||||
if (InheritanceUtil.isInheritorOrSelf(implClass, (PsiClass)intTarget, true)) {
|
||||
PsiMethod provider = ContainerUtil.find(
|
||||
implClass.findMethodsByName("provider", false),
|
||||
m -> m.hasModifierProperty(PsiModifier.PUBLIC) && m.hasModifierProperty(PsiModifier.STATIC) && m.getParameterList().getParametersCount() == 0);
|
||||
if (provider != null) {
|
||||
PsiType type = provider.getReturnType();
|
||||
PsiClass typeClass = type instanceof PsiClassType ? ((PsiClassType)type).resolve() : null;
|
||||
if (!InheritanceUtil.isInheritorOrSelf(typeClass, (PsiClass)intTarget, true)) {
|
||||
String message = JavaErrorMessages.message("module.service.provider.type", implClass.getName());
|
||||
results.add(HighlightInfo.newHighlightInfo(HighlightInfoType.ERROR).range(range(implRef)).descriptionAndTooltip(message).create());
|
||||
}
|
||||
}
|
||||
else if (InheritanceUtil.isInheritorOrSelf(implClass, (PsiClass)intTarget, true)) {
|
||||
if (implClass.hasModifierProperty(PsiModifier.ABSTRACT)) {
|
||||
String message = JavaErrorMessages.message("module.service.abstract", implClass.getName());
|
||||
results.add(HighlightInfo.newHighlightInfo(HighlightInfoType.ERROR).range(range(implRef)).descriptionAndTooltip(message).create());
|
||||
@@ -399,14 +409,6 @@ public class ModuleHighlightUtil {
|
||||
results.add(HighlightInfo.newHighlightInfo(HighlightInfoType.ERROR).range(range(implRef)).descriptionAndTooltip(message).create());
|
||||
}
|
||||
}
|
||||
else if ((provider = findProvider(implClass)) != null) {
|
||||
PsiType type = provider.getReturnType();
|
||||
PsiClass typeClass = type instanceof PsiClassType ? ((PsiClassType)type).resolve() : null;
|
||||
if (!InheritanceUtil.isInheritorOrSelf(typeClass, (PsiClass)intTarget, true)) {
|
||||
String message = JavaErrorMessages.message("module.service.provider.type", implClass.getName());
|
||||
results.add(HighlightInfo.newHighlightInfo(HighlightInfoType.ERROR).range(range(implRef)).descriptionAndTooltip(message).create());
|
||||
}
|
||||
}
|
||||
else {
|
||||
String message = JavaErrorMessages.message("module.service.impl");
|
||||
results.add(HighlightInfo.newHighlightInfo(HighlightInfoType.ERROR).range(range(implRef)).descriptionAndTooltip(message).create());
|
||||
@@ -417,11 +419,6 @@ public class ModuleHighlightUtil {
|
||||
return results;
|
||||
}
|
||||
|
||||
private static PsiMethod findProvider(PsiClass implClass) {
|
||||
return JBIterable.of(implClass.findMethodsByName("provider", false))
|
||||
.find(p -> p.hasModifierProperty(PsiModifier.PUBLIC) && p.hasModifierProperty(PsiModifier.STATIC) && p.getParameterList().getParametersCount() == 0);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
static HighlightInfo checkPackageAccessibility(@NotNull PsiJavaCodeReferenceElement ref,
|
||||
@NotNull PsiElement target,
|
||||
|
||||
@@ -156,6 +156,7 @@ class ModuleHighlightingTest : LightJava9ModulesCodeInsightFixtureTestCase() {
|
||||
|
||||
fun testProvides() {
|
||||
addFile("pkg/main/C.java", "package pkg.main;\npublic interface C { }")
|
||||
addFile("pkg/main/CT.java", "package pkg.main;\npublic interface CT<T> { }")
|
||||
addFile("pkg/main/Impl1.java", "package pkg.main;\nclass Impl1 { }")
|
||||
addFile("pkg/main/Impl2.java", "package pkg.main;\npublic class Impl2 { }")
|
||||
addFile("pkg/main/Impl3.java", "package pkg.main;\npublic abstract class Impl3 implements C { }")
|
||||
@@ -165,6 +166,7 @@ class ModuleHighlightingTest : LightJava9ModulesCodeInsightFixtureTestCase() {
|
||||
addFile("pkg/main/Impl7.java", "package pkg.main;\npublic class Impl7 {\n public static void provider();\n}")
|
||||
addFile("pkg/main/Impl8.java", "package pkg.main;\npublic class Impl8 {\n public static C provider();\n}")
|
||||
addFile("pkg/main/Impl9.java", "package pkg.main;\npublic class Impl9 {\n public class Inner implements C { }\n}")
|
||||
addFile("pkg/main/Impl10.java", "package pkg.main;\npublic class Impl10<T> implements CT<T> {\n private Impl10() { }\n public static CT provider();\n}")
|
||||
addFile("module-info.java", "module M2 {\n exports pkg.m2;\n}", M2)
|
||||
addFile("pkg/m2/C.java", "package pkg.m2;\npublic class C { }", M2)
|
||||
addFile("pkg/m2/Impl.java", "package pkg.m2;\npublic class Impl extends C { }", M2)
|
||||
@@ -181,6 +183,7 @@ class ModuleHighlightingTest : LightJava9ModulesCodeInsightFixtureTestCase() {
|
||||
provides pkg.main.C with pkg.main.<error descr="The 'provider' method return type must be a subtype of the service interface type: Impl7">Impl7</error>;
|
||||
provides pkg.main.C with pkg.main.Impl8;
|
||||
provides pkg.main.C with pkg.main.Impl9.<error descr="The service implementation is an inner class: Inner">Inner</error>;
|
||||
provides pkg.main.CT with pkg.main.Impl10;
|
||||
provides pkg.m2.C with pkg.m2.<error descr="The service implementation must be defined in the same module as the provides directive">Impl</error>;
|
||||
}""".trimIndent())
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user