[
https://issues.apache.org/jira/browse/CAMEL-26434?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
]
Work on CAMEL-26434 started by shashank.
----------------------------------------
> camel-core - doTry: after a route called from the doTry failed unhandled, a
> route called from the doCatch cannot handle its own failure with its error
> handler
> --------------------------------------------------------------------------------------------------------------------------------------------------------------
>
> Key: CAMEL-26434
> URL: https://issues.apache.org/jira/browse/CAMEL-26434
> Project: Camel
> Issue Type: Bug
> Components: camel-core
> Reporter: shashank
> Assignee: shashank
> Priority: Minor
>
> Found while working on CAMEL-26333 (apache/camel#28756), from a question in
> its review.
> When the {{doTry}} block calls a route (such as with {{direct}}) that fails
> *unhandled* (default error handler, no {{onException}}), that route's error
> handler marks the exchange as failure handled
> ({{ExchangeExtension.isFailureHandled() == true}},
> {{errorHandlerHandled=false}}) before the exception goes back to the caller.
> The {{doCatch}} then catches the exception, but {{CatchProcessor}} only
> clears the exception, not that mark. A route called from the {{doCatch}} that
> fails can then not apply its own error handler:
> {{RedeliveryErrorHandler.isDone}} treats an exchange that is failure handled
> as done, so neither its dead letter channel nor its handled {{onException}}
> run, and the exchange fails with that route's exception.
> When the {{doTry}} block fails in the same route (no error handler involved,
> as doTry children are not wrapped in the route error handler), the same route
> called from the {{doCatch}} handles its failure as expected.
> {code:java}
> // the doTry calls a route that fails unhandled
> from("direct:viaCallee")
> .doTry().to("direct:failing")
>
> .doCatch(IllegalArgumentException.class).to("mock:catch").to("direct:dlcRoute")
> .end()
> .to("mock:after");
> // control: the doTry fails in the same route
> from("direct:inRoute")
> .doTry().throwException(new IllegalArgumentException("in route"))
>
> .doCatch(IllegalArgumentException.class).to("mock:catch").to("direct:dlcRoute")
> .end()
> .to("mock:after");
> from("direct:failing").throwException(new IllegalArgumentException("callee"));
> from("direct:dlcRoute").errorHandler(deadLetterChannel("mock:dead").redeliveryDelay(0))
> .throwException(new IOException("in catch"));
> // direct:viaCalleeOnException and direct:inRouteOnException: as above, with
> .to("direct:onExceptionRoute") in the doCatch
> from("direct:onExceptionRoute")
> .onException(IOException.class).handled(true).to("mock:handled").end()
> .throwException(new IOException("in catch"));
> {code}
> On main (baaf532, 2026-10-31), with a JUnit test ({{ContextTestSupport}}, the
> two failing cases failed on all three surefire runs):
> ||send||doCatch calls||exception of the exchange||mock:dead||mock:handled||
> |direct:viaCallee|dead letter channel route|{{IOException: in catch}}|0|0|
> |direct:inRoute (control)|dead letter channel route|none|1|0|
> |direct:viaCalleeOnException|handled onException route|{{IOException: in
> catch}}|0|0|
> |direct:inRouteOnException (control)|handled onException route|none|0|1|
> In the two failing cases the exchange is {{failureHandled=true}},
> {{errorHandlerHandled=false}} when it comes back.
> Expected: a route called from a {{doCatch}} handles (or continues) its own
> failure with its error handler, whether the {{doTry}} failed in the same
> route or in a route it called.
> *Proposal*
> * Clear the failure handled mark (and {{errorHandlerHandled}}, if set) when
> the {{doCatch}} takes over the exception in {{CatchProcessor}}, as
> CAMEL-26333 does around the {{doFinally}} block in {{FinallyProcessor}}, and
> check that the caller still behaves as before after the {{doCatch}} (it
> continues after the {{doTry}}, as the exception is caught). The related
> history is CAMEL-2577 and CAMEL-7275 (no nested error handlers for the
> children of doTry), which this does not change: the routes called from the
> {{doCatch}} have error handlers of their own.
> * Tests: the four cases above, plus a nested {{doTry}} and an asynchronous
> callee.
> _Filed with Claude Code on behalf of allthingssecurity._
--
This message was sent by Atlassian Jira
(v10.3.26#10030026)