Contexts and Dependency Injection (CDI) in Camel Quarkus
CDI plays a central role in Quarkus and Camel Quarkus offers a first class support for it too.
You may use @Inject
, @ConfigProperty
and similar annotations e.g. to inject beans and configuration values to
your Camel RouteBuilder`s. Here is the `RouteBuilder
from our timer-log-cdi
example:
import javax.enterprise.context.ApplicationScoped;
import javax.inject.Inject;
import org.apache.camel.builder.RouteBuilder;
import org.eclipse.microprofile.config.inject.ConfigProperty;
@ApplicationScoped (1)
public class TimerRoute extends RouteBuilder {
@ConfigProperty(name = "timer.period", defaultValue = "1000") (2)
String period;
@Inject
Counter counter;
@Override
public void configure() throws Exception {
fromF("timer:foo?period=%s", period)
.setBody(exchange -> "Incremented the counter: " + counter.increment())
.to("log:cdi-example?showExchangePattern=false&showBodyType=false");
}
}
1 | The @ApplicationScoped annotation is required for @Inject and @ConfigProperty to work in a RouteBuilder .
Note that the @ApplicationScoped beans are managed by the CDI container and their life cycle is thus a bit more
complex than the one of the plain RouteBuilder . In other words, using @ApplicationScoped in RouteBuilder comes
with some boot time penalty and you should therefore only annotate your RouteBuilder with @ApplicationScoped when
you really need it. |
2 | The value for the timer.period property is defined in src/main/resources/application.properties of the example project. |
Please refer to the Quarkus Dependency Injection guide for more details. |
CDI and the Camel Bean component
Refer to a bean by name
To refer to a bean in a route definition by name, just annotate the the bean with @Named("myNamedBean")
and
@ApplicationScoped
(or some other
supported scope). The @RegisterForReflection
annotation
is important for the native mode.
import javax.enterprise.context.ApplicationScoped;
import javax.inject.Named;
import io.quarkus.runtime.annotations.RegisterForReflection;
@ApplicationScoped
@Named("myNamedBean")
@RegisterForReflection
public class NamedBean {
public String hello(String name) {
return "Hello " + name + " from the NamedBean";
}
}
Then you can use the myNamedBean
name in a route definition:
import org.apache.camel.builder.RouteBuilder;
public class CamelRoute extends RouteBuilder {
@Override
public void configure() {
from("direct:named")
.to("bean:namedBean?method=hello");
}
}