Error Message in Active MQ - jms

I am sending xml messages over the activemq queue using Camel route. Message is reaching to the queue but its not able to read it. Not sure if it is a apache camel issue or Active MQ issue.
My camel route is
<route>
<from uri="seda:elixirBatchQueue" />
<inOnly uri="activemq:queue:TESTQUEUE"/>
</route>
Error Message in the queue is
javax.jms.JMSException: Failed to build body from bytes. Reason: java.io.StreamCorruptedException: invalid type code: 00

The problem was with ActiveMQ as it was not able to understand the message format. When I converted it to String, Queue was able to recognize message as a DOM4J document.

Try this it works for me.
producer.Send(objectMessage.Body);
The library I used -->> Apache.NMS.ActiveMQ

Related

JMS - Items Not going to out Queue

I am using the JMeter JMS Publisher to send an item to a display - OK, but when I validate the item using JMS Subscriber it errors with 404 ? Looking at the JMS browser they are in the In Queue but not buffering to the out Queue ? I can force it through the JMS browser but cannot understand why the JMS subscriber part is not working ?
Any help would be appreciated.
Looking into JMS Subscriber Source code
if (sampleCounter == 0) {
res.setSuccessful(false);
res.setResponseCode("404");
res.setResponseMessage(sampleCounter + " samples messages received, last try had following response message:"+
res.getResponseMessage());
JMeter returns status 404 when the subscriber gets 0 results on attempt to consume the messages from the queue.
If you see the messages in the queue using the browser application it means that your JMS Subscriber configuration is not correct.
You can enable debug logging for JMeter's JMS protocol by adding the next line to log4j2.xml file:
<Logger name="org.apache.jmeter.protocol.jms" level="debug" />
Once done you should see the JNDI configuration, queue names, etc. so you could cross-check it with the values in the JMS Browser application and amend JMeter configuration to match it.

Junk Chars sent in message body when sending MQ message using jmsTemplate in Spring

I am using jmsTemplate to send messages to MQ Queue. When the consuming MQ application gets the message they are able to see junk chars like below in message. I need to remove them as they are causing parse exception.
WS-OUTPUT-BUFFER:RFH �����*����4MQSTR ������Ï´���∑∞_é¥û∞(Ω¥û|_Ω™æµ¬æ∞(Ω¥û∞_é¥û∑∑���ë∞|_Ωû∞ÖΩæûêÛµÛµÈä§É†âÉ
Ñ<…§(â§+äàâäà†&<·∞ÖΩæû∞ä_Ωû⁄fl‡Â›Âfi„fi∞ä_Ωû∞Ñ•¥û§ÖÈ雵¥„fiŸé›µ¥„µfiŸfiŸfiŸfiŸfiŸfiŸfiŸfiŸ¥‡éfiflé›∂éé„„fi„⁄Ÿ∞Ñ•¥û∞Ö%¿û∞Ö
%¿û∞|_Ωû���∫∞ÛΩºû∞ÑÑâ§Ö∑¥æ±•fiû„⁄Â∞ÑÑâ§Öû∞∂/•%§∂ÇÛ•µΩéµ∑¥æ±•fiû⁄∞∂/•%§∂ÇÛ•µΩéµû∞µ>é?¥•>è∑¥æ±•fiû›∞µ>é?¥•>èû∞ÛΩ
ºû∑∑∑<?xml version="1.0" encoding="UTF-8"?>
I had a similar issue when the receiving application could not handle the MQRFH2 header.
Therefore I had to set the TARGCLIENT (short TC) property with WMQ_CLIENT_NONJMS_MQ (value 1) on the JMS Destination object like this:
<Resource
name="jms/YOUR.QUEUE.NAME"
auth="Container"
type="com.ibm.mq.jms.MQQueue"
factory="com.ibm.mq.jms.MQQueueFactory"
QU="YOUR.QUEUE.NAME"
TC="1"/>
See also Exchanging messages between a JMS application and a traditional IBM MQ application.

Spring Integration - JMS to Kafka message transfer - End to End Transaction

I am consuming messages from JMS ActiveMQ using the following code:
<jms:message-driven-channel-adapter
id="helloJMSAdapater" destination="helloJMSQueue" connection-factory="jmsConnectionfactory"
channel="helloChannel" extract-payload="true" />
<integration:channel id="helloChannel" />
My requirement is to consume from here and post it to Kafka outbound adapter. Using the below config:
<int-kafka:outbound-channel-adapter
id="kafkaOutboundChannelAdapter"
kafka-producer-context-ref="kafkaProducerContext"
channel="inputToKafka">
</int-kafka:outbound-channel-adapter>
Here are what i want to achieve:
My queue is a durable topic and dont want to acknowledge the records unless it is successfully published to Kafka. In short, i want to have a transaction behaviour from consuming message from jms to publishing it to Kafka.
I noticed that my messages are immediately dequeued and if processing encounters some exception, i am unable to reprocess it. I dont want that to happen.
Also, when kafka encounters some issue, i want it to be returned to some method so that i can persist the failure message and as said before does not want to acknowledge it.
I am really struggling to get it to work. Can someone please help me out?
You really can have transaction-manager on the <jms:message-driven-channel-adapter> to start TX.
When <int-kafka:outbound-channel-adapter> throws an exception it causes the TX to be ralled back and therefore the message will be requeued.
If you are interested in the persisting errors, there is an error-channel option on the <jms:message-driven-channel-adapter>, but you still have to re-throw exception to let TX to rallback.
To make all that to work you should be sure that there is only single thread from the begging to the end. No <queue> or executor channel in the flow.
Also it isn't clear why do you use so old Apache Kafka still...

Why does my camel route try to reply to the JMS consumer?

I have an Apache Camel route configured in Spring which takes a message from a JMS (ActiveMQ) queue, transforms the message and uses the CXF component to send the results to a web service. This all works fine but I always get an exception thrown at the end of the route that the CXF response object isn't synchronizable, referring to the fact that it's trying to convert the exchange/message body back into a JMS message. But why?
Here's my camel context extract:-
<route>
<from uri="jms:queue:transactions" />
<process ref="convertToFormatForCXF" />
<to uri="cxf:bean:myService?defaultOperationName=process" />
<stop />
</route>
and here's a snippet from the logs:-
EndpointMessageListener WARN Execution of JMS message listener failed. Caused by: [org.apache.camel.RuntimeCamelException - java.lang.RuntimeException: net.sophis.soa.dataexchange.LogoutResponse]
org.apache.camel.RuntimeCamelException: java.lang.RuntimeException: net.sophis.soa.dataexchange.LogoutResponse
at org.apache.camel.util.ObjectHelper.wrapRuntimeCamelException(ObjectHelper.java:1363)
at org.apache.camel.component.jms.EndpointMessageListener.onMessage(EndpointMessageListener.java:124)
Even the doesn't prevent the stack trace. Now I've found out that if I add the disableReplyTo=true to the JMS consumer then the stacktrace doesn't show which is excellent.
I suppose I'm just trying to work out what was happening? Was the CXF response object going to be added to the 'transactions' JMS queue? My intention was for the flow to stop once the CXF producer had completed.
Can anyone help my understanding please? The Camel documentation wasn't much help on this.
Was the CXF response object going to be added to the 'transactions' JMS queue?
No. It would have been added to a temporary queue.
From http://camel.apache.org/jms.html#JMS-Request-replyoverJMS
The JmsProducer detects the InOut and provides a JMSReplyTo header with the reply destination to be used. By default Camel uses a temporary queue, but you can use the replyTo option on the endpoint to specify a fixed reply queue (see more below about fixed reply queue).
Camel will automatic setup a consumer which listen on the reply queue, so you should not do anything.

How to restart the message consumer in Spring Integration?

My consumer, e.g. service activator that is consuming messages coming from ActiveMQ fromChannel should be restarted when exception occurs or ActiveMQ fails. How to do it for the following spring integration context ?
<!-- RECEIVER. message driven adapter -> jmsInChannel -> activator. -->
<si:channel id="fromChannel"/>
<int-jms:message-driven-channel-adapter id="messageDrivenAdapter"
channel="fromChannel" destination="forward" connection-factory="connectionFactory"
max-concurrent-consumers="2" auto-startup="true" acknowledge="auto" extract-payload="false" />
<si:service-activator id ="activator"
input-channel="fromChannel"
ref="messageService"
method="process"/>
<bean id="messageService" class="com.ucware.ucpo.forward.jms.MessageService"/>
My first idea was to use Retry Advice and add to a service but am not sure if this a right solution for unhandled exceptions. I also would like the receiver to restart if the ActiveMQ server is down.
The listener container within the message-driven-channel-adapter will automatically keep trying to reconnect when it loses connectivity to the broker.
If you set `acknowledge="transacted"' the message will be rolled back on an exception and the broker will resubmit it.
A stateful retry advice would allow you to give up and take some other action after some number of retries (but you can also configure that into ActiveMQ itself where it will send the message to a DLQ after some number of delivery attempts).
Reading your post I instantly thought of this video. Which gives a good insight on how to monitor and control SI application through itself.
Additionally you should have a look at ApplicationEvent documentation of SI.
Glueing that all together you could monitor the JMS message adapter with JMX and stop and restart it through sending an ApplicationEvent on issues. Regarding catching exceptions it depends on what Exceptions you actually want to handle. I'd create an errorChannel that receives exceptions being thrown by components and create a new service that restarts these components after receiving errors.
Following your idea leveraging Spring Retry's capabilites in SI.

Resources