IDEA-87501 (Detail exceptions intention drops resources from try statement)

This commit is contained in:
Bas Leijdekkers
2012-06-20 14:16:26 +02:00
parent e67e20c7b9
commit ee05c7598d
13 changed files with 390 additions and 346 deletions
@@ -1,5 +1,5 @@
/*
* Copyright 2003-2008 Dave Griffith, Bas Leijdekkers
* Copyright 2003-2012 Dave Griffith, Bas Leijdekkers
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -26,16 +26,16 @@ import java.util.*;
public class DetailExceptionsIntention extends Intention {
@Override
@NotNull
public PsiElementPredicate getElementPredicate() {
return new DetailExceptionsPredicate();
}
public void processIntention(PsiElement element)
throws IncorrectOperationException {
@Override
public void processIntention(@NotNull PsiElement element) throws IncorrectOperationException {
final PsiJavaToken token = (PsiJavaToken)element;
final PsiTryStatement tryStatement =
(PsiTryStatement)token.getParent();
final PsiTryStatement tryStatement = (PsiTryStatement)token.getParent();
if (tryStatement == null) {
return;
}
@@ -43,26 +43,28 @@ public class DetailExceptionsIntention extends Intention {
final int length = text.length();
@NonNls final StringBuilder newTryStatement = new StringBuilder(length);
newTryStatement.append("try");
final Set<PsiType> exceptionsThrown = new HashSet<PsiType>();
final PsiResourceList resourceList = tryStatement.getResourceList();
if (resourceList != null) {
newTryStatement.append(resourceList.getText());
ExceptionUtils.calculateExceptionsThrownForResourceList(resourceList, exceptionsThrown);
}
final PsiCodeBlock tryBlock = tryStatement.getTryBlock();
if (tryBlock == null) {
return;
}
final String tryBlockText = tryBlock.getText();
newTryStatement.append(tryBlockText);
final Set<PsiType> exceptionsThrown = new HashSet<PsiType>();
ExceptionUtils.calculateExceptionsThrownForCodeBlock(tryBlock,
exceptionsThrown);
final Comparator comparator = new HeirarchicalTypeComparator();
final List<PsiType> exceptionsAlreadyEmitted =
new ArrayList<PsiType>();
ExceptionUtils.calculateExceptionsThrownForCodeBlock(tryBlock, exceptionsThrown);
final Comparator<PsiType> comparator = new HierarchicalTypeComparator();
final List<PsiType> exceptionsAlreadyEmitted = new ArrayList<PsiType>();
final PsiCatchSection[] catchSections = tryStatement.getCatchSections();
for (PsiCatchSection catchSection : catchSections) {
final PsiParameter param = catchSection.getParameter();
final PsiParameter parameter = catchSection.getParameter();
final PsiCodeBlock block = catchSection.getCatchBlock();
if (param != null && block != null) {
final PsiType caughtType = param.getType();
final List<PsiType> exceptionsToExpand =
new ArrayList<PsiType>(10);
if (parameter != null && block != null) {
final PsiType caughtType = parameter.getType();
final List<PsiType> exceptionsToExpand = new ArrayList<PsiType>(10);
for (Object aExceptionsThrown : exceptionsThrown) {
final PsiType thrownType = (PsiType)aExceptionsThrown;
if (caughtType.isAssignableFrom(thrownType)) {
@@ -73,11 +75,10 @@ public class DetailExceptionsIntention extends Intention {
Collections.sort(exceptionsToExpand, comparator);
for (PsiType thrownType : exceptionsToExpand) {
newTryStatement.append("catch(");
final String exceptionType =
thrownType.getCanonicalText();
final String exceptionType = thrownType.getCanonicalText();
newTryStatement.append(exceptionType);
newTryStatement.append(' ');
final String parameterName = param.getName();
final String parameterName = parameter.getName();
newTryStatement.append(parameterName);
newTryStatement.append(')');
final String blockText = block.getText();
@@ -1,5 +1,5 @@
/*
* Copyright 2003-2005 Dave Griffith
* Copyright 2003-2012 Dave Griffith, Bas Leijdekkers
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -25,6 +25,7 @@ import java.util.Set;
class DetailExceptionsPredicate implements PsiElementPredicate {
@Override
public boolean satisfiedBy(PsiElement element) {
if (!(element instanceof PsiJavaToken)) {
return false;
@@ -43,16 +44,19 @@ class DetailExceptionsPredicate implements PsiElementPredicate {
}
final Set<PsiType> exceptionsThrown = new HashSet<PsiType>(10);
final PsiCodeBlock tryBlock = tryStatement.getTryBlock();
ExceptionUtils.calculateExceptionsThrownForCodeBlock(tryBlock,
exceptionsThrown);
final Set<PsiType> exceptionsCaught =
ExceptionUtils.getExceptionTypesHandled(tryStatement);
final PsiResourceList resourceList = tryStatement.getResourceList();
if (resourceList != null) {
ExceptionUtils.calculateExceptionsThrownForResourceList(resourceList, exceptionsThrown);
}
ExceptionUtils.calculateExceptionsThrownForCodeBlock(tryBlock, exceptionsThrown);
final Set<PsiType> exceptionsCaught = ExceptionUtils.getExceptionTypesHandled(tryStatement);
for (PsiType typeThrown : exceptionsThrown) {
if (!exceptionsCaught.contains(typeThrown)) {
for (PsiType typeCaught : exceptionsCaught) {
if (typeCaught.isAssignableFrom(typeThrown)) {
return true;
}
if (exceptionsCaught.contains(typeThrown)) {
continue;
}
for (PsiType typeCaught : exceptionsCaught) {
if (typeCaught.isAssignableFrom(typeThrown)) {
return true;
}
}
}
@@ -1,5 +1,5 @@
/*
* Copyright 2003-2006 Dave Griffith, Bas Leijdekkers
* Copyright 2003-2012 Dave Griffith, Bas Leijdekkers
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -17,174 +17,144 @@ package com.siyeh.ipp.exceptions;
import com.intellij.psi.*;
import java.util.Collections;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
class ExceptionUtils {
private ExceptionUtils() {
super();
}
private ExceptionUtils() {}
public static Set<PsiType> getExceptionTypesHandled(
PsiTryStatement statement) {
public static Set<PsiType> getExceptionTypesHandled(PsiTryStatement statement) {
final Set<PsiType> out = new HashSet<PsiType>(10);
final PsiParameter[] params = statement.getCatchBlockParameters();
for (PsiParameter param : params) {
final PsiType type = param.getType();
out.add(type);
final PsiParameter[] parameters = statement.getCatchBlockParameters();
for (PsiParameter parameter : parameters) {
final PsiType type = parameter.getType();
if (type instanceof PsiDisjunctionType) {
final PsiDisjunctionType disjunctionType = (PsiDisjunctionType)type;
final List<PsiType> disjunctions = disjunctionType.getDisjunctions();
out.addAll(disjunctions);
} else {
out.add(type);
}
}
return out;
}
private static void calculateExceptionsThrownForStatement(
PsiStatement statement,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForStatement(PsiStatement statement, Set<PsiType> exceptionTypes) {
if (statement == null) {
return;
}
if (statement instanceof PsiBreakStatement ||
statement instanceof PsiContinueStatement) {
if (statement instanceof PsiBreakStatement || statement instanceof PsiContinueStatement) {
// don't do anything
}
else if (statement instanceof PsiReturnStatement) {
final PsiReturnStatement returnStatement =
(PsiReturnStatement)statement;
final PsiReturnStatement returnStatement = (PsiReturnStatement)statement;
final PsiExpression returnValue = returnStatement.getReturnValue();
if (returnValue != null) {
calculateExceptionsThrown(returnValue, exceptionTypes);
calculateExceptionsThrownForExpression(returnValue, exceptionTypes);
}
}
else if (statement instanceof PsiThrowStatement) {
final PsiThrowStatement throwStatement =
(PsiThrowStatement)statement;
calculateExceptionsThrownForThrowStatement(throwStatement,
exceptionTypes);
final PsiThrowStatement throwStatement = (PsiThrowStatement)statement;
calculateExceptionsThrownForThrowStatement(throwStatement, exceptionTypes);
}
else if (statement instanceof PsiExpressionListStatement) {
final PsiExpressionListStatement expressionListStatement =
(PsiExpressionListStatement)statement;
calculateExceptionsThrownForExpressionListStatement(
expressionListStatement, exceptionTypes);
final PsiExpressionListStatement expressionListStatement = (PsiExpressionListStatement)statement;
calculateExceptionsThrownForExpressionListStatement(expressionListStatement, exceptionTypes);
}
else if (statement instanceof PsiExpressionStatement) {
final PsiExpressionStatement expressionStatement =
(PsiExpressionStatement)statement;
final PsiExpression expression =
expressionStatement.getExpression();
calculateExceptionsThrown(expression, exceptionTypes);
final PsiExpressionStatement expressionStatement = (PsiExpressionStatement)statement;
final PsiExpression expression = expressionStatement.getExpression();
calculateExceptionsThrownForExpression(expression, exceptionTypes);
}
else if (statement instanceof PsiAssertStatement) {
final PsiAssertStatement assertStatement =
(PsiAssertStatement)statement;
calculateExceptionsThrownForAssertStatement(assertStatement,
exceptionTypes);
final PsiAssertStatement assertStatement = (PsiAssertStatement)statement;
calculateExceptionsThrownForAssertStatement(assertStatement, exceptionTypes);
}
else if (statement instanceof PsiDeclarationStatement) {
final PsiDeclarationStatement declarationStatement =
(PsiDeclarationStatement)statement;
calculateExceptionsThrownForDeclarationStatemt(declarationStatement,
exceptionTypes);
final PsiDeclarationStatement declarationStatement = (PsiDeclarationStatement)statement;
calculateExceptionsThrownForDeclarationStatement(declarationStatement, exceptionTypes);
}
else if (statement instanceof PsiForStatement) {
final PsiForStatement forStatement = (PsiForStatement)statement;
calculateExceptionsThrownForForExpression(
forStatement, exceptionTypes);
calculateExceptionsThrownForForStatement(forStatement, exceptionTypes);
}
else if (statement instanceof PsiForeachStatement) {
final PsiForeachStatement foreachStatement = (PsiForeachStatement)statement;
calculateExceptionsThrownForForeachStatement(foreachStatement, exceptionTypes);
}
else if (statement instanceof PsiWhileStatement) {
final PsiWhileStatement whileStatement =
(PsiWhileStatement)statement;
calculateExceptionsThrownForWhileStatement(
whileStatement, exceptionTypes);
final PsiWhileStatement whileStatement = (PsiWhileStatement)statement;
calculateExceptionsThrownForWhileStatement(whileStatement, exceptionTypes);
}
else if (statement instanceof PsiDoWhileStatement) {
final PsiDoWhileStatement doWhileStatement =
(PsiDoWhileStatement)statement;
calculateExceptionsThrownForDoWhileStatement(doWhileStatement,
exceptionTypes);
final PsiDoWhileStatement doWhileStatement = (PsiDoWhileStatement)statement;
calculateExceptionsThrownForDoWhileStatement(doWhileStatement, exceptionTypes);
}
else if (statement instanceof PsiSynchronizedStatement) {
final PsiSynchronizedStatement synchronizedStatement =
(PsiSynchronizedStatement)statement;
calculateExceptionsThrownForSynchronizedStatement(
synchronizedStatement, exceptionTypes);
final PsiSynchronizedStatement synchronizedStatement = (PsiSynchronizedStatement)statement;
calculateExceptionsThrownForSynchronizedStatement(synchronizedStatement, exceptionTypes);
}
else if (statement instanceof PsiBlockStatement) {
final PsiBlockStatement block = (PsiBlockStatement)statement;
calculateExceptionsThrownForBlockStatement(block, exceptionTypes);
}
else if (statement instanceof PsiLabeledStatement) {
final PsiLabeledStatement labeledStatement =
(PsiLabeledStatement)statement;
calculateExceptionsThrownForLabeledStatement(labeledStatement,
exceptionTypes);
final PsiLabeledStatement labeledStatement = (PsiLabeledStatement)statement;
calculateExceptionsThrownForLabeledStatement(labeledStatement, exceptionTypes);
}
else if (statement instanceof PsiIfStatement) {
final PsiIfStatement ifStatement = (PsiIfStatement)statement;
calculateExceptionsThrownForIfStatement(ifStatement,
exceptionTypes);
calculateExceptionsThrownForIfStatement(ifStatement, exceptionTypes);
}
else if (statement instanceof PsiTryStatement) {
final PsiTryStatement tryStatement = (PsiTryStatement)statement;
calculateExceptionsThrownForTryStatement(tryStatement,
exceptionTypes);
calculateExceptionsThrownForTryStatement(tryStatement, exceptionTypes);
}
else if (statement instanceof PsiSwitchStatement) {
final PsiSwitchStatement switchStatement =
(PsiSwitchStatement)statement;
calculateExceptionsThrownForSwitchStatement(switchStatement,
exceptionTypes);
final PsiSwitchStatement switchStatement = (PsiSwitchStatement)statement;
calculateExceptionsThrownForSwitchStatement(switchStatement, exceptionTypes);
}
}
private static void calculateExceptionsThrownForLabeledStatement(
PsiLabeledStatement labeledStatement,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForLabeledStatement(PsiLabeledStatement labeledStatement, Set<PsiType> exceptionTypes) {
final PsiStatement statement = labeledStatement.getStatement();
calculateExceptionsThrownForStatement(statement, exceptionTypes);
}
private static void calculateExceptionsThrownForExpressionListStatement(
PsiExpressionListStatement listStatement,
Set<PsiType> exceptionTypes) {
final PsiExpressionList expressionList =
listStatement.getExpressionList();
private static void calculateExceptionsThrownForExpressionListStatement(PsiExpressionListStatement listStatement,
Set<PsiType> exceptionTypes) {
final PsiExpressionList expressionList = listStatement.getExpressionList();
final PsiExpression[] expressions = expressionList.getExpressions();
for (PsiExpression expression : expressions) {
calculateExceptionsThrown(expression, exceptionTypes);
calculateExceptionsThrownForExpression(expression, exceptionTypes);
}
}
private static void calculateExceptionsThrownForDeclarationStatemt(
PsiDeclarationStatement declarationStatement,
Set<PsiType> exceptionTypes) {
final PsiElement[] elements =
declarationStatement.getDeclaredElements();
private static void calculateExceptionsThrownForDeclarationStatement(PsiDeclarationStatement declarationStatement,
Set<PsiType> exceptionTypes) {
final PsiElement[] elements = declarationStatement.getDeclaredElements();
for (PsiElement element : elements) {
if (element instanceof PsiVariable) {
final PsiVariable var = (PsiVariable)element;
final PsiExpression initializer = var.getInitializer();
final PsiVariable variable = (PsiVariable)element;
final PsiExpression initializer = variable.getInitializer();
if (initializer != null) {
calculateExceptionsThrown(initializer, exceptionTypes);
calculateExceptionsThrownForExpression(initializer, exceptionTypes);
}
}
}
}
private static void calculateExceptionsThrownForAssertStatement(
PsiAssertStatement assertStatement,
Set<PsiType> exceptionTypes) {
final PsiExpression assertCondition =
assertStatement.getAssertCondition();
calculateExceptionsThrown(assertCondition, exceptionTypes);
final PsiExpression assertDescription =
assertStatement.getAssertDescription();
calculateExceptionsThrown(assertDescription, exceptionTypes);
private static void calculateExceptionsThrownForAssertStatement(PsiAssertStatement assertStatement, Set<PsiType> exceptionTypes) {
final PsiExpression assertCondition = assertStatement.getAssertCondition();
calculateExceptionsThrownForExpression(assertCondition, exceptionTypes);
final PsiExpression assertDescription = assertStatement.getAssertDescription();
calculateExceptionsThrownForExpression(assertDescription, exceptionTypes);
}
private static void calculateExceptionsThrownForThrowStatement(
PsiThrowStatement throwStatement,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForThrowStatement(PsiThrowStatement throwStatement, Set<PsiType> exceptionTypes) {
final PsiExpression exception = throwStatement.getException();
if (exception == null) {
return;
@@ -193,26 +163,25 @@ class ExceptionUtils {
if (type != null) {
exceptionTypes.add(type);
}
calculateExceptionsThrown(exception, exceptionTypes);
calculateExceptionsThrownForExpression(exception, exceptionTypes);
}
private static void calculateExceptionsThrownForSwitchStatement(
PsiSwitchStatement switchStatement,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForSwitchStatement(PsiSwitchStatement switchStatement, Set<PsiType> exceptionTypes) {
final PsiExpression switchExpression = switchStatement.getExpression();
calculateExceptionsThrown(switchExpression, exceptionTypes);
calculateExceptionsThrownForExpression(switchExpression, exceptionTypes);
final PsiCodeBlock body = switchStatement.getBody();
calculateExceptionsThrownForCodeBlock(body, exceptionTypes);
}
private static void calculateExceptionsThrownForTryStatement(
PsiTryStatement tryStatement,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForTryStatement(PsiTryStatement tryStatement, Set<PsiType> exceptionTypes) {
final Set<PsiType> exceptionThrown = new HashSet<PsiType>(10);
final PsiResourceList resourceList = tryStatement.getResourceList();
if (resourceList != null) {
calculateExceptionsThrownForResourceList(resourceList, exceptionTypes);
}
final PsiCodeBlock tryBlock = tryStatement.getTryBlock();
calculateExceptionsThrownForCodeBlock(tryBlock, exceptionThrown);
final Set<PsiType> exceptionHandled =
getExceptionTypesHandled(tryStatement);
final Set<PsiType> exceptionHandled = getExceptionTypesHandled(tryStatement);
for (PsiType thrownType : exceptionThrown) {
boolean found = false;
for (PsiType handledType : exceptionHandled) {
@@ -235,299 +204,255 @@ class ExceptionUtils {
}
}
private static void calculateExceptionsThrownForIfStatement(
PsiIfStatement ifStatement,
Set<PsiType> exceptionTypes) {
public static void calculateExceptionsThrownForResourceList(PsiResourceList resourceList, Set<PsiType> exceptionTypes) {
final List<PsiResourceVariable> resourceVariables = resourceList.getResourceVariables();
for (PsiResourceVariable variable : resourceVariables) {
final PsiExpression initializer = variable.getInitializer();
if (initializer != null) {
calculateExceptionsThrownForExpression(initializer, exceptionTypes);
}
final PsiType type = variable.getType();
final PsiClassType autoCloseable = getJavaLangAutoCloseable(resourceList);
if (!(type instanceof PsiClassType) || !autoCloseable.isAssignableFrom(type)) {
continue;
}
final PsiClassType classType = (PsiClassType)type;
final PsiClass aClass = classType.resolve();
if (aClass == null) {
continue;
}
final PsiMethod[] closeMethods = aClass.findMethodsByName("close", true);
for (PsiMethod method : closeMethods) {
final PsiParameterList list = method.getParameterList();
if (list.getParametersCount() == 0) {
calculateExceptionsDeclaredForMethod(method, exceptionTypes);
break;
}
}
}
}
private static PsiClassType getJavaLangAutoCloseable(PsiElement context) {
final PsiElementFactory factory = JavaPsiFacade.getInstance(context.getProject()).getElementFactory();
return factory.createTypeByFQClassName(CommonClassNames.JAVA_LANG_AUTO_CLOSEABLE, context.getResolveScope());
}
private static void calculateExceptionsThrownForIfStatement(PsiIfStatement ifStatement, Set<PsiType> exceptionTypes) {
final PsiExpression condition = ifStatement.getCondition();
calculateExceptionsThrownForExpression(condition, exceptionTypes);
final PsiStatement thenBranch = ifStatement.getThenBranch();
final PsiStatement elseBranch = ifStatement.getElseBranch();
calculateExceptionsThrown(condition, exceptionTypes);
calculateExceptionsThrownForStatement(thenBranch, exceptionTypes);
final PsiStatement elseBranch = ifStatement.getElseBranch();
calculateExceptionsThrownForStatement(elseBranch, exceptionTypes);
}
private static void calculateExceptionsThrownForBlockStatement(
PsiBlockStatement block,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForBlockStatement(PsiBlockStatement block, Set<PsiType> exceptionTypes) {
final PsiCodeBlock codeBlock = block.getCodeBlock();
calculateExceptionsThrownForCodeBlock(codeBlock, exceptionTypes);
}
private static void calculateExceptionsThrownForSynchronizedStatement(
PsiSynchronizedStatement synchronizedStatement,
Set<PsiType> exceptionTypes) {
final PsiExpression lockExpression =
synchronizedStatement.getLockExpression();
private static void calculateExceptionsThrownForSynchronizedStatement(PsiSynchronizedStatement synchronizedStatement,
Set<PsiType> exceptionTypes) {
final PsiExpression lockExpression = synchronizedStatement.getLockExpression();
if (lockExpression != null) {
calculateExceptionsThrown(lockExpression, exceptionTypes);
calculateExceptionsThrownForExpression(lockExpression, exceptionTypes);
}
final PsiCodeBlock body = synchronizedStatement.getBody();
calculateExceptionsThrownForCodeBlock(body, exceptionTypes);
}
private static void calculateExceptionsThrownForDoWhileStatement(
PsiDoWhileStatement loopStatement,
Set<PsiType> exceptionTypes) {
final PsiExpression condition = loopStatement.getCondition();
calculateExceptionsThrown(condition, exceptionTypes);
final PsiStatement body = loopStatement.getBody();
private static void calculateExceptionsThrownForDoWhileStatement(PsiDoWhileStatement doWhileStatement, Set<PsiType> exceptionTypes) {
final PsiExpression condition = doWhileStatement.getCondition();
calculateExceptionsThrownForExpression(condition, exceptionTypes);
final PsiStatement body = doWhileStatement.getBody();
calculateExceptionsThrownForStatement(body, exceptionTypes);
}
private static void calculateExceptionsThrownForWhileStatement(
PsiWhileStatement loopStatement,
Set<PsiType> exceptionTypes) {
final PsiExpression condition = loopStatement.getCondition();
calculateExceptionsThrown(condition, exceptionTypes);
final PsiStatement body = loopStatement.getBody();
private static void calculateExceptionsThrownForWhileStatement(PsiWhileStatement whileStatement, Set<PsiType> exceptionTypes) {
final PsiExpression condition = whileStatement.getCondition();
calculateExceptionsThrownForExpression(condition, exceptionTypes);
final PsiStatement body = whileStatement.getBody();
calculateExceptionsThrownForStatement(body, exceptionTypes);
}
private static void calculateExceptionsThrownForForExpression(
PsiForStatement loopStatement,
Set<PsiType> exceptionTypes) {
final PsiStatement initialization = loopStatement.getInitialization();
final PsiExpression condition = loopStatement.getCondition();
final PsiStatement update = loopStatement.getUpdate();
final PsiStatement body = loopStatement.getBody();
private static void calculateExceptionsThrownForForStatement(PsiForStatement forStatement, Set<PsiType> exceptionTypes) {
final PsiStatement initialization = forStatement.getInitialization();
calculateExceptionsThrownForStatement(initialization, exceptionTypes);
calculateExceptionsThrown(condition, exceptionTypes);
final PsiExpression condition = forStatement.getCondition();
calculateExceptionsThrownForExpression(condition, exceptionTypes);
final PsiStatement update = forStatement.getUpdate();
calculateExceptionsThrownForStatement(update, exceptionTypes);
final PsiStatement body = forStatement.getBody();
calculateExceptionsThrownForStatement(body, exceptionTypes);
}
private static void calculateExceptionsThrown(PsiExpression expression,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForForeachStatement(PsiForeachStatement foreachStatement, Set<PsiType> exceptionTypes) {
final PsiExpression iteratedValue = foreachStatement.getIteratedValue();
calculateExceptionsThrownForExpression(iteratedValue, exceptionTypes);
final PsiStatement body = foreachStatement.getBody();
calculateExceptionsThrownForStatement(body, exceptionTypes);
}
private static void calculateExceptionsThrownForExpression(PsiExpression expression, Set<PsiType> exceptionTypes) {
if (expression == null) {
return;
}
if (expression instanceof PsiThisExpression ||
expression instanceof PsiLiteralExpression ||
expression instanceof PsiSuperExpression ||
expression instanceof PsiClassObjectAccessExpression) {
if (expression instanceof PsiThisExpression || expression instanceof PsiLiteralExpression ||
expression instanceof PsiSuperExpression || expression instanceof PsiClassObjectAccessExpression) {
}
else if (expression instanceof PsiTypeCastExpression) {
final PsiTypeCastExpression typeCastExpression =
(PsiTypeCastExpression)expression;
calculateExceptionsThrownForTypeCast(typeCastExpression,
exceptionTypes);
final PsiTypeCastExpression typeCastExpression = (PsiTypeCastExpression)expression;
calculateExceptionsThrownForTypeCast(typeCastExpression, exceptionTypes);
}
else if (expression instanceof PsiInstanceOfExpression) {
final PsiInstanceOfExpression instanceOfExpression =
(PsiInstanceOfExpression)expression;
calculateExceptionsThrownForInstanceOf(instanceOfExpression,
exceptionTypes);
final PsiInstanceOfExpression instanceOfExpression = (PsiInstanceOfExpression)expression;
calculateExceptionsThrownForInstanceOf(instanceOfExpression, exceptionTypes);
}
else if (expression instanceof PsiReferenceExpression) {
final PsiReferenceExpression referenceExpression =
(PsiReferenceExpression)expression;
final PsiExpression qualifier =
referenceExpression.getQualifierExpression();
final PsiReferenceExpression referenceExpression = (PsiReferenceExpression)expression;
final PsiExpression qualifier = referenceExpression.getQualifierExpression();
if (qualifier != null) {
calculateExceptionsThrown(qualifier, exceptionTypes);
calculateExceptionsThrownForExpression(qualifier, exceptionTypes);
}
}
else if (expression instanceof PsiMethodCallExpression) {
final PsiMethodCallExpression methodCallExpression =
(PsiMethodCallExpression)expression;
calculateExceptionsThrownForMethodCall(methodCallExpression,
exceptionTypes);
final PsiMethodCallExpression methodCallExpression = (PsiMethodCallExpression)expression;
calculateExceptionsThrownForMethodCall(methodCallExpression, exceptionTypes);
}
else if (expression instanceof PsiNewExpression) {
final PsiNewExpression newExpression = (PsiNewExpression)expression;
calculateExceptionsThrownForNewExpression(newExpression,
exceptionTypes);
calculateExceptionsThrownForNewExpression(newExpression, exceptionTypes);
}
else if (expression instanceof PsiArrayInitializerExpression) {
final PsiArrayInitializerExpression arrayInitializerExpression =
(PsiArrayInitializerExpression)expression;
calculateExceptionsThrownForArrayInitializerExpression(
arrayInitializerExpression, exceptionTypes);
final PsiArrayInitializerExpression arrayInitializerExpression = (PsiArrayInitializerExpression)expression;
calculateExceptionsThrownForArrayInitializerExpression(arrayInitializerExpression, exceptionTypes);
}
else if (expression instanceof PsiArrayAccessExpression) {
final PsiArrayAccessExpression arrayAccessExpression =
(PsiArrayAccessExpression)expression;
calculateExceptionsThrownForArrayAccessExpression(
arrayAccessExpression, exceptionTypes);
final PsiArrayAccessExpression arrayAccessExpression = (PsiArrayAccessExpression)expression;
calculateExceptionsThrownForArrayAccessExpression(arrayAccessExpression, exceptionTypes);
}
else if (expression instanceof PsiPrefixExpression) {
final PsiPrefixExpression prefixExpression =
(PsiPrefixExpression)expression;
calculateExceptionsThrownForPrefixException(prefixExpression,
exceptionTypes);
final PsiPrefixExpression prefixExpression = (PsiPrefixExpression)expression;
calculateExceptionsThrownForPrefixException(prefixExpression, exceptionTypes);
}
else if (expression instanceof PsiPostfixExpression) {
final PsiPostfixExpression postfixExpression =
(PsiPostfixExpression)expression;
calculateExceptionsThrownForPostixExpression(postfixExpression,
exceptionTypes);
final PsiPostfixExpression postfixExpression = (PsiPostfixExpression)expression;
calculateExceptionsThrownForPostfixExpression(postfixExpression, exceptionTypes);
}
else if (expression instanceof PsiBinaryExpression) {
final PsiBinaryExpression binaryExpression =
(PsiBinaryExpression)expression;
calculateExceptionsThrownForBinaryExpression(binaryExpression,
exceptionTypes);
final PsiBinaryExpression binaryExpression = (PsiBinaryExpression)expression;
calculateExceptionsThrownForBinaryExpression(binaryExpression, exceptionTypes);
}
else if (expression instanceof PsiAssignmentExpression) {
final PsiAssignmentExpression assignmentExpression =
(PsiAssignmentExpression)expression;
calculateExceptionsThrownForAssignmentExpression(
assignmentExpression, exceptionTypes);
final PsiAssignmentExpression assignmentExpression = (PsiAssignmentExpression)expression;
calculateExceptionsThrownForAssignmentExpression(assignmentExpression, exceptionTypes);
}
else if (expression instanceof PsiConditionalExpression) {
final PsiConditionalExpression conditionalExpression =
(PsiConditionalExpression)expression;
calculateExceptionsThrownForConditionalExcpression(
conditionalExpression, exceptionTypes);
final PsiConditionalExpression conditionalExpression = (PsiConditionalExpression)expression;
calculateExceptionsThrownForConditionalExpression(conditionalExpression, exceptionTypes);
}
}
private static void calculateExceptionsThrownForTypeCast(
PsiTypeCastExpression typeCastExpression,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForTypeCast(PsiTypeCastExpression typeCastExpression, Set<PsiType> exceptionTypes) {
final PsiExpression operand = typeCastExpression.getOperand();
calculateExceptionsThrown(operand, exceptionTypes);
calculateExceptionsThrownForExpression(operand, exceptionTypes);
}
private static void calculateExceptionsThrownForInstanceOf(
PsiInstanceOfExpression instanceOfExpression,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForInstanceOf(PsiInstanceOfExpression instanceOfExpression, Set<PsiType> exceptionTypes) {
final PsiExpression operand = instanceOfExpression.getOperand();
calculateExceptionsThrown(operand, exceptionTypes);
calculateExceptionsThrownForExpression(operand, exceptionTypes);
}
private static void calculateExceptionsThrownForNewExpression(
PsiNewExpression newExpression, Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForNewExpression(PsiNewExpression newExpression, Set<PsiType> exceptionTypes) {
final PsiExpressionList argumentList = newExpression.getArgumentList();
if (argumentList != null) {
final PsiExpression[] args = argumentList.getExpressions();
for (PsiExpression arg : args) {
calculateExceptionsThrown(arg, exceptionTypes);
final PsiExpression[] arguments = argumentList.getExpressions();
for (PsiExpression argument : arguments) {
calculateExceptionsThrownForExpression(argument, exceptionTypes);
}
}
final PsiExpression[] arrayDims = newExpression.getArrayDimensions();
for (PsiExpression arrayDim : arrayDims) {
calculateExceptionsThrown(arrayDim, exceptionTypes);
final PsiExpression[] arrayDimensions = newExpression.getArrayDimensions();
for (PsiExpression arrayDimension : arrayDimensions) {
calculateExceptionsThrownForExpression(arrayDimension, exceptionTypes);
}
final PsiExpression qualifier = newExpression.getQualifier();
calculateExceptionsThrown(qualifier, exceptionTypes);
final PsiArrayInitializerExpression arrayInitializer =
newExpression.getArrayInitializer();
calculateExceptionsThrown(arrayInitializer, exceptionTypes);
calculateExceptionsThrownForExpression(qualifier, exceptionTypes);
final PsiArrayInitializerExpression arrayInitializer = newExpression.getArrayInitializer();
calculateExceptionsThrownForExpression(arrayInitializer, exceptionTypes);
final PsiMethod method = newExpression.resolveMethod();
if (method != null) {
final PsiReferenceList throwsList = method.getThrowsList();
final PsiJavaCodeReferenceElement[] list =
throwsList.getReferenceElements();
for (final PsiJavaCodeReferenceElement referenceElement : list) {
final PsiClass exceptionClass =
(PsiClass)referenceElement.resolve();
if (exceptionClass != null) {
final PsiManager psiManager = exceptionClass.getManager();
final PsiElementFactory factory = JavaPsiFacade.getInstance(psiManager.getProject()).getElementFactory();
final PsiClassType exceptionType =
factory.createType(exceptionClass);
exceptionTypes.add(exceptionType);
}
}
}
calculateExceptionsDeclaredForMethod(method, exceptionTypes);
}
private static void calculateExceptionsThrownForMethodCall(
PsiMethodCallExpression methodCallExpression,
Set<PsiType> exceptionTypes) {
final PsiExpressionList argumentList =
methodCallExpression.getArgumentList();
private static void calculateExceptionsThrownForMethodCall(PsiMethodCallExpression methodCallExpression, Set<PsiType> exceptionTypes) {
final PsiExpressionList argumentList = methodCallExpression.getArgumentList();
final PsiExpression[] expressions = argumentList.getExpressions();
for (PsiExpression expression : expressions) {
calculateExceptionsThrown(expression, exceptionTypes);
calculateExceptionsThrownForExpression(expression, exceptionTypes);
}
final PsiReferenceExpression methodExpression =
methodCallExpression.getMethodExpression();
calculateExceptionsThrown(methodExpression, exceptionTypes);
final PsiReferenceExpression methodExpression = methodCallExpression.getMethodExpression();
calculateExceptionsThrownForExpression(methodExpression, exceptionTypes);
final PsiMethod method = methodCallExpression.resolveMethod();
if (method != null) {
final PsiReferenceList throwsList = method.getThrowsList();
final PsiJavaCodeReferenceElement[] list =
throwsList.getReferenceElements();
for (final PsiJavaCodeReferenceElement referenceElement : list) {
final PsiClass exceptionClass =
(PsiClass)referenceElement.resolve();
if (exceptionClass != null) {
final PsiManager psiManager = exceptionClass.getManager();
final PsiElementFactory factory = JavaPsiFacade.getInstance(psiManager.getProject()).getElementFactory();
final PsiClassType exceptionType =
factory.createType(exceptionClass);
exceptionTypes.add(exceptionType);
}
}
}
calculateExceptionsDeclaredForMethod(method, exceptionTypes);
}
private static void calculateExceptionsThrownForConditionalExcpression(
PsiConditionalExpression conditionalExpression,
Set<PsiType> exceptionTypes) {
public static void calculateExceptionsDeclaredForMethod(PsiMethod method, Set<PsiType> exceptionTypes) {
if (method == null) {
return;
}
final PsiReferenceList throwsList = method.getThrowsList();
final PsiClassType[] types = throwsList.getReferencedTypes();
Collections.addAll(exceptionTypes, types);
}
private static void calculateExceptionsThrownForConditionalExpression(PsiConditionalExpression conditionalExpression,
Set<PsiType> exceptionTypes) {
final PsiExpression condition = conditionalExpression.getCondition();
final PsiExpression elseExpression =
conditionalExpression.getElseExpression();
final PsiExpression thenExpression =
conditionalExpression.getThenExpression();
calculateExceptionsThrown(condition, exceptionTypes);
calculateExceptionsThrown(elseExpression, exceptionTypes);
calculateExceptionsThrown(thenExpression, exceptionTypes);
final PsiExpression elseExpression = conditionalExpression.getElseExpression();
final PsiExpression thenExpression = conditionalExpression.getThenExpression();
calculateExceptionsThrownForExpression(condition, exceptionTypes);
calculateExceptionsThrownForExpression(elseExpression, exceptionTypes);
calculateExceptionsThrownForExpression(thenExpression, exceptionTypes);
}
private static void calculateExceptionsThrownForBinaryExpression(
PsiBinaryExpression binaryExpression,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForBinaryExpression(PsiBinaryExpression binaryExpression, Set<PsiType> exceptionTypes) {
final PsiExpression lOperand = binaryExpression.getLOperand();
calculateExceptionsThrown(lOperand, exceptionTypes);
calculateExceptionsThrownForExpression(lOperand, exceptionTypes);
final PsiExpression rhs = binaryExpression.getROperand();
calculateExceptionsThrown(rhs, exceptionTypes);
calculateExceptionsThrownForExpression(rhs, exceptionTypes);
}
private static void calculateExceptionsThrownForAssignmentExpression(
PsiAssignmentExpression assignmentExpression,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForAssignmentExpression(PsiAssignmentExpression assignmentExpression,
Set<PsiType> exceptionTypes) {
final PsiExpression lOperand = assignmentExpression.getLExpression();
calculateExceptionsThrown(lOperand, exceptionTypes);
calculateExceptionsThrownForExpression(lOperand, exceptionTypes);
final PsiExpression rhs = assignmentExpression.getRExpression();
calculateExceptionsThrown(rhs, exceptionTypes);
calculateExceptionsThrownForExpression(rhs, exceptionTypes);
}
private static void calculateExceptionsThrownForArrayInitializerExpression(
PsiArrayInitializerExpression arrayInitializerExpression,
Set<PsiType> exceptionTypes) {
final PsiExpression[] initializers =
arrayInitializerExpression.getInitializers();
private static void calculateExceptionsThrownForArrayInitializerExpression(PsiArrayInitializerExpression arrayInitializerExpression,
Set<PsiType> exceptionTypes) {
final PsiExpression[] initializers = arrayInitializerExpression.getInitializers();
for (PsiExpression initializer : initializers) {
calculateExceptionsThrown(initializer, exceptionTypes);
calculateExceptionsThrownForExpression(initializer, exceptionTypes);
}
}
private static void calculateExceptionsThrownForArrayAccessExpression(
PsiArrayAccessExpression arrayAccessExpression,
Set<PsiType> exceptionTypes) {
final PsiExpression arrayExpression =
arrayAccessExpression.getArrayExpression();
calculateExceptionsThrown(arrayExpression, exceptionTypes);
final PsiExpression indexExpression =
arrayAccessExpression.getIndexExpression();
calculateExceptionsThrown(indexExpression, exceptionTypes);
private static void calculateExceptionsThrownForArrayAccessExpression(PsiArrayAccessExpression arrayAccessExpression,
Set<PsiType> exceptionTypes) {
final PsiExpression arrayExpression = arrayAccessExpression.getArrayExpression();
calculateExceptionsThrownForExpression(arrayExpression, exceptionTypes);
final PsiExpression indexExpression = arrayAccessExpression.getIndexExpression();
calculateExceptionsThrownForExpression(indexExpression, exceptionTypes);
}
private static void calculateExceptionsThrownForPrefixException(
PsiPrefixExpression prefixExpression,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForPrefixException(PsiPrefixExpression prefixExpression, Set<PsiType> exceptionTypes) {
final PsiExpression operand = prefixExpression.getOperand();
calculateExceptionsThrown(operand, exceptionTypes);
calculateExceptionsThrownForExpression(operand, exceptionTypes);
}
private static void calculateExceptionsThrownForPostixExpression(
PsiPostfixExpression postfixExpression,
Set<PsiType> exceptionTypes) {
private static void calculateExceptionsThrownForPostfixExpression(PsiPostfixExpression postfixExpression, Set<PsiType> exceptionTypes) {
final PsiExpression operand = postfixExpression.getOperand();
calculateExceptionsThrown(operand, exceptionTypes);
calculateExceptionsThrownForExpression(operand, exceptionTypes);
}
public static void calculateExceptionsThrownForCodeBlock(
@@ -1,5 +1,5 @@
/*
* Copyright 2003-2006 Dave Griffith, Bas Leijdekkers
* Copyright 2003-2012 Dave Griffith, Bas Leijdekkers
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -19,8 +19,9 @@ import com.intellij.psi.PsiType;
import java.util.Comparator;
class HeirarchicalTypeComparator implements Comparator<PsiType> {
class HierarchicalTypeComparator implements Comparator<PsiType> {
@Override
public int compare(PsiType type1, PsiType type2) {
if (type1.isAssignableFrom(type2)) {
return 1;
@@ -1,20 +0,0 @@
package com.siyeh.ipp;
import java.sql.DriverManager;
import java.sql.Connection;
public class DetailExceptionTestCase{
public void foo()
{
Connection conn;
try{
Class.forName("logon.name");
DriverManager
.getConnection("jdbc:mysql://localhost/test", "root", "");
} catch(ClassNotFoundException e){
} catch(Exception e){
}
}
}
@@ -0,0 +1,16 @@
package com.siyeh.ipp.exceptions.detail;
class Disjunction {
void foo() {
t<caret>ry{
if (true) {
throw new IllegalArgumentException();
} else {
throw new NullPointerException();
}
} catch (IllegalArgumentException | NullPointerException e) {
}
}
}
@@ -0,0 +1,14 @@
package com.siyeh.ipp.exceptions.detail;
import java.util.List;
class Foreach {
void foo(List<String> list) {
<caret>try {
for (String s : list) {
throw new IllegalArgumentException();
}
} catch (RuntimeException e) {}
}
}
@@ -0,0 +1,15 @@
package com.siyeh.ipp.exceptions.detail;
import java.util.List;
class Foreach {
void foo(List<String> list) {
try {
for (String s : list) {
throw new IllegalArgumentException();
}
} catch (IllegalArgumentException e) {
}
}
}
@@ -0,0 +1,16 @@
package com.siyeh.ipp.exceptions.detail;
class Simple {
void foo() {
<caret>try{
if (true) {
throw new IllegalArgumentException();
} else {
throw new NullPointerException();
}
} catch (RuntimeException e) {
}
}
}
@@ -0,0 +1,18 @@
package com.siyeh.ipp.exceptions.detail;
class Simple {
void foo() {
try {
if (true) {
throw new IllegalArgumentException();
} else {
throw new NullPointerException();
}
} catch (IllegalArgumentException e) {
} catch (NullPointerException e) {
}
}
}
@@ -0,0 +1,14 @@
package com.siyeh.ipp.exceptions.detail;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
class TryWithResources {
void foo(File file1, File file2) {
<caret>try (FileInputStream in = new FileInputStream(file1); FileOutputStream out = new FileOutputStream(file2)) {
throw new IllegalArgumentException();
} catch (Exception e) {}
}
}
@@ -0,0 +1,15 @@
package com.siyeh.ipp.exceptions.detail;
import java.io.*;
class TryWithResources {
void foo(File file1, File file2) {
try (FileInputStream in = new FileInputStream(file1); FileOutputStream out = new FileOutputStream(file2)) {
throw new IllegalArgumentException();
} catch (FileNotFoundException e) {
} catch (IOException e) {
} catch (IllegalArgumentException e) {
}
}
}
@@ -0,0 +1,25 @@
package com.siyeh.ipp.exceptions;
import com.siyeh.IntentionPowerPackBundle;
import com.siyeh.ipp.IPPTestCase;
/**
* @author Bas Leijdekkers
*/
public class DetailExceptionsIntentionTest extends IPPTestCase {
public void testDisjunction() { assertIntentionNotAvailable(); }
public void testSimple() { doTest(); }
public void testForeach() { doTest(); }
public void testTryWithResources() { doTest(); }
@Override
protected String getIntentionName() {
return IntentionPowerPackBundle.message("detail.exceptions.intention.name");
}
@Override
protected String getRelativePath() {
return "exceptions/detail";
}
}