Base classes for Kotlin inspections
This commit is contained in:
@@ -101,6 +101,7 @@ import org.jetbrains.jet.plugin.libraries.AbstractDecompiledTextTest
|
|||||||
import org.jetbrains.jet.plugin.imports.AbstractOptimizeImportsTest
|
import org.jetbrains.jet.plugin.imports.AbstractOptimizeImportsTest
|
||||||
import org.jetbrains.jet.plugin.debugger.AbstractSmartStepIntoTest
|
import org.jetbrains.jet.plugin.debugger.AbstractSmartStepIntoTest
|
||||||
import org.jetbrains.jet.plugin.stubs.AbstractStubBuilderTest
|
import org.jetbrains.jet.plugin.stubs.AbstractStubBuilderTest
|
||||||
|
import org.jetbrains.jet.plugin.codeInsight.AbstractJetInspectionTest
|
||||||
|
|
||||||
fun main(args: Array<String>) {
|
fun main(args: Array<String>) {
|
||||||
System.setProperty("java.awt.headless", "true")
|
System.setProperty("java.awt.headless", "true")
|
||||||
@@ -379,6 +380,10 @@ fun main(args: Array<String>) {
|
|||||||
model("intentions/attributeCallReplacements/replaceUnaryPrefixIntention", testMethod = "doTestReplaceUnaryPrefixIntention")
|
model("intentions/attributeCallReplacements/replaceUnaryPrefixIntention", testMethod = "doTestReplaceUnaryPrefixIntention")
|
||||||
model("intentions/attributeCallReplacements/replaceInvokeIntention", testMethod = "doTestReplaceInvokeIntention")
|
model("intentions/attributeCallReplacements/replaceInvokeIntention", testMethod = "doTestReplaceInvokeIntention")
|
||||||
model("intentions/simplifyNegatedBinaryExpressionIntention", testMethod = "doTestSimplifyNegatedBinaryExpressionIntention")
|
model("intentions/simplifyNegatedBinaryExpressionIntention", testMethod = "doTestSimplifyNegatedBinaryExpressionIntention")
|
||||||
|
}
|
||||||
|
|
||||||
|
testClass(javaClass<AbstractJetInspectionTest>()) {
|
||||||
|
model("codeInsight/inspections", extension = null, recursive = false)
|
||||||
model("intentions/convertNegatedBooleanSequence", testMethod="doTestConvertNegatedBooleanSequence")
|
model("intentions/convertNegatedBooleanSequence", testMethod="doTestConvertNegatedBooleanSequence")
|
||||||
model("intentions/convertNegatedExpressionWithDemorgansLaw", testMethod = "doTestConvertNegatedExpressionWithDemorgansLaw")
|
model("intentions/convertNegatedExpressionWithDemorgansLaw", testMethod = "doTestConvertNegatedExpressionWithDemorgansLaw")
|
||||||
model("intentions/swapBinaryExpression", testMethod = "doTestSwapBinaryExpression")
|
model("intentions/swapBinaryExpression", testMethod = "doTestSwapBinaryExpression")
|
||||||
|
|||||||
@@ -0,0 +1,34 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2014 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.jetbrains.jet.plugin.inspections
|
||||||
|
|
||||||
|
import com.intellij.codeInspection.LocalInspectionTool
|
||||||
|
import com.intellij.codeInspection.CustomSuppressableInspectionTool
|
||||||
|
import com.intellij.psi.PsiElement
|
||||||
|
import com.intellij.codeInspection.SuppressIntentionAction
|
||||||
|
import com.intellij.codeInspection.SuppressManager
|
||||||
|
import com.intellij.codeInsight.daemon.HighlightDisplayKey
|
||||||
|
|
||||||
|
public abstract class AbstractKotlinInspection: LocalInspectionTool(), CustomSuppressableInspectionTool {
|
||||||
|
public override fun getSuppressActions(element: PsiElement?): Array<SuppressIntentionAction>? {
|
||||||
|
return SuppressManager.getInstance()!!.createSuppressActions(HighlightDisplayKey.find(getShortName())!!)
|
||||||
|
}
|
||||||
|
|
||||||
|
public override fun isSuppressedFor(element: PsiElement): Boolean {
|
||||||
|
return SuppressManager.getInstance()!!.isSuppressedFor(element, getID())
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,80 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2014 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.jetbrains.jet.plugin.inspections
|
||||||
|
|
||||||
|
import com.intellij.psi.PsiElement
|
||||||
|
import org.jetbrains.jet.lang.psi.JetElement
|
||||||
|
import com.intellij.psi.PsiElementVisitor
|
||||||
|
import com.intellij.codeInspection.LocalInspectionToolSession
|
||||||
|
import com.intellij.codeInspection.ProblemsHolder
|
||||||
|
import com.intellij.codeInspection.ProblemHighlightType
|
||||||
|
import com.intellij.codeInspection.LocalQuickFix
|
||||||
|
import com.intellij.openapi.project.Project
|
||||||
|
import com.intellij.codeInspection.ProblemDescriptor
|
||||||
|
import org.jetbrains.jet.plugin.intentions.JetSelfTargetingIntention
|
||||||
|
import com.intellij.openapi.fileEditor.FileDocumentManager
|
||||||
|
import com.intellij.openapi.editor.EditorFactory
|
||||||
|
import com.intellij.openapi.editor.Editor
|
||||||
|
|
||||||
|
public abstract class IntentionBasedInspection<T: JetElement>(
|
||||||
|
protected val intention: JetSelfTargetingIntention<T>
|
||||||
|
) : AbstractKotlinInspection() {
|
||||||
|
override fun buildVisitor(holder: ProblemsHolder, isOnTheFly: Boolean, session: LocalInspectionToolSession): PsiElementVisitor {
|
||||||
|
return object: PsiElementVisitor() {
|
||||||
|
override fun visitElement(element: PsiElement?) {
|
||||||
|
if (!intention.elementType.isInstance(element)) return
|
||||||
|
|
||||||
|
[suppress("UNCHECKED_CAST")]
|
||||||
|
val targetElement = element as T
|
||||||
|
|
||||||
|
if (!intention.isApplicableTo(targetElement)) return
|
||||||
|
|
||||||
|
val fix = object: LocalQuickFix {
|
||||||
|
override fun getFamilyName(): String {
|
||||||
|
return getName()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun getName(): String {
|
||||||
|
return intention.getText()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun applyFix(project: Project, descriptor: ProblemDescriptor) {
|
||||||
|
targetElement.getOrCreateEditor()?.let { editor ->
|
||||||
|
editor.getCaretModel().moveToOffset(targetElement.getTextOffset())
|
||||||
|
intention.applyTo(targetElement, editor)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
holder.registerProblem(targetElement, intention.getText(), ProblemHighlightType.GENERIC_ERROR_OR_WARNING, fix)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun PsiElement.getOrCreateEditor(): Editor? {
|
||||||
|
val file = getContainingFile()?.getVirtualFile()
|
||||||
|
if (file == null) return null
|
||||||
|
|
||||||
|
val document = FileDocumentManager.getInstance()!!.getDocument(file)
|
||||||
|
if (document == null) return null
|
||||||
|
|
||||||
|
val editorFactory = EditorFactory.getInstance()!!
|
||||||
|
|
||||||
|
val editors = editorFactory.getEditors(document)
|
||||||
|
return if (editors.isEmpty()) editorFactory.createEditor(document) else editors[0]
|
||||||
|
}
|
||||||
@@ -29,9 +29,9 @@ public abstract class JetSelfTargetingIntention<T: JetElement>(val key: String,
|
|||||||
setText(JetBundle.message(key))
|
setText(JetBundle.message(key))
|
||||||
}
|
}
|
||||||
|
|
||||||
protected abstract fun isApplicableTo(element: T): Boolean
|
abstract fun isApplicableTo(element: T): Boolean
|
||||||
protected open fun isApplicableTo(element: T, editor: Editor): Boolean = isApplicableTo(element)
|
open fun isApplicableTo(element: T, editor: Editor): Boolean = isApplicableTo(element)
|
||||||
protected abstract fun applyTo(element: T, editor: Editor)
|
abstract fun applyTo(element: T, editor: Editor)
|
||||||
|
|
||||||
protected fun getTarget(editor: Editor, file: PsiFile): T? {
|
protected fun getTarget(editor: Editor, file: PsiFile): T? {
|
||||||
val offset = editor.getCaretModel().getOffset()
|
val offset = editor.getCaretModel().getOffset()
|
||||||
|
|||||||
@@ -0,0 +1,46 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2014 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.jetbrains.jet.plugin.codeInsight
|
||||||
|
|
||||||
|
import java.io.File
|
||||||
|
import org.jetbrains.jet.InTextDirectivesUtils
|
||||||
|
import com.intellij.openapi.util.io.FileUtil
|
||||||
|
import com.intellij.codeInspection.LocalInspectionTool
|
||||||
|
import com.intellij.testFramework.fixtures.LightCodeInsightFixtureTestCase
|
||||||
|
import com.intellij.testFramework.LightProjectDescriptor
|
||||||
|
import org.jetbrains.jet.plugin.JetLightProjectDescriptor
|
||||||
|
import org.jetbrains.jet.plugin.PluginTestCaseBase
|
||||||
|
import com.intellij.codeInspection.InspectionEP
|
||||||
|
import com.intellij.codeInspection.ex.LocalInspectionToolWrapper
|
||||||
|
|
||||||
|
public abstract class AbstractJetInspectionTest: LightCodeInsightFixtureTestCase() {
|
||||||
|
override fun getProjectDescriptor(): LightProjectDescriptor = JetLightProjectDescriptor.INSTANCE
|
||||||
|
|
||||||
|
override fun setUp() {
|
||||||
|
super.setUp()
|
||||||
|
myFixture!!.setTestDataPath("${PluginTestCaseBase.getTestDataPathBase()}/codeInsight/inspections")
|
||||||
|
}
|
||||||
|
|
||||||
|
protected fun doTest(path: String) {
|
||||||
|
val testDir = File(path).getName()
|
||||||
|
|
||||||
|
val options = FileUtil.loadFile(File(path, "options.test"), true)
|
||||||
|
val inspectionClass = Class.forName(InTextDirectivesUtils.findStringWithPrefixes(options, "// INSPECTION_CLASS: ")!!)
|
||||||
|
|
||||||
|
myFixture!!.testInspection(testDir, LocalInspectionToolWrapper(inspectionClass.newInstance() as LocalInspectionTool))
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user