use of javax.jms.Destination in project camel by apache.
the class JmsProducer method resolveOrCreateDestination.
protected Destination resolveOrCreateDestination(String destinationName, Session session) throws JMSException {
Destination dest = null;
boolean isPubSub = isTopicPrefix(destinationName) || (!isQueuePrefix(destinationName) && endpoint.isPubSubDomain());
// try using destination resolver to lookup the destination
if (endpoint.getDestinationResolver() != null) {
dest = endpoint.getDestinationResolver().resolveDestinationName(session, destinationName, isPubSub);
if (LOG.isDebugEnabled()) {
LOG.debug("Resolved JMSReplyTo destination {} using DestinationResolver {} as PubSubDomain {} -> {}", new Object[] { destinationName, endpoint.getDestinationResolver(), isPubSub, dest });
}
}
if (dest == null) {
// must normalize the destination name
String before = destinationName;
destinationName = normalizeDestinationName(destinationName);
LOG.trace("Normalized JMSReplyTo destination name {} -> {}", before, destinationName);
// okay then fallback and create the queue/topic
if (isPubSub) {
LOG.debug("Creating JMSReplyTo topic: {}", destinationName);
dest = session.createTopic(destinationName);
} else {
LOG.debug("Creating JMSReplyTo queue: {}", destinationName);
dest = session.createQueue(destinationName);
}
}
return dest;
}
use of javax.jms.Destination in project camel by apache.
the class JmsProducer method processInOut.
protected boolean processInOut(final Exchange exchange, final AsyncCallback callback) {
final org.apache.camel.Message in = exchange.getIn();
String destinationName = in.getHeader(JmsConstants.JMS_DESTINATION_NAME, String.class);
// remove the header so it wont be propagated
in.removeHeader(JmsConstants.JMS_DESTINATION_NAME);
if (destinationName == null) {
destinationName = endpoint.getDestinationName();
}
Destination destination = in.getHeader(JmsConstants.JMS_DESTINATION, Destination.class);
// remove the header so it wont be propagated
in.removeHeader(JmsConstants.JMS_DESTINATION);
if (destination == null) {
destination = endpoint.getDestination();
}
if (destination != null) {
// prefer to use destination over destination name
destinationName = null;
}
initReplyManager();
// the request timeout can be overruled by a header otherwise the endpoint configured value is used
final long timeout = exchange.getIn().getHeader(JmsConstants.JMS_REQUEST_TIMEOUT, endpoint.getRequestTimeout(), long.class);
final JmsConfiguration configuration = endpoint.getConfiguration();
// when using message id as correlation id, we need at first to use a provisional correlation id
// which we then update to the real JMSMessageID when the message has been sent
// this is done with the help of the MessageSentCallback
final boolean msgIdAsCorrId = configuration.isUseMessageIDAsCorrelationID();
final String provisionalCorrelationId = msgIdAsCorrId ? getUuidGenerator().generateUuid() : null;
MessageSentCallback messageSentCallback = null;
if (msgIdAsCorrId) {
messageSentCallback = new UseMessageIdAsCorrelationIdMessageSentCallback(replyManager, provisionalCorrelationId, timeout);
}
final String correlationProperty = configuration.getCorrelationProperty();
final String correlationPropertyToUse = ofNullable(correlationProperty).orElse("JMSCorrelationID");
final String originalCorrelationId = in.getHeader(correlationPropertyToUse, String.class);
boolean generateFreshCorrId = (ObjectHelper.isEmpty(originalCorrelationId) && !msgIdAsCorrId) || (originalCorrelationId != null && originalCorrelationId.startsWith(GENERATED_CORRELATION_ID_PREFIX));
if (generateFreshCorrId) {
// we append the 'Camel-' prefix to know it was generated by us
in.setHeader(correlationPropertyToUse, GENERATED_CORRELATION_ID_PREFIX + getUuidGenerator().generateUuid());
}
MessageCreator messageCreator = new MessageCreator() {
public Message createMessage(Session session) throws JMSException {
Message answer = endpoint.getBinding().makeJmsMessage(exchange, in, session, null);
Destination replyTo = null;
String replyToOverride = configuration.getReplyToOverride();
if (replyToOverride != null) {
replyTo = resolveOrCreateDestination(replyToOverride, session);
} else {
// get the reply to destination to be used from the reply manager
replyTo = replyManager.getReplyTo();
}
if (replyTo == null) {
throw new RuntimeExchangeException("Failed to resolve replyTo destination", exchange);
}
JmsMessageHelper.setJMSReplyTo(answer, replyTo);
replyManager.setReplyToSelectorHeader(in, answer);
String correlationId = determineCorrelationId(answer, provisionalCorrelationId);
replyManager.registerReply(replyManager, exchange, callback, originalCorrelationId, correlationId, timeout);
if (correlationProperty != null) {
replyManager.setCorrelationProperty(correlationProperty);
}
if (LOG.isDebugEnabled()) {
LOG.debug("Using {}: {}, JMSReplyTo destination: {}, with request timeout: {} ms.", new Object[] { correlationPropertyToUse, correlationId, replyTo, timeout });
}
LOG.trace("Created javax.jms.Message: {}", answer);
return answer;
}
};
doSend(true, destinationName, destination, messageCreator, messageSentCallback);
// continue routing asynchronously (reply will be processed async when its received)
return false;
}
use of javax.jms.Destination in project camel by apache.
the class JmsProducer method processInOnly.
protected boolean processInOnly(final Exchange exchange, final AsyncCallback callback) {
final org.apache.camel.Message in = exchange.getIn();
String destinationName = in.getHeader(JmsConstants.JMS_DESTINATION_NAME, String.class);
if (destinationName != null) {
// remove the header so it wont be propagated
in.removeHeader(JmsConstants.JMS_DESTINATION_NAME);
}
if (destinationName == null) {
destinationName = endpoint.getDestinationName();
}
Destination destination = in.getHeader(JmsConstants.JMS_DESTINATION, Destination.class);
if (destination != null) {
// remove the header so it wont be propagated
in.removeHeader(JmsConstants.JMS_DESTINATION);
}
if (destination == null) {
destination = endpoint.getDestination();
}
if (destination != null) {
// prefer to use destination over destination name
destinationName = null;
}
final String to = destinationName != null ? destinationName : "" + destination;
MessageSentCallback messageSentCallback = getEndpoint().getConfiguration().isIncludeSentJMSMessageID() ? new InOnlyMessageSentCallback(exchange) : null;
MessageCreator messageCreator = new MessageCreator() {
public Message createMessage(Session session) throws JMSException {
Message answer = endpoint.getBinding().makeJmsMessage(exchange, in, session, null);
// when in InOnly mode the JMSReplyTo is a bit complicated
// we only want to set the JMSReplyTo on the answer if
// there is a JMSReplyTo from the header/endpoint and
// we have been told to preserveMessageQos
Object jmsReplyTo = JmsMessageHelper.getJMSReplyTo(answer);
if (endpoint.isDisableReplyTo()) {
// honor disable reply to configuration
LOG.trace("ReplyTo is disabled on endpoint: {}", endpoint);
JmsMessageHelper.setJMSReplyTo(answer, null);
} else {
// if the binding did not create the reply to then we have to try to create it here
if (jmsReplyTo == null) {
// prefer reply to from header over endpoint configured
jmsReplyTo = exchange.getIn().getHeader("JMSReplyTo", String.class);
if (jmsReplyTo == null) {
jmsReplyTo = endpoint.getReplyTo();
}
}
}
// unless we use preserveMessageQos=true to tell that we still want to use JMSReplyTo
if (jmsReplyTo != null && !(endpoint.isPreserveMessageQos() || endpoint.isExplicitQosEnabled())) {
// this behavior is also documented at the camel website
if (LOG.isDebugEnabled()) {
LOG.debug("Disabling JMSReplyTo: {} for destination: {}. Use preserveMessageQos=true to force Camel to keep the JMSReplyTo on endpoint: {}", new Object[] { jmsReplyTo, to, endpoint });
}
jmsReplyTo = null;
}
// and if needed create the destination using the session if needed to
if (jmsReplyTo != null && jmsReplyTo instanceof String) {
String replyTo = (String) jmsReplyTo;
// we need to null it as we use the String to resolve it as a Destination instance
jmsReplyTo = resolveOrCreateDestination(replyTo, session);
}
// set the JMSReplyTo on the answer if we are to use it
Destination replyTo = null;
String replyToOverride = endpoint.getConfiguration().getReplyToOverride();
if (replyToOverride != null) {
replyTo = resolveOrCreateDestination(replyToOverride, session);
} else if (jmsReplyTo instanceof Destination) {
replyTo = (Destination) jmsReplyTo;
}
if (replyTo != null) {
LOG.debug("Using JMSReplyTo destination: {}", replyTo);
JmsMessageHelper.setJMSReplyTo(answer, replyTo);
} else {
// do not use JMSReplyTo
log.trace("Not using JMSReplyTo");
JmsMessageHelper.setJMSReplyTo(answer, null);
}
LOG.trace("Created javax.jms.Message: {}", answer);
return answer;
}
};
doSend(false, destinationName, destination, messageCreator, messageSentCallback);
// after sending then set the OUT message id to the JMSMessageID so its identical
setMessageId(exchange);
// we are synchronous so return true
callback.done(true);
return true;
}
use of javax.jms.Destination in project camel by apache.
the class EndpointMessageListener method onMessage.
@Override
public void onMessage(Message message, Session session) throws JMSException {
LOG.trace("onMessage START");
LOG.debug("{} consumer received JMS message: {}", endpoint, message);
boolean sendReply;
RuntimeCamelException rce;
try {
Object replyDestination = getReplyToDestination(message);
// we can only send back a reply if there was a reply destination configured
// and disableReplyTo hasn't been explicit enabled
sendReply = replyDestination != null && !disableReplyTo;
// we should also not send back reply to ourself if this destination and replyDestination is the same
Destination destination = JmsMessageHelper.getJMSDestination(message);
if (destination != null && sendReply && !endpoint.isReplyToSameDestinationAllowed() && destination.equals(replyDestination)) {
LOG.debug("JMSDestination and JMSReplyTo is the same, will skip sending a reply message to itself: {}", destination);
sendReply = false;
}
final Exchange exchange = createExchange(message, session, replyDestination);
if (eagerLoadingOfProperties) {
exchange.getIn().getHeaders();
}
String correlationId = message.getJMSCorrelationID();
if (correlationId != null) {
LOG.debug("Received Message has JMSCorrelationID [{}]", correlationId);
}
// process the exchange either asynchronously or synchronous
LOG.trace("onMessage.process START");
AsyncCallback callback = new EndpointMessageListenerAsyncCallback(message, exchange, endpoint, sendReply, replyDestination);
// async is by default false, which mean we by default will process the exchange synchronously
// to keep backwards compatible, as well ensure this consumer will pickup messages in order
// (eg to not consume the next message before the previous has been fully processed)
// but if end user explicit configure consumerAsync=true, then we can process the message
// asynchronously (unless endpoint has been configured synchronous, or we use transaction)
boolean forceSync = endpoint.isSynchronous() || endpoint.isTransacted();
if (forceSync || !isAsync()) {
// must process synchronous if transacted or configured to do so
if (LOG.isTraceEnabled()) {
LOG.trace("Processing exchange {} synchronously", exchange.getExchangeId());
}
try {
processor.process(exchange);
} catch (Exception e) {
exchange.setException(e);
} finally {
callback.done(true);
}
} else {
// process asynchronous using the async routing engine
if (LOG.isTraceEnabled()) {
LOG.trace("Processing exchange {} asynchronously", exchange.getExchangeId());
}
boolean sync = processor.process(exchange, callback);
if (!sync) {
// will be done async so return now
return;
}
}
// if we failed processed the exchange from the async callback task, then grab the exception
rce = exchange.getException(RuntimeCamelException.class);
} catch (Exception e) {
rce = wrapRuntimeCamelException(e);
}
// the JMS listener will use the error handler to handle the uncaught exception
if (rce != null) {
LOG.trace("onMessage END throwing exception: {}", rce.getMessage());
// on the JmsEndpoint to handle the exception
throw rce;
}
LOG.trace("onMessage END");
}
use of javax.jms.Destination in project camel by apache.
the class JmsProducerWithJMSHeaderTest method testInOnlyJMSDestination.
@Test
public void testInOnlyJMSDestination() throws Exception {
Destination queue = new ActiveMQQueue("foo");
MockEndpoint mock = getMockEndpoint("mock:result");
mock.expectedMessageCount(1);
mock.message(0).header("JMSDestination").isNotNull();
template.sendBodyAndHeader("activemq:queue:bar", "Hello World", JmsConstants.JMS_DESTINATION, queue);
assertMockEndpointsSatisfied();
assertEquals("queue://foo", mock.getReceivedExchanges().get(0).getIn().getHeader("JMSDestination", Destination.class).toString());
}
Aggregations