mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
highlighting for caught exceptions
This commit is contained in:
@@ -308,3 +308,6 @@ closure.is.too.complex.to.analyze=Closure is complex to analyze.\nTypes of local
|
||||
create.parameter.from.usage=Create Parameter ''{0}''
|
||||
wrong.number.of.type.arguments=Wrong number of type arguments\: {0}; required\: {1}
|
||||
type.argument.0.is.not.in.its.bound.should.extend.1=Type parameter ''{0}'' is not in its bound; should extend ''{1}''
|
||||
catch.statement.parameter.type.should.be.a.subclass.of.throwable=Catch statement parameter type should be a subclass of Throwable
|
||||
exception.0.has.already.been.caught=Exception ''{0}'' has already been caught
|
||||
unnecessary.type=Unnecessary exception ''{0}''. ''{1}'' is already declared
|
||||
|
||||
@@ -227,6 +227,71 @@ public class GroovyAnnotator extends GroovyElementVisitor implements Annotator {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visitTryStatement(GrTryCatchStatement statement) {
|
||||
final GrCatchClause[] clauses = statement.getCatchClauses();
|
||||
List<PsiType> usedExceptions = new ArrayList<PsiType>();
|
||||
|
||||
final PsiClassType throwable = PsiType.getJavaLangThrowable(statement.getManager(), statement.getResolveScope());
|
||||
|
||||
for (GrCatchClause clause : clauses) {
|
||||
final GrParameter parameter = clause.getParameter();
|
||||
if (parameter == null) continue;
|
||||
|
||||
final GrTypeElement typeElement = parameter.getTypeElementGroovy();
|
||||
|
||||
PsiType type = typeElement != null ? typeElement.getType() : null;
|
||||
if (type == null) {
|
||||
type = throwable;
|
||||
}
|
||||
|
||||
if (!throwable.isAssignableFrom(type)) {
|
||||
LOG.assertTrue(typeElement != null);
|
||||
myHolder.createErrorAnnotation(typeElement,
|
||||
GroovyBundle.message("catch.statement.parameter.type.should.be.a.subclass.of.throwable"));
|
||||
continue;
|
||||
}
|
||||
|
||||
if (typeElement instanceof GrDisjunctionTypeElement) {
|
||||
final GrTypeElement[] elements = ((GrDisjunctionTypeElement)typeElement).getTypeElements();
|
||||
PsiType[] types = new PsiType[elements.length];
|
||||
for (int i = 0; i < elements.length; i++) {
|
||||
types[i] = elements[i].getType();
|
||||
}
|
||||
|
||||
List<PsiType> usedInsideDisjunction = new ArrayList<PsiType>();
|
||||
for (int i = 0; i < types.length; i++) {
|
||||
if (checkExceptionUsed(usedExceptions, parameter, elements[i], types[i])) {
|
||||
usedInsideDisjunction.add(types[i]);
|
||||
for (int j = 0; j < types.length; j++) {
|
||||
if (i != j && types[j].isAssignableFrom(types[i])) {
|
||||
myHolder.createWarningAnnotation(elements[i], GroovyBundle.message("unnecessary.type", types[i].getCanonicalText(),
|
||||
types[j].getCanonicalText()));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
usedExceptions.addAll(usedInsideDisjunction);
|
||||
}
|
||||
else {
|
||||
if (checkExceptionUsed(usedExceptions, parameter, typeElement, type)) {
|
||||
usedExceptions.add(type);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private boolean checkExceptionUsed(List<PsiType> usedExceptions, GrParameter parameter, GrTypeElement typeElement, PsiType type) {
|
||||
for (PsiType exception : usedExceptions) {
|
||||
if (exception.isAssignableFrom(type)) {
|
||||
myHolder.createWarningAnnotation(typeElement != null ? typeElement : parameter.getNameIdentifierGroovy(), GroovyBundle.message("exception.0.has.already.been.caught", type.getCanonicalText()));
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visitReferenceExpression(final GrReferenceExpression referenceExpression) {
|
||||
checkStringNameIdentifier(referenceExpression);
|
||||
|
||||
@@ -936,4 +936,52 @@ def test() {
|
||||
}
|
||||
''', GroovyAssignabilityCheckInspection)
|
||||
}
|
||||
|
||||
void testTryCatch1() {
|
||||
testHighlighting('''\
|
||||
try {}
|
||||
catch (Exception e){}
|
||||
catch (<warning descr="Exception 'java.io.IOException' has already been caught">IOException</warning> e){}
|
||||
''')
|
||||
}
|
||||
|
||||
void testTryCatch2() {
|
||||
testHighlighting('''\
|
||||
try {}
|
||||
catch (e){}
|
||||
catch (<warning descr="Exception 'java.lang.Throwable' has already been caught">e</warning>){}
|
||||
''')
|
||||
}
|
||||
|
||||
void testTryCatch3() {
|
||||
testHighlighting('''\
|
||||
try {}
|
||||
catch (e){}
|
||||
catch (<warning descr="Exception 'java.io.IOException' has already been caught">IOException</warning> e){}
|
||||
''')
|
||||
}
|
||||
|
||||
void testTryCatch4() {
|
||||
testHighlighting('''\
|
||||
try {}
|
||||
catch (Exception | <warning descr="Unnecessary exception 'java.io.IOException'. 'java.lang.Exception' is already declared">IOException</warning> e){}
|
||||
''')
|
||||
}
|
||||
|
||||
void testTryCatch5() {
|
||||
testHighlighting('''\
|
||||
try {}
|
||||
catch (RuntimeException | IOException e){}
|
||||
catch (<warning descr="Exception 'java.lang.NullPointerException' has already been caught">NullPointerException</warning> e){}
|
||||
''')
|
||||
}
|
||||
|
||||
void testTryCatch6() {
|
||||
testHighlighting('''\
|
||||
try {}
|
||||
catch (NullPointerException | IOException e){}
|
||||
catch (ClassNotFoundException | <warning descr="Exception 'java.lang.NullPointerException' has already been caught">NullPointerException</warning> e){}
|
||||
''')
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user