[Java. Logging] Detect logger availability for Field based loggers more precisely

IDEA-345098

GitOrigin-RevId: c6d27cb77582974061d768c2fec7837ef9178d70
This commit is contained in:
Georgii Ustinov
2024-02-19 14:25:18 +00:00
committed by intellij-monorepo-bot
parent 388ce94e56
commit 4e05f3a24a
7 changed files with 80 additions and 14 deletions
@@ -10,20 +10,20 @@ import com.intellij.psi.search.GlobalSearchScope
import com.intellij.psi.util.parentsOfType
object GenerateLoggerUtil {
fun findSuitableLoggers(module: Module?, filterByImportExclusion : Boolean = false): List<JvmLogger> {
fun findSuitableLoggers(module: Module?, filterByImportExclusion: Boolean = false): List<JvmLogger> {
val project = module?.project ?: return emptyList()
return JvmLogger.getAllLoggers(false).filter {
it.isAvailable(module) && !(filterByImportExclusion && isLoggerExcluded(project, it))
}
}
private fun isLoggerExcluded(project: Project, logger: JvmLogger) : Boolean {
private fun isLoggerExcluded(project: Project, logger: JvmLogger): Boolean {
val clazz = JavaPsiFacade.getInstance(project).findClass(logger.loggerTypeName, GlobalSearchScope.everythingScope(project))
?: return true
return JavaCompletionUtil.isInExcludedPackage(clazz, false)
}
fun getAllNestedClasses(element: PsiElement) = element.parentsOfType(PsiClass::class.java, true)
fun getAllNestedClasses(element: PsiElement): Sequence<PsiClass> = element.parentsOfType(PsiClass::class.java, true)
.filter { clazz -> clazz !is PsiAnonymousClass && clazz !is PsiImplicitClass }
fun getPossiblePlacesForLogger(element: PsiElement, loggerList: List<JvmLogger>): List<PsiClass> = getAllNestedClasses(element)
@@ -36,8 +36,13 @@ class JvmLoggerFieldDelegate(
override fun isAvailable(module: Module?): Boolean = JavaLibraryUtil.hasLibraryClass(module, loggerTypeName)
override fun isPossibleToPlaceLoggerAtClass(clazz: PsiClass): Boolean = clazz
.fields.any { it.name == LOGGER_IDENTIFIER || it.type.canonicalText == loggerTypeName }.not()
override fun isPossibleToPlaceLoggerAtClass(clazz: PsiClass): Boolean {
val resolveHelper = JavaPsiFacade.getInstance(clazz.project).resolveHelper
return clazz.allFields.any {
resolveHelper.isAccessible(it, clazz, null) &&
(it.name == LOGGER_IDENTIFIER || it.type.canonicalText == loggerTypeName)
}.not()
}
override fun createLogger(project: Project, clazz: PsiClass): PsiField? {
val factory = JavaPsiFacade.getElementFactory(project)
@@ -0,0 +1,12 @@
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class A extends Int {
void foo() {
lo<caret>
}
}
interface Int {
final Logger log = LoggerFactory.getLogger(Int.class);
}
@@ -0,0 +1,12 @@
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class A {
static final Logger log = LoggerFactory.getLogger(A.class);
public static class B {
void foo() {
lo<caret>
}
}
}
@@ -0,0 +1,15 @@
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class A extends Int {
public static class B {
void foo() {
lo<caret>
}
}
}
interface Int {
final Logger log = LoggerFactory.getLogger(Int.class);
}
@@ -48,17 +48,27 @@ class LoggerCompletionTest : LightFixtureCompletionTestCase() {
}
@NeedsIndex.SmartMode(reason = "Logger completion is not supported in the dumb mode")
fun testLoggerAlreadyExists() {
fun testLoggerAlreadyExistsSimple() {
JvmLoggerTestSetupUtil.setupSlf4j(myFixture)
val name = getTestName(true)
configureByFile("$name.java")
assertStringItems("log", "long", "clone")
doAntiTest()
}
TestCase.assertFalse(
lookup.items.any {
it is JvmLoggerLookupElement
}
)
@NeedsIndex.SmartMode(reason = "Logger completion is not supported in the dumb mode")
fun testLoggerAlreadyExistsInheritance() {
JvmLoggerTestSetupUtil.setupSlf4j(myFixture)
doAntiTest()
}
@NeedsIndex.SmartMode(reason = "Logger completion is not supported in the dumb mode")
fun testLoggerAlreadyExistsNestedClasses() {
JvmLoggerTestSetupUtil.setupSlf4j(myFixture)
doAntiTest()
}
@NeedsIndex.SmartMode(reason = "Logger completion is not supported in the dumb mode")
fun testLoggerAlreadyExistsNestedClassesWithInheritance() {
JvmLoggerTestSetupUtil.setupSlf4j(myFixture)
doAntiTest()
}
@NeedsIndex.SmartMode(reason = "Logger completion is not supported in the dumb mode")
@@ -87,6 +97,18 @@ class LoggerCompletionTest : LightFixtureCompletionTestCase() {
override fun getBasePath() = JavaTestUtil.getRelativeJavaTestDataPath() + "/codeInsight/completion/logger"
override fun doAntiTest() {
val name = getTestName(true)
configureByFile("$name.java")
assertStringItems("log", "long", "clone")
TestCase.assertFalse(
lookup.items.any {
it is JvmLoggerLookupElement
}
)
}
private fun doTest(position: Int, vararg names: String) {
val name = getTestName(false)
configureByFile("before$name.java")