从onRedelivery触发新的onException路由

时间:2014-06-13 16:53:17

标签: error-handling apache-camel

我有一个ErrorHandlerDefaultErrorHandler),我提供了onRedelivery参考号。默认情况下,ErrorHandler会无限次重试。但是,如果存在某种条件(当前由onRedelivery ref确定),我想退出重新传递循环并执行不同的路由。

我最初的想法是让onRedelivery引用抛出和异常,并将相应的onException指向适当的路线。但是,我发现RedeliveryErrorHandler捕获了此异常并继续循环。

我还发现我可以将Exchange.REDELIVERY_EXHAUSTED设置为true,这将退出重新传递循环,但不会将我引导到恢复路径。

有什么建议吗?

Edit

所以我发现如果我将原始异常类型添加到我onException的{​​{1}}中的异常类型的RouteBuilder,并且我设置了{ {1}}为true,原始异常将被抛出到ErrorHandler范围并被Exchange.REDELIVERY_EXHAUSTED捕获。但是,我真的更喜欢抛出并捕获一个新的异常类型,以便处理对于这种情况是明确的。

RouteBuilder

所以使用onException的{​​{1}}建议非常棒,因为它允许我以编程方式确定何时停止重试。它也是。它只走了一半的想法。第二部分是将失败的交换发送到新的/不同的路由以进行错误处理。这是通过使用Answer而不是Peter's来完成的。

1 个答案:

答案 0 :(得分:1)

retryWhiledeadLetterChannel结合使用:

public class MyRouteBuilder extends RouteBuilder {
    @Override
    public void configure() {
        errorHandler(deadLetterChannel("direct:special")
            .retryWhile(method(new MyPredicate())));

        from("direct:start")
            .log("Starting...")
            .throwException(new Exception("dummy"));

        from("direct:special")
            .log("...Special");
    }
}

public class MyPredicate implements Predicate {
    @Override
    public boolean matches(final Exchange exchange) {
        AtomicInteger counter = exchange.getProperty("myCounter");
        if (counter == null) {
            counter = new AtomicInteger(0);
            exchange.setProperty("myCounter", counter);
        }
        int count = counter.incrementAndGet();
        LOG.info("Count = {}", count);
        return count < 3; // or whatever condition is suitable
    }
}

打印:

INFO  Starting...
INFO  Count = 1
INFO  Count = 2
INFO  Count = 3
INFO  ...Special