AMQP-334 Fix Nested Cause Classification
Consider Foo caused by Bar caused by Baz. If Bar is categorized TRUE and Baz categorized FALSE, classiy() should return TRUE (hit on Bar), but it returned FALSE. The early exit from the cause traversal was not taken because we were always testing against the top level throwable (Bar). Add a test to verify this scenario; test against the cause on each iteration through the loop.
This commit is contained in:
@@ -110,7 +110,7 @@ public class BinaryExceptionClassifier extends SubclassClassifier<Throwable, Boo
|
||||
if (classified.equals(this.getDefault())) {
|
||||
Throwable cause = classifiable;
|
||||
do {
|
||||
if (this.getClassified().containsKey(classifiable.getClass())) {
|
||||
if (this.getClassified().containsKey(cause.getClass())) {
|
||||
return classified; // non-default classification
|
||||
}
|
||||
cause = cause.getCause();
|
||||
|
||||
@@ -21,9 +21,13 @@ import static org.junit.Assert.assertTrue;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
import org.springframework.beans.DirectFieldAccessor;
|
||||
|
||||
public class BinaryExceptionClassifierTests {
|
||||
|
||||
BinaryExceptionClassifier classifier = new BinaryExceptionClassifier(false);
|
||||
@@ -65,6 +69,27 @@ public class BinaryExceptionClassifierTests {
|
||||
assertTrue(binaryExceptionClassifier.classify(new RuntimeException(new IllegalStateException("Foo"))));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testClassifySubclassMatchInCause() {
|
||||
Collection<Class<? extends Throwable>> set = Collections
|
||||
.<Class<? extends Throwable>> singleton(IllegalStateException.class);
|
||||
BinaryExceptionClassifier binaryExceptionClassifier = new BinaryExceptionClassifier(set);
|
||||
binaryExceptionClassifier.setTraverseCauses(true);
|
||||
assertTrue(binaryExceptionClassifier.classify(new RuntimeException(new FooException("Foo"))));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testClassifySubclassMatchInCauseFalse() {
|
||||
Map<Class<? extends Throwable>, Boolean> map = new HashMap<Class<? extends Throwable>, Boolean>();
|
||||
map.put(IllegalStateException.class, true);
|
||||
map.put(BarException.class, false);
|
||||
BinaryExceptionClassifier binaryExceptionClassifier = new BinaryExceptionClassifier(map, true);
|
||||
binaryExceptionClassifier.setTraverseCauses(true);
|
||||
assertTrue(binaryExceptionClassifier.classify(new RuntimeException(new FooException("Foo", new BarException()))));
|
||||
assertTrue(((Map<?, ?>) new DirectFieldAccessor(binaryExceptionClassifier).getPropertyValue("classified"))
|
||||
.containsKey(FooException.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testTypesProvidedInConstructor() {
|
||||
classifier = new BinaryExceptionClassifier(Collections
|
||||
@@ -86,4 +111,26 @@ public class BinaryExceptionClassifierTests {
|
||||
classifier.setTraverseCauses(true);
|
||||
assertFalse(classifier.classify(new RuntimeException(new RuntimeException(new IllegalStateException("Foo")))));
|
||||
}
|
||||
|
||||
@SuppressWarnings("serial")
|
||||
private class FooException extends IllegalStateException {
|
||||
|
||||
private FooException(String s) {
|
||||
super(s);
|
||||
}
|
||||
|
||||
private FooException(String s, Throwable t) {
|
||||
super(s, t);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@SuppressWarnings("serial")
|
||||
private class BarException extends RuntimeException {
|
||||
|
||||
private BarException() {
|
||||
super();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user