免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 1183 | 回复: 0
打印 上一主题 下一主题

用Spring JMS使异步消息变得简单(二) [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2007-08-08 16:02 |只看该作者 |倒序浏览
技术
  表3列出了例子应用中用到的一些技术和开源框架

表3,JMS应用中用到的框架
  使用Hermes 的JMS资源设置
  为异步处理消息,首先,我们需要消息队列来发送和接收消息。我们在JBoss中使用xml配置文件创建消息队列并且用JMS控制台来浏览队列详细资料。清单1显示了XML配置文件JMS配置片断。(这个片断可以被添加到%JBOSS_HOME%\server\all\deploy-hasingleton\jms目录下的jbossmq-destinations-service.xml文件中。)
  清单1,JBoss MQ服务器中JMS队列配置
<!--  Credit Request Send Queue  -->
<mbean code="org.jboss.mq.server.jmx.Queue"
  name="jboss.mq.destination:service=Queue,name=CreditRequestSendQueue">
  <depends optional-attribute-name="DestinationManager">
    jboss.mq:service=DestinationManager
  </depends>
</mbean>
<!--  Credit Request Receive Queue  -->
<mbean code="org.jboss.mq.server.jmx.Queue"
  name="jboss.mq.destination:service=Queue,name=CreditRequestReceiveQueue">
  <depends optional-attribute-name="DestinationManager">
    jboss.mq:service=DestinationManager
  </depends>
</mbean>  现在,让我们看看怎么使用一个叫做Hermes的JMS工具浏览消息队列。Hermes是一个Java Swing应用,它能创建、管理和监控JMS提供者中的JMS destination。这样的JMS提供者有JBossMQ, WebSphereMQ, ActiveMQ 和 Arjuna。从website下载Hermes并解压zip文件到一个本地目录(如c:\dev\tools\hermes)。一旦安装,双击hermes.bat (在bin目录)启动程序。
  为在Hermes中配置JBossMQ服务器,参考Hermes站点上的demo。它一步一步形象说明了JBoss MQ的配置。当配置一个新的JNDI初始上下文时,输入下面的配置信息。
  providerURL = jnp://localhost:1099
  initialContextFactory = org.jnp.interfaces.NamingContextFactory
  urlPkgPrefixes = org.jnp.interfaces:org.jboss.naming
  securityCredentials = admin
  securityPrincipal = admin
  当创建一个新destinations时,输入queue/CreditRequestSendQueue 和 queue/CreditRequestReceiveQueue。图2显示了JMS控制台主屏幕,它显示了为样本JMS应用创建的新消息。


图2.Hermes中所有destinations的截屏
  图3是消息发送者发送一些消息到CreditRequestSendQueue后,Hermes JMS控制台显示的消息队列详细资料。你能看到这里队列中有5个消息并且控制台显示了消息的详细信息如message ID、message destination、time stamp、和实际的消息。

图3.Hermes中队列详细资料截屏
使用Spring JMS,异步消息变得简单
  用在样本应用中的这些消息队列名和其它JMS以及JNDI参数如下表4所示。

表4,Spring JMS配置参数
  Spring配置
  已经有了运行样本应用所需的JMS destinations,现在该是进入用XML Spring配置文件(叫做spring-jms.xml)装配JMS组件的细节的时候了。用IOC设计模式中的setter依赖注入原理装入这些组件。让我们仔细看看组件,为每一个JMS组件显示了一个XML配置片断。
  JNDI上下文是获取JMS资源的入口,所以我们首先配置一个JNDI模板。清单2显示了一名为jndiTemplate的Spring bean,它具有取得JNDI初始上下文必须的常用参数。
  清单2,JNDI上下文模板
<bean id="jndiTemplate" class="org.springframework.jndi.JndiTemplate">
    <property name="environment">
        <props>
            <prop key="java.naming.factory.initial">
                org.jnp.interfaces.NamingContextFactory
            </prop>
            <prop key="java.naming.provider.url">
                localhost
            </prop>
            <prop key="java.naming.factory.url.pkgs">
                org.jnp.interfaces:org.jboss.naming
            </prop>
        </props>
    </property>
</bean>  下一步,我们配置队列连接工厂。清单3显示了队列连接工厂。
  清单3,JMS对了连接工厂配置
<bean id="jmsQueueConnectionFactory"
      class="org.springframework.jndi.JndiObjectFactoryBean">
    <property name="jndiTemplate">
        <ref bean="jndiTemplate"/>
    </property>
    <property name="jndiName">
        <value>UIL2ConnectionFactory</value>
    </property>
</bean>  我们定义了两个JMS destinations来发送和接收消息。清单4和清单5显示了这些细节。
  清单4,发送队列配置
<bean id="sendDestination"
    class="org.springframework.jndi.JndiObjectFactoryBean">
    <property name="jndiTemplate">
        <ref bean="jndiTemplate"/>
    </property>
    <property name="jndiName">
        <value>queue/CreditRequestSendQueue</value>
    </property>
</bean>  清单5,接收队列配置
<bean id="receiveDestination"
    class="org.springframework.jndi.JndiObjectFactoryBean">
    <property name="jndiTemplate">
        <ref bean="jndiTemplate"/>
    </property>
    <property name="jndiName">
        <value>queue/CreditReqeustReceiveQueue</value>
    </property>
</bean>  然后,我们配置JmsTemplate组件。我们在样本应用中使用JmsTemplate102。使用defaultDestination属性来指定JMS destination。
  清单6,JMS template配置
<bean id="jmsTemplate"
      class="org.springframework.jms.core.JmsTemplate102">
    <property name="connectionFactory">
        <ref bean="jmsQueueConnectionFactory"/>
    </property>
    <property name="defaultDestination">
        <ref bean="destination"/>
    </property>
    <property name="receiveTimeout">
        <value>30000</value>
    </property>
</bean>  最后,我们配置发送和接收者组件。清单7和清单8显示了Sender 和Receiver 对象配置。
  清单7,JMS Sender配置
Listing 7. JMS Sender configuration
<bean id="jmsSender" class="springexample.client.JMSSender">
    <property name="jmsTemplate">
        <ref bean="jmsTemplate"/>
    </property>
</bean>  清单8,JMS Receiver配置
<bean id="jmsReceiver" class="springexample.client.JMSReceiver">
    <property name="jmsTemplate">
        <ref bean="jmsTemplate"/>
    </property>
</bean>测试和监控
  我些了一个叫做LoanApplicationControllerTest的测试类来测试LoanProc应用。我们使用这个类来设置贷款参数和调用那个信用请求服务类。
  让我们看看使用传统JMS而不用Spring JMS API的消息发送者实现。清单9显示了MessageSenderJMS这个类的sendMessage方法,这个类具备使用JMS API处理消息的所有必须步骤。
  清单9,传统JMS实现
public void sendMessage() {
    queueName = "queue/CreditRequestSendQueue";
    System.out.println("Queue name is " + queueName);
    /*
     * Create JNDI Initial Context
     */
    try {
        Hashtable env = new Hashtable();
        env.put("java.naming.factory.initial",
            "org.jnp.interfaces.NamingContextFactory");
        env.put("java.naming.provider.url","localhost");
        env.put("java.naming.factory.url.pkgs",
            "org.jnp.interfaces:org.jboss.naming");
        jndiContext = new InitialContext(env);
    } catch (NamingException e) {
        System.out.println("Could not create JNDI API " +
            "context: " + e.toString());
    }
    /*
     * Get queue connection factory and queue objects from JNDI context.
     */
    try {
        queueConnectionFactory = (QueueConnectionFactory)
        jndiContext.lookup("UIL2ConnectionFactory");
        queue = (Queue) jndiContext.lookup(queueName);
    } catch (NamingException e) {
        System.out.println("JNDI API lookup failed: " +
            e.toString());
    }
    /*
     * Create connection, session, sender objects.
     * Send the message.
     * Cleanup JMS connection.
     */
    try {
        queueConnection =
            queueConnectionFactory.createQueueConnection();
        queueSession = queueConnection.createQueueSession(false,
                Session.AUTO_ACKNOWLEDGE);
        queueSender = queueSession.createSender(queue);
        message = queueSession.createTextMessage();
        message.setText("This is a sample JMS message.");
        System.out.println("Sending message: " + message.getText());
        queueSender.send(message);
    } catch (JMSException e) {
        System.out.println("Exception occurred: " + e.toString());
    } finally {
        if (queueConnection != null) {
            try {
                queueConnection.close();
            } catch (JMSException e) {}
        }
    }
}  现在,让我们看看用Spring实现的消息发送者。清单10显示了MessageSenderSpringJMS类中send方法代码。
  清单10,用Spring API 的JMS实现
public void send() {
    try {
        ClassPathXmlApplicationContext appContext = new ClassPathXmlApplicationContext(new String[] {
                "spring-jms.xml"});
        System.out.println("Classpath loaded");
        JMSSender jmsSender = (JMSSender)appContext.getBean("jmsSender");
        jmsSender.sendMesage();
        System.out.println("Message sent using Spring JMS.");
    } catch(Exception e) {
        e.printStackTrace();
    }
}  如你所见,所有与管理JMS资源相关的资源步骤都由Spring容器用配置文件处理。我们仅需要获取JMSSender引用并且调用它上面的sendMessage即可。
  结论
  本文中,我们看到Spring框架如何简化了使用JMS API的异步消息应用开发的工作。Spring移走了所有JMS消息处理必须的样板代码,如获取连接工厂,从Java代码创建队列和会话对象并在运行时用配置文件装配它们。由于这个强大的IOC原理,我们可以不必修改Java代码便可动态交换JMS资源对象。
  因为异步消息是构成SOA框架整体所需的一部分,Spring非常适合放入SOA工具集。同样,JMS管理工具如Hermes使得创建,管理和控制JMS资源变得简单,尤其对系统管理员

本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u/19726/showart_356130.html
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP