How do you publish a JMS topic with Spring JMS?

wsb3383 picture wsb3383 · Aug 19, 2010 · Viewed 39.1k times · Source

I have a component that sends messages to a queue to be handled by another system. It should also publish a topic about job statuses every once in a while. Can I just use the same JmsTemplate used to send to a queue AND to publish to a topic?

I created a new topic in ActiveMQ, except that when I send from JmsTemplate a message, a new queue with the topic name gets created with the sent message (instead of sending the data to the actual topic), what am I doing wrong here?

here's my config:

<bean id="connectionFactory" class="org.springframework.jms.connection.CachingConnectionFactory">
    <constructor-arg ref="amqConnectionFactory" />
    <property name="exceptionListener" ref="jmsExceptionListener" />
    <property name="sessionCacheSize" value="100" />
</bean>

<!--  JmsTemplate Definition -->
<bean id="jmsTemplate" class="org.springframework.jms.core.JmsTemplate">
    <constructor-arg ref="connectionFactory" />
</bean>


<bean id="messageFacade" class="org.foo.MessageFacadeJms">
    <property name="jmsTemplate" ref="jmsTemplate" />
</bean>

MessageFacadeJms is the class I use to send a queue message (and it works), can I also just used that to publish a topic?

Can I just use this to do both queue sending and topic publishing?:

jmsTemplate.convertAndSend("TOPIC_NAME" /* or queue name */, message);

Answer

skaffman picture skaffman · Aug 19, 2010

This might seem a bit odd, you need to tell JmsTemplate that it's a topic rather than a queue, by setting its pubSubDomain property to true.

That means you're going to need two JmsTemplate beans, one for the queue, and one for the topic:

<bean id="jmsQueueTemplate" class="org.springframework.jms.core.JmsTemplate">
   <constructor-arg ref="connectionFactory" />
   <property name="pubSubDomain" value="false"/>
</bean>

<bean id="jmsTopicTemplate" class="org.springframework.jms.core.JmsTemplate">
   <constructor-arg ref="connectionFactory" />
   <property name="pubSubDomain" value="true"/>
</bean>