Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ErrorHandler for stopping a route when an error occurs #2724

Closed
nicolaferraro opened this issue Oct 28, 2021 · 9 comments · Fixed by #2727
Closed

ErrorHandler for stopping a route when an error occurs #2724

nicolaferraro opened this issue Oct 28, 2021 · 9 comments · Fixed by #2727
Milestone

Comments

@nicolaferraro
Copy link
Member

I was trying to implement the "stop route" behavior when encountering an error in a KameletBinding and it looks I can use a controlbus to implement it.

Something like:

kind: KameletBinding
spec:
  source:
    # ...
  sink:
    # ...
  errorHandler:
    dead-letter-channel:
      endpoint:
        uri: "controlbus:route?routeId=${routeId}&action=stop"

Even if the concept of dead-letter-channel is a bit stretched here, that should do the work.
The only problem is that error handlers in Camel do not use dynamic dispatch and so the ${routeId} placeholder is not resolved. Everything works when providing the right route ID.

Since bindings have a single main route, I wonder if we can simply call it e.g. binding in order to use a URI like controlbus:route?routeId=binding&action=stop.

@davsclaus you're the master, do you see another way?

cc: @squakez

@nicolaferraro nicolaferraro added this to the 1.7.0 milestone Oct 28, 2021
@astefanutti
Copy link
Member

Also what would be needed is that the error would be stored into the route last error, so that it integrates nicely with #2719, and the error message be reported into the integration / binding status.

@davsclaus
Copy link
Contributor

@nicolaferraro you can use current which will be the current route, though you may have trouble if you have multiple routes linked via direct - bit a single route then. current should be fine.

@squakez
Copy link
Contributor

squakez commented Oct 28, 2021

I am not familiar with the controlbus, and, having had a look at it, it seems a possible approach. However, as you've commented, it seems more an hack to have it working. Another similar alternative could be to use a kamelet stop action instead:

  errorHandler:
    dead-letter-channel:
      endpoint:
        ref:
          kind: Kamelet
          apiVersion: camel.apache.org/v1alpha1
          name: stop-route

or we can include a new parameter to the errorHandler to configure both a dlc, log or anything else supported plus an action which will be in charge to control the route, ie:

  errorHandler:
    dead-letter-channel:
    ...
    action: stop
    ...

In that case we should change also something on the came-k-runtime (more or less here)

About the routes names we use, maybe this snippet can be helpful:

[1] 2021-10-28 15:42:27,228 INFO  [org.apa.cam.imp.eng.AbstractCamelContext] (main) Routes shutdown summary (total:4 stopped:4)
[1] 2021-10-28 15:42:27,228 INFO  [org.apa.cam.imp.eng.AbstractCamelContext] (main)     Stopped route1 (kamelet://incremental-id-source/source)
[1] 2021-10-28 15:42:27,229 INFO  [org.apa.cam.imp.eng.AbstractCamelContext] (main)     Stopped source (timer://tick)
[1] 2021-10-28 15:42:27,229 INFO  [org.apa.cam.imp.eng.AbstractCamelContext] (main)     Stopped sink (kamelet://source)
[1] 2021-10-28 15:42:27,229 INFO  [org.apa.cam.imp.eng.AbstractCamelContext] (main)     Stopped errorHandler (kamelet://source)

Basically we control the names of the routes for the KameletBinding, so, maybe it is just a matter to identify them and properly shutdown them.

@nicolaferraro
Copy link
Member Author

anything

Yeah, I like the Kamelet approach for the error handler. It may also be useful to add additional behavior, such as setting the last error as @astefanutti was mentioning. The action, such as "stop" or "ignore" could be part of the Kamelet itself.

@davsclaus
Copy link
Contributor

Another ticket to allow to control Camel to auto stop un-healthy routes
https://issues.apache.org/jira/browse/CAMEL-17148

@nicolaferraro
Copy link
Member Author

nicolaferraro commented Oct 29, 2021

@davsclaus I see that the lastError on the route is not set when an exception is thrown in an exchange. Is that something linked to health-check only?

@davsclaus
Copy link
Contributor

davsclaus commented Oct 29, 2021

its 2 different things

  • lastError is only on starting up camel, if a route fails to startup, its something gnodet added in the 3.x refactoring AFAIR.

  • when all routes is started, then its the consumers of the routes, that take in and process messages, and if they fail, the their errors are handled via camel error handler in the routes DSL, or the exception handler on the consumer (there is a bridge option to turn that into a fake message to route this message and let the Camel routing error handler deal with it)

@nicolaferraro
Copy link
Member Author

Ok, btw let's give the main route a name, since when using the Kamelet strategy we're basically switching to another route, so we need a way to stop the main one.

For the "lastError" field, @astefanutti I'm not sure it's the right place to put the reason why we stopped a route in case of exchange error, since as @davsclaus was saying, it contains lifecycle errors that were throws while trying to change the state of a route (starting, stopping, ..)

@astefanutti
Copy link
Member

While currently the "last error" concept is only implemented for route lifecycle operations, my understanding is that it's generic and not limited to route lifecycle:

https://github.com/apache/camel/blob/1b374423fb9371075184d5ab2d9c3b15015b2334/core/camel-api/src/main/java/org/apache/camel/health/HealthCheck.java#L111

Intuitively, when the decision is taken to stop a route because an error during the processing of an exchange occurred, I would expect the error details to be reported as well in the health check result, as an explanation of the DOWN status.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants