【问题标题】:Unable to send JMS message to activemq Queue using Spring's JmsTemplate无法使用 Spring 的 JmsTemplate 将 JMS 消息发送到 activemq 队列
【发布时间】:2015-02-19 19:23:41
【问题描述】:

我是一名开发人员,在拥有大约 5 年的 .NET 经验后重返 Java。虽然我对 MVC 框架有所了解,但我对 Spring MVC 和 Spring 框架完全陌生。

我有一个任务,我打算将实体保存在 activemq JMS 队列中。在发送更复杂的对象之前,我决定先用一个简单的 TextMessage 进行尝试。每次我尝试从映射到视图上的输入按钮控件的控制器发送时,我都会在 Tomcat 中得到一个 java.lang.NullPointerException。除此之外,它没有向我显示太多信息。它只告诉我它的来源来自 ApiMessageSender 类中的这行代码。

jmsTemplate.send(new MessageCreator(){  

        @Override  
        public Message createMessage(Session session) throws JMSException {  
            return session.createTextMessage(message);  
        }  
    });  

spring web mvc web 应用程序中的实现由三个类组成。 1) ApiMessageSender.java

import javax.jms.*;  
import org.springframework.beans.factory.annotation.Autowired;  
import org.springframework.jms.core.JmsTemplate;  
import org.springframework.jms.core.MessageCreator;  
import org.springframework.stereotype.Component;  

@Component("messageSender")  
public class ApiMessageSender {  
@Autowired  
private JmsTemplate jmsTemplate;  
public void sendMessage(final String message){  
    jmsTemplate.send(new MessageCreator(){  

        @Override  
        public Message createMessage(Session session) throws JMSException {  
            return session.createTextMessage(message);  
        }  
    });  
}  
}  

2) 完成 Spring IoC 管道的 WebAppConfig.java。这个类代替了 ApplicationContext.xml 文件,在这个项目中根本没有使用。队列名称是在执行应用程序之前从 ActiveMQ 管理 Web 界面手动创建的。

@Bean
    public org.apache.activemq.ActiveMQConnectionFactory connectionFactory() {
        org.apache.activemq.ActiveMQConnectionFactory connectionFactory = new org.apache.activemq.ActiveMQConnectionFactory();
        connectionFactory.setBrokerURL("tcp://localhost:61616");
        return connectionFactory;
    }

    @Bean
    public org.springframework.jms.core.JmsTemplate jmsTemplate() {
        org.springframework.jms.core.JmsTemplate jmsTemplate = new org.springframework.jms.core.JmsTemplate(connectionFactory());
        jmsTemplate.setDefaultDestinationName("apiqueue");
        return jmsTemplate;
    }

3) ApiController.java

控制器中的此操作方法,当在视图上单击按钮时被调用。我已将特定代码 sn-p 注释掉,以便我可以继续处理其他要求。

@RequestMapping(value="/create", method=RequestMethod.POST)
    public ModelAndView createNewApi(@ModelAttribute @Valid Api api,
            BindingResult result,
            final RedirectAttributes redirectAttributes) {

        if (result.hasErrors())
            return new ModelAndView("api-new");

        ModelAndView mav = new ModelAndView();
        String message = "New api "+api.getApiKey()+" was successfully created.";

        apiService.create(api);

        //Send object to Queue.
        /*GenericXmlApplicationContext ctx=new GenericXmlApplicationContext();  
        ctx.load("classpath:applicationContext.xml");  
        ctx.refresh();*/  

       /* ApiMessageSender sender = new ApiMessageSender();  
        sender.sendMessage("hello jms3");*/
        //ctx.close();
        //End of messaging task. The message should be successfully in the JMS Queue.

        mav.setViewName("redirect:/api/list.html");

        redirectAttributes.addFlashAttribute("message", message);   
        return mav;     
    }

这可能是什么问题?为什么我在这里得到 java.lang.NullPointerException?我怎样才能得到这个工作? 非常感谢。

【问题讨论】:

  • 能否请您发布异常堆栈跟踪并标记相应的行。

标签: java spring spring-mvc activemq jmstemplate


【解决方案1】:

如果没有完整的堆栈跟踪,很难完全确定,但根据注释掉的代码,您的问题可能是您使用的是“ApiMessageSender sender = new ApiMessageSender();”实例化您的 ApiMessageSender。通过这样做,您的 jmsTemplate 将永远不会自动装配,因为您没有使用 Spring 来实例化您的 bean。所以我最好的猜测(没有发布堆栈跟踪)是,当您的代码调用 jmsTemplate.send 时,它会得到一个空指针,因为 jmsTemplate 从未设置。

执行此操作的正确方法是使用 SpringDispatcherServlet 设置您的 Spring MVC 上下文并启动您的 bean。然后您可以将您的 ApiMessageSender 自动连接到您的控制器类中,而不是调用“new ApiMessageSender()”

在此处查看文档:http://docs.spring.io/spring/docs/current/spring-framework-reference/html/mvc.html

您不需要直接在控制器方法中引用应用程序上下文。一切都应该通过您的 web.xml 文件使用 Spring 进行设置。

【讨论】:

  • 你好 xraiderx,你的建议奏效了。我将 ApiMessageSender 注释为 @Autowired 并在执行应用程序时,消息出现在队列中。我单击消息以查看是否可以以文本格式看到它,ActiveMQ 给了我一条错误消息“处理此请求时发生异常,请查看日志以获取更多信息!”。消息仍在队列中,但我看不到它的字符串或文本内容。在我们从队列中消费消息之前,是否无法查看此信息?非常感谢。
猜你喜欢
  • 1970-01-01
  • 2021-10-20
  • 1970-01-01
  • 1970-01-01
  • 2016-05-02
  • 2020-04-05
  • 2015-08-25
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多