Do not disable 'redundant visibility modifier' inspection completely in Explicit API mode.
Instead, disable it only for effectively public declarations. Add tests for this IDE inspection.
This commit is contained in:
+17
@@ -1,3 +1,20 @@
|
|||||||
private class Foo {
|
private class Foo {
|
||||||
fun method() {}
|
fun method() {}
|
||||||
|
}
|
||||||
|
|
||||||
|
public interface I {
|
||||||
|
public fun bar()
|
||||||
|
}
|
||||||
|
|
||||||
|
public fun f() {
|
||||||
|
val i = object : I {
|
||||||
|
internal var foo = 0
|
||||||
|
override fun bar() {}
|
||||||
|
}
|
||||||
|
i.foo = 1
|
||||||
|
|
||||||
|
class LocalClass {
|
||||||
|
internal var foo = 0
|
||||||
|
}
|
||||||
|
LocalClass().foo = 1
|
||||||
}
|
}
|
||||||
+9
@@ -1,5 +1,7 @@
|
|||||||
package
|
package
|
||||||
|
|
||||||
|
public fun f(): kotlin.Unit
|
||||||
|
|
||||||
private final class Foo {
|
private final class Foo {
|
||||||
public constructor Foo()
|
public constructor Foo()
|
||||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
@@ -7,3 +9,10 @@ private final class Foo {
|
|||||||
public final fun method(): kotlin.Unit
|
public final fun method(): kotlin.Unit
|
||||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public interface I {
|
||||||
|
public abstract fun bar(): kotlin.Unit
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|||||||
+5
-1
@@ -13,6 +13,8 @@ import org.jetbrains.kotlin.descriptors.PropertyDescriptor
|
|||||||
import org.jetbrains.kotlin.descriptors.Visibilities
|
import org.jetbrains.kotlin.descriptors.Visibilities
|
||||||
import org.jetbrains.kotlin.descriptors.Visibility
|
import org.jetbrains.kotlin.descriptors.Visibility
|
||||||
import org.jetbrains.kotlin.config.ExplicitApiMode
|
import org.jetbrains.kotlin.config.ExplicitApiMode
|
||||||
|
import org.jetbrains.kotlin.descriptors.DeclarationDescriptorWithVisibility
|
||||||
|
import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptorIfAny
|
||||||
import org.jetbrains.kotlin.idea.core.implicitVisibility
|
import org.jetbrains.kotlin.idea.core.implicitVisibility
|
||||||
import org.jetbrains.kotlin.idea.project.languageVersionSettings
|
import org.jetbrains.kotlin.idea.project.languageVersionSettings
|
||||||
import org.jetbrains.kotlin.idea.quickfix.RemoveModifierFix
|
import org.jetbrains.kotlin.idea.quickfix.RemoveModifierFix
|
||||||
@@ -25,16 +27,18 @@ import org.jetbrains.kotlin.psi.declarationVisitor
|
|||||||
import org.jetbrains.kotlin.psi.psiUtil.containingClassOrObject
|
import org.jetbrains.kotlin.psi.psiUtil.containingClassOrObject
|
||||||
import org.jetbrains.kotlin.psi.psiUtil.visibilityModifier
|
import org.jetbrains.kotlin.psi.psiUtil.visibilityModifier
|
||||||
import org.jetbrains.kotlin.utils.addToStdlib.firstNotNullResult
|
import org.jetbrains.kotlin.utils.addToStdlib.firstNotNullResult
|
||||||
|
import org.jetbrains.kotlin.resolve.descriptorUtil.isEffectivelyPublicApi
|
||||||
|
|
||||||
class RedundantVisibilityModifierInspection : AbstractKotlinInspection(), CleanupLocalInspectionTool {
|
class RedundantVisibilityModifierInspection : AbstractKotlinInspection(), CleanupLocalInspectionTool {
|
||||||
override fun buildVisitor(holder: ProblemsHolder, isOnTheFly: Boolean, session: LocalInspectionToolSession): PsiElementVisitor {
|
override fun buildVisitor(holder: ProblemsHolder, isOnTheFly: Boolean, session: LocalInspectionToolSession): PsiElementVisitor {
|
||||||
return declarationVisitor(fun(declaration: KtDeclaration) {
|
return declarationVisitor(fun(declaration: KtDeclaration) {
|
||||||
val isInApiMode = declaration.languageVersionSettings.getFlag(AnalysisFlags.explicitApiMode) != ExplicitApiMode.DISABLED
|
val isInApiMode = declaration.languageVersionSettings.getFlag(AnalysisFlags.explicitApiMode) != ExplicitApiMode.DISABLED
|
||||||
if (isInApiMode) return@declarationVisitor
|
|
||||||
|
|
||||||
if (declaration is KtPropertyAccessor && declaration.isGetter) return // There is a quick fix for REDUNDANT_MODIFIER_IN_GETTER
|
if (declaration is KtPropertyAccessor && declaration.isGetter) return // There is a quick fix for REDUNDANT_MODIFIER_IN_GETTER
|
||||||
val visibilityModifier = declaration.visibilityModifier() ?: return
|
val visibilityModifier = declaration.visibilityModifier() ?: return
|
||||||
val implicitVisibility = declaration.implicitVisibility()
|
val implicitVisibility = declaration.implicitVisibility()
|
||||||
|
if (isInApiMode && (declaration.resolveToDescriptorIfAny() as? DeclarationDescriptorWithVisibility)?.isEffectivelyPublicApi == true) return@declarationVisitor
|
||||||
|
|
||||||
val redundantVisibility = when {
|
val redundantVisibility = when {
|
||||||
visibilityModifier.node.elementType == implicitVisibility ->
|
visibilityModifier.node.elementType == implicitVisibility ->
|
||||||
implicitVisibility
|
implicitVisibility
|
||||||
|
|||||||
Vendored
+34
@@ -0,0 +1,34 @@
|
|||||||
|
<problems>
|
||||||
|
<problem>
|
||||||
|
<file>redundantVisibilityModifierWithExplicitApi.kt</file>
|
||||||
|
<line>24</line>
|
||||||
|
<module>light_idea_test_case</module>
|
||||||
|
<entry_point TYPE="file" FQNAME="temp:///src/redundantVisibilityModifierWithExplicitApi.kt" />
|
||||||
|
<problem_class severity="WARNING" attribute_key="NOT_USED_ELEMENT_ATTRIBUTES">Redundant visibility modifier</problem_class>
|
||||||
|
<description>Redundant visibility modifier</description>
|
||||||
|
</problem>
|
||||||
|
<problem>
|
||||||
|
<file>redundantVisibilityModifierWithExplicitApi.kt</file>
|
||||||
|
<line>29</line>
|
||||||
|
<module>light_idea_test_case</module>
|
||||||
|
<entry_point TYPE="file" FQNAME="temp:///src/redundantVisibilityModifierWithExplicitApi.kt" />
|
||||||
|
<problem_class severity="WARNING" attribute_key="NOT_USED_ELEMENT_ATTRIBUTES">Redundant visibility modifier</problem_class>
|
||||||
|
<description>Redundant visibility modifier</description>
|
||||||
|
</problem>
|
||||||
|
<problem>
|
||||||
|
<file>redundantVisibilityModifierWithExplicitApi.kt</file>
|
||||||
|
<line>40</line>
|
||||||
|
<module>light_idea_test_case</module>
|
||||||
|
<entry_point TYPE="file" FQNAME="temp:///src/redundantVisibilityModifierWithExplicitApi.kt" />
|
||||||
|
<problem_class severity="WARNING" attribute_key="NOT_USED_ELEMENT_ATTRIBUTES">Redundant visibility modifier</problem_class>
|
||||||
|
<description>Redundant visibility modifier</description>
|
||||||
|
</problem>
|
||||||
|
<problem>
|
||||||
|
<file>redundantVisibilityModifierWithExplicitApi.kt</file>
|
||||||
|
<line>46</line>
|
||||||
|
<module>light_idea_test_case</module>
|
||||||
|
<entry_point TYPE="file" FQNAME="temp:///src/redundantVisibilityModifierWithExplicitApi.kt" />
|
||||||
|
<problem_class severity="WARNING" attribute_key="NOT_USED_ELEMENT_ATTRIBUTES">Redundant visibility modifier</problem_class>
|
||||||
|
<description>Redundant visibility modifier</description>
|
||||||
|
</problem>
|
||||||
|
</problems>
|
||||||
idea/testData/inspections/redundantVisibilityModifierWithExplicitApi/inspectionData/inspections.test
Vendored
+2
@@ -0,0 +1,2 @@
|
|||||||
|
// INSPECTION_CLASS: org.jetbrains.kotlin.idea.inspections.RedundantVisibilityModifierInspection
|
||||||
|
// COMPILER_ARGUMENTS: -Xexplicit-api=strict
|
||||||
+49
@@ -0,0 +1,49 @@
|
|||||||
|
public class C {
|
||||||
|
public val foo: Int = 0
|
||||||
|
|
||||||
|
public fun bar() {}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
open class D {
|
||||||
|
protected open fun willRemainProtected() {
|
||||||
|
}
|
||||||
|
|
||||||
|
protected open fun willBecomePublic() {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class E : D() {
|
||||||
|
protected override fun willRemainProtected() {
|
||||||
|
}
|
||||||
|
|
||||||
|
public override fun willBecomePublic() {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
enum class F private constructor(val x: Int) {
|
||||||
|
FIRST(42)
|
||||||
|
}
|
||||||
|
|
||||||
|
sealed class G constructor(val y: Int) {
|
||||||
|
private constructor(): this(42)
|
||||||
|
|
||||||
|
object H : G()
|
||||||
|
}
|
||||||
|
|
||||||
|
interface I {
|
||||||
|
fun bar()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun f() {
|
||||||
|
val i = object : I {
|
||||||
|
internal var foo = 0
|
||||||
|
override fun bar() {}
|
||||||
|
}
|
||||||
|
i.foo = 1
|
||||||
|
|
||||||
|
class LocalClass {
|
||||||
|
internal var foo = 0
|
||||||
|
}
|
||||||
|
LocalClass().foo = 1
|
||||||
|
}
|
||||||
+5
@@ -313,6 +313,11 @@ public class InspectionTestGenerated extends AbstractInspectionTest {
|
|||||||
runTest("idea/testData/inspections/redundantVisibilityModifier/inspectionData/inspections.test");
|
runTest("idea/testData/inspections/redundantVisibilityModifier/inspectionData/inspections.test");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("redundantVisibilityModifierWithExplicitApi/inspectionData/inspections.test")
|
||||||
|
public void testRedundantVisibilityModifierWithExplicitApi_inspectionData_Inspections_test() throws Exception {
|
||||||
|
runTest("idea/testData/inspections/redundantVisibilityModifierWithExplicitApi/inspectionData/inspections.test");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("redundantWith/inspectionData/inspections.test")
|
@TestMetadata("redundantWith/inspectionData/inspections.test")
|
||||||
public void testRedundantWith_inspectionData_Inspections_test() throws Exception {
|
public void testRedundantWith_inspectionData_Inspections_test() throws Exception {
|
||||||
runTest("idea/testData/inspections/redundantWith/inspectionData/inspections.test");
|
runTest("idea/testData/inspections/redundantWith/inspectionData/inspections.test");
|
||||||
|
|||||||
Reference in New Issue
Block a user