Joel
Joel

Reputation: 16664

How do you use the jms:listener-container tag in Spring JMS?

Spring/JMS newbie here. So thanks for your patience...

I followed this blog post to set up my JMS producer:

http://bsnyderblog.blogspot.com/2010/02/using-spring-jmstemplate-to-send-jms.html

It seems to be working fine... I attach to my ActiveMQ process using jconsole is showing that it's actually doing something. So now I'm trying to add a consumer to the same project. For now, I just want it to listen for it's own jms messages and process them.

So I'm following this blog post:

http://bsnyderblog.blogspot.com/2010/02/using-spring-to-receive-jms-messages.html

Seems pretty straight forward. However, I get this error when I deploy to Tomcat 8:

org.springframework.beans.factory.parsing.BeanDefinitionParsingException: Configuration problem: Cannot locate BeanDefinitionDecorator for element [listener-container]
  Offending resource: ServletContext resource [/WEB-INF/dispatcher-servlet.xml]

So, here's my dispatcher-servlet.xml:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:p="http://www.springframework.org/schema/p"
       xmlns:jms="http://www.springframework.org/schema/jms"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.0.xsd
            http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.0.xsd
            http://www.springframework.org/schema/jms http://www.springframework.org/schema/jms/spring-jms.xsd">

    <!-- set up all the controllers -->
    <context:component-scan base-package="springjmstest.controller"/>

    <!-- A connection to ActiveMQ -->
    <bean id="jmsConnectionFactory" class="org.apache.activemq.ActiveMQConnectionFactory" p:brokerURL="tcp://localhost:61616"/>

    <!-- A cached connection to wrap the ActiveMQ connection -->
    <bean id="cachedConnectionFactory" class="org.springframework.jms.connection.CachingConnectionFactory"
          p:targetConnectionFactory-ref="jmsConnectionFactory"
          p:sessionCacheSize="10"/>

    <!-- A destination in ActiveMQ -->
    <bean id="destination" class="org.apache.activemq.command.ActiveMQQueue">
        <constructor-arg value="jobs"/>
    </bean>

    <!-- A JmsTemplate instance that uses the cached connection and destination -->
    <bean id="producerTemplate" class="org.springframework.jms.core.JmsTemplate"
          p:connectionFactory-ref="cachedConnectionFactory"
          p:defaultDestination-ref="destination"/>

    <!-- Register the listener for JMS messages on the "jobs" queue -->
    <bean id="simpleMessageListener" class="springjmstest.consumer.SimpleMessageListener">
        <jms:listener-container container-type="default" connection-factory="jmsConnectionFactory" acknowledge="auto">
            <jms:listener destination="jobs" ref="simpleMessageListener" method="onMessage"/>
        </jms:listener-container>
    </bean>
</beans>

I've been messing around with the xmlns and xsi:schemaLocation attributes, looking at examples online, but I don't get anything. (In fact, the only reference I'm getting from Google to the same error as me is a comment in the same blog post. He seems to imply he fixed it by messing with those attributes, but he never really says what he did to fix it.)

Here's my listener class:

public class SimpleMessageListener implements MessageListener {
    @Override
    public void onMessage(Message message) {
        TextMessage msg = (TextMessage) message;
        try {
            String text = msg.getText();
            System.out.println("processing message: " + text);
        } catch (JMSException e) {
            throw new RuntimeException(e);
        }
    }
}

IntelliJ seems happy with the way I have it set up (links to the classes properly, etc), but Tomcat 8 isn't (isn't that how it always is? ;) )

So now I'm starting to wonder if I just have a dependency problem. Here's my dependencies tag in my pom.xml:

<dependencies>
    <!-- web dependencies -->
    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>javax.servlet-api</artifactId>
        <version>3.0.1</version>
        <scope>provided</scope>
    </dependency>
    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>jstl</artifactId>
        <version>1.2</version>
        <scope>provided</scope>
    </dependency>

    <!-- Spring -->
    <dependency>
        <groupId>org.springframework.integration</groupId>
        <artifactId>spring-integration-core</artifactId>
        <version>4.0.0.RELEASE</version>
    </dependency>
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-webmvc</artifactId>
        <version>4.0.3.RELEASE</version>
    </dependency>
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-jms</artifactId>
        <version>4.0.3.RELEASE</version>
    </dependency>

    <!-- ActiveMQ -->
    <dependency>
        <groupId>org.apache.activemq</groupId>
        <artifactId>activemq-client</artifactId>
        <version>5.9.1</version>
    </dependency>
</dependencies>

And in case it matters, I'm using Java 8.

Thanks for the help.

Upvotes: 1

Views: 2843

Answers (1)

Alexandre Santos
Alexandre Santos

Reputation: 8338

Try this:

<bean id="jmsProducerTemplate" class="org.springframework.jms.core.JmsTemplate"
      p:connectionFactory-ref="connectionFactory"/>

<jms:listener-container container-type="default" 
                        connection-factory="connectionFactory"
                        acknowledge="auto">

<jms:listener destination="YOURQUEUENAME" ref="theListenerClassYouAreUsing" />

</jms:listener-container>

Upvotes: 2

Related Questions