1

We have a requirement where we will have messages coming in 3 different queues.

I need to write code such that messages from Queue A are given higher priority over Queue B followed by Queue C.

However I cannot keep any of the Queue waiting for too long so there should be some dedicated receivers for each thread.

Can you please suggest any existing framework that can do this for me?

A possible solution is a higher number of dedicated receivers for queue A that also look at B and C if there are no messages in A.

A slightly lesser number of dedicated receivers for Queue B that also look at A and C if there are no messages in B.

A very few dedicated receivers for Queue C that also look at A and B if there are no messages in C.

Is it possible to implement this solution at JMS consumer\receiver level or Do I need to write custom code for it?

NoNaMe
  • 6,020
  • 30
  • 82
  • 110
K Smith
  • 11
  • 1

3 Answers3

0

JMS has no means to control priority of message handling. I propose to convert each message in a task (immediately as it arrives) and submit tasks to a prioritized Executor. See Java Executors: how can I set task priority?

Community
  • 1
  • 1
Alexei Kaigorodov
  • 13,189
  • 1
  • 21
  • 38
0

If you control the queues (as in, the writing code can have a queue reference you provide), then you would put a single PriorityBlockingQueue, with a comparator that sort the A, B, C.

If you cannot avoid 3 queues (as in you only get the queue reference to read from), then you unfortunately have to poll each, not take(). However you cannot spin at full speed and must wait, so I would think that you should take(timeout) on the A queue for as long as your minimal response time allows for servicing the B and C queues (which would be large anyway if A always have priority). You only call A.take() if the B and C queues are empty of course (but don't rely on .size() if you don't know the queue implementation; just trust the last poll() outcome you just tried).

Of course you can spin 3 threads to simply take() and put in a single priority queue that you control. But that is a bit overkill.

user2023577
  • 1,752
  • 1
  • 12
  • 23
  • so if I understand correctly, what you are proposing is I keep adding the incoming messages from 3 different queues to a common PriorityBlockingQueue which does the prioritization using a Comparator and processes my messages. I have few concerns 1). Wouldn't this slow down processing because of all the synchronization between take and add operations? 2) Can I not come across OutOFMemory issues if hundreds of messages are being added to PriorityBlockingQueue every second? –  K Smith Feb 08 '16 at 02:12
  • 1) not noticeably. 2) Blocking queue have finite size that you can set. That's the point of blocking queue. When queue is full, q.put() will block by waiting for notfull condition and the q.offer() will fail to enqueue. Here you want to use the offer() method so your jsp can detect immediately that it is full. It's your dev job to plan that size. A hundred integers is nothing, a hundred gigapixel images is another thing... – user2023577 Feb 08 '16 at 13:04
0

Use the JMSPriority property on the JMS message, dump the messages on the same queue and let the provider do the work of prioritizing.

Scott Sosna
  • 1,443
  • 1
  • 8
  • 8
  • Thanks but this approach is too slow for a production environment. Queue Manager needs to evaluate every message with the already existing messages in the Queue to prioritize. Secondly there is a risk that the lower priority messages may never get processed –  K Smith Feb 05 '16 at 02:22