Provide inspection and quickfixes for usages of static fields which will be no longer accessible in future versions

For this inspection three kinds of fixes are potentially available:
- Add 'const' modifier to kotlin property
- Add '@JvmField' annotation to kotlin property
- Change field reference to getter invocation

In case user chooses to 'cleanup code', these fixes are prioritized in this order
This commit is contained in:
Pavel V. Talanov
2015-10-12 21:35:47 +03:00
parent 47cca7db1f
commit d603142cc6
44 changed files with 679 additions and 35 deletions
@@ -17,6 +17,7 @@
package org.jetbrains.kotlin.idea.test
import com.intellij.codeInsight.intention.IntentionAction
import com.intellij.psi.PsiFile
import com.intellij.testFramework.UsefulTestCase
import org.jetbrains.kotlin.diagnostics.Severity
import org.jetbrains.kotlin.idea.caches.resolve.analyzeFully
@@ -42,7 +43,7 @@ public object DirectiveBasedActionUtils {
expectedErrors)
}
public fun checkAvailableActionsAreExpected(file: JetFile, availableActions: Collection<IntentionAction>) {
public fun checkAvailableActionsAreExpected(file: PsiFile, availableActions: Collection<IntentionAction>) {
val expectedActions = InTextDirectivesUtils.findLinesWithPrefixesRemoved(file.getText(), "// ACTION:").sorted()
UsefulTestCase.assertEmpty("Irrelevant actions should not be specified in ACTION directive for they are not checked anyway",
@@ -70,6 +71,11 @@ public object DirectiveBasedActionUtils {
"Inject language or reference",
"Suppress '",
"Run inspection on",
"Inspection '"
"Inspection '",
"Suppress for ",
"Suppress all ",
"Edit cleanup profile settings",
"Fix all '",
"Cleanup code"
)
}
+8
View File
@@ -1260,6 +1260,14 @@
cleanupTool="true"
level="WARNING"/>
<localInspection implementationClass="org.jetbrains.kotlin.idea.inspections.DeprecatedUsageOfStaticFieldInspection"
displayName="This field will not be generated in future versions of Kotlin. Use 'const' modifier, '@JvmField' annotation or access data through corresponding object."
groupName="Kotlin"
language="JAVA"
enabledByDefault="true"
cleanupTool="true"
level="WARNING"/>
<referenceImporter implementation="org.jetbrains.kotlin.idea.quickfix.KotlinReferenceImporter"/>
<fileType.fileViewProviderFactory filetype="KJSM" implementationClass="com.intellij.psi.ClassFileViewProviderFactory"/>
@@ -0,0 +1,156 @@
/*
* Copyright 2010-2015 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.kotlin.idea.inspections
import com.intellij.codeInspection.*
import com.intellij.openapi.project.Project
import com.intellij.psi.*
import org.jetbrains.kotlin.asJava.KotlinLightClass
import org.jetbrains.kotlin.asJava.KotlinLightFieldForDeclaration
import org.jetbrains.kotlin.idea.quickfix.AddConstModifierFix
import org.jetbrains.kotlin.idea.quickfix.AddConstModifierIntention
import org.jetbrains.kotlin.idea.quickfix.replaceReferencesToGetterByReferenceToField
import org.jetbrains.kotlin.lexer.JetTokens
import org.jetbrains.kotlin.load.java.JvmAbi
import org.jetbrains.kotlin.psi.JetClass
import org.jetbrains.kotlin.psi.JetObjectDeclaration
import org.jetbrains.kotlin.psi.JetProperty
import org.jetbrains.kotlin.psi.JetPsiFactory
import java.util.*
class DeprecatedUsageOfStaticFieldInspection : LocalInspectionTool(), CleanupLocalInspectionTool {
override fun buildVisitor(holder: ProblemsHolder, isOnTheFly: Boolean, session: LocalInspectionToolSession): PsiElementVisitor {
return object : JavaElementVisitor() {
override fun visitReferenceExpression(expression: PsiReferenceExpression) {
val resolvedTo = expression.reference?.resolve() as? PsiField ?: return
if (!resolvedTo.hasModifierProperty(PsiModifier.STATIC) || !resolvedTo.isDeprecated) return
val kotlinProperty = (resolvedTo as? KotlinLightFieldForDeclaration)?.getOrigin() as? JetProperty
// NOTE: this is hack to avoid test failing with "action is still available" error
if (kotlinProperty?.hasJvmFieldAnnotationOrConstModifier() ?: false) return
val kotlinClassOrObject = (resolvedTo.containingClass as? KotlinLightClass)?.getOrigin() ?: return
val containingObject = when (kotlinClassOrObject) {
is JetObjectDeclaration -> kotlinClassOrObject as JetObjectDeclaration // KT-9578
is JetClass -> kotlinClassOrObject.getCompanionObjects().singleOrNull() ?: return
else -> return
}
holder.registerProblem(
expression, "This field will not be generated in future versions of Kotlin. Use 'const' modifier, '@JvmField' annotation or access data through corresponding object.",
ProblemHighlightType.LIKE_DEPRECATED,
*createFixes(containingObject, kotlinProperty).toTypedArray()
)
}
}
}
private fun createFixes(containingObject: JetObjectDeclaration, property: JetProperty?): List<LocalQuickFix> {
if (containingObject.getContainingJetFile().isCompiled) return listOf(ReplaceWithGetterInvocationFix())
// order matters here, 'cleanup' applies fixes in this order
val fixes = ArrayList<LocalQuickFix>()
if (property != null && AddConstModifierIntention.isApplicableTo(property)) {
fixes.add(AddConstModifierLocalFix())
}
if (containingObject.isCompanion()) {
val classWithCompanion = containingObject.parent?.parent as? JetClass ?: return listOf()
if (!classWithCompanion.isInterface()) {
fixes.add(AddJvmFieldAnnotationFix())
}
} else {
fixes.add(AddJvmFieldAnnotationFix())
}
fixes.add(ReplaceWithGetterInvocationFix())
return fixes
}
}
abstract class StaticFieldUsageFix: LocalQuickFix {
override fun applyFix(project: Project, descriptor: ProblemDescriptor) {
val deprecatedField = descriptor.psiElement.reference?.resolve() as? PsiField ?: return
val kotlinProperty = (deprecatedField as? KotlinLightFieldForDeclaration)?.getOrigin() as? JetProperty
if (kotlinProperty != null && kotlinProperty.hasJvmFieldAnnotationOrConstModifier()) return
doFix(deprecatedField, kotlinProperty, descriptor)
}
abstract fun doFix(deprecatedField: PsiField, property: JetProperty?, problemDescriptor: ProblemDescriptor)
}
class AddJvmFieldAnnotationFix : StaticFieldUsageFix() {
override fun doFix(deprecatedField: PsiField, property: JetProperty?, problemDescriptor: ProblemDescriptor) {
replaceReferencesToGetterByReferenceToField(property ?: return)
property.addAnnotationEntry(JetPsiFactory(property).createAnnotationEntry("@JvmField"))
}
override fun getName(): String = "Annotate property with @JvmField"
override fun getFamilyName(): String = name
}
class AddConstModifierLocalFix : StaticFieldUsageFix() {
override fun getName(): String = "Add 'const' modifier to a property"
override fun getFamilyName(): String = name
override fun doFix(deprecatedField: PsiField, property: JetProperty?, problemDescriptor: ProblemDescriptor) {
AddConstModifierFix.addConstModifier(property ?: return)
}
}
class ReplaceWithGetterInvocationFix : StaticFieldUsageFix() {
override fun getName(): String = "Replace with getter invocation"
override fun getFamilyName(): String = name
override fun doFix(deprecatedField: PsiField, property: JetProperty?, problemDescriptor: ProblemDescriptor) {
val lightClass = deprecatedField.containingClass as? KotlinLightClass ?: return
fun replaceWithGetterInvocation(objectField: PsiField) {
val factory = PsiElementFactory.SERVICE.getInstance(deprecatedField.project)
val elementToReplace = problemDescriptor.psiElement
val getterInvocation = factory.createExpressionFromText(
objectField.containingClass!!.qualifiedName + "." + objectField.name + "." + JvmAbi.getterName(deprecatedField.name!!) + "()",
elementToReplace
)
elementToReplace.replace(getterInvocation)
}
val kotlinClass = lightClass.getOrigin()
when (kotlinClass) {
is JetObjectDeclaration -> {
val instanceField = lightClass.findFieldByName(JvmAbi.INSTANCE_FIELD, false) ?: return
replaceWithGetterInvocation(instanceField)
}
is JetClass -> {
val companionObjectName = kotlinClass.getCompanionObjects().singleOrNull()?.name ?: return
val companionObjectField = lightClass.findFieldByName(companionObjectName, false) ?: return
replaceWithGetterInvocation(companionObjectField)
}
}
}
}
private fun JetProperty.hasJvmFieldAnnotationOrConstModifier(): Boolean {
return hasModifier(JetTokens.CONST_KEYWORD) || annotationEntries.any { it.text == "@JvmField" }
}
@@ -48,30 +48,8 @@ public class AddConstModifierFix(val property: JetProperty) : AddModifierFix(pro
companion object {
fun addConstModifier(property: JetProperty) {
val project = property.project
val getter = LightClassUtil.getLightClassPropertyMethods(property).getter
val javaScope = GlobalSearchScope.getScopeRestrictedByFileTypes(project.allScope(), JavaFileType.INSTANCE)
val getterUsages = if (getter != null)
ReferencesSearch.search(getter, javaScope).findAll()
else
emptyList()
replaceReferencesToGetterByReferenceToField(property)
property.addModifier(JetTokens.CONST_KEYWORD)
val backingField = LightClassUtil.getLightClassPropertyMethods(property).backingField
if (backingField != null) {
val factory = PsiElementFactory.SERVICE.getInstance(project)
val fieldFQName = backingField.containingClass!!.qualifiedName + "." + backingField.name
getterUsages.forEach {
val call = it.element.getNonStrictParentOfType<PsiMethodCallExpression>()
if (call != null && it.element == call.methodExpression) {
val fieldRef = factory.createExpressionFromText(fieldFQName, it.element)
call.replace(fieldRef)
}
}
}
}
}
}
@@ -82,12 +60,18 @@ public class AddConstModifierIntention : JetSelfTargetingIntention<JetProperty>(
}
override fun isApplicableTo(element: JetProperty, caretOffset: Int): Boolean {
if (element.isLocal || element.isVar || element.hasDelegate() || element.initializer == null || element.getter?.hasBody() == true ||
element.receiverTypeReference != null) {
return false
return isApplicableTo(element)
}
companion object {
fun isApplicableTo(element: JetProperty): Boolean {
if (element.isLocal || element.isVar || element.hasDelegate() || element.initializer == null
|| element.getter?.hasBody() == true || element.receiverTypeReference != null) {
return false
}
val propertyDescriptor = element.descriptor as? VariableDescriptor ?: return false
return ConstModifierChecker.checkCanBeConst(element, element, propertyDescriptor) == null
}
val propertyDescriptor = element.descriptor as? VariableDescriptor ?: return false
return ConstModifierChecker.checkCanBeConst(element, element, propertyDescriptor) == null
}
}
@@ -104,3 +88,29 @@ public object ConstFixFactory : JetSingleIntentionActionFactory() {
return null
}
}
fun replaceReferencesToGetterByReferenceToField(property: JetProperty) {
val project = property.project
val getter = LightClassUtil.getLightClassPropertyMethods(property).getter
val javaScope = GlobalSearchScope.getScopeRestrictedByFileTypes(project.allScope(), JavaFileType.INSTANCE)
val getterUsages = if (getter != null)
ReferencesSearch.search(getter, javaScope).findAll()
else
emptyList()
val backingField = LightClassUtil.getLightClassPropertyMethods(property).backingField
if (backingField != null) {
val factory = PsiElementFactory.SERVICE.getInstance(project)
val fieldFQName = backingField.containingClass!!.qualifiedName + "." + backingField.name
getterUsages.forEach {
val call = it.element.getNonStrictParentOfType<PsiMethodCallExpression>()
if (call != null && it.element == call.methodExpression) {
val fieldRef = factory.createExpressionFromText(fieldFQName, it.element)
call.replace(fieldRef)
}
}
}
}
@@ -0,0 +1 @@
org.jetbrains.kotlin.idea.inspections.DeprecatedUsageOfStaticFieldInspection
@@ -0,0 +1,22 @@
package a
class A
class Cl {
companion object {
@JvmField val property1 = A()
const val property2 = 2
}
}
interface Int {
companion object {
val property1 = A()
const val property2 = 2
}
}
object Obj {
@JvmField val property1 = A()
const val property2 = 2
}
@@ -0,0 +1,19 @@
// "Cleanup code" "true"
import a.*;
class B {
void bar() {
Cl.property1;
Cl.property2;
Cl.property1;
Cl.property2;
Int.Companion.getProperty1();
Int.property2;
Int.Companion.getProperty1();
Int.property2;
Obj.property1;
Obj.property2;
Obj.property1;
Obj.property2;
}
}
@@ -0,0 +1,19 @@
// "Cleanup code" "true"
import a.*;
class B {
void bar() {
Cl.prope<caret>rty1;
Cl.property2;
Cl.Companion.getProperty1();
Cl.Companion.getProperty2();
Int.property1;
Int.property2;
Int.Companion.getProperty1();
Int.Companion.getProperty2();
Obj.property1;
Obj.property2;
Obj.INSTANCE.getProperty1();
Obj.INSTANCE.getProperty2();
}
}
@@ -0,0 +1,22 @@
package a
class A
class Cl {
companion object {
val property1 = A()
val property2 = 2
}
}
interface Int {
companion object {
val property1 = A()
val property2 = 2
}
}
object Obj {
val property1 = A()
val property2 = 2
}
@@ -0,0 +1,7 @@
package a
class A {
companion object Named {
const val property = 1
}
}
@@ -0,0 +1,10 @@
// "Add 'const' modifier to a property" "true"
import a.A;
class B {
void bar() {
A a = A.property;
A a2 = a.A.property;
A a3 = A.property;
}
}
@@ -0,0 +1,10 @@
// "Add 'const' modifier to a property" "true"
import a.A;
class B {
void bar() {
A a = A.pro<caret>perty;
A a2 = A.Named.getProperty();
A a3 = A.property;
}
}
@@ -0,0 +1,7 @@
package a
class A {
companion object Named {
val property = 1
}
}
@@ -0,0 +1,10 @@
// "Replace with getter invocation" "true"
import a.A;
class B {
void bar() {
A a = a.A.Named.getProperty();
A a2 = A.Named.getProperty();
A a3 = A.property;
}
}
@@ -0,0 +1,10 @@
// "Replace with getter invocation" "true"
import a.A;
class B {
void bar() {
A a = A.pro<caret>perty;
A a2 = A.Named.getProperty();
A a3 = A.property;
}
}
@@ -0,0 +1,7 @@
package a
class A {
companion object Named {
val property = A()
}
}
@@ -0,0 +1,7 @@
package a
class A {
companion object {
@JvmField val property = A()
}
}
@@ -0,0 +1,10 @@
// "Annotate property with @JvmField" "true"
import a.A;
class B {
void bar() {
A a = A.property;
A a2 = a.A.property;
A a3 = A.property;
}
}
@@ -0,0 +1,10 @@
// "Annotate property with @JvmField" "true"
import a.A;
class B {
void bar() {
A a = A.pro<caret>perty;
A a2 = A.Companion.getProperty();
A a3 = A.property;
}
}
@@ -0,0 +1,7 @@
package a
class A {
companion object {
val property = A()
}
}
@@ -0,0 +1,7 @@
package a
interface A {
companion object Named {
const val property = 1
}
}
@@ -0,0 +1,10 @@
// "Add 'const' modifier to a property" "true"
import a.A;
class B {
void bar() {
A a = A.property;
A a2 = a.A.property;
A a3 = A.property;
}
}
@@ -0,0 +1,10 @@
// "Add 'const' modifier to a property" "true"
import a.A;
class B {
void bar() {
A a = A.prop<caret>erty;
A a2 = A.Named.getProperty();
A a3 = A.property;
}
}
@@ -0,0 +1,7 @@
package a
interface A {
companion object Named {
val property = 1
}
}
@@ -0,0 +1,10 @@
// "Replace with getter invocation" "true"
import a.A;
class B {
void bar() {
A a = a.A.Companion.getProperty();
A a2 = A.Companion.getProperty();
A a3 = A.property;
}
}
@@ -0,0 +1,10 @@
// "Replace with getter invocation" "true"
import a.A;
class B {
void bar() {
A a = A.prop<caret>erty;
A a2 = A.Companion.getProperty();
A a3 = A.property;
}
}
@@ -0,0 +1,7 @@
package a
interface A {
companion object {
val property = 1
}
}
@@ -0,0 +1,20 @@
// "Annotate property with @JvmField" "false"
import a.A;
class B {
void bar() {
A a = A.prop<caret>erty;
A a2 = A.Named.getProperty();
A a3 = A.property;
}
}
// ACTION: Add 'const' modifier to a property
// ACTION: Add static import for 'a.A.property'
// ACTION: Annotate 'property' as @Deprecated
// ACTION: Annotate 'property' as @NotNull
// ACTION: Annotate 'property' as @Nullable
// ACTION: Change variable 'a' type to 'int'
// ACTION: Migrate 'a' type to 'int'
// ACTION: Replace with getter invocation
// ACTION: Split into declaration and assignment
@@ -0,0 +1,7 @@
package a
interface A {
companion object Named {
val property = 1
}
}
@@ -0,0 +1,5 @@
package a
object Obj {
const val property = 1
}
@@ -0,0 +1,11 @@
// "Add 'const' modifier to a property" "true"
import a.Obj;
import a.A;
class B {
void bar() {
A a = Obj.property;
A a2 = a.Obj.property;
A a3 = Obj.property;
}
}
@@ -0,0 +1,11 @@
// "Add 'const' modifier to a property" "true"
import a.Obj;
import a.A;
class B {
void bar() {
A a = Obj.pro<caret>perty;
A a2 = Obj.INSTANCE.getProperty();
A a3 = Obj.property;
}
}
@@ -0,0 +1,5 @@
package a
object Obj {
val property = 1
}
@@ -0,0 +1,16 @@
// "Add 'const' modifier to a property" "false"
import a.Obj;
import a.A;
class B {
void bar() {
A a = Obj.pro<caret>perty;
Obj.INSTANCE.getProperty();
}
}
// ACTION: Annotate 'property' as @Deprecated
// ACTION: Add static import for 'a.Obj.property'
// ACTION: Annotate property with @JvmField
// ACTION: Split into declaration and assignment
// ACTION: Replace with getter invocation
@@ -0,0 +1,7 @@
package a
object Obj {
val property = A()
}
class A
@@ -0,0 +1,11 @@
// "Replace with getter invocation" "true"
import a.Obj;
import a.A;
class B {
void bar() {
A a = a.Obj.INSTANCE.getProperty();
A a2 = Obj.getProperty();
A a3 = Obj.property;
}
}
@@ -0,0 +1,11 @@
// "Replace with getter invocation" "true"
import a.Obj;
import a.A;
class B {
void bar() {
A a = Obj.pro<caret>perty;
A a2 = Obj.getProperty();
A a3 = Obj.property;
}
}
@@ -0,0 +1,7 @@
package a
object Obj {
val property = A()
}
class A
@@ -0,0 +1,7 @@
package a
object Obj {
@JvmField val property = A()
}
class A
@@ -0,0 +1,11 @@
// "Annotate property with @JvmField" "true"
import a.Obj;
import a.A;
class B {
void bar() {
A a = Obj.property;
A a2 = a.Obj.property;
A a3 = Obj.property;
}
}
@@ -0,0 +1,11 @@
// "Annotate property with @JvmField" "true"
import a.Obj;
import a.A;
class B {
void bar() {
A a = Obj.pro<caret>perty;
A a2 = Obj.getProperty();
A a3 = Obj.property;
}
}
@@ -0,0 +1,7 @@
package a
object Obj {
val property = A()
}
class A
@@ -129,12 +129,11 @@ public abstract class AbstractQuickFixMultiFileTest extends KotlinDaemonAnalyzer
assert mainFileDir != null;
final String mainFileName = mainFile.getName();
final String extraFileNamePrefix = mainFileName.replace(".Main.kt", ".").replace(".Main.java", ".");
File[] extraFiles = mainFileDir.listFiles(
new FilenameFilter() {
@Override
public boolean accept(@NotNull File dir, @NotNull String name) {
return name.startsWith(extraFileNamePrefix) && !name.equals(mainFileName);
return name.startsWith(extraFileNamePrefix(mainFileName)) && !name.equals(mainFileName);
}
}
);
@@ -209,7 +208,7 @@ public abstract class AbstractQuickFixMultiFileTest extends KotlinDaemonAnalyzer
"Infos:" + infos);
}
else {
DirectiveBasedActionUtils.INSTANCE$.checkAvailableActionsAreExpected((JetFile) getFile(), availableActions);
DirectiveBasedActionUtils.INSTANCE$.checkAvailableActionsAreExpected(getFile(), availableActions);
}
}
else {
@@ -233,10 +232,9 @@ public abstract class AbstractQuickFixMultiFileTest extends KotlinDaemonAnalyzer
PsiFile mainFile = myFile;
String mainFileName = mainFile.getName();
String extraFileNamePrefix = mainFileName.replace(".Main.kt", ".");
for (PsiFile file : mainFile.getContainingDirectory().getFiles()) {
String fileName = file.getName();
if (fileName.equals(mainFileName) || !fileName.startsWith(extraFileNamePrefix)) continue;
if (fileName.equals(mainFileName) || !fileName.startsWith(extraFileNamePrefix(myFile.getName()))) continue;
myFile = file;
String extraFileFullPath = testFullPath.replace(mainFileName, fileName);
@@ -267,4 +265,9 @@ public abstract class AbstractQuickFixMultiFileTest extends KotlinDaemonAnalyzer
protected String getTestDataPath() {
return JetTestUtils.getHomeDirectory() + "/";
}
@NotNull
private static String extraFileNamePrefix(@NotNull String mainFileName) {
return mainFileName.replace(".Main.kt", ".").replace(".Main.java", ".");
}
}
@@ -1111,6 +1111,81 @@ public class QuickFixMultiFileTestGenerated extends AbstractQuickFixMultiFileTes
}
}
@TestMetadata("idea/testData/quickfix/migration/deprecatedStaticField")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class DeprecatedStaticField extends AbstractQuickFixMultiFileTest {
public void testAllFilesPresentInDeprecatedStaticField() throws Exception {
JetTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("idea/testData/quickfix/migration/deprecatedStaticField"), Pattern.compile("^(\\w+)\\.before\\.Main\\.\\w+$"), true);
}
@TestMetadata("cleanUp.before.Main.java")
public void testCleanUp() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/cleanUp.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("companionObjectOfClass_const.before.Main.java")
public void testCompanionObjectOfClass_const() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/companionObjectOfClass_const.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("companionObjectOfClass_getterReference.before.Main.java")
public void testCompanionObjectOfClass_getterReference() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/companionObjectOfClass_getterReference.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("companionObjectOfClass_jvmField.before.Main.java")
public void testCompanionObjectOfClass_jvmField() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/companionObjectOfClass_jvmField.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("companionObjectOfInterface_const.before.Main.java")
public void testCompanionObjectOfInterface_const() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/companionObjectOfInterface_const.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("companionObjectOfInterface_getterReference.before.Main.java")
public void testCompanionObjectOfInterface_getterReference() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/companionObjectOfInterface_getterReference.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("companionObjectOfInterface_jvmField_unavailable.before.Main.java")
public void testCompanionObjectOfInterface_jvmField_unavailable() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/companionObjectOfInterface_jvmField_unavailable.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("object_const.before.Main.java")
public void testObject_const() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/object_const.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("object_const_unavailable.before.Main.java")
public void testObject_const_unavailable() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/object_const_unavailable.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("object_getterReference.before.Main.java")
public void testObject_getterReference() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/object_getterReference.before.Main.java");
doTestWithExtraFile(fileName);
}
@TestMetadata("object_jvmField.before.Main.java")
public void testObject_jvmField() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/migration/deprecatedStaticField/object_jvmField.before.Main.java");
doTestWithExtraFile(fileName);
}
}
@TestMetadata("idea/testData/quickfix/migration/javaAnnotationPositionedArguments")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)