IDEA-152303 ('Optional.get() without isPresent() check' inspection should support assertions)

This commit is contained in:
Bas Leijdekkers
2016-02-29 20:45:45 +01:00
parent 8347d14e92
commit a42dad9bac
2 changed files with 43 additions and 13 deletions
@@ -90,15 +90,13 @@ public class OptionalGetWithoutIsPresentInspection extends BaseInspection {
if (condition != null) {
if (!ControlFlowUtils.statementMayCompleteNormally(ifStatement.getThenBranch())) {
checker.negate = true;
checker.checkExpression(condition);
if (checker.hasIsPresentCall()) {
if (checker.checkExpression(condition)) {
return true;
}
}
else if (!ControlFlowUtils.statementMayCompleteNormally(ifStatement.getElseBranch())) {
checker.negate = false;
checker.checkExpression(condition);
if (checker.hasIsPresentCall()) {
if (checker.checkExpression(condition)) {
return true;
}
}
@@ -108,11 +106,30 @@ public class OptionalGetWithoutIsPresentInspection extends BaseInspection {
final PsiAssertStatement assertStatement = (PsiAssertStatement)sibling;
final PsiExpression condition = assertStatement.getAssertCondition();
checker.negate = false;
checker.checkExpression(condition);
if (checker.hasIsPresentCall()) {
if (checker.checkExpression(condition)) {
return true;
}
}
else if (sibling instanceof PsiExpressionStatement) {
final PsiExpressionStatement expressionStatement = (PsiExpressionStatement)sibling;
final PsiExpression expression = expressionStatement.getExpression();
if (expression instanceof PsiMethodCallExpression) {
final PsiMethodCallExpression methodCallExpression = (PsiMethodCallExpression)expression;
if (MethodCallUtils.isCallToMethod(methodCallExpression, "org.junit.Assert", PsiType.VOID, "assertTrue", null) ||
MethodCallUtils.isCallToMethod(methodCallExpression, "junit.framework.Assert", PsiType.VOID, "assertTrue", null) ||
MethodCallUtils.isCallToMethod(methodCallExpression, "org.testng.Assert", PsiType.VOID, "assertTrue", null) ||
MethodCallUtils.isCallToMethod(methodCallExpression, "org.testng.AssertJUnit", PsiType.VOID, "assertTrue", null)) {
checker.negate = false;
final PsiExpressionList argumentList = methodCallExpression.getArgumentList();
final PsiExpression[] arguments = argumentList.getExpressions();
for (PsiExpression argument : arguments) {
if (checker.checkExpression(argument)) {
return true;
}
}
}
}
}
sibling = PsiTreeUtil.getPrevSiblingOfType(sibling, PsiStatement.class);
}
checker.negate = false;
@@ -185,16 +202,16 @@ public class OptionalGetWithoutIsPresentInspection extends BaseInspection {
checkExpression(expression.getCondition());
}
private void checkExpression(PsiExpression expression) {
private boolean checkExpression(PsiExpression expression) {
expression = PsiUtil.deparenthesizeExpression(expression);
if (expression instanceof PsiPrefixExpression) {
final PsiPrefixExpression prefixExpression = (PsiPrefixExpression)expression;
final IElementType tokenType = prefixExpression.getOperationTokenType();
if (tokenType != JavaTokenType.EXCL) {
return;
return false;
}
negate = !negate;
checkExpression(prefixExpression.getOperand());
return checkExpression(prefixExpression.getOperand());
}
else if (expression instanceof PsiPolyadicExpression) {
final PsiPolyadicExpression binaryExpression = (PsiPolyadicExpression)expression;
@@ -205,11 +222,11 @@ public class OptionalGetWithoutIsPresentInspection extends BaseInspection {
final PsiReferenceExpression methodExpression = methodCallExpression.getMethodExpression();
final String name = methodExpression.getReferenceName();
if (!"isPresent".equals(name)) {
return;
return false;
}
final PsiExpression qualifier = ParenthesesUtils.stripParentheses(methodExpression.getQualifierExpression());
if (!(qualifier instanceof PsiReferenceExpression)) {
return;
return false;
}
final PsiReferenceExpression referenceExpression = (PsiReferenceExpression)qualifier;
hasIsPresentCall = !negate && EquivalenceChecker.expressionsAreEquivalent(referenceExpression, this.referenceExpression);
@@ -219,10 +236,11 @@ public class OptionalGetWithoutIsPresentInspection extends BaseInspection {
final PsiExpression definition = VariableSearchUtils.findDefinition(referenceExpression, null);
final PsiExpression optionalDefinition = VariableSearchUtils.findDefinition(this.referenceExpression, null);
if (definition == null || optionalDefinition == null || optionalDefinition.getTextOffset() > definition.getTextOffset()) {
return;
return false;
}
checkExpression(definition);
return checkExpression(definition);
}
return hasIsPresentCall;
}
public boolean hasIsPresentCall() {
@@ -38,4 +38,16 @@ class OptionalWithoutIsPresent {
System.out.println(string);
}
}
private void checkAsserts() {
Optional<String> o1 = Optional.empty();
assert o1.isPresent();
System.out.println(o1.get());
Optional<String> o2 = Optional.empty();
org.junit.Assert.assertTrue(o2.isPresent());
System.out.println(o2.get());
Optional<String> o3 = Optional.empty();
org.testng.Assert.assertTrue(o3.isPresent());
System.out.println(o3.get());
}
}