Introduce "Logger initialized with foreign class" inspection

^KT-38982 Fixed
This commit is contained in:
Toshiaki Kameyama
2020-05-16 11:48:19 +09:00
committed by Nikita Bobko
parent c6e23ffa3b
commit 23c4eac45b
35 changed files with 707 additions and 1 deletions
@@ -3316,6 +3316,14 @@
language="kotlin"
key="inspection.redundant.elvis.return.null.display.name" bundle="messages.KotlinBundle"/>
<localInspection implementationClass="org.jetbrains.kotlin.idea.inspections.logging.KotlinLoggerInitializedWithForeignClassInspection"
groupPath="Kotlin"
groupName="Logging"
enabledByDefault="false"
level="WARNING"
language="kotlin"
key="inspection.logger.initialized.with.foreign.class.display.name" bundle="messages.KotlinBundle"/>
<projectService serviceImplementation="org.jetbrains.kotlin.idea.codeInsight.KotlinCodeInsightWorkspaceSettings"/>
<applicationService serviceImplementation="org.jetbrains.kotlin.idea.codeInsight.KotlinCodeInsightSettings"/>
@@ -0,0 +1,7 @@
<html>
<body>
This inspection reports any <b>Logger</b>s which are initialized with a class literal from a different class than the <b>Logger</b> is contained in.
<br /><br />
Use the table below to specify the logger factory classes and logger factory methods recognized by this inspection.
</body>
</html>
@@ -2206,4 +2206,9 @@ kotlin.script.definitions.model.name.name=Name
codestyle.name.kotlin=Kotlin
add.missing.class.keyword=Add missing 'class' keyword
fix.move.typealias.to.top.level=Move typealias to top level
fix.change.jvm.name=Change JVM name
fix.change.jvm.name=Change JVM name
inspection.logger.initialized.with.foreign.class.display.name=Logger initialized with foreign class
logger.initialized.with.foreign.class=Logger initialized with foreign class ''{0}''
logger.factory.method.name=Logger factory method name
logger.factory.class.name=Logger factory class name
choose.logger.factory.class=Choose logger factory class
@@ -0,0 +1,155 @@
/*
* Copyright 2010-2020 JetBrains s.r.o. and Kotlin Programming Language contributors.
* Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file.
*/
package org.jetbrains.kotlin.idea.inspections.logging
import com.intellij.codeInspection.LocalQuickFix
import com.intellij.codeInspection.ProblemDescriptor
import com.intellij.codeInspection.ProblemsHolder
import com.intellij.codeInspection.ui.ListTable
import com.intellij.codeInspection.ui.ListWrappingTableModel
import com.intellij.openapi.project.Project
import com.intellij.util.xmlb.Accessor
import com.intellij.util.xmlb.SerializationFilterBase
import com.intellij.util.xmlb.XmlSerializer
import com.siyeh.ig.BaseInspection
import com.siyeh.ig.ui.UiUtils
import org.jdom.Element
import org.jetbrains.kotlin.idea.KotlinBundle
import org.jetbrains.kotlin.idea.caches.resolve.resolveToCall
import org.jetbrains.kotlin.idea.inspections.AbstractKotlinInspection
import org.jetbrains.kotlin.idea.intentions.callExpression
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.psi.*
import org.jetbrains.kotlin.psi.psiUtil.containingClass
import org.jetbrains.kotlin.psi.psiUtil.getStrictParentOfType
import org.jetbrains.kotlin.resolve.descriptorUtil.fqNameOrNull
import org.jetbrains.kotlin.utils.addToStdlib.safeAs
import javax.swing.JComponent
class KotlinLoggerInitializedWithForeignClassInspection : AbstractKotlinInspection() {
companion object {
private val DEFAULT_LOGGER_FACTORIES = listOf(
"java.util.logging.Logger" to "getLogger",
"org.slf4j.LoggerFactory" to "getLogger",
"org.apache.commons.logging.LogFactory" to "getLog",
"org.apache.log4j.Logger" to "getLogger",
"org.apache.logging.log4j.LogManager" to "getLogger",
)
private val DEFAULT_LOGGER_FACTORY_CLASS_NAMES = DEFAULT_LOGGER_FACTORIES.map { it.first }
private val DEFAULT_LOGGER_FACTORY_METHOD_NAMES = DEFAULT_LOGGER_FACTORIES.map { it.second }
private val DEFAULT_LOGGER_FACTORY_CLASS_NAME = BaseInspection.formatString(DEFAULT_LOGGER_FACTORY_CLASS_NAMES)
private val DEFAULT_LOGGER_FACTORY_METHOD_NAME = BaseInspection.formatString(DEFAULT_LOGGER_FACTORY_METHOD_NAMES)
}
@Suppress("MemberVisibilityCanBePrivate")
var loggerFactoryClassName: String = DEFAULT_LOGGER_FACTORY_CLASS_NAME
@Suppress("MemberVisibilityCanBePrivate")
var loggerFactoryMethodName: String = DEFAULT_LOGGER_FACTORY_METHOD_NAME
private val loggerFactoryClassNames = DEFAULT_LOGGER_FACTORY_CLASS_NAMES.toMutableList()
private val loggerFactoryMethodNames = DEFAULT_LOGGER_FACTORY_METHOD_NAMES.toMutableList()
private val loggerFactoryFqNames
get() = loggerFactoryClassNames.zip(loggerFactoryMethodNames).groupBy(
{ (_, methodName) -> methodName },
{ (className, methodName) -> FqName("${className}.${methodName}") }
)
override fun createOptionsPanel(): JComponent? {
val table = ListTable(
ListWrappingTableModel(
listOf(loggerFactoryClassNames, loggerFactoryMethodNames),
KotlinBundle.message("logger.factory.class.name"),
KotlinBundle.message("logger.factory.method.name")
)
)
return UiUtils.createAddRemoveTreeClassChooserPanel(table, KotlinBundle.message("choose.logger.factory.class"))
}
override fun readSettings(element: Element) {
super.readSettings(element)
BaseInspection.parseString(loggerFactoryClassName, loggerFactoryClassNames)
BaseInspection.parseString(loggerFactoryMethodName, loggerFactoryMethodNames)
if (loggerFactoryClassNames.isEmpty() || loggerFactoryClassNames.size != loggerFactoryMethodNames.size) {
BaseInspection.parseString(DEFAULT_LOGGER_FACTORY_CLASS_NAME, loggerFactoryClassNames)
BaseInspection.parseString(DEFAULT_LOGGER_FACTORY_METHOD_NAME, loggerFactoryMethodNames)
}
}
override fun writeSettings(element: Element) {
loggerFactoryClassName = BaseInspection.formatString(loggerFactoryClassNames)
loggerFactoryMethodName = BaseInspection.formatString(loggerFactoryMethodNames)
XmlSerializer.serializeInto(this, element, object : SerializationFilterBase() {
override fun accepts(accessor: Accessor, bean: Any, beanValue: Any?): Boolean {
if (accessor.name == "loggerFactoryClassName" && beanValue == DEFAULT_LOGGER_FACTORY_CLASS_NAME) return false
if (accessor.name == "loggerFactoryMethodName" && beanValue == DEFAULT_LOGGER_FACTORY_METHOD_NAME) return false
return true
}
})
}
override fun buildVisitor(holder: ProblemsHolder, isOnTheFly: Boolean) = callExpressionVisitor(fun(call) {
val containingClassName = call.containingClass()?.name ?: return
val callee = call.calleeExpression ?: return
val loggerMethodFqNames = loggerFactoryFqNames[callee.text] ?: return
val argument = call.valueArguments.singleOrNull()?.getArgumentExpression() as? KtDotQualifiedExpression ?: return
val argumentSelector = argument.selectorExpression ?: return
val classLiteral = when (val argumentReceiver = argument.receiverExpression) {
// Foo::class.java, Foo::class.qualifiedName, Foo::class.simpleName
is KtClassLiteralExpression -> {
val selectorText = argumentSelector.safeAs<KtNameReferenceExpression>()?.text
if (selectorText !in listOf("java", "qualifiedName", "simpleName")) return
argumentReceiver
}
// Foo::class.java.name, Foo::class.java.simpleName, Foo::class.java.canonicalName
is KtDotQualifiedExpression -> {
val classLiteral = argumentReceiver.receiverExpression as? KtClassLiteralExpression ?: return
if (argumentReceiver.selectorExpression.safeAs<KtNameReferenceExpression>()?.text != "java") return
val selectorText = argumentSelector.safeAs<KtNameReferenceExpression>()?.text
?: argumentSelector.safeAs<KtCallExpression>()?.calleeExpression?.text
if (selectorText !in listOf("name", "simpleName", "canonicalName", "getName", "getSimpleName", "getCanonicalName")) return
classLiteral
}
else -> return
}
val classLiteralName = classLiteral.receiverExpression?.text ?: return
if (containingClassName == classLiteralName) return
if (call.resolveToCall()?.resultingDescriptor?.fqNameOrNull() !in loggerMethodFqNames) return
holder.registerProblem(
classLiteral,
KotlinBundle.message("logger.initialized.with.foreign.class", "$classLiteralName::class"),
ReplaceForeignFix(containingClassName)
)
})
private class ReplaceForeignFix(private val containingClassName: String) : LocalQuickFix {
override fun getName() = KotlinBundle.message("replace.with.0", "$containingClassName::class")
override fun getFamilyName() = name
override fun applyFix(project: Project, descriptor: ProblemDescriptor) {
val argument = descriptor.psiElement.getStrictParentOfType<KtValueArgument>()?.getArgumentExpression()
as? KtDotQualifiedExpression ?: return
val receiver = argument.receiverExpression
val selector = argument.selectorExpression ?: return
val psiFactory = KtPsiFactory(argument)
val newArgument = when (receiver) {
is KtClassLiteralExpression -> {
psiFactory.createExpressionByPattern("${containingClassName}::class.$0", selector)
}
is KtDotQualifiedExpression -> {
psiFactory.createExpressionByPattern("${containingClassName}::class.java.$0", selector)
}
else -> return
}
argument.replace(newArgument)
}
}
}
@@ -0,0 +1 @@
org.jetbrains.kotlin.idea.inspections.logging.KotlinLoggerInitializedWithForeignClassInspection
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Bar::class.java.canonicalName)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(Foo::class.java.canonicalName)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Bar::class.java.getCanonicalName())
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(Foo::class.java.getCanonicalName())
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Bar::class.java.getName())
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(Foo::class.java.getName())
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Bar::class.java.getSimpleName())
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(Foo::class.java.getSimpleName())
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Bar::class.qualifiedName)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(Foo::class.qualifiedName)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Bar::class.simpleName)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(Foo::class.simpleName)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Bar::class.java.name)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(Foo::class.java.name)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,14 @@
// WITH_RUNTIME
// PROBLEM: none
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Foo::class.java)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,15 @@
// WITH_RUNTIME
// PROBLEM: Logger initialized with foreign class 'Bar::class'
// FIX: Replace with 'Foo::class'
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Bar::class.java)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,15 @@
// WITH_RUNTIME
// PROBLEM: Logger initialized with foreign class 'Bar::class'
// FIX: Replace with 'Foo::class'
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(Foo::class.java)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(<caret>Bar::class.java.simpleName)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,13 @@
// WITH_RUNTIME
package org.apache.commons.logging
class Foo {
private val logger = LogFactory.getLog(Foo::class.java.simpleName)
}
class Bar
object LogFactory {
fun getLog(clazz: Class<*>) {}
fun getLog(name: String?) {}
}
@@ -0,0 +1,12 @@
// WITH_RUNTIME
package org.apache.log4j
class Foo {
private val logger = Logger.getLogger(<caret>Bar::class.java)
}
class Bar
object Logger {
fun getLogger(clazz: Class<*>) {}
}
@@ -0,0 +1,12 @@
// WITH_RUNTIME
package org.apache.log4j
class Foo {
private val logger = Logger.getLogger(Foo::class.java)
}
class Bar
object Logger {
fun getLogger(clazz: Class<*>) {}
}
@@ -0,0 +1,12 @@
// WITH_RUNTIME
package org.apache.logging.log4j
class Foo {
private val logger = LogManager.getLogger(<caret>Bar::class.java)
}
class Bar
object LogManager {
fun getLogger(clazz: Class<*>) {}
}
@@ -0,0 +1,12 @@
// WITH_RUNTIME
package org.apache.logging.log4j
class Foo {
private val logger = LogManager.getLogger(Foo::class.java)
}
class Bar
object LogManager {
fun getLogger(clazz: Class<*>) {}
}
@@ -0,0 +1,12 @@
// WITH_RUNTIME
package org.slf4j
class Foo {
private val logger = LoggerFactory.getLogger(<caret>Bar::class.java)
}
class Bar
object LoggerFactory {
fun getLogger(clazz: Class<*>) {}
}
@@ -0,0 +1,12 @@
// WITH_RUNTIME
package org.slf4j
class Foo {
private val logger = LoggerFactory.getLogger(Foo::class.java)
}
class Bar
object LoggerFactory {
fun getLogger(clazz: Class<*>) {}
}
@@ -0,0 +1,10 @@
// RUNTIME_WITH_FULL_JDK
package util
import java.util.logging.Logger
class Foo {
private val logger = Logger.getLogger(<caret>Bar::class.qualifiedName)
}
class Bar
@@ -0,0 +1,10 @@
// RUNTIME_WITH_FULL_JDK
package util
import java.util.logging.Logger
class Foo {
private val logger = Logger.getLogger(Foo::class.qualifiedName)
}
class Bar
@@ -0,0 +1,10 @@
// RUNTIME_WITH_FULL_JDK
package util
import java.util.logging.Logger.getLogger
class Foo {
private val logger = getLogger(<caret>Bar::class.qualifiedName)
}
class Bar
@@ -0,0 +1,10 @@
// RUNTIME_WITH_FULL_JDK
package util
import java.util.logging.Logger.getLogger
class Foo {
private val logger = getLogger(Foo::class.qualifiedName)
}
class Bar
@@ -5797,6 +5797,172 @@ public class LocalInspectionTestGenerated extends AbstractLocalInspectionTest {
}
}
@TestMetadata("idea/testData/inspectionsLocal/logging")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class Logging extends AbstractLocalInspectionTest {
private void runTest(String testDataFilePath) throws Exception {
KotlinTestUtils.runTest(this::doTest, this, testDataFilePath);
}
public void testAllFilesPresentInLogging() throws Exception {
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("idea/testData/inspectionsLocal/logging"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), null, true);
}
@TestMetadata("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class LoggerInitializedWithForeignClass extends AbstractLocalInspectionTest {
private void runTest(String testDataFilePath) throws Exception {
KotlinTestUtils.runTest(this::doTest, this, testDataFilePath);
}
public void testAllFilesPresentInLoggerInitializedWithForeignClass() throws Exception {
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), null, true);
}
@TestMetadata("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class Commons extends AbstractLocalInspectionTest {
private void runTest(String testDataFilePath) throws Exception {
KotlinTestUtils.runTest(this::doTest, this, testDataFilePath);
}
public void testAllFilesPresentInCommons() throws Exception {
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), null, true);
}
@TestMetadata("canonicalName.kt")
public void testCanonicalName() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/canonicalName.kt");
}
@TestMetadata("getCanonicalName.kt")
public void testGetCanonicalName() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/getCanonicalName.kt");
}
@TestMetadata("getName.kt")
public void testGetName() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/getName.kt");
}
@TestMetadata("getSimpleName.kt")
public void testGetSimpleName() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/getSimpleName.kt");
}
@TestMetadata("kclassQualiiedName.kt")
public void testKclassQualiiedName() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/kclassQualiiedName.kt");
}
@TestMetadata("kclassSimpleName.kt")
public void testKclassSimpleName() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/kclassSimpleName.kt");
}
@TestMetadata("name.kt")
public void testName() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/name.kt");
}
@TestMetadata("nonForeignClass.kt")
public void testNonForeignClass() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/nonForeignClass.kt");
}
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/simple.kt");
}
@TestMetadata("simpleName.kt")
public void testSimpleName() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/commons/simpleName.kt");
}
}
@TestMetadata("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/log4j")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class Log4j extends AbstractLocalInspectionTest {
private void runTest(String testDataFilePath) throws Exception {
KotlinTestUtils.runTest(this::doTest, this, testDataFilePath);
}
public void testAllFilesPresentInLog4j() throws Exception {
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/log4j"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), null, true);
}
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/log4j/simple.kt");
}
}
@TestMetadata("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/log4j2")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class Log4j2 extends AbstractLocalInspectionTest {
private void runTest(String testDataFilePath) throws Exception {
KotlinTestUtils.runTest(this::doTest, this, testDataFilePath);
}
public void testAllFilesPresentInLog4j2() throws Exception {
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/log4j2"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), null, true);
}
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/log4j2/simple.kt");
}
}
@TestMetadata("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/slf4j")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class Slf4j extends AbstractLocalInspectionTest {
private void runTest(String testDataFilePath) throws Exception {
KotlinTestUtils.runTest(this::doTest, this, testDataFilePath);
}
public void testAllFilesPresentInSlf4j() throws Exception {
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/slf4j"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), null, true);
}
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/slf4j/simple.kt");
}
}
@TestMetadata("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/util")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class Util extends AbstractLocalInspectionTest {
private void runTest(String testDataFilePath) throws Exception {
KotlinTestUtils.runTest(this::doTest, this, testDataFilePath);
}
public void testAllFilesPresentInUtil() throws Exception {
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/util"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), null, true);
}
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/util/simple.kt");
}
@TestMetadata("simple2.kt")
public void testSimple2() throws Exception {
runTest("idea/testData/inspectionsLocal/logging/loggerInitializedWithForeignClass/util/simple2.kt");
}
}
}
}
@TestMetadata("idea/testData/inspectionsLocal/mainFunctionReturnUnit")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)