Is Apache Camel route step scope always singleton? - apache-camel

I mean that if (for example) processor bean is declared in Blueprint XML and included into just one route, then its single instance is used by every thread that executes message routing within this route. So I guess that there is no sense in prototype scope for such bean declaration.
The only right place to use prototype scope for route step declaration is the case when bean is used in several routes. In this case there will be created separate instance of bean for every route.
Am I wright?

No if you refer to the same bean id in multiple routes its the same instance you are using.
You can configure Camel bean component to turn off its cache with cache=false and define the bean to be prototype scoped to have a new instance per call - however its seldom used and also a bad practice. Its better to code your beans as thread-safe.

Related

Camel 2.21.1 RouterBuilder OSGI Service getting exception due to Simple language not found in OSGI Service Registry

I am extending Camel RouteBuilder in order to define a Camel route, thus my specialized class is a OSGI component and on #Activate method the camel context is being created, like:
camelContext = new OsgiDefaultCamelContext(bundleContext);
After that the camelContext.addRoute(this) method is invoked, but when the camelContext.start() method is invoked the org.apache.camel.NoSuchLanguageException is threw. Thus, looks like there is a racing condition due to org.apache.camel.language.simple.SimpleLanguage is not register yet in OSGI SR.
Note:
There is no OSGI injection in route builder specialization, thus this one will be ready to activate sooner even before camel-core components.
Then, I'm wondering if it's a issue once makes no sense to my custom bundle add Camel internal dependency (like to SimpleLanguage reference) just to get out this racing condition.
You need to do more setup of CamelContext if you manually create Camel in OSGi.
if you crate osgi camel context yourself, there is a few more setup you need to do
take a look in camel-core-osgi there is a helper class with a method that setup a bunch of stuff
I'm wondering if there is a race condition with Camel-core activator and my custom bundle (no Camel OSGI dependency at all), because bundle language is register with the following invoke stack bundle activation

How to capture error at compile level in Apache Camel

I have route like
.bean(OrderService.class, "doSomething")
Now my question is if for any reason any developer misspell method name in route, we would not be able to identify at compile level or we may realize after going to production.
How to handle these scenario?
At a minimum I would recommend a test which ensures that your Camel components are registered with the Camel context, and if they're not, one would expect an exception to be thrown at application startup time.
In essence, you would want a Spring test suite (since Camel will leverage Spring's context for its own context) to ensure that your bean is wired in correctly here.
This cannot be a compile-time error or check since this is specific to how the application context is built, which is done dynamically at runtime.

Apache Camel unique property name in two different routes

We have multiple routes running independently on a quartz scheduler, most of the functionalities are similar, so we have created some common routes to call inside parent routes for code reuse.
Is generic route property will be treated as a local variable and will not be shared among two different routes or value of the property will be changed by some other route.
<setProperty propertyName="remoteServerException">
<simple>${exception.message}</simple>
</setProperty>
Above is one of the property used in common route, and called from multiple routes, is it fine to be called like this? Please advice.
The <setProperty> is referring to properties on the Camel Exchange which is the instance, that contains the message being routed - there is one Exchange per message and its not shared - its local for that given message. So if you have some kind of shared route, you call via direct endpoints etc, then calling <setProperty> will not cause harm, its operating only on the Exchange instance.

How to access header and property from callee in ASynch Route in Apache Camel

I have Apache Camel Route which listens to ActiveMQ queue. During the processing, at one point, route sets the header and property on the exchange.
Now during the integration testing, we want to check the value of the header and property.
The question is, how do we access these two things ie. header and property.
I have tried using the producerTemplate's asyncRequestBody/asyncRequestBodyAndHeader etc. With Future object I can access Exchange, however, I am not able to access the header and property set on the exchange.
I have made sure that the route is InOut type.
If you can get the exchange, can you not just use exchange.getProperty(name) to get the property you're looking for?
I have set properties in my route:
<setProperty propertyName="sampleProperty">
<simple>${body}</simple>
</setProperty>
and retrieve them later using {property.sampleProperty}

Dynamic nested component views with UI Router

I have an Angular application that already uses UI Router. It currently uses nested views as most people do using the dot notation i.e. parent.childState.
However, it is now apparent that some parts of this application need to be reused elsewhere, lets call this Module A This module is tabbed and currently has a state associated with each tab. Currently, like most UI Router applications, the routes are set up during the application configuration phase.
With this new component Id like it to register its own routes, and that those routes are child routes of whatever parent view they are in.
Is this possible?
You can do the following :
Declare a provider in your Module A which will be able to register all the components of your application where you want to insert your module. One of the parameter will be obvisouly the state prefix. This provider will call the $stateProvider internally, either when you call the provider's function, or when you instantiate the service that match to the provider (the $get).
If you choose the $get function you'll need to add an angular.run() to force the instantiation of the service resulting of the $get. Otherwise the $get will be called later and the states won't be mapped resulting in a $stateNotFound. This is usefull if you want to be able to overload some configuration before the $stateProvider is called, if you don't need that, don't use the $stateProvider in the $get function.
So now all you have to do in others module is to have a dependency on the Module A and use the said provider.

Resources