Remove explicit type intention should not be available on public
This commit is contained in:
@@ -75,16 +75,13 @@ public class ConvertToExpressionBodyIntention : JetSelfTargetingOffsetIndependen
|
||||
editor.getCaretModel().moveToOffset(range.getEndOffset())
|
||||
}
|
||||
else {
|
||||
(declaration : PsiElement).deleteChildRange(colon, typeRef)
|
||||
(declaration as PsiElement).deleteChildRange(colon, typeRef)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun canOmitType(declaration: JetCallableDeclaration, expression: JetExpression): Boolean {
|
||||
if (declaration.getModifierList()?.hasModifier(JetTokens.OVERRIDE_KEYWORD) ?: false) return true
|
||||
|
||||
val descriptor = declaration.resolveToDescriptor()
|
||||
if ((descriptor as? DeclarationDescriptorWithVisibility)?.getVisibility()?.isPublicAPI() ?: false) return false
|
||||
if (!declaration.canRemoveTypeSpecificationByVisibility()) return false
|
||||
|
||||
// Workaround for anonymous objects and similar expressions without resolution scope
|
||||
// TODO: This should probably be fixed in front-end so that resolution scope is recorded for anonymous objects as well
|
||||
@@ -92,7 +89,7 @@ public class ConvertToExpressionBodyIntention : JetSelfTargetingOffsetIndependen
|
||||
?.getStatements()?.singleOrNull() as? JetExpression
|
||||
?: return false
|
||||
|
||||
val declaredType = (descriptor as? CallableDescriptor)?.getReturnType() ?: return false
|
||||
val declaredType = (declaration.resolveToDescriptor() as? CallableDescriptor)?.getReturnType() ?: return false
|
||||
val scope = scopeExpression.analyze()[BindingContext.RESOLUTION_SCOPE, scopeExpression] ?: return false
|
||||
val expressionType = expression.analyzeInContext(scope).getType(expression) ?: return false
|
||||
return expressionType.isSubtypeOf(declaredType)
|
||||
|
||||
@@ -39,16 +39,17 @@ import java.util.*
|
||||
|
||||
public class RemoveExplicitTypeIntention : JetSelfTargetingIntention<JetCallableDeclaration>(javaClass(), "Remove explicit type specification") {
|
||||
override fun isApplicableTo(element: JetCallableDeclaration, caretOffset: Int): Boolean {
|
||||
//TODO: check for public API
|
||||
if (element.getContainingFile() is JetCodeFragment) return false
|
||||
if (element.getTypeReference() == null) return false
|
||||
|
||||
val initializer = (element as? JetWithExpressionInitializer)?.getInitializer()
|
||||
if (initializer != null && initializer.getTextRange().containsOffset(caretOffset)) return false
|
||||
|
||||
if (!element.canRemoveTypeSpecificationByVisibility()) return false
|
||||
|
||||
return when (element) {
|
||||
is JetProperty -> true
|
||||
is JetNamedFunction -> !element.hasBlockBody() && element.getBodyExpression() != null
|
||||
is JetProperty -> initializer != null
|
||||
is JetNamedFunction -> !element.hasBlockBody() && initializer != null
|
||||
is JetParameter -> element.isLoopParameter()
|
||||
else -> false
|
||||
}
|
||||
|
||||
@@ -18,15 +18,20 @@ package org.jetbrains.kotlin.idea.intentions
|
||||
|
||||
import com.intellij.openapi.util.TextRange
|
||||
import org.jetbrains.kotlin.JetNodeTypes
|
||||
import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
||||
import org.jetbrains.kotlin.analyzer.analyzeInContext
|
||||
import org.jetbrains.kotlin.descriptors.CallableDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptorWithVisibility
|
||||
import org.jetbrains.kotlin.descriptors.ValueParameterDescriptor
|
||||
import org.jetbrains.kotlin.idea.caches.resolve.analyze
|
||||
import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptor
|
||||
import org.jetbrains.kotlin.idea.references.JetReference
|
||||
import org.jetbrains.kotlin.idea.util.IdeDescriptorRenderers
|
||||
import org.jetbrains.kotlin.idea.util.ShortenReferences
|
||||
import org.jetbrains.kotlin.lexer.JetTokens
|
||||
import org.jetbrains.kotlin.psi.*
|
||||
import org.jetbrains.kotlin.resolve.BindingContext
|
||||
import org.jetbrains.kotlin.types.JetType
|
||||
import org.jetbrains.kotlin.types.typeUtil.isSubtypeOf
|
||||
|
||||
fun JetCallableDeclaration.setType(type: JetType) {
|
||||
if (type.isError()) return
|
||||
@@ -59,3 +64,10 @@ fun isAutoCreatedItUsage(expression: JetSimpleNameExpression): Boolean {
|
||||
val target = reference?.resolveToDescriptors(context)?.singleOrNull() as? ValueParameterDescriptor? ?: return false
|
||||
return context[BindingContext.AUTO_CREATED_IT, target]
|
||||
}
|
||||
|
||||
fun JetCallableDeclaration.canRemoveTypeSpecificationByVisibility(): Boolean {
|
||||
val descriptor = resolveToDescriptor()
|
||||
val isOverride = getModifierList()?.hasModifier(JetTokens.OVERRIDE_KEYWORD) ?: false
|
||||
if (!isOverride && (descriptor as? DeclarationDescriptorWithVisibility)?.getVisibility()?.isPublicAPI() ?: false) return false
|
||||
return true
|
||||
}
|
||||
@@ -0,0 +1,2 @@
|
||||
// IS_APPLICABLE: false
|
||||
public var x: String? = null
|
||||
@@ -0,0 +1,7 @@
|
||||
public trait I {
|
||||
public fun foo(): String
|
||||
}
|
||||
|
||||
public class C : I {
|
||||
override fun foo(): <caret>String = ""
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
public trait I {
|
||||
public fun foo(): String
|
||||
}
|
||||
|
||||
public class C : I {
|
||||
override fun foo() = ""
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
// IS_APPLICABLE: false
|
||||
public trait I {
|
||||
public val v: String?
|
||||
}
|
||||
|
||||
public trait I1 : I {
|
||||
override val v: String<caret>
|
||||
}
|
||||
@@ -5050,6 +5050,24 @@ public class IntentionTestGenerated extends AbstractIntentionTest {
|
||||
JetTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("idea/testData/intentions/removeExplicitType"), Pattern.compile("^(.+)\\.kt$"), true);
|
||||
}
|
||||
|
||||
@TestMetadata("notOnPublic.kt")
|
||||
public void testNotOnPublic() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/testData/intentions/removeExplicitType/notOnPublic.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("onOverride.kt")
|
||||
public void testOnOverride() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/testData/intentions/removeExplicitType/onOverride.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("onOverrideInTrait.kt")
|
||||
public void testOnOverrideInTrait() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/testData/intentions/removeExplicitType/onOverrideInTrait.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("onType.kt")
|
||||
public void testOnType() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/testData/intentions/removeExplicitType/onType.kt");
|
||||
|
||||
Reference in New Issue
Block a user