Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to make a JMS Synchronous request

I have an webapp that is expected to fetch and display data from an External App which is accessible only via messaging (JMS).

So, if a user submits a request on a browser, the same HTTP request thread will have to interact with the Messaging system (MQ Series) such that the same request thread can display the data received from the Messaging System.

Is there a pattern I can make use of here? I saw some vague references on the net that use "Correlation ID" in this way:

Msg m = new TextMsg("findDataXYZ");
String cr_id = m.setCorrelationID(id);

sendQueue.send(m).

// now start listening to the Queue for a msg that bears that specific cr_id

Response r = receiverQueue.receive(cr_id);

Is there something better out there? The other patterns I found expect the response to be received asynchronously.. which is not an option for me, since I have to send the response back on the same HTTP request.

like image 885
rk2010 Avatar asked May 28 '12 01:05

rk2010


People also ask

Is JMS synchronous or asynchronous?

0.1, an API for accessing enterprise messaging systems from Java. Because JMS is equipped to handle both synchronous and asynchronous messaging, it represents a possible alternative to strictly synchronous RMI.

What is asynchronous messaging in JMS?

Asynchronous: A JMS provider can deliver messages to a client as they arrive; a client does not have to request messages in order to receive them. Reliable: The JMS API can ensure that a message is delivered once and only once.

What is correlation ID in JMS?

A correlation ID is used to correlate response messages with request messages when an application invokes a request-response operation. With WebSphere® MQ and WebSphere MQ JMS, you can correlate using either a correlation ID or a message ID.


2 Answers

The request/reply messaging pattern is useful for your requirement. You typically use a CorrelationId to relate request & reply messages.

While sending request message you set JMSReplyTo destination on the message. Typically a temporary queue is used as JMSReplyTo destination. When creating a consumer to receive response use a selector with JMSCorrelationId, something like

cons = session.createConsumer(tempDestination,"JMSCorrelationId="+requestMsg.JMSMessageId);

At the other end, the application that is processing the request message must use the JMSReplyTo destination to send response. It must also use the MessageId of the request message and set it as CorrelationId of the response message.

like image 131
Shashi Avatar answered Oct 06 '22 16:10

Shashi


First, open the response queue. Then pass that object to the set reply-to method on the message. That way the service responding to your request knows where to send the reply. Typically the service will copy the message ID to the correlation ID field so when you send the message, take the message ID you get back and use that to listen on the reply queue. Of course if you use a dynamic reply-to queue even that isn't neessary - just listen for the next message on the queue.

There's sample code that shows all of this. If you installed to the default location, the sample code lives at "C:\Program Files (x86)\IBM\WebSphere MQ\tools\jms\samples\simple\SimpleRequestor.java" on a Windows box or /var/mqm/toolsjms/samples/simple/SimpleRequestor.java on a *nix box.

And on the off chance you are wondering "install what, exactly?" the WMQ client install is downloadable for free as SupportPac MQC71.

like image 22
T.Rob Avatar answered Oct 06 '22 15:10

T.Rob