diff --git a/java/java-analysis-impl/src/com/intellij/codeInspection/sillyAssignment/SillyAssignmentInspection.java b/java/java-analysis-impl/src/com/intellij/codeInspection/sillyAssignment/SillyAssignmentInspectionBase.java similarity index 95% rename from java/java-analysis-impl/src/com/intellij/codeInspection/sillyAssignment/SillyAssignmentInspection.java rename to java/java-analysis-impl/src/com/intellij/codeInspection/sillyAssignment/SillyAssignmentInspectionBase.java index 3135f4869313..c6aeb59b5b24 100644 --- a/java/java-analysis-impl/src/com/intellij/codeInspection/sillyAssignment/SillyAssignmentInspection.java +++ b/java/java-analysis-impl/src/com/intellij/codeInspection/sillyAssignment/SillyAssignmentInspectionBase.java @@ -1,5 +1,5 @@ /* - * Copyright 2000-2012 JetBrains s.r.o. + * Copyright 2000-2014 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. @@ -24,11 +24,8 @@ import org.jetbrains.annotations.NonNls; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; -/** - * User: anna - * Date: 15-Nov-2005 - */ -public class SillyAssignmentInspection extends BaseJavaBatchLocalInspectionTool { +public class SillyAssignmentInspectionBase extends BaseJavaBatchLocalInspectionTool { + @Override @NotNull public String getGroupDisplayName() { @@ -94,7 +91,7 @@ public class SillyAssignmentInspection extends BaseJavaBatchLocalInspectionTool }; } - private static void checkSillyAssignment(PsiAssignmentExpression assignment, ProblemsHolder holder) { + private void checkSillyAssignment(PsiAssignmentExpression assignment, ProblemsHolder holder) { if (assignment.getOperationTokenType() != JavaTokenType.EQ) return; PsiExpression lExpression = assignment.getLExpression(); PsiExpression rExpression = assignment.getRExpression(); @@ -118,7 +115,11 @@ public class SillyAssignmentInspection extends BaseJavaBatchLocalInspectionTool final PsiVariable variable = (PsiVariable)lRef.resolve(); if (variable == null) return; holder.registerProblem(assignment, InspectionsBundle.message("assignment.to.itself.problem.descriptor", variable.getName()), - ProblemHighlightType.LIKE_UNUSED_SYMBOL); + ProblemHighlightType.LIKE_UNUSED_SYMBOL, createRemoveAssignmentFix()); + } + + protected LocalQuickFix createRemoveAssignmentFix() { + return null; } /** diff --git a/java/java-impl/src/com/intellij/codeInspection/RemoveAssignmentFix.java b/java/java-impl/src/com/intellij/codeInspection/RemoveAssignmentFix.java new file mode 100644 index 000000000000..b80e3a07121d --- /dev/null +++ b/java/java-impl/src/com/intellij/codeInspection/RemoveAssignmentFix.java @@ -0,0 +1,65 @@ +/* + * Copyright 2000-2014 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 com.intellij.codeInspection; + +import com.intellij.codeInsight.FileModificationService; +import com.intellij.openapi.project.Project; +import com.intellij.psi.*; +import com.intellij.psi.util.PsiUtil; +import org.jetbrains.annotations.NotNull; + +public class RemoveAssignmentFix extends RemoveInitializerFix { + @NotNull + @Override + public String getName() { + return InspectionsBundle.message("inspection.unused.assignment.remove.assignment.quickfix"); + } + + @Override + public void applyFix(@NotNull Project project, @NotNull ProblemDescriptor descriptor) { + final PsiElement element = descriptor.getPsiElement(); + final PsiElement parent; + if (element instanceof PsiReferenceExpression) { + parent = element.getParent(); + } else { + parent = element; + } + if (!(parent instanceof PsiAssignmentExpression)) return; + final PsiExpression rExpression = ((PsiAssignmentExpression)parent).getRExpression(); + final PsiElement gParent = parent.getParent(); + if (gParent instanceof PsiExpression && rExpression != null) { + if (!FileModificationService.getInstance().prepareFileForWrite(gParent.getContainingFile())) return; + if (gParent instanceof PsiParenthesizedExpression) { + gParent.replace(rExpression); + } else { + parent.replace(rExpression); + } + return; + } + + PsiElement resolve = null; + if (element instanceof PsiReferenceExpression) { + resolve = ((PsiReferenceExpression)element).resolve(); + } else { + final PsiExpression lExpr = PsiUtil.deparenthesizeExpression(((PsiAssignmentExpression)parent).getLExpression()); + if (lExpr instanceof PsiReferenceExpression) { + resolve = ((PsiReferenceExpression)lExpr).resolve(); + } + } + if (!(resolve instanceof PsiVariable)) return; + sideEffectAwareRemove(project, rExpression, parent, (PsiVariable)resolve); + } +} diff --git a/java/java-impl/src/com/intellij/codeInspection/RemoveInitializerFix.java b/java/java-impl/src/com/intellij/codeInspection/RemoveInitializerFix.java new file mode 100644 index 000000000000..58755b0ad740 --- /dev/null +++ b/java/java-impl/src/com/intellij/codeInspection/RemoveInitializerFix.java @@ -0,0 +1,98 @@ +/* + * Copyright 2000-2014 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 com.intellij.codeInspection; + +import com.intellij.codeInsight.FileModificationService; +import com.intellij.codeInsight.daemon.impl.quickfix.RemoveUnusedVariableFix; +import com.intellij.codeInsight.daemon.impl.quickfix.RemoveUnusedVariableUtil; +import com.intellij.openapi.diagnostic.Logger; +import com.intellij.openapi.fileEditor.FileEditorManager; +import com.intellij.openapi.project.Project; +import com.intellij.psi.*; +import com.intellij.psi.util.PsiExpressionTrimRenderer; +import com.intellij.psi.util.PsiUtil; +import com.intellij.util.IncorrectOperationException; +import org.jetbrains.annotations.NotNull; + +import java.util.ArrayList; +import java.util.List; + +public class RemoveInitializerFix implements LocalQuickFix { + private static final Logger LOG = Logger.getInstance("#" + RemoveInitializerFix.class.getName()); + + @Override + @NotNull + public String getName() { + return InspectionsBundle.message("inspection.unused.assignment.remove.quickfix"); + } + + @Override + public void applyFix(@NotNull Project project, @NotNull ProblemDescriptor descriptor) { + final PsiElement psiInitializer = descriptor.getPsiElement(); + if (!(psiInitializer instanceof PsiExpression)) return; + if (!(psiInitializer.getParent() instanceof PsiVariable)) return; + + final PsiVariable variable = (PsiVariable)psiInitializer.getParent(); + sideEffectAwareRemove(project, psiInitializer, psiInitializer, variable); + } + + protected void sideEffectAwareRemove(Project project, PsiElement psiInitializer, PsiElement elementToDelete, PsiVariable variable) { + if (!FileModificationService.getInstance().prepareFileForWrite(elementToDelete.getContainingFile())) return; + + final PsiElement declaration = variable.getParent(); + final List sideEffects = new ArrayList(); + boolean hasSideEffects = RemoveUnusedVariableUtil.checkSideEffects(psiInitializer, variable, sideEffects); + int res = RemoveUnusedVariableUtil.DELETE_ALL; + if (hasSideEffects) { + hasSideEffects = PsiUtil.isStatement(psiInitializer); + res = RemoveUnusedVariableFix.showSideEffectsWarning(sideEffects, variable, + FileEditorManager.getInstance(project).getSelectedTextEditor(), + hasSideEffects, sideEffects.get(0).getText(), + variable.getTypeElement().getText() + + " " + + variable.getName() + + ";
" + + PsiExpressionTrimRenderer + .render((PsiExpression)psiInitializer) + ); + } + try { + if (res == RemoveUnusedVariableUtil.DELETE_ALL) { + elementToDelete.delete(); + } + else if (res == RemoveUnusedVariableUtil.MAKE_STATEMENT) { + final PsiElementFactory factory = JavaPsiFacade.getInstance(project).getElementFactory(); + final PsiStatement statementFromText = factory.createStatementFromText(psiInitializer.getText() + ";", null); + final PsiElement parent = elementToDelete.getParent(); + if (parent instanceof PsiExpressionStatement) { + parent.replace(statementFromText); + } else { + declaration.getParent().addAfter(statementFromText, declaration); + elementToDelete.delete(); + } + } + } + catch (IncorrectOperationException e) { + LOG.error(e); + } + } + + @Override + @NotNull + public String getFamilyName() { + return getName(); + } +} diff --git a/java/java-impl/src/com/intellij/codeInspection/dataFlow/DataFlowInspection.java b/java/java-impl/src/com/intellij/codeInspection/dataFlow/DataFlowInspection.java index e80dd146ff28..73d8848d4d17 100644 --- a/java/java-impl/src/com/intellij/codeInspection/dataFlow/DataFlowInspection.java +++ b/java/java-impl/src/com/intellij/codeInspection/dataFlow/DataFlowInspection.java @@ -16,11 +16,7 @@ package com.intellij.codeInspection.dataFlow; import com.intellij.codeInsight.NullableNotNullDialog; -import com.intellij.codeInspection.AddAssertStatementFix; -import com.intellij.codeInspection.InspectionsBundle; -import com.intellij.codeInspection.LocalQuickFix; -import com.intellij.codeInspection.SurroundWithIfFix; -import com.intellij.codeInspection.defUse.DefUseInspection; +import com.intellij.codeInspection.*; import com.intellij.ide.DataManager; import com.intellij.openapi.actionSystem.CommonDataKeys; import com.intellij.openapi.project.Project; @@ -54,7 +50,7 @@ public class DataFlowInspection extends DataFlowInspectionBase { if (toRemove && !onTheFly) { return LocalQuickFix.EMPTY_ARRAY; } - return new LocalQuickFix[]{toRemove ? new DefUseInspection.RemoveAssignmentFix() : createSimplifyToAssignmentFix()}; + return new LocalQuickFix[]{toRemove ? new RemoveAssignmentFix() : createSimplifyToAssignmentFix()}; } @Override diff --git a/java/java-impl/src/com/intellij/codeInspection/defUse/DefUseInspection.java b/java/java-impl/src/com/intellij/codeInspection/defUse/DefUseInspection.java index 5d2ab663f35b..33c52c70547c 100644 --- a/java/java-impl/src/com/intellij/codeInspection/defUse/DefUseInspection.java +++ b/java/java-impl/src/com/intellij/codeInspection/defUse/DefUseInspection.java @@ -24,26 +24,10 @@ */ package com.intellij.codeInspection.defUse; -import com.intellij.codeInsight.FileModificationService; -import com.intellij.codeInsight.daemon.impl.quickfix.RemoveUnusedVariableFix; -import com.intellij.codeInsight.daemon.impl.quickfix.RemoveUnusedVariableUtil; -import com.intellij.codeInspection.InspectionsBundle; -import com.intellij.codeInspection.LocalQuickFix; -import com.intellij.codeInspection.ProblemDescriptor; +import com.intellij.codeInspection.*; import com.intellij.openapi.diagnostic.Logger; -import com.intellij.openapi.fileEditor.FileEditorManager; -import com.intellij.openapi.project.Project; -import com.intellij.psi.*; -import com.intellij.psi.util.PsiExpressionTrimRenderer; -import com.intellij.psi.util.PsiUtil; -import com.intellij.util.IncorrectOperationException; -import org.jetbrains.annotations.NotNull; - -import java.util.ArrayList; -import java.util.List; public class DefUseInspection extends DefUseInspectionBase { - private static final Logger LOG = Logger.getInstance("#com.intellij.codeInspection.defUse.DefUseInspection"); @Override protected LocalQuickFix createRemoveInitializerFix() { @@ -54,99 +38,4 @@ public class DefUseInspection extends DefUseInspectionBase { protected LocalQuickFix createRemoveAssignmentFix() { return new RemoveAssignmentFix(); } - - public static class RemoveAssignmentFix extends RemoveInitializerFix { - @NotNull - @Override - public String getName() { - return InspectionsBundle.message("inspection.unused.assignment.remove.assignment.quickfix"); - } - - @Override - public void applyFix(@NotNull Project project, @NotNull ProblemDescriptor descriptor) { - final PsiElement left = descriptor.getPsiElement(); - if (!(left instanceof PsiReferenceExpression)) return; - final PsiElement parent = left.getParent(); - if (!(parent instanceof PsiAssignmentExpression)) return; - final PsiExpression rExpression = ((PsiAssignmentExpression)parent).getRExpression(); - final PsiElement gParent = parent.getParent(); - if (gParent instanceof PsiExpression && rExpression != null) { - if (!FileModificationService.getInstance().prepareFileForWrite(gParent.getContainingFile())) return; - if (gParent instanceof PsiParenthesizedExpression) { - gParent.replace(rExpression); - } else { - parent.replace(rExpression); - } - return; - } - - final PsiElement resolve = ((PsiReferenceExpression)left).resolve(); - if (!(resolve instanceof PsiVariable)) return; - sideEffectAwareRemove(project, rExpression, parent, (PsiVariable)resolve); - } - } - private static class RemoveInitializerFix implements LocalQuickFix { - @Override - @NotNull - public String getName() { - return InspectionsBundle.message("inspection.unused.assignment.remove.quickfix"); - } - - @Override - public void applyFix(@NotNull Project project, @NotNull ProblemDescriptor descriptor) { - final PsiElement psiInitializer = descriptor.getPsiElement(); - if (!(psiInitializer instanceof PsiExpression)) return; - if (!(psiInitializer.getParent() instanceof PsiVariable)) return; - - final PsiVariable variable = (PsiVariable)psiInitializer.getParent(); - sideEffectAwareRemove(project, psiInitializer, psiInitializer, variable); - } - - protected void sideEffectAwareRemove(Project project, PsiElement psiInitializer, PsiElement elementToDelete, PsiVariable variable) { - if (!FileModificationService.getInstance().prepareFileForWrite(elementToDelete.getContainingFile())) return; - - final PsiElement declaration = variable.getParent(); - final List sideEffects = new ArrayList(); - boolean hasSideEffects = RemoveUnusedVariableUtil.checkSideEffects(psiInitializer, variable, sideEffects); - int res = RemoveUnusedVariableUtil.DELETE_ALL; - if (hasSideEffects) { - hasSideEffects = PsiUtil.isStatement(psiInitializer); - res = RemoveUnusedVariableFix.showSideEffectsWarning(sideEffects, variable, - FileEditorManager.getInstance(project).getSelectedTextEditor(), - hasSideEffects, sideEffects.get(0).getText(), - variable.getTypeElement().getText() + - " " + - variable.getName() + - ";
" + - PsiExpressionTrimRenderer - .render((PsiExpression)psiInitializer) - ); - } - try { - if (res == RemoveUnusedVariableUtil.DELETE_ALL) { - elementToDelete.delete(); - } - else if (res == RemoveUnusedVariableUtil.MAKE_STATEMENT) { - final PsiElementFactory factory = JavaPsiFacade.getInstance(project).getElementFactory(); - final PsiStatement statementFromText = factory.createStatementFromText(psiInitializer.getText() + ";", null); - final PsiElement parent = elementToDelete.getParent(); - if (parent instanceof PsiExpressionStatement) { - parent.replace(statementFromText); - } else { - declaration.getParent().addAfter(statementFromText, declaration); - elementToDelete.delete(); - } - } - } - catch (IncorrectOperationException e) { - LOG.error(e); - } - } - - @Override - @NotNull - public String getFamilyName() { - return getName(); - } - } } diff --git a/java/java-impl/src/com/intellij/codeInspection/sillyAssignment/SillyAssignmentInspection.java b/java/java-impl/src/com/intellij/codeInspection/sillyAssignment/SillyAssignmentInspection.java new file mode 100644 index 000000000000..70edc6b1e9f8 --- /dev/null +++ b/java/java-impl/src/com/intellij/codeInspection/sillyAssignment/SillyAssignmentInspection.java @@ -0,0 +1,31 @@ +/* + * Copyright 2000-2012 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 com.intellij.codeInspection.sillyAssignment; + +import com.intellij.codeInspection.LocalQuickFix; +import com.intellij.codeInspection.RemoveAssignmentFix; + +/** + * User: anna + * Date: 15-Nov-2005 + */ +public class SillyAssignmentInspection extends SillyAssignmentInspectionBase { + + @Override + protected LocalQuickFix createRemoveAssignmentFix() { + return new RemoveAssignmentFix(); + } +} diff --git a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/quickFix/unusedAssignment/afterSillyAssignment.java b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/quickFix/unusedAssignment/afterSillyAssignment.java new file mode 100644 index 000000000000..8b0859f170f3 --- /dev/null +++ b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/quickFix/unusedAssignment/afterSillyAssignment.java @@ -0,0 +1,7 @@ +// "Remove redundant assignment" "true" +class A { + { + String ss = ""; + + } +} \ No newline at end of file diff --git a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/quickFix/unusedAssignment/beforeSillyAssignment.java b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/quickFix/unusedAssignment/beforeSillyAssignment.java new file mode 100644 index 000000000000..81147747a999 --- /dev/null +++ b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/quickFix/unusedAssignment/beforeSillyAssignment.java @@ -0,0 +1,8 @@ +// "Remove redundant assignment" "true" +class A { + { + String ss = ""; + + ss = ss; + } +} \ No newline at end of file diff --git a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/quickFix/RemoveUnusedAssignmentTest.java b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/quickFix/RemoveUnusedAssignmentTest.java index a8816f832323..10dbc98534e7 100644 --- a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/quickFix/RemoveUnusedAssignmentTest.java +++ b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/quickFix/RemoveUnusedAssignmentTest.java @@ -17,6 +17,7 @@ package com.intellij.codeInsight.daemon.quickFix; import com.intellij.codeInspection.LocalInspectionTool; import com.intellij.codeInspection.defUse.DefUseInspection; +import com.intellij.codeInspection.sillyAssignment.SillyAssignmentInspection; import com.intellij.pom.java.LanguageLevel; import org.jetbrains.annotations.NotNull; @@ -26,7 +27,7 @@ public class RemoveUnusedAssignmentTest extends LightQuickFixTestCase { @NotNull @Override protected LocalInspectionTool[] configureLocalInspectionTools() { - return new LocalInspectionTool[] {new DefUseInspection()}; + return new LocalInspectionTool[] {new DefUseInspection(), new SillyAssignmentInspection()}; } @Override