kotlinapache-camelquarkus

Using AdviceWith with Kotlin and Quarkus


I am trying to write tests for my camel routes. I use Kotlin with Quarkus.

As I realized, CamelContext tries to run the AdviceWithRouteBuilder before my own RouteBuilder with my production routes so tests are failing to start. I initialize the advice like:

fun configureMockEventTopicEndpoint() {
    AdviceWith.adviceWith(
        "event-collector",
        context,
        ReplaceDirectThem()
    )
}

class ReplaceDirectThem : AdviceWithRouteBuilder() {
    override fun configure() {
        replaceFromWith("direct:abc")
        interceptSendToEndpoint("jms:topic:*")
            .skipSendToOriginalEndpoint()
            .to("mock:jms:topic:someTopic")
    }
}

in this case, it throws:

Caused by: java.lang.IllegalArgumentException: originalRoute must be specified on: Routes: []

Obviously since this is running before my actual route builder. When I make it java like:

fun configureEventTopicEndpoint() {
    AdviceWith.adviceWith(
        "event-collector",
        context,
        object : AdviceWithRouteBuilder() {
            override fun configure() {
                replaceFromWith("direct:abc")
                interceptSendToEndpoint("jms:topic:*")
                    .skipSendToOriginalEndpoint()
                    .to("mock:jms:topic:sendstuff")
            }
        }
    )
}

Then it throws:

class org.apache.camel.support.ObjectHelper cannot access a member of class .....CamelRoutesTest$configureMockEventTopicEndpoint$1 with modifiers ""

What am I missing here?

I tried both ways as described above. Also checked the source code of camel and realized MainConfigurationProperties.routeBuilders are seeing my test route builders before my own prod routes

I expect my routes to run before the test route builders so they can be edited. In the end tests should be succesfull.


Solution

  • This seems to be a bug. AdviceWithRouteBuilder types are included in the Camel Quarkus build time RouteBuilder discovery, but there's no way to set the original route being advised. Hence the 'originalRoute must be specified on...' exception.

    You can can work around this issue by making any AdviceWithRouteBuilder classes private. For example, with the original example above.

    private class ReplaceDirectThem : AdviceWithRouteBuilder() {
        override fun configure() {
            replaceFromWith("direct:abc")
            interceptSendToEndpoint("jms:topic:*")
                .skipSendToOriginalEndpoint()
                .to("mock:jms:topic:someTopic")
        }
    }