To D
Camel supports the Message Endpoint from the EIP patterns using the Endpoint interface.
How does an application connect to a messaging channel to send and receive messages?

Connect an application to a messaging channel using a Message Endpoint, a client of the messaging system that the application can then use to send or receive messages.
Options
The To D eip supports 1 options, which are listed below.
Name | Description | Default | Type |
---|---|---|---|
description |
Sets the description of this node. |
String |
|
disabled |
Whether to disable this EIP from the route during build time. Once an EIP has been disabled then it cannot be enabled later at runtime. |
false |
Boolean |
uri |
Required The uri of the endpoint to send to. The uri can be dynamic computed using the org.apache.camel.language.simple.SimpleLanguage expression. |
String |
|
variableSend |
To use a variable as the source for the message body to send. This makes it handy to use variables for user data and to easily control what data to use for sending and receiving. Important: When using send variable then the message body is taken from this variable instead of the current message, however the headers from the message will still be used as well. In other words, the variable is used instead of the message body, but everything else is as usual. |
String |
|
variableReceive |
To use a variable as the source for the message body to send. This makes it handy to use variables for user data and to easily control what data to use for sending and receiving. Important: When using send variable then the message body is taken from this variable instead of the current Message , however the headers from the Message will still be used as well. In other words, the variable is used instead of the message body, but everything else is as usual. |
String |
|
pattern |
Sets the optional ExchangePattern used to invoke this endpoint. Enum values:
|
ExchangePattern |
|
cacheSize |
Sets the maximum size used by the org.apache.camel.spi.ProducerCache which is used to cache and reuse producers when using this recipient list, when uris are reused. Beware that when using dynamic endpoints then it affects how well the cache can be utilized. If each dynamic endpoint is unique then its best to turn off caching by setting this to -1, which allows Camel to not cache both the producers and endpoints; they are regarded as prototype scoped and will be stopped and discarded after use. This reduces memory usage as otherwise producers/endpoints are stored in memory in the caches. However if there are a high degree of dynamic endpoints that have been used before, then it can benefit to use the cache to reuse both producers and endpoints and therefore the cache size can be set accordingly or rely on the default size (1000). If there is a mix of unique and used before dynamic endpoints, then setting a reasonable cache size can help reduce memory usage to avoid storing too many non frequent used producers. |
Integer |
|
ignoreInvalidEndpoint |
Whether to ignore invalid endpoint URIs and skip sending the message. |
false |
Boolean |
allowOptimisedComponents |
Whether to allow components to optimise toD if they are org.apache.camel.spi.SendDynamicAware . |
true |
Boolean |
autoStartComponents |
Whether to auto startup components when toD is starting up. |
true |
Boolean |
Exchange properties
The To D eip supports 1 exchange properties, which are listed below.
The exchange properties are set on the Exchange
by the EIP, unless otherwise specified in the
description.
This means those properties are available after
this EIP has completed processing the Exchange
.
Name | Description | Default | Type |
---|---|---|---|
CamelToEndpoint |
Endpoint URI where this Exchange is being sent to. |
String |
Different between To and ToD
The to
is used for sending messages
to a static endpoint.
In other words to
sends messages
only to the same endpoint.
The toD
is used for sending messages
to a dynamic endpoint.
The dynamic endpoint is evaluated
on-demand by an Expression.
By default, the Simple expression
is used to compute
the dynamic endpoint URI.
Using ToD
For example, to send a message to an endpoint which is dynamically determined by a message header, you can do as shown below:
- Java
-
from("direct:start") .toD("${header.foo}");
- XML
-
<route> <from uri="direct:start"/> <toD uri="${header.foo}"/> </route>
You can also prefix the uri with a value because the endpoint URI is evaluated using the Simple language:
- Java
-
from("direct:start") .toD("mock:${header.foo}");
- XML
-
<route> <from uri="direct:start"/> <toD uri="mock:${header.foo}"/> </route>
In the example above, we compute the dynamic endpoint with a prefix "mock:" and then the header foo is appended. So, for example, if the header foo has value order, then the endpoint is computed as "mock:order".
Using other languages with toD
You can also use other languages such as XPath.
Doing this requires starting with language:
as shown below. If you do not
specify language:
then the
endpoint is a component name. And in some
cases, there is both a component and
language with the same name such as
xquery.
- Java
-
from("direct:start") .toD("language:xpath:/order/@uri");
- XML
-
<route> <from uri="direct:start"/> <toD uri="language:xpath:/order/@uri"/> </route>
Avoid creating endless dynamic endpoints that take up resources
When using dynamic computed endpoints with
toD
then you may compute a lot
of dynamic endpoints,
which results in an overhead of resources in
use, by each dynamic endpoint uri, and its
associated producer.
For example, HTTP-based endpoints where you may have dynamic values in URI parameters when calling the HTTP service, such as:
from("direct:login")
.toD("http:myloginserver:8080/login?userid=${header.userName}");
In the example above then the parameter
userid
is dynamically computed,
and would result in one instance of endpoint
and producer
for each different userid. To avoid having
too many dynamic endpoints you can configure
toD
to reduce its cache size,
for example,
to use a cache size of 10:
- Java
-
from("direct:login") .toD("http:myloginserver:8080/login?userid=${header.userName}", 10);
- XML
-
<route> <from uri="direct:login"/> <toD uri="http:myloginserver:8080/login?userid=${header.userName}" cacheSize="10"/> </route>
this will only reduce the endpoint
cache of the toD that
has a chance
of being reused in case a message is
routed with the same
userName header.
Therefore, reducing the cache size
will not solve the endless
dynamic endpoint problem.
Instead, you should use static
endpoints with to and
provide the dynamic parts in Camel
message headers (if possible).
|
Using static endpoints to avoid endless dynamic endpoints
In the example above then the parameter
userid
is dynamically
computed, and would result in one
instance of endpoint and producer
for each different userid. To avoid
having too dynamic endpoints, you use a
single static endpoint and use headers
to provide the dynamic parts:
from("direct:login")
.setHeader(Exchange.HTTP_PATH, constant("/login"))
.setHeader(Exchange.HTTP_QUERY, simple("userid=${header.userName}"))
.toD("http:myloginserver:8080");
However, you can use optimized components
for toD
that can
solve this out of the box,
as documented next.
Using optimized components with toD
A better solution would be if the HTTP
component could be optimized to handle the
variations of dynamic computed endpoint
uris.
This is with among the following components,
which have been optimized for
toD
:
-
camel-http
-
camel-jetty
-
camel-netty-http
-
camel-undertow
-
camel-vertx-http
A number of non-HTTP components has been optimized as well:
-
camel-amqp
-
camel-file
-
camel-ftp
-
camel-jms
-
camel-kafka
-
camel-paho-mqtt5
-
camel-paho
-
camel-sjms
-
camel-sjms2
-
camel-spring-rabbitmq
For the optimisation to work, then:
-
The optimization is detected and activated during startup of the Camel routes with
toD
. -
The dynamic uri in
toD
must provide the component name as either static or resolved via property placeholders. -
The supported components must be on the classpath.
The HTTP based components will be optimized to use the same hostname:port for each endpoint, and the dynamic values for context-path and query parameters will be provided as headers:
For example, this route:
from("direct:login")
.toD("http:myloginserver:8080/login?userid=${header.userName}");
It Will essentially be optimized to (pseudo route):
from("direct:login")
.setHeader(Exchange.HTTP_PATH, expression("/login"))
.setHeader(Exchange.HTTP_QUERY, expression("userid=${header.userName}"))
.toD("http:myloginserver:8080")
.removeHeader(Exchange.HTTP_PATH)
.removeHeader(Exchange.HTTP_QUERY);
Where expression will be evaluated
dynamically. Notice how the uri in
toD
is now static (http:myloginserver:8080
).
This optimization allows Camel to reuse the
same endpoint and its associated producer
for all dynamic variations.
This yields much lower resource overhead as
the same http producer will be used for all
the different variations of
userids
.
When the optimized component
is in use, then you cannot
use the headers |
In case of problems then you can turn on
DEBUG logging level on org.apache.camel.processor.SendDynamicProcessor
which will log
during startup if toD
was
optimized, or if there was a failure loading
the optimized component, with a stacktrace
logged.
Detected SendDynamicAware component: http optimising toD: http:myloginserver:8080/login?userid=${header.userName}