JMS MQ Channels keep increasing and exhausted - spring-integration

I have configured queueconnection factory in the WebSphere admin console and using jndi lookup to use it. MQ Queue Connection Factories in WebSphere Application Server has settings. Connection pool Max size to 30 and session pool Max size to 20
These are than used in several jms:message-driven-channel-adapter or jms channels or jms:inbound-channel-adapter as part of various spring integration workflows that I have in my application.
Over a period we see that the connection count on MQ channel keeps increasing upto maximum allowed (about 1800).Once we bounce the server the count comes back to normal below 50.
Is there any setting missing ?
How can I be sure if the JMS session pools are being closed/released ?
Any help is appreciated
<jee:jndi-lookup id="queueConnectionFactory" jndi-name="$env{Queue.ConnectionFactory}" />
<si-jms:message-driven-channel-adapter
id="messageDrivenAdapter" channel="routingChannel"
container="messageListenerContainer" />
<bean id="messageListenerContainer"
class="org.springframework.jms.listener.DefaultMessageListenerContainer">
<property name="connectionFactory" ref="queueConnectionFactory" />
<property name="destination" ref="inQueue" />
<property name="transactionManager" ref="txManager" />
<property name="taskExecutor" ref="MQExecutor" />
</bean>
<si-jms:channel id="regChannel" queue="regQueue" connection-factory="queueConnectionFactory" transaction-manager="txManager" task-executor="regtaskExecutor" />

In my old days when we use Spring Integration on WebSphere we had a bean like this:
<bean id="connectionFactory" class="org.springframework.jms.connection.DelegatingConnectionFactory">
<property name="targetConnectionFactory">
<jee:jndi-lookup jndi-name="someConnectionFactory"/>
</property>
<property name="shouldStopConnections" value="true"/>
</bean>
Let's see if that can help you!

Related

Performance Issue using DefaultMessageListenerContainer with CachingConnectionFactory

In our application we are using SingleConnectionFactory with DefaultMessageListenerContainer consuming from IBM MQ server, performance wise the app is doing pretty good, however on MQ end our application is opening too many new connections randomly. Here is the current config we have.
Try with this instead of caching or single:
<bean id="connectionFactory" class="org.springframework.jms.connection.DelegatingConnectionFactory">
<property name="targetConnectionFactory" ref="primaryRawInputConnectionFactory" />
<property name="shouldStopConnections" value="true"/>
</bean>

Migration Of Spring Batch from 2.2 to 4.x (XML Configuration Of Partition Jobs

I am migrating Spring Batch Partition Jobs with XML configuration to Spring batch 4.x. I am trying to take advantage to an improvement in the MessageChannelPartitionHandler where it looks for completion of remote steps with both a reply channel and a datasource polling.
When I use this configuration:
<int:channel id="partitioned.jms.requests">
<int:dispatcher task-executor="springbatch.partitioned.jms.taskExecutor"/>
</int:channel>
<int:channel id="partitioned.jms.reply" />
<bean id="partitioned.jms.handler" class="org.springframework.batch.integration.partition.MessageChannelPartitionHandler">
<property name="messagingOperations">
<bean class="org.springframework.integration.core.MessagingTemplate">
<property name="defaultChannel" ref="partitioned.jms.requests"/>
</bean>
</property>
<property name="stepName" value="process.partitioned.step"/>
<property name="gridSize" value="${process.step.partitioned.gridSize}"/>
<property name="dataSource" ref="springbatch.repositoryDataSource" />
<property name="pollInterval" value="${springbatch.partition.verification.interval}"/>
</bean>
The step completes but I see an error in the logs.
no output-channel or replyChannel header available
I looked at the class and see I can add a replyChannel property to the MessageChannelPartitionHandler class. If I add the following:
<property name="replyChannel" ref="claim.acp.process.partitioned.jms.reply"/>
I get error back that a pollable channel is needed.
How do I create a pollable channel (assuming from the same JMS queue)?
You need to show the rest of your configuration.
If you are using DB polling for the results, set the output-channel on the jms outbound gateway to "nullChannel" and the replies received over JMS will be discarded.
Or, use an outbound channel adapter (instead of a gateway) (and an inbound-channel-adapter on the slaves). That avoids the replies being returned altogether.
You have to set pollRepositoryForResults to true.
To answer your specific question
<int:channel id="replies>
<int:queue />
<int:channel>

How to avoid runaway threads in apache camel's default task executor?

I am trying to find out how the apache camel handles the default thread pool with concurrent consumers. Checked the stackoverflow, camel documentation and apache camel in action book but not much information on what is the optimal values being used with the ThreadPool (uses Spring's ThreadPoolTaskExecutor with optimal values - cached threadpool-like)
Here is the configuration I used for my application
from("jms:queue:test??concurrentConsumers=1&maxConcurrentConsumers=10&maxMessagesPerTask=-1&defaultTaskExecutorType=ThreadPool &preserveMessageQos=true").inOnly("direct:deliver-normal-route-1");
If there any connectivity issues in MQ, I see the thread ID's like 500K+ numbers. Is the cached threadpool create a runaway threads if there is an exception?
To avoid this scenario, I implemented my custom thread pool like,
from("jms:queue:test??concurrentConsumers=1&maxConcurrentConsumers=10&maxMessagesPerTask=-1&taskExecutor=#myTaskExecutor&preserveMessageQos=true").inOnly("direct:deliver-normal-route-1");
<bean id="myTaskExecutor" class="org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor">
<property name="threadNamePrefix" value="myThread" />
<property name="corePoolSize" value="10" />
<property name="maxPoolSize" value="20" />
<property name="queueCapacity" value="100" />
<property name="keepAliveSeconds" value="60"></property>
<property name="awaitTerminationSeconds" value="5" />
<property name="waitForTasksToCompleteOnShutdown"
value="true" />
</bean>
With this custom threadpool configuration I don't see any runaway threads. I tested with stopping the MQ channel for few minutes, same threads been resumed and reused unlike the Default threadpool of Camel.

Synchronizing JMS Message Queue and JDBC transaction- Is Transaction proxy needed

We need to persist message from a JMS Queue to a database in a transaction ensuring that JMS message is not acknowledged in case any error is thrown during DB persist.
Based on the solution provided here- Transaction handling while using message driven channel adapter & service activator
Below is the approach I arrived at
<int-jms:message-driven-channel-adapter id="jmsIn"
transaction-manager="transactionManager"
connection-factory="sConnectionFactory"
destination-name="emsQueue"
acknowledge="transacted" channel="jmsInChannel"/>
<int:channel id=" jmsInChannel " />
<bean id="dataSource"
class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="org.hsqldb.jdbcDriver" />
<property name="url" value="jdbc:hsqldb:mem:testdb" />
</bean>
<!-- Transaction manager for a datasource -->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource" />
</bean>
<bean id="sconnectionFactory" class="org.springframework.jms.connection.TransactionAwareConnectionFactoryProxy">
<property name="targetConnectionFactory">
<bean class="project.TestConnectionFactory">
</bean>
</property>
<property name="synchedLocalTransactionAllowed" value="true" />
</bean>
Please confirm if the understanding is correct. Also, have the below queries
Is the TransactionAwareConnectionFactoryProxy necessary in this scenario
JMS Queue and JDBC are two separate transactional resources. Is injecting jdbc transaction manager into JMS adapter as shown in this example equivalent to using a ChainedTransactionManager(chaining JMS Transaction Mananger and JDBC transaction manager)
For TransactionAwareConnectionFactoryProxy, please, consult its JavaDocs:
* Proxy for a target CCI {#link javax.resource.cci.ConnectionFactory}, adding
* awareness of Spring-managed transactions. Similar to a transactional JNDI
* ConnectionFactory as provided by a Java EE server.
*
* <p>Data access code that should remain unaware of Spring's data access support
* can work with this proxy to seamlessly participate in Spring-managed transactions.
* Note that the transaction manager, for example the {#link CciLocalTransactionManager},
* still needs to work with underlying ConnectionFactory, <i>not</i> with this proxy.
I'm not sure how is that related to your request about JMS+DB transaction, but I think you should worry about transaction manager which supports both those transactional resources.
For this purpose Spring suggests JtaTransactionManager for XA transactions.
Or you can consider to use ChainedTransactionManager based on the Dave Syer article: http://www.javaworld.com/article/2077963/open-source-tools/distributed-transactions-in-spring--with-and-without-xa.html
UPDATE
If local transaction are fine for you, you really can go ahead with the TransactionAwareConnectionFactoryProxy and its synchedLocalTransactionAllowed to true. And, of course, use that DataSourceTransactionManager directly from the <int-jms:message-driven-channel-adapter>.
Otherwise you have to go with the ChainedTransactionManager. This solution really adds some overhead over the first TransactionAwareConnectionFactoryProxy-based one.

how to export spring task:executor as mbean?

We are using task:executor in our spring integration application. We need to monitor this threadpool via mbean browser. So far we have good control over all spring integration channels , message handlers etc and those are showing in our mbean browser but we like to see task executor threadpool also be visible so we can see how many threads are in pool, how many being used etc
Is it possible to export them as mbean? if so how it can be done?
<bean id="exporter" class="org.springframework.jmx.export.MBeanExporter">
<property name="beans">
<map>
<entry key="exec:name=exec" value-ref="exec" />
</map>
</property>
</bean>
<task:executor id="exec" />

Resources