From eb94a196bcb7d27ec5940626ee4c8c2de9d9474c Mon Sep 17 00:00:00 2001 From: "alexey.afanasiev" Date: Tue, 12 Sep 2017 13:42:11 +0300 Subject: [PATCH] Add explicit type to methods in "Convert to @CompileStatic" action (IDEA-95853) --- .../intentions/style/AddReturnTypeFix.java | 13 +++--- .../ConvertToStaticProcessor.java | 42 +++++++++++++------ .../fixes/EmptyReturnTypeFix.kt | 33 +++++++++++++++ .../ChangeSignatureForJavaTest.groovy | 4 +- 4 files changed, 73 insertions(+), 19 deletions(-) create mode 100644 plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/convertToStatic/fixes/EmptyReturnTypeFix.kt diff --git a/plugins/groovy/src/org/jetbrains/plugins/groovy/intentions/style/AddReturnTypeFix.java b/plugins/groovy/src/org/jetbrains/plugins/groovy/intentions/style/AddReturnTypeFix.java index 574ab32e92aa..de6eeeef4da8 100644 --- a/plugins/groovy/src/org/jetbrains/plugins/groovy/intentions/style/AddReturnTypeFix.java +++ b/plugins/groovy/src/org/jetbrains/plugins/groovy/intentions/style/AddReturnTypeFix.java @@ -99,15 +99,18 @@ public class AddReturnTypeFix implements IntentionAction { public void invoke(@NotNull Project project, Editor editor, PsiFile file) throws IncorrectOperationException { final GrMethod method = findMethod(file, editor.getCaretModel().getOffset()); if (method == null) return; - - PsiType type = method.getInferredReturnType(); - if (type == null) type = PsiType.getJavaLangObject(PsiManager.getInstance(project), file.getResolveScope()); - type = TypesUtil.unboxPrimitiveTypeWrapper(type); - GrReferenceAdjuster.shortenAllReferencesIn(method.setReturnType(type)); + applyFix(project, method); } @Override public boolean startInWriteAction() { return true; } + + public static void applyFix(@NotNull Project project, @NotNull GrMethod method) { + PsiType type = method.getInferredReturnType(); + if (type == null) type = PsiType.getJavaLangObject(PsiManager.getInstance(project), method.getResolveScope()); + type = TypesUtil.unboxPrimitiveTypeWrapper(type); + GrReferenceAdjuster.shortenAllReferencesIn(method.setReturnType(type)); + } } diff --git a/plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/convertToStatic/ConvertToStaticProcessor.java b/plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/convertToStatic/ConvertToStaticProcessor.java index a17d0ffb9e55..0c910aedfd76 100644 --- a/plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/convertToStatic/ConvertToStaticProcessor.java +++ b/plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/convertToStatic/ConvertToStaticProcessor.java @@ -39,6 +39,7 @@ import org.jetbrains.plugins.groovy.lang.psi.util.PsiUtil; import org.jetbrains.plugins.groovy.refactoring.GroovyRefactoringBundle; import org.jetbrains.plugins.groovy.refactoring.convertToStatic.fixes.BaseFix; import org.jetbrains.plugins.groovy.refactoring.convertToStatic.fixes.EmptyFieldTypeFix; +import org.jetbrains.plugins.groovy.refactoring.convertToStatic.fixes.EmptyReturnTypeFix; import java.util.*; @@ -51,7 +52,7 @@ public class ConvertToStaticProcessor extends BaseRefactoringProcessor { private final GroovyFile[] myFiles; - private BaseFix[] myFixes = {new EmptyFieldTypeFix()}; + private BaseFix[] myFixes = {new EmptyFieldTypeFix(), new EmptyReturnTypeFix()}; protected ConvertToStaticProcessor(Project project, GroovyFile... files) { super(project); @@ -94,9 +95,13 @@ public class ConvertToStaticProcessor extends BaseRefactoringProcessor { LOG.assertTrue(file.isValid()); if (file.isScript()) continue; - applyFixes(file); - putCompileAnnotations(file); - checkErrors(file); + try { + applyFixes(file); + putCompileAnnotations(file); + checkErrors(file); + } catch (Exception e) { + LOG.error("Error in converting file: " + file.getName(), e); + } PsiDocumentManager.getInstance(myProject).commitDocument(document); @@ -115,6 +120,12 @@ public class ConvertToStaticProcessor extends BaseRefactoringProcessor { } private void putCompileAnnotations(@NotNull GroovyFile file) { + GrTypeDefinition[] classes = file.getTypeDefinitions(); + + for (GrTypeDefinition typeDef : classes) { //put annotations + addAnnotation(typeDef, true); + } + Set classesWithUnresolvedRef = new HashSet<>(); Set methodsWithUnresolvedRef = new HashSet<>(); @@ -130,13 +141,11 @@ public class ConvertToStaticProcessor extends BaseRefactoringProcessor { file.accept(new ResolveHighlightingVisitor(file, myProject, callback)); file.accept(new InaccessibleElementVisitor(file, myProject, callback)); - GrTypeDefinition[] classes = file.getTypeDefinitions(); - - for (GrTypeDefinition typeDef : classes) { - boolean isStaticClass = false; - if (!classesWithUnresolvedRef.contains(typeDef)) { - isStaticClass = true; - addAnnotation(typeDef, true); + for (GrTypeDefinition typeDef : classes) { //remove if found not compilable code in class def + boolean isStaticClass = true; + if (classesWithUnresolvedRef.contains(typeDef)) { + isStaticClass = false; + removeAnnotation(typeDef); } for (GrMethod method : typeDef.getCodeMethods()) { @@ -172,9 +181,18 @@ public class ConvertToStaticProcessor extends BaseRefactoringProcessor { } void addAnnotation(@NotNull PsiModifierListOwner owner, boolean isStatic) { + PsiModifierList modifierList = owner.getModifierList(); + String annotation = isStatic ? GROOVY_TRANSFORM_COMPILE_STATIC : GROOVY_TRANSFORM_COMPILE_DYNAMIC; + if (modifierList != null && modifierList.findAnnotation(annotation) == null) { + modifierList.addAnnotation(annotation); + } + } + + void removeAnnotation(@NotNull PsiModifierListOwner owner) { PsiModifierList modifierList = owner.getModifierList(); if (modifierList != null) { - modifierList.addAnnotation(isStatic ? GROOVY_TRANSFORM_COMPILE_STATIC : GROOVY_TRANSFORM_COMPILE_DYNAMIC); + PsiAnnotation psiAnnotation = modifierList.findAnnotation(GROOVY_TRANSFORM_COMPILE_STATIC); + if (psiAnnotation != null) psiAnnotation.delete(); } } diff --git a/plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/convertToStatic/fixes/EmptyReturnTypeFix.kt b/plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/convertToStatic/fixes/EmptyReturnTypeFix.kt new file mode 100644 index 000000000000..735ecb548247 --- /dev/null +++ b/plugins/groovy/src/org/jetbrains/plugins/groovy/refactoring/convertToStatic/fixes/EmptyReturnTypeFix.kt @@ -0,0 +1,33 @@ +/* + * Copyright 2000-2017 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.plugins.groovy.refactoring.convertToStatic.fixes + +import com.intellij.psi.impl.light.LightElement +import org.jetbrains.plugins.groovy.intentions.style.AddReturnTypeFix +import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression +import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrMethod + +class EmptyReturnTypeFix : BaseFix() { + override fun visitReferenceExpression(referenceExpression: GrReferenceExpression) { + val resolveResult = referenceExpression.advancedResolve() + if (!resolveResult.isAccessible || !resolveResult.isApplicable) return + val method = resolveResult.element as? GrMethod ?: return + if (method is LightElement) return + method.returnTypeElementGroovy?.let { return } + + AddReturnTypeFix.applyFix(referenceExpression.project, method) + } +} \ No newline at end of file diff --git a/plugins/groovy/test/org/jetbrains/plugins/groovy/refactoring/changeSignature/ChangeSignatureForJavaTest.groovy b/plugins/groovy/test/org/jetbrains/plugins/groovy/refactoring/changeSignature/ChangeSignatureForJavaTest.groovy index 422887ac19d0..dd64a2161fcd 100644 --- a/plugins/groovy/test/org/jetbrains/plugins/groovy/refactoring/changeSignature/ChangeSignatureForJavaTest.groovy +++ b/plugins/groovy/test/org/jetbrains/plugins/groovy/refactoring/changeSignature/ChangeSignatureForJavaTest.groovy @@ -1,5 +1,5 @@ /* - * Copyright 2000-2016 JetBrains s.r.o. + * Copyright 2000-2017 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. @@ -309,7 +309,7 @@ class ChangeSignatureForJavaTest extends LightCodeInsightFixtureTestCase { private final List myInfos SimpleExceptionsGen(List infos = []) { - myInfos = infos + myInfos = infos as List } @Override