Cleanup code: KotlinRedundantOverrideInspection

This commit is contained in:
Mikhail Glukhikh
2018-09-04 14:40:29 +03:00
parent 6cee310c54
commit 607392a2ab
@@ -18,49 +18,49 @@ import org.jetbrains.kotlin.types.typeUtil.isSubtypeOf
class KotlinRedundantOverrideInspection : AbstractKotlinInspection(), CleanupLocalInspectionTool { class KotlinRedundantOverrideInspection : AbstractKotlinInspection(), CleanupLocalInspectionTool {
override fun buildVisitor(holder: ProblemsHolder, isOnTheFly: Boolean, session: LocalInspectionToolSession) = override fun buildVisitor(holder: ProblemsHolder, isOnTheFly: Boolean, session: LocalInspectionToolSession) =
namedFunctionVisitor(fun(function) { namedFunctionVisitor(fun(function) {
val funKeyword = function.funKeyword ?: return val funKeyword = function.funKeyword ?: return
val modifierList = function.modifierList ?: return val modifierList = function.modifierList ?: return
if (!modifierList.hasModifier(KtTokens.OVERRIDE_KEYWORD)) return if (!modifierList.hasModifier(KtTokens.OVERRIDE_KEYWORD)) return
if (MODIFIER_EXCLUDE_OVERRIDE.any { modifierList.hasModifier(it) }) return if (MODIFIER_EXCLUDE_OVERRIDE.any { modifierList.hasModifier(it) }) return
if (function.annotationEntries.isNotEmpty()) return if (function.annotationEntries.isNotEmpty()) return
if (function.containingClass()?.isData() == true) return if (function.containingClass()?.isData() == true) return
val bodyExpression = function.bodyExpression ?: return val bodyExpression = function.bodyExpression ?: return
val qualifiedExpression = when (bodyExpression) { val qualifiedExpression = when (bodyExpression) {
is KtDotQualifiedExpression -> bodyExpression is KtDotQualifiedExpression -> bodyExpression
is KtBlockExpression -> { is KtBlockExpression -> {
val body = bodyExpression.statements.singleOrNull() val body = bodyExpression.statements.singleOrNull()
when (body) { when (body) {
is KtReturnExpression -> body.returnedExpression is KtReturnExpression -> body.returnedExpression
is KtDotQualifiedExpression -> body.takeIf { is KtDotQualifiedExpression -> body.takeIf { _ ->
function.typeReference.let { it == null || it.text == "Unit" } function.typeReference.let { it == null || it.text == "Unit" }
}
else -> null
} }
else -> null
} }
else -> null
} as? KtDotQualifiedExpression ?: return
val superExpression = qualifiedExpression.receiverExpression as? KtSuperExpression ?: return }
if (superExpression.superTypeQualifier != null) return else -> null
} as? KtDotQualifiedExpression ?: return
val superCallElement = qualifiedExpression.selectorExpression as? KtCallElement ?: return val superExpression = qualifiedExpression.receiverExpression as? KtSuperExpression ?: return
if (!isSameFunctionName(superCallElement, function)) return if (superExpression.superTypeQualifier != null) return
if (!isSameArguments(superCallElement, function)) return
if (function.isDefinedInDelegatedSuperType(qualifiedExpression)) return
val descriptor = holder.manager.createProblemDescriptor( val superCallElement = qualifiedExpression.selectorExpression as? KtCallElement ?: return
function, if (!isSameFunctionName(superCallElement, function)) return
TextRange(modifierList.startOffsetInParent, funKeyword.endOffset - function.startOffset), if (!isSameArguments(superCallElement, function)) return
"Redundant overriding method", if (function.isDefinedInDelegatedSuperType(qualifiedExpression)) return
ProblemHighlightType.LIKE_UNUSED_SYMBOL,
isOnTheFly, val descriptor = holder.manager.createProblemDescriptor(
RedundantOverrideFix() function,
) TextRange(modifierList.startOffsetInParent, funKeyword.endOffset - function.startOffset),
holder.registerProblem(descriptor) "Redundant overriding method",
}) ProblemHighlightType.LIKE_UNUSED_SYMBOL,
isOnTheFly,
RedundantOverrideFix()
)
holder.registerProblem(descriptor)
})
private fun isSameArguments(superCallElement: KtCallElement, function: KtNamedFunction): Boolean { private fun isSameArguments(superCallElement: KtCallElement, function: KtNamedFunction): Boolean {
val arguments = superCallElement.valueArguments val arguments = superCallElement.valueArguments
@@ -92,7 +92,7 @@ class KotlinRedundantOverrideInspection : AbstractKotlinInspection(), CleanupLoc
private fun KtNamedFunction.isDefinedInDelegatedSuperType(superQualifiedExpression: KtDotQualifiedExpression): Boolean { private fun KtNamedFunction.isDefinedInDelegatedSuperType(superQualifiedExpression: KtDotQualifiedExpression): Boolean {
val delegatedSuperTypeEntries = val delegatedSuperTypeEntries =
containingClassOrObject?.superTypeListEntries?.filterIsInstance<KtDelegatedSuperTypeEntry>() ?: return false containingClassOrObject?.superTypeListEntries?.filterIsInstance<KtDelegatedSuperTypeEntry>() ?: return false
if (delegatedSuperTypeEntries.isEmpty()) return false if (delegatedSuperTypeEntries.isEmpty()) return false
val context = superQualifiedExpression.analyze() val context = superQualifiedExpression.analyze()