spring(Blazeds)-flex中实现jms的持久化(durable)订阅

这几天用spring-flex做一个能够接收离线消息的Flex应用,在网上找了很多资料,但是都没提到如何实现离线消息,最后在blazeds的开发文档里找到了如何让blazeds message service实现持久化订阅JMS消息。但是还是找不到在spring-flex里如何配置,最后只能两个并用了,下面把过程贴上来给大家看看!

环境: 

JMS服务器: activemq5.2
spring-flex 1.0
blazeds

1、首先是在tomcat中配置JMS服务器信息:
在应用根目录下/META-INF/context.xml(没有可以自己创建)中增加如下内容:

 
 
  1. < Context   antiJARLocking = "true" >  
  2.      < Resource  
  3.          name = "jms/flex/ActiveMqConnectionFactory"  
  4.          auth = "Container"  
  5.          type = "org.apache.activemq.ActiveMQConnectionFactory"  
  6.          description = "JMS Connection Factory"  
  7.          factory = "org.apache.activemq.jndi.JNDIReferenceFactory"  
  8.          brokerURL = "tcp://localhost:61616"  
  9.          brokerName = "LocalActiveMQBroker"  
  10.          useEmbeddedBroker = "false" />  
  11.  
  12.      < Resource   name = "jms/JMSChat"  
  13.          auth = "Container"  
  14.          type = "org.apache.activemq.command.ActiveMQTopic"  
  15.          factory = "org.apache.activemq.jndi.JNDIReferenceFactory"  
  16.          physicalName = "stockQuoteTopic" />  
  17. </ Context >  

2、在web.xml文件中增加如下内容:

 
 
  1. < resource-ref >  
  2.          < description > Connection Factory </ description >  
  3.          < res-ref-name > jms/flex/ActiveMqConnectionFactory </ res-ref-name >  
  4.          < res-type > javax.jms.QueueConnectionFactory </ res-type >  
  5.          < res-auth > Container </ res-auth >  
  6.      </ resource-ref >  
  7.  
  8.      < resource-env-ref >  
  9.          < resource-env-ref-name > jms/JMSChat </ resource-env-ref-name >  
  10.          < resource-env-ref-type > javax.jms.Topic </ resource-env-ref-type >  
  11.      </ resource-env-ref >  

3、接下来是配置Blazeds的message service

 
 
  1. <? xml   version = "1.0"   encoding = "UTF-8" ?>  
  2. < service   id = "message-service"   class = "flex.messaging.services.MessageService" >  
  3.      < adapters >  
  4.          < adapter-definition   id = "actionscript"   class = "flex.messaging.services.messaging.adapters.ActionScriptAdapter"   default = "true"   />  
  5.          < adapter-definition   id = "jms"   class = "flex.messaging.services.messaging.adapters.JMSAdapter" />  
  6.      </ adapters >  
  7.      < destination   id = "JMSChat" >  
  8.          < properties >  
  9. <!--这里的配置是最关键的,只有durable 属性设计为true才能实现持久化订阅-->
  10.              < server >  
  11.                 < durable > true</ durable >  
  12.             </ server >  
  13.              < jms >  
  14.                  < destination-type > Topic </ destination-type >  
  15.                  < message-type > javax.jms.TextMessage </ message-type >  
  16.                  < connection-factory > java:comp/env/jms/flex/ActiveMqConnectionFactory </ connection-factory >  
  17.                  < destination-jndi-name > java:comp/env/jms/JMSChat </ destination-jndi-name >  
  18.                  < delivery-mode > PERSISTENT </ delivery-mode >  
  19.                  < message-priority > DEFAULT_PRIORITY </ message-priority >  
  20.                  < acknowledge-mode > AUTO_ACKNOWLEDGE </ acknowledge-mode >  
  21.                  < initial-context-environment >  
  22.                      < property >  
  23.                          < name > Context.INITIAL_CONTEXT_FACTORY </ name >  
  24.                          < value > org.apache.activemq.jndi.ActiveMQInitialContextFactory </ value >  
  25.                      </ property >  
  26.                      < property >  
  27.                          < name > Context.PROVIDER_URL </ name >  
  28.                          < value > tcp://localhost:61616 </ value >  
  29.                      </ property >  
  30.                  </ initial-context-environment >  
  31.              </ jms >  
  32.          </ properties >  
  33.          < channels >  
  34.              < channel   ref = "my-polling-amf" />  
  35.              < channel   ref = "my-streaming-amf" />  
  36.          </ channels >  
  37.          < adapter   ref = "jms" />  
  38.      </ destination >  
  39.  
  40. </ service >  

 4、前端Flex聊天室代码

 
 
  1. <? xml   version = "1.0"   encoding = "utf-8" ?>  
  2. < mx:Application   creationComplete = "init()"    xmlns:mx = "http://www.adobe.com/2006/mxml"   fontSize = "12" >  
  3.      < mx:Script >  
  4.          <![CDATA[  
  5.             import mx.controls.Alert;  
  6.             import mx.messaging.messages.AsyncMessage;  
  7.             import mx.messaging.messages.IMessage;  
  8.             import flash.external.ExternalInterface;     
  9.               
  10.             //以下代码向浏览器反向插入js方法监听浏览器关闭事件  
  11.             private function init():void{  
  12.                 ExternalInterface.call(FUNCTION_USEREXIT);     
  13.                 ExternalInterface.addCallback("checkExit",checkExit);  
  14.             }  
  15.             //关闭浏览器时退出  
  16.             public function checkExit():String {     
  17.                       logout();  
  18.                       var userExitStr:String = "你已经离开聊天室,下次再见!";     
  19.                       return userExitStr;     
  20.             }  
  21.               
  22.             //监听浏览器关闭事件函数  
  23.             private static var FUNCTION_USEREXIT:String =      
  24.                 "document.insertScript = function () " +     
  25.                 "{ " +     
  26.                     "window.onbeforeunload = function() " +     
  27.                     "{ " +     
  28.                         "var flexObj = JMSChat.checkExit(); " +//JMSChat是swf在html中object的id     
  29.                         "if(flexObj != \"\") " +     
  30.                         "{ " +     
  31.                             "return flexObj; " +     
  32.                         "}else{ " +     
  33.                             "return; " +     
  34.                         "} " +     
  35.                     "} " +     
  36.                 "} ";    
  37.                   
  38.               
  39.             private function login():void{  
  40.                 //订阅主题的时候带上一个唯一ID,jms服务器会记录ID,在下次登录时发送离线消息  
  41.                 if(userName.text==""){  
  42.                     Alert.show("请输入您的用户名");  
  43.                 }else{  
  44.                     consumer.subscribe(userName.text);  
  45.                     userName.enabled=false;  
  46.                 }  
  47.             }  
  48.               
  49.             private function logout():void{  
  50.                 //退订消息的时候,true表示在jms服务器端记录离线消息,flase的时候将不记录离线消息  
  51.                 consumer.unsubscribe(true);  
  52.                 userName.text="";  
  53.                 userName.enabled=true;  
  54.             }  
  55.  
  56.             private function send():void  
  57.             {  
  58.                 var message:IMessage = new AsyncMessage();  
  59.                 if(userName.enabled){  
  60.                     Alert.show("您还未登录!");  
  61.                 }else{  
  62.                     message.body=userName.text+" : "+ msg.text;  
  63.                     producer.send(message);  
  64.                     msg.text = "";  
  65.                 }  
  66.             }  
  67.                               
  68.             private function messageHandler(message:IMessage):void  
  69.             {  
  70.                 chatRoom.text += message.body+ "\n";      
  71.             }  
  72.         ]]>  
  73.      </ mx:Script >     
  74.      < mx:ChannelSet   id = "cs" >  
  75.          < mx:AMFChannel   url = "http://192.168.0.109:8080/FlexJms/messagebroker/amflongpolling" />  
  76.          < mx:AMFChannel   url = "http://192.168.0.109:8080/FlexJms/messagebroker/amfpolling" />  
  77.      </ mx:ChannelSet >  
  78.      < mx:Producer   id = "producer"   destination = "JMSChat"   channelSet = "{cs}" />  
  79.      < mx:Consumer   id = "consumer"    destination = "JMSChat"   channelSet = "{cs}"  
  80.           message = "messageHandler(event.message)" />  
  81.       
  82.      < mx:Panel   title = "聊天室"   width = "100%"   height = "100%" >  
  83.          < mx:TextArea   id = "chatRoom"   width = "100%"   height = "100%" />  
  84.          < mx:ControlBar >  
  85.               < mx:Label   text = "用户名" />  
  86.               < mx:TextInput   id = "userName"   />  
  87.               < mx:TextInput   id = "msg"   width = "100%"   enter = "send()" />  
  88.               < mx:Button   label = "发送"   click = "send()" />    
  89.               < mx:Button   label = "登陆"   click = "login()" />    
  90.               < mx:Button   label = "退出"   click = "logout()" />  
  91.               < mx:Button   label = "清屏"   click = "chatRoom.text=''" />    
  92.          </ mx:ControlBar >  
  93.      </ mx:Panel >  
  94.       
  95. </ mx:Application >  

 以下是截图:

 

这个时候我们“退出test”, 然后用test2发送多条信息!

 

过两分钟后我们再用test登录:

 

这就简单的实现了离线消息的发送。下图是activemq控制台上持久消息订阅用户信息图:
可通过http://localhost:8161/admin 查看.

 

这里记录了JMS信息的持久订阅者及等发送信息等内容。

你可能感兴趣的:(spring,应用服务器,jms,activemq,Flex)