Wednesday, December 02, 2009
ActiveMQ, Spring, JNDI and Tomcat
This article is about setting up ActiveMQ with spring while specifying connection factory and queue names as a JNDI resource in tomcat's context.xml file.
After searching the internet for hours and pouring through a number of articles and trying out different things, here's what worked for me.
Spring configuration.
<!-- look up the JMS ConnectionFactory in JNDI -->
<bean id="connectionFactory" class="org.springframework.jndi.JndiObjectFactoryBean">
<property name="jndiName">
<value>java:comp/env/jms/ConnectionFactory</value>
</property>
</bean>
<!-- look up the Destination in JNDI -->
<bean id="destination" class="org.springframework.jndi.JndiObjectFactoryBean">
<property name="jndiName">
<value>java:comp/env/jms/queue/FacebokFeedsQ</value>
</property>
</bean>
<bean id="jmsTemplate" class="org.springframework.jms.core.JmsTemplate">
<property name="connectionFactory">
<!-- lets wrap in a pool to avoid creating a connection per send -->
<bean class="org.springframework.jms.connection.SingleConnectionFactory">
<property name="targetConnectionFactory">
<ref bean="connectionFactory">
</ref>
</property>
</bean>
</property></bean>
<bean id="qWriter" class="com.sample.QWriter">
<property name="jmsTemplate" ref="jmsTemplate">
<property name="destination" ref="destination">
</property></property></bean>
Corresponding Java Class to send messages
public class QWriter {
protected final Log log = LogFactory.getLog(getClass());
private JmsTemplate jmsTemplate;
private Destination destination;
public void addToQueue(final Map map){
log.debug("Putting message on queue");
jmsTemplate.send(destination, new MessageCreator() {
@Override
public Message createMessage(Session session) throws JMSException{
MapMessage message = session.createMapMessage();
for (Iterator i = map.keySet().iterator(); i
.hasNext();) {
String key = (String) i.next();
message.setString(key, (String) map.get(key));
}
return message;
}
});
}
public void setJmsTemplate(JmsTemplate jmsTemplate) {
this.jmsTemplate = jmsTemplate;
}
public void setDestination(Destination destination) {
this.destination = destination;
}
}
context.xml in Tomcat
<Resource name="jms/ConnectionFactory"
auth="Container"
type="org.apache.activemq.ActiveMQConnectionFactory"
description="JMS Connection Factory"
factory="org.apache.activemq.jndi.JNDIReferenceFactory"
brokerURL="tcp://queue.ahanet.net:61613?trace=true"
brokerName="InrixMQBroker"
/>
<Resource name="jms/queue/FacebokFeedsQ"
auth="Container"
type="org.apache.activemq.command.ActiveMQQueue"
factory="org.apache.activemq.jndi.JNDIReferenceFactory"
physicalName="facebookfeeds.queue.local"
/>
References
1. http://static.springsource.org/spring/docs/2.5.x/reference/jms.html#jms-mdp
2. http://activemq.apache.org/spring-support.html
3. http://svn.apache.org/repos/asf/activemq/trunk/activemq-core/src/test/resources/spring-jndi.xml
After searching the internet for hours and pouring through a number of articles and trying out different things, here's what worked for me.
Spring configuration.
<!-- look up the JMS ConnectionFactory in JNDI -->
<bean id="connectionFactory" class="org.springframework.jndi.JndiObjectFactoryBean">
<property name="jndiName">
<value>java:comp/env/jms/ConnectionFactory</value>
</property>
</bean>
<!-- look up the Destination in JNDI -->
<bean id="destination" class="org.springframework.jndi.JndiObjectFactoryBean">
<property name="jndiName">
<value>java:comp/env/jms/queue/FacebokFeedsQ</value>
</property>
</bean>
<bean id="jmsTemplate" class="org.springframework.jms.core.JmsTemplate">
<property name="connectionFactory">
<!-- lets wrap in a pool to avoid creating a connection per send -->
<bean class="org.springframework.jms.connection.SingleConnectionFactory">
<property name="targetConnectionFactory">
<ref bean="connectionFactory">
</ref>
</property>
</bean>
</property></bean>
<bean id="qWriter" class="com.sample.QWriter">
<property name="jmsTemplate" ref="jmsTemplate">
<property name="destination" ref="destination">
</property></property></bean>
Corresponding Java Class to send messages
public class QWriter {
protected final Log log = LogFactory.getLog(getClass());
private JmsTemplate jmsTemplate;
private Destination destination;
public void addToQueue(final Map map){
log.debug("Putting message on queue");
jmsTemplate.send(destination, new MessageCreator() {
@Override
public Message createMessage(Session session) throws JMSException{
MapMessage message = session.createMapMessage();
for (Iterator i = map.keySet().iterator(); i
.hasNext();) {
String key = (String) i.next();
message.setString(key, (String) map.get(key));
}
return message;
}
});
}
public void setJmsTemplate(JmsTemplate jmsTemplate) {
this.jmsTemplate = jmsTemplate;
}
public void setDestination(Destination destination) {
this.destination = destination;
}
}
context.xml in Tomcat
<Resource name="jms/ConnectionFactory"
auth="Container"
type="org.apache.activemq.ActiveMQConnectionFactory"
description="JMS Connection Factory"
factory="org.apache.activemq.jndi.JNDIReferenceFactory"
brokerURL="tcp://queue.ahanet.net:61613?trace=true"
brokerName="InrixMQBroker"
/>
<Resource name="jms/queue/FacebokFeedsQ"
auth="Container"
type="org.apache.activemq.command.ActiveMQQueue"
factory="org.apache.activemq.jndi.JNDIReferenceFactory"
physicalName="facebookfeeds.queue.local"
/>
References
1. http://static.springsource.org/spring/docs/2.5.x/reference/jms.html#jms-mdp
2. http://activemq.apache.org/spring-support.html
3. http://svn.apache.org/repos/asf/activemq/trunk/activemq-core/src/test/resources/spring-jndi.xml
Labels: ActiveMQ, JNDI, Spring, Tomcat