Spring JMS Topic Listener Example
August 30, 2020
This page will walk through Spring JMS topic listener example. To listen topic, we need to enable publish/subscribe functionality. By default JMS messaging is performed for point-to-point to listen queue.
Here in our example we will create listener using
@JmsListener
and publish message using JmsTemplate
.
Contents
Technologies Used
Find the technologies being used in our example.1. Java 11
2. Spring 5.2.8.RELEASE
3. Spring Boot 2.3.2.RELEASE
4. Maven 3.5.2
Enable Publish/Subscribe
By default publish and subscribe for a topic is set to false and only queue can be sent and received. We can enable publish/subscribe in following ways.1. Using
application.properties
in Spring Boot application.
spring.jms.pub-sub-domain=true
2. Using Java configuration file.
@Bean public DefaultJmsListenerContainerFactory jmsContainerFactory() { DefaultJmsListenerContainerFactory containerFactory = new DefaultJmsListenerContainerFactory(); containerFactory.setPubSubDomain(true); ------ return containerFactory; }
setPubSubDomain()
is false. We need to pass true value to enable publish/subscribe for a topic.
Creating Listener with @JmsListener
The@JmsListener
annotation marks a method to be a JMS message listener for the specified destination. To enable @JmsListener
, we need to annotate our Java configuration class with @EnableJms
annotation. Find the sample lsiteners.
@JmsListener(destination = "spring", containerFactory = "jmsContainerFactory") public void receiveMessage1(News news) { ------ } @JmsListener(destination = "spring", containerFactory = "jmsContainerFactory") public void receiveMessage2(News news) { ------ }
Publishing Topic using JmsTemplate
TheJmsTemplate
is the helper class to send, receive and convert JMS messages. In our code snippet, we are publishing a topic
that will be received by listeners with specified destination as spring.
Topic springTopic = jmsTemplate.getConnectionFactory().createConnection() .createSession().createTopic("spring"); jmsTemplate.convertAndSend(springTopic, news);
Complete Example
pom.xml<parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>2.3.2.RELEASE</version> <relativePath /> </parent> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-activemq</artifactId> </dependency> <dependency> <groupId>org.apache.activemq</groupId> <artifactId>activemq-broker</artifactId> </dependency> <dependency> <groupId>com.fasterxml.jackson.core</groupId> <artifactId>jackson-databind</artifactId> </dependency> </dependencies>
package com.concretepage.config; import org.apache.activemq.ActiveMQConnectionFactory; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.jms.annotation.EnableJms; import org.springframework.jms.config.DefaultJmsListenerContainerFactory; import org.springframework.jms.connection.CachingConnectionFactory; import org.springframework.jms.support.converter.MappingJackson2MessageConverter; import org.springframework.jms.support.converter.MessageConverter; import org.springframework.jms.support.converter.MessageType; @Configuration @EnableJms public class JMSConfig { @Bean public DefaultJmsListenerContainerFactory jmsContainerFactory() { DefaultJmsListenerContainerFactory containerFactory = new DefaultJmsListenerContainerFactory(); containerFactory.setPubSubDomain(true); containerFactory.setConnectionFactory(connectionFactory()); containerFactory.setMessageConverter(jacksonJmsMessageConverter()); return containerFactory; } @Bean public CachingConnectionFactory connectionFactory() { CachingConnectionFactory cachConnectionFactory = new CachingConnectionFactory(); ActiveMQConnectionFactory connectionFactory = new ActiveMQConnectionFactory(); connectionFactory.setBrokerURL("tcp://localhost:61616"); cachConnectionFactory.setTargetConnectionFactory(connectionFactory); return cachConnectionFactory; } @Bean public MessageConverter jacksonJmsMessageConverter() { MappingJackson2MessageConverter converter = new MappingJackson2MessageConverter(); converter.setTargetType(MessageType.TEXT); converter.setTypeIdPropertyName("_type"); return converter; } }
package com.concretepage.receiver; import org.springframework.jms.annotation.JmsListener; import org.springframework.stereotype.Component; import com.concretepage.News; @Component public class NewsReceiver1 { @JmsListener(destination = "spring", containerFactory = "jmsContainerFactory") public void receiveNews(News news) { System.out.println("Receiver1: " + news); } }
package com.concretepage.receiver; import org.springframework.jms.annotation.JmsListener; import org.springframework.stereotype.Component; import com.concretepage.News; @Component public class NewsReceiver2 { @JmsListener(destination = "spring", containerFactory = "jmsContainerFactory") public void receiveMessage(News news) { System.out.println("Receiver2: " + news); } }
package com.concretepage; public class News { private int id; private String title; public News() {} public News(int id, String title) { this.id = id; this.title = title; } //Sets and Gets @Override public String toString() { return id + ", " + title; } }
package com.concretepage; import javax.jms.JMSException; import javax.jms.Topic; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.context.ConfigurableApplicationContext; import org.springframework.jms.JmsException; import org.springframework.jms.core.JmsTemplate; @SpringBootApplication public class Application { public static void main(String[] args) throws JmsException, JMSException { ConfigurableApplicationContext context = SpringApplication.run(Application.class, args); JmsTemplate jmsTemplate = context.getBean(JmsTemplate.class); Topic springTopic = jmsTemplate.getConnectionFactory().createConnection() .createSession().createTopic("spring"); News news = new News(100, "Latest news on Spring"); jmsTemplate.convertAndSend(springTopic, news); } }

References
JMS (Java Message Service)Spring @JmsListener