关闭

spring的jms:用spring的JmsTemplate发送和接收消息

标签: springjmsbeanclassobjectstring
7294人阅读 评论(0) 收藏 举报

         Spring是一个完整的J2EE框架和解决方案,完整并且模块化,你可以用的他的全部也可以只用他的一部分特性,Spring 包含 IoC, AOP, 事务处理,ORM, 也包括一个简单的MVC框架.
         用Spring,自我感觉,可以使你的代码至少节约30%,它的很多template很不错的,比如简单封装后的jdbctemplate,jmstemplate等。
         ioc用后就会爱不释手,它让你的代码风格完全改观。以前我要产生个对象,绝大多数时候只回想到new一个对象,而用spring的ioc,beanfactory,只需要配置一个xml文件即可。这种方式实现了松偶合,对单元测试非常有利。
        还有它的aop,也是很不错的,
       用spring的感觉,正如它的名字一样:如沐春风.
       关于spring中的jms,最近一个项目用到,刚好研究了一下,在这里做一个整理备份.在此感谢同事Eric的帮助.
        spring把jms进行了简单的封装,用它的JmsTemplate可以很方便的发送和接收消息,并且资源的管理都由template来管理了.
1:在web.xml文件中配置一个spring用的上下文:

 <context-param>
  
<param-name>contextConfigLocation</param-name>
  
<param-value>
   /WEB-INF/jmsconfig.xml
  
</param-value>
 
</context-param>

jmsconfig.xml用来装配jms,内容如下:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING/DTD BEAN/EN" "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
  
<bean id="jmsConnectionFactory"
    class
="org.springframework.jndi.JndiObjectFactoryBean">
    
<property name="jndiName">
      
<value>jms/Ntelagent/RequestQCF</value>
    
</property>
  
</bean>
  
<bean id="destination"
    class
="org.springframework.jndi.JndiObjectFactoryBean">
    
<property name="jndiName">
      
<value>jms/Ntelagent/RequestQ</value>
    
</property>
  
</bean>  
  
   
<bean id="jmsConnectionFactoryForReceive"
    class
="org.springframework.jndi.JndiObjectFactoryBean">
    
<property name="jndiName">
      
<value>jms/Ntelagent/ResponseQCF</value>
    
</property>
  
</bean> 
  
<bean id="destinationForReceive"
    class
="org.springframework.jndi.JndiObjectFactoryBean">
    
<property name="jndiName">
      
<value>jms/Ntelagent/ResponseQ</value>
    
</property>
  
</bean>


  
<bean id="jmsTemplate" class="org.springframework.jms.core.JmsTemplate102">
    
<property name="connectionFactory">
      
<ref bean="jmsConnectionFactory"/>
    
</property>
    
<property name="defaultDestination">
      
<ref bean="destination"/>
    
</property>
    
<property name="messageConverter">
      
<ref bean="jmsTrxConverter"/>
    
</property>
    
<property name="receiveTimeout">
     
<value>1</value>
    
</property>
  
</bean>
  
    
<bean id="jmsTemplateForReceive" class="org.springframework.jms.core.JmsTemplate102">
    
<property name="connectionFactory">
      
<ref bean="jmsConnectionFactoryForReceive"/>
    
</property>
    
<property name="defaultDestination">
      
<ref bean="destinationForReceive"/>
    
</property>
    
<property name="messageConverter">
      
<ref bean="jmsTrxConverter"/>
    
</property>
    
<property name="receiveTimeout">
     
<value>1</value>
    
</property>
  
</bean>
  
  
<bean id="jmsTrxConverter" class="co.transport.jms.JmsTransactionConverter">
     
<property name="rspQueue">
      
<ref bean="destinationForReceive"/>
    
</property>  
  
</bean>
  
  
<bean id="jmsRequestTransport" class="co.transport.jms.JmsRequestTransport">
    
<property name="jmsTemplate">
      
<ref bean="jmsTemplate"/>
    
</property>
    
<property name="jmsTemplateForReceive">
      
<ref bean="jmsTemplateForReceive"/>
    
</property>    
  
</bean>

</beans>

其中:
      jmsConnectionFactory为jms连接工厂,属性jndiName的value为server服务配置的jndi名称.
      destination为消息队列,属性jndiName为消息队列的jndi名称.
       jmsTemplate为配置spring消息模版:采用JmsTemplate102(如果你的JMS实现符合JMS规范1.1版,则应该使用JmsTemplate),其中的messageConverter属性配置了一个消息转换器,因为通常消息在发送前和接收后都需要进行一个前置和后置处理,转换器便进行这个工作。
      由于我的sendQueue很receiveRueue是不同的queue,所以我配置了两个jmsTemplate:    

      jmsTemplateForReceive负责接收消息,jmsTemplate负责发发送消息.


发送消息的代码很简单:
jmsTemplate.convertAndSend(request);
接收消息也很简单:
Object obj = jmsTemplate.receiveAndConvert(); 
如果需要用一个过滤器接收特定的消息,则:
Object obj = this.jmsTemplateForReceive.receiveSelectedAndConvert(this.messageSelector);

发送和接收消息的class如下:



public class JmsRequestTransport implements RequestTransport {
 
private JmsTemplate jmsTemplate;
 
 
private JmsTemplate jmsTemplateForReceive;
 
 
private String messageSelector;
 
 
private String destinationName; 
 
 
public void setJmsTemplate(JmsTemplate template){
  
this.jmsTemplate = template;
 }


 
public void request(Object request) {
  jmsTemplate.convertAndSend(request);
 }

 
 
public Object receive() 
  System.out.println(
"in JmsRequestTransport: destinationName = " + this.jmsTemplateForReceive.getDefaultDestinationName());
  System.out.println(
"in JmsRequestTransport: messageSelector = " + messageSelector);
  Object obj 
= this.jmsTemplateForReceive.receiveSelectedAndConvert(this.messageSelector);  
  
return obj;  
 }


 
public String getMessageSelector() {
  
return messageSelector;
 }


 
public void setMessageSelector(String string) {
  messageSelector 
= string;
 }


 
public String getDestinationName() {
  
return destinationName;
 }


 
public void setDestinationName(String string) {
  destinationName 
= string;
 }


 
public JmsTemplate getJmsTemplateForReceive() {
  
return jmsTemplateForReceive;
 }


 
public void setJmsTemplateForReceive(JmsTemplate template) {
  jmsTemplateForReceive 
= template;
 }


}


要实现一个消息转换器,只需要实现MessageConverter接口,MessageConverter很简单,它只有两个方法需要实现:
public Object fromMessage(Message msg){}
public Message toMessage(Object obj, Session session) throws JMSException{}
fromMessage为接收消息后,对消息进行的转换(通常是把一个message转化为一个Object对象)
toMessage为发送消息前需要的转化(通常为把一个Object转化为一个message对象)
我的JmsTransactionConverter转换器如下:

public class JmsTransactionConverter implements MessageConverter {
 
 
private Queue rspQueue; 

 
public JmsTransactionConverter(){}
  
 
public Object fromMessage(Message msg){
  MessageBean msgBean 
= new MessageBean();
  TextMessage massage 
= (TextMessage)msg;

  
try {
   String str 
= massage.getText();   
   msgBean.setHead(
"HeadTest");
   msgBean.setOutput(str);
   msgBean.setStatus(
"success");
   
  }
 catch (JMSException e) {
   
// TODO Auto-generated catch block
   msgBean = null;
   e.printStackTrace();
  }

  
finally {
   
return msgBean;
  }

   
 }

 
 
public Message toMessage(Object obj, Session session) throws JMSException{

  String s 
= (String)obj;

  TextMessage message 
= session.createTextMessage(s);  
  message.setStringProperty(
"mytype","java");  
  
return message;
 }


 
public Queue getRspQueue() {
  
return rspQueue;
 }


 
public void setRspQueue(Queue queue) {
  rspQueue 
= queue;
 }


}


其中:MessageBean是一个简单javabean:

public class MessageBean {
 
 
private String head;
 
 
private String output;
 
 
private String status;

 
public String getHead() {
  
return head;
 }


 
public String getOutput() {
  
return output;
 }


 
public String getStatus() {
  
return status;
 }



 
public void setHead(String string) {
  head 
= string;
 }


 
public void setOutput(String string) {
  output 
= string;
 }


 
public void setStatus(String string) {
  status 
= string;
 }


}



然后就可以用两个servlet来测试发送和接收消息:
发送消息:

public class JMSTestServlet extends HttpServlet {

 
/**
 * 
@see javax.servlet.http.HttpServlet#void (javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse)
 
*/

 
 
public void doPost(HttpServletRequest req, HttpServletResponse resp)
  
throws ServletException, IOException
 
{
  doGet(req, resp);
 }

 
 
public void doGet(HttpServletRequest req, HttpServletResponse resp)
  
throws ServletException, IOException{
  ServletOutputStream out 
= resp.getOutputStream();
  
try {
   ServletContext servletContext 
= this.getServletContext();
   WebApplicationContext wac 
= WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext);
   JmsRequestTransport transport 
= (JmsRequestTransport)wac.getBean("jmsRequestTransport");
   System.out.println(
"in JMSTestServlet.doGet:begin send message");
   String messageToSend 
= req.getParameter("message");
   
if(messageToSend == null)
   
{
    messageToSend 
= "Default Message";
   }

   transport.request(messageToSend);
   String s 
= "in JMSTestServlet.doGet:after send message and message is: " + messageToSend;
   
   out.println(
"<HTML><BODY>");
   out.println(s);
   out.println(
"<br><input type=button name=back value=back  onclick=history.back()>");
   out.println(
"<br><a href=receiveServlet>receive</a>");
   out.println(
"</HTML></BODY>");
 
  }
 catch(Exception e) {
   out.println(
"<HTML><BODY>");
   out.println(e.toString());
   out.println(
"</HTML></BODY>");  
  }

 }

 

接收消息:

public class receiveServlet extends HttpServlet {

 
/**
 * 
@see javax.servlet.http.HttpServlet#void (javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse)
 
*/

 
public void doPost(HttpServletRequest req, HttpServletResponse resp)
  
throws ServletException, IOException
 
{
  doGet(req, resp);
 }
 

 
public void doGet(HttpServletRequest req, HttpServletResponse resp)
  
throws ServletException, IOException {
  ServletOutputStream out 
= resp.getOutputStream();
  String selector 
= req.getParameter("selector");
  String distination 
= req.getParameter("distination");
  
try {   
   String s 
= "nothing";
   ServletContext servletContext 
= this.getServletContext();
   WebApplicationContext wac 
= WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext);
   JmsRequestTransport transport 
= (JmsRequestTransport)wac.getBean("jmsRequestTransport");

   System.out.println(
"selector = " + selector);
   System.out.println(
"distination = " + distination);
   
   transport.setDestinationName(distination);
   transport.setMessageSelector(selector);
   
   Object obj 
= transport.receive();
   
if(obj != null{
    MessageBean msgBean 
= (MessageBean)obj;
    
//System.out.println("in receiveServlet:");
    s = "receive the message is: " + msgBean.getHead() + "," +
     msgBean.getOutput() 
+ "" +
     msgBean.getStatus();    
   }
 else {
    s 
= "there is no message where " + selector;
   }

  
   out.println(
"<HTML><BODY>");
   out.println(s);
   out.println(
"<br>selector is :" + selector);
   out.println(
"<br>distination is :" + distination);
   out.println(
"<br><a href=jsp/sendMessage.jsp>sendMessage</a>");
   out.println(
"</HTML></BODY>");
   
  }
 catch(Exception e) {
   out.println(
"<HTML><BODY>");
   out.println(
"<br>selector is :" + selector);
   out.println(
"<br>distination is :" + distination);
   out.println(
"<br>" + e.toString());
   out.println(
"</HTML></BODY>");  
   
  }


 }


}


0
0

查看评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
    个人资料
    • 访问:201140次
    • 积分:2892
    • 等级:
    • 排名:第13019名
    • 原创:64篇
    • 转载:3篇
    • 译文:3篇
    • 评论:173条
    最新评论
    java示例代码
    水晶报表