0
<rabbit:listener-container connection-factory="connectionFactory" concurrency="5" error-handler="genericErrorHandler" prefetch="10">
    <rabbit:listener ref="SmsListener" method="listen" queue-names="smsQueue" />
    <rabbit:listener ref="TestListener" method="listen" queue-names="testQueue" />
    <rabbit:listener ref="VaultListener" method="listen" queue-names="vaultQueue" />
    <rabbit:listener ref="AggregatedDataListener" method="listen" queue-names="AggregatedHourlyQueue" />
</rabbit:listener-container>

With this configuration above I would like to know whether the attributes(e.g. concurrency) of the container are shared among all the listeners or do every listener have a container of their own and the <rabbit:listener-container /> is just a namespace (as pointed out in this answer)?

In addition since there is one channel per thread, does this imply that when the channels are busy consuming messages from one queue, meanwhile the other queue sharing the container piles up the messages and waits on the channel ?

Also I would like to know the better approach of defining listener:

  1. Every listener should be enclosed in their own container.

    or

  2. Listeners can be enclosed in the same container as shown in the above code snippet.

Community
  • 1
  • 1
Simrandeep Singh
  • 547
  • 4
  • 12

1 Answers1

0

As the question you cited explains, each <listener/> element gets its own container, the <listener-container/> outer element is simply a convenience to save having to specify its attributes on each listener. They are not "shared" in the sense that the threads are shared across the containers.

In this case, each container gets 5 threads; there is no relationship between the individual containers at runtime.

  1. Putting each listener in a separate container element has no difference at runtime to what you have now.
  2. There is no way to have multiple "listeners" in on container, although you can specify multiple queues for each listener, in which case the threads are indeed shared across those queues.
Gary Russell
  • 166,535
  • 14
  • 146
  • 179
  • We have been recently observing a situation where our consumers completely stop consuming messages and resume consuming only on server(backend server - tomcat) restart. This has been happening intermittently. This is our configuration: `` Is it something to do with the configuration or just the case of thread pool exhaustion or anything else ? – Simrandeep Singh Oct 08 '15 at 06:38
  • `consumers completely stop consuming messages `. Each time someone has reported such a situation, it has been caused by the container threads being "stuck" in user code, or something the message listener is invoking. The best way to diagnose is to take a thread dump (`jstack`) to determine what the threads are doing; debug logging might help you too. It is not thread exhaustion with that configuration because the containers use a `SimpleAsyncTaskExecutor` by default, which has no pool. – Gary Russell Oct 08 '15 at 13:20
  • Hi Gary Just want to confirm whether setting `receiveTimeout` will help me in preventing my containers from getting stuck? – Simrandeep Singh Nov 17 '15 at 11:11
  • No; it's a problem in your user code; the container can't do anything if your code holds up the thread. The receive timeout is how often the container thread will timeout looking for messages in its internal queue. It's only applied when the listener returns the thread to the container. You need to figure out what's wrong with your code and fix it. – Gary Russell Nov 17 '15 at 13:25
  • Thanks Gary The issue was indeed at our end with the listener threads getting stuck waiting for response to a server call. The interesting part was that the performance eventually slowed down over time making it hard for us to debug the exact issue. But looking at the thread dump and analysing the data helped us find the root cause of the issue. Now we have introduced time out at our end to prevent consumers from getting stuck. – Simrandeep Singh Nov 26 '15 at 08:46