From 605736b6ba1686b46408f02f4b31a25da5265dec Mon Sep 17 00:00:00 2001 From: Toshiaki Kameyama Date: Wed, 4 Jul 2018 19:47:57 +0900 Subject: [PATCH] Introduce "redundant asDynamic" inspection #KT-25177 Fixed --- .../RedundantAsDynamic.html | 5 +++ idea/src/META-INF/plugin.xml | 9 ++++ idea/src/META-INF/plugin.xml.173 | 10 +++++ idea/src/META-INF/plugin.xml.181 | 9 ++++ idea/src/META-INF/plugin.xml.183 | 9 ++++ idea/src/META-INF/plugin.xml.as31 | 9 ++++ idea/src/META-INF/plugin.xml.as32 | 9 ++++ .../RedundantAsDynamicInspection.kt | 45 +++++++++++++++++++ .../redundantAsDynamic/.inspection | 1 + .../redundantAsDynamic/simple.kt | 4 ++ .../redundantAsDynamic/simple.kt.after | 4 ++ .../LocalInspectionTestGenerated.java | 18 ++++++++ 12 files changed, 132 insertions(+) create mode 100644 idea/resources/inspectionDescriptions/RedundantAsDynamic.html create mode 100644 idea/src/org/jetbrains/kotlin/idea/inspections/RedundantAsDynamicInspection.kt create mode 100644 idea/testData/inspectionsLocal/redundantAsDynamic/.inspection create mode 100644 idea/testData/inspectionsLocal/redundantAsDynamic/simple.kt create mode 100644 idea/testData/inspectionsLocal/redundantAsDynamic/simple.kt.after diff --git a/idea/resources/inspectionDescriptions/RedundantAsDynamic.html b/idea/resources/inspectionDescriptions/RedundantAsDynamic.html new file mode 100644 index 00000000000..470f6b9e44c --- /dev/null +++ b/idea/resources/inspectionDescriptions/RedundantAsDynamic.html @@ -0,0 +1,5 @@ + + +This inspection reports a redundant asDynamic call. + + \ No newline at end of file diff --git a/idea/src/META-INF/plugin.xml b/idea/src/META-INF/plugin.xml index 25fa66e0862..6b63ed1b4f8 100644 --- a/idea/src/META-INF/plugin.xml +++ b/idea/src/META-INF/plugin.xml @@ -2976,6 +2976,15 @@ The Kotlin plugin provides language support in IntelliJ IDEA and Android Studio. language="kotlin" /> + + diff --git a/idea/src/META-INF/plugin.xml.173 b/idea/src/META-INF/plugin.xml.173 index b97708bebf1..135fea172ad 100644 --- a/idea/src/META-INF/plugin.xml.173 +++ b/idea/src/META-INF/plugin.xml.173 @@ -2957,6 +2957,7 @@ The Kotlin plugin provides language support in IntelliJ IDEA and Android Studio. language="kotlin" /> + + + diff --git a/idea/src/META-INF/plugin.xml.181 b/idea/src/META-INF/plugin.xml.181 index 219e2bdbfff..fb04162945a 100644 --- a/idea/src/META-INF/plugin.xml.181 +++ b/idea/src/META-INF/plugin.xml.181 @@ -2975,6 +2975,15 @@ The Kotlin plugin provides language support in IntelliJ IDEA and Android Studio. language="kotlin" /> + + diff --git a/idea/src/META-INF/plugin.xml.183 b/idea/src/META-INF/plugin.xml.183 index b6ca6c9347b..cdb2070f36e 100644 --- a/idea/src/META-INF/plugin.xml.183 +++ b/idea/src/META-INF/plugin.xml.183 @@ -2976,6 +2976,15 @@ The Kotlin plugin provides language support in IntelliJ IDEA and Android Studio. language="kotlin" /> + + diff --git a/idea/src/META-INF/plugin.xml.as31 b/idea/src/META-INF/plugin.xml.as31 index 43d1c86d3a6..6af811ec3ce 100644 --- a/idea/src/META-INF/plugin.xml.as31 +++ b/idea/src/META-INF/plugin.xml.as31 @@ -2975,6 +2975,15 @@ The Kotlin plugin provides language support in IntelliJ IDEA and Android Studio. language="kotlin" /> + + diff --git a/idea/src/META-INF/plugin.xml.as32 b/idea/src/META-INF/plugin.xml.as32 index 661d114bb0c..c7dc72cd2e9 100644 --- a/idea/src/META-INF/plugin.xml.as32 +++ b/idea/src/META-INF/plugin.xml.as32 @@ -2975,6 +2975,15 @@ The Kotlin plugin provides language support in IntelliJ IDEA and Android Studio. language="kotlin" /> + + diff --git a/idea/src/org/jetbrains/kotlin/idea/inspections/RedundantAsDynamicInspection.kt b/idea/src/org/jetbrains/kotlin/idea/inspections/RedundantAsDynamicInspection.kt new file mode 100644 index 00000000000..4a872bc0b47 --- /dev/null +++ b/idea/src/org/jetbrains/kotlin/idea/inspections/RedundantAsDynamicInspection.kt @@ -0,0 +1,45 @@ +/* + * Copyright 2010-2018 JetBrains s.r.o. 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 + +import com.intellij.codeInspection.LocalQuickFix +import com.intellij.codeInspection.ProblemDescriptor +import com.intellij.codeInspection.ProblemHighlightType +import com.intellij.codeInspection.ProblemsHolder +import com.intellij.openapi.project.Project +import org.jetbrains.kotlin.idea.intentions.getCallableDescriptor +import org.jetbrains.kotlin.idea.project.platform +import org.jetbrains.kotlin.js.resolve.JsPlatform +import org.jetbrains.kotlin.psi.KtCallExpression +import org.jetbrains.kotlin.psi.callExpressionVisitor +import org.jetbrains.kotlin.psi.psiUtil.getQualifiedExpressionForSelector +import org.jetbrains.kotlin.types.DynamicType + +class RedundantAsDynamicInspection : AbstractKotlinInspection() { + override fun buildVisitor(holder: ProblemsHolder, isOnTheFly: Boolean) = + callExpressionVisitor(fun(call) { + if (call.platform != JsPlatform) return + if (call.calleeExpression?.text != "asDynamic") return + if (call.getQualifiedExpressionForSelector()?.receiverExpression?.getCallableDescriptor()?.returnType !is DynamicType) return + holder.registerProblem( + call, + "Redundant 'asDynamic' call", + ProblemHighlightType.GENERIC_ERROR_OR_WARNING, + RemoveAsDynamicCallFix() + ) + }) +} + +private class RemoveAsDynamicCallFix : LocalQuickFix { + override fun getName() = "Remove 'asDynamic' call" + + override fun getFamilyName() = name + + override fun applyFix(project: Project, descriptor: ProblemDescriptor) { + val qualifiedExpression = (descriptor.psiElement as? KtCallExpression)?.getQualifiedExpressionForSelector() ?: return + qualifiedExpression.replace(qualifiedExpression.receiverExpression) + } +} diff --git a/idea/testData/inspectionsLocal/redundantAsDynamic/.inspection b/idea/testData/inspectionsLocal/redundantAsDynamic/.inspection new file mode 100644 index 00000000000..fbd5f7c0655 --- /dev/null +++ b/idea/testData/inspectionsLocal/redundantAsDynamic/.inspection @@ -0,0 +1 @@ +org.jetbrains.kotlin.idea.inspections.RedundantAsDynamicInspection \ No newline at end of file diff --git a/idea/testData/inspectionsLocal/redundantAsDynamic/simple.kt b/idea/testData/inspectionsLocal/redundantAsDynamic/simple.kt new file mode 100644 index 00000000000..1350b1eeb9b --- /dev/null +++ b/idea/testData/inspectionsLocal/redundantAsDynamic/simple.kt @@ -0,0 +1,4 @@ +// JS +fun test(d: dynamic) { + d.asDynamic().foo() +} \ No newline at end of file diff --git a/idea/testData/inspectionsLocal/redundantAsDynamic/simple.kt.after b/idea/testData/inspectionsLocal/redundantAsDynamic/simple.kt.after new file mode 100644 index 00000000000..1daa5c1901e --- /dev/null +++ b/idea/testData/inspectionsLocal/redundantAsDynamic/simple.kt.after @@ -0,0 +1,4 @@ +// JS +fun test(d: dynamic) { + d.foo() +} \ No newline at end of file diff --git a/idea/tests/org/jetbrains/kotlin/idea/inspections/LocalInspectionTestGenerated.java b/idea/tests/org/jetbrains/kotlin/idea/inspections/LocalInspectionTestGenerated.java index 42c62dda192..01eefbbe5e8 100644 --- a/idea/tests/org/jetbrains/kotlin/idea/inspections/LocalInspectionTestGenerated.java +++ b/idea/tests/org/jetbrains/kotlin/idea/inspections/LocalInspectionTestGenerated.java @@ -3487,6 +3487,24 @@ public class LocalInspectionTestGenerated extends AbstractLocalInspectionTest { } } + @TestMetadata("idea/testData/inspectionsLocal/redundantAsDynamic") + @TestDataPath("$PROJECT_ROOT") + @RunWith(JUnit3RunnerWithInners.class) + public static class RedundantAsDynamic extends AbstractLocalInspectionTest { + private void runTest(String testDataFilePath) throws Exception { + KotlinTestUtils.runTest(this::doTest, TargetBackend.ANY, testDataFilePath); + } + + public void testAllFilesPresentInRedundantAsDynamic() throws Exception { + KotlinTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("idea/testData/inspectionsLocal/redundantAsDynamic"), Pattern.compile("^([\\w\\-_]+)\\.(kt|kts)$"), TargetBackend.ANY, true); + } + + @TestMetadata("simple.kt") + public void testSimple() throws Exception { + runTest("idea/testData/inspectionsLocal/redundantAsDynamic/simple.kt"); + } + } + @TestMetadata("idea/testData/inspectionsLocal/redundantCompanionReference") @TestDataPath("$PROJECT_ROOT") @RunWith(JUnit3RunnerWithInners.class)