`
wangleifire
  • 浏览: 511174 次
  • 性别: Icon_minigender_1
  • 来自: 深圳
社区版块
存档分类
最新评论

ESB学习笔记(Spring Integration实战)

阅读更多

ESB学习笔记(Spring Integration实战)

  • 介绍
    Spring Integration是Spring公司的一套ESB框架。
    前面ESB介绍中我也做了一定了解。我们来看一下它主要做什么的。
    Spring Integration is motivated by the following goals:
    • Provide a simple model for implementing complex enterprise integration solutions.(暂时相信它吧,谁让它搞个Spring框架,的确给人方便一把。)
    • Facilitate asynchronous, message-driven behavior within a Spring-based application.(这个不谈,Spring框架就是它玩的。再说这一点与它竞争只有Mule啦。)
    • Promote intuitive, incremental adoption for existing Spring users. (也暂时相信它,别人都只说给用户提升。)

    Spring Integration is guided by the following principles:
    • Components should be loosely coupled for modularity and testability.(松耦合,好像很早很早就听说过。像做梦一样)
    • The framework should enforce separation of concerns between business logic and integration logic.(分开程度要取决业务吧。)
    • Extension points should be abstract in nature but within well-defined boundaries to promote reuse and portability.(美妙现实世界产品)

  • 源码下载打开它的网页,http://www.springsource.org/spring-integration
    主页上也没有东东,但有个下源代码的地方,svn开工啦。
    Java代码 复制代码
    1. svn co https://src.springframework.org/svn/spring-integration/trunk  springintegration   
    svn co https://src.springframework.org/svn/spring-integration/trunk  springintegration 
    

    下载完后,进入build-spring-integration目录执行ant.完成后,导入到Eclipse中。
    导入项目会有很多,先添加时会有报错。这里需要添加一个变量。
    IVY_CACHE=<checkout-dir>/ivy-cache/repository

    这里要注意的事,也是我遇到问题。执行ant时,他会去下载lvy,如果你本身在%ANT_HOME%\lib里有lvy.jar包,由于我暂时找不到如何处理,我就直接将Ant中的jar删除掉后就没有问题。
    另外在ant过程中,测试步骤可能会在file模块中出现问题,可以将相关test类中代码注释掉。

  • HelloWorld源码分析在samples项目中,打开helloworld包里面有三个文件。
    Java代码 复制代码
    1. package org.springframework.integration.samples.helloworld;   
    2.   
    3. /**  
    4.  * @author Mark Fisher  
    5.  */  
    6. public class HelloService {   
    7.   
    8.     public String sayHello(String name) {   
    9.         return "Hello " + name;   
    10.     }   
    11.   
    12. }  
    package org.springframework.integration.samples.helloworld;
    
    /**
     * @author Mark Fisher
     */
    public class HelloService {
    
    	public String sayHello(String name) {
    		return "Hello " + name;
    	}
    
    }
    

    helloworldDemo.xml
    Xml代码 复制代码
    1. <?xml version="1.0" encoding="UTF-8"?>  
    2. <beans:beans xmlns="http://www.springframework.org/schema/integration"  
    3.     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  
    4.     xmlns:beans="http://www.springframework.org/schema/beans"  
    5.     xsi:schemaLocation="http://www.springframework.org/schema/beans   
    6.             http://www.springframework.org/schema/beans/spring-beans-2.5.xsd   
    7.             http://www.springframework.org/schema/integration   
    8.             http://www.springframework.org/schema/integration/spring-integration-1.0.xsd">  
    9.   
    10.     <channel id="inputChannel"/>  
    11.   
    12.     <channel id="outputChannel">  
    13.         <queue capacity="10"/>  
    14.     </channel>  
    15.   
    16.     <service-activator input-channel="inputChannel"  
    17.                        output-channel="outputChannel"  
    18.                        ref="helloService"  
    19.                        method="sayHello"/>  
    20.   
    21.     <beans:bean id="helloService" class="org.springframework.integration.samples.helloworld.HelloService"/>  
    22. </beans:beans>  
    <?xml version="1.0" encoding="UTF-8"?>
    <beans:beans xmlns="http://www.springframework.org/schema/integration"
    	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    	xmlns:beans="http://www.springframework.org/schema/beans"
    	xsi:schemaLocation="http://www.springframework.org/schema/beans
    			http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
    			http://www.springframework.org/schema/integration
    			http://www.springframework.org/schema/integration/spring-integration-1.0.xsd">
    
    	<channel id="inputChannel"/>
    
    	<channel id="outputChannel">
    		<queue capacity="10"/>
    	</channel>
    
    	<service-activator input-channel="inputChannel"
    	                   output-channel="outputChannel"
    	                   ref="helloService"
    	                   method="sayHello"/>
    
    	<beans:bean id="helloService" class="org.springframework.integration.samples.helloworld.HelloService"/>
    </beans:beans>
    

    HelloWorldDemo.java
    Java代码 复制代码
    1. package org.springframework.integration.samples.helloworld;   
    2.   
    3. import org.springframework.context.support.AbstractApplicationContext;   
    4. import org.springframework.context.support.ClassPathXmlApplicationContext;   
    5. import org.springframework.integration.channel.BeanFactoryChannelResolver;   
    6. import org.springframework.integration.channel.ChannelResolver;   
    7. import org.springframework.integration.channel.PollableChannel;   
    8. import org.springframework.integration.core.MessageChannel;   
    9. import org.springframework.integration.message.StringMessage;   
    10.   
    11. /**  
    12.  * Demonstrates a basic message endpoint.   
    13.  *   
    14.  * @author Mark Fisher  
    15.  */  
    16. public class HelloWorldDemo {   
    17.   
    18.     public static void main(String[] args) {   
    19.         AbstractApplicationContext context = new ClassPathXmlApplicationContext("helloWorldDemo.xml", HelloWorldDemo.class);   
    20.         ChannelResolver channelResolver = new BeanFactoryChannelResolver(context);   
    21.         MessageChannel inputChannel = channelResolver.resolveChannelName("inputChannel");   
    22.         PollableChannel outputChannel = (PollableChannel) channelResolver.resolveChannelName("outputChannel");   
    23.         inputChannel.send(new StringMessage("World"));   
    24.         System.out.println(outputChannel.receive(0).getPayload());   
    25.         context.stop();   
    26.     }   
    27.   
    28. }  
    package org.springframework.integration.samples.helloworld;
    
    import org.springframework.context.support.AbstractApplicationContext;
    import org.springframework.context.support.ClassPathXmlApplicationContext;
    import org.springframework.integration.channel.BeanFactoryChannelResolver;
    import org.springframework.integration.channel.ChannelResolver;
    import org.springframework.integration.channel.PollableChannel;
    import org.springframework.integration.core.MessageChannel;
    import org.springframework.integration.message.StringMessage;
    
    /**
     * Demonstrates a basic message endpoint. 
     * 
     * @author Mark Fisher
     */
    public class HelloWorldDemo {
    
    	public static void main(String[] args) {
    		AbstractApplicationContext context = new ClassPathXmlApplicationContext("helloWorldDemo.xml", HelloWorldDemo.class);
    		ChannelResolver channelResolver = new BeanFactoryChannelResolver(context);
    		MessageChannel inputChannel = channelResolver.resolveChannelName("inputChannel");
    		PollableChannel outputChannel = (PollableChannel) channelResolver.resolveChannelName("outputChannel");
    		inputChannel.send(new StringMessage("World"));
    		System.out.println(outputChannel.receive(0).getPayload());
    		context.stop();
    	}
    
    }
    


  • Cafe源码分析 Cafe示例描述的是星巴克的订单处理故事。
    其示例描述在:http://www.enterpriseintegrationpatterns.com/ramblings/18_starbucks.html
    这里简单描述一下,以免大家看英文太累
    文章讲在星巴克喝咖啡时,收银员可能只有一个,而冲咖啡员工会有多个,如何让收银员产生订单异步发送给冲咖啡员工。并且冲咖啡员工可能是竞争上岗的,就当他们是计件工吧。
    这里要考虑问题:
    1,冲咖啡员工使用不同设备,不同咖啡冲调时间可能不同。 
    2,冲咖啡员工可能会将相同类型的咖啡同时一起冲调。
    星巴克如何处理这个问题?
    就当他解决了这个问题,它是如何把每个咖啡又送回给每个客户呢?当然,星巴克采用“标识关系模式”,将每个咖啡杯上标上名称,并通过叫喊方式。
    但并不是每天都是美好的,总有出错的时候。例如,收银员无法支付?冲调一杯你不喜欢的咖啡,你要换一杯?冲咖啡的设备坏了,星巴克要退你钱...这些异常情况如何处理。
    因此就会有以下三种方式异常处理:
    1,关闭交易,什么都不做。
    2,重做,重新发起行为。
    3,修正行为,相当于退钱这种行为。
    因此,这里这篇文章后面讨论一下两阶段提交为什么不适合星巴克,如果你让收银员、冲咖啡员工,买单的人需要在一个“事务”中,交易所有完成后,再进行下一个业务。估计星巴克会马上倒闭啦。因此星巴克采用“Conversation pattern”模式。

    好啦,业务了解清楚,我们再来看一下完整XML文件。在这里我没有采用示例详细的xml方式,而没有采用annotation方式。

    Xml代码 复制代码
    1. <?xml version="1.0" encoding="UTF-8"?>  
    2. <beans:beans xmlns="http://www.springframework.org/schema/integration"  
    3.     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  
    4.     xmlns:beans="http://www.springframework.org/schema/beans"  
    5.     xmlns:stream="http://www.springframework.org/schema/integration/stream"  
    6.     xsi:schemaLocation="http://www.springframework.org/schema/beans   
    7.             http://www.springframework.org/schema/beans/spring-beans-2.5.xsd   
    8.             http://www.springframework.org/schema/integration   
    9.             http://www.springframework.org/schema/integration/spring-integration-1.0.xsd   
    10.             http://www.springframework.org/schema/integration/stream   
    11.             http://www.springframework.org/schema/integration/stream/spring-integration-stream-1.0.xsd">  
    12.   
    13.     <gateway id="cafe" service-interface="org.springframework.integration.samples.cafe.Cafe"/>  
    14.   
    15.     <channel id="orders"/>  
    16.     <splitter input-channel="orders" ref="orderSplitter" method="split" output-channel="drinks"/>  
    17.   
    18.     <channel id="drinks"/>  
    19.     <router input-channel="drinks" ref="drinkRouter" method="resolveOrderItemChannel"/>  
    20.   
    21.     <channel id="coldDrinks">  
    22.         <queue capacity="10"/>  
    23.     </channel>  
    24.     <service-activator input-channel="coldDrinks" ref="barista"  
    25.                        method="prepareColdDrink" output-channel="preparedDrinks"/>  
    26.   
    27.     <channel id="hotDrinks">  
    28.         <queue capacity="10"/>  
    29.     </channel>  
    30.     <service-activator input-channel="hotDrinks" ref="barista"  
    31.                        method="prepareHotDrink" output-channel="preparedDrinks"/>  
    32.   
    33.     <channel id="preparedDrinks"/>  
    34.     <aggregator input-channel="preparedDrinks" ref="waiter"  
    35.                 method="prepareDelivery" output-channel="deliveries"/>  
    36.   
    37.     <stream:stdout-channel-adapter id="deliveries"/>  
    38.   
    39.     <beans:bean id="orderSplitter"  
    40.                 class="org.springframework.integration.samples.cafe.xml.OrderSplitter"/>  
    41.   
    42.     <beans:bean id="drinkRouter"  
    43.                 class="org.springframework.integration.samples.cafe.xml.DrinkRouter"/>  
    44.   
    45.     <beans:bean id="barista" class="org.springframework.integration.samples.cafe.xml.Barista"/>  
    46.   
    47.     <beans:bean id="waiter" class="org.springframework.integration.samples.cafe.xml.Waiter"/>  
    48.   
    49.     <poller id="poller" default="true">  
    50.         <interval-trigger interval="1000"/>  
    51.     </poller>  
    52.   
    53. </beans:beans>  
    <?xml version="1.0" encoding="UTF-8"?>
    <beans:beans xmlns="http://www.springframework.org/schema/integration"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns:beans="http://www.springframework.org/schema/beans"
        xmlns:stream="http://www.springframework.org/schema/integration/stream"
        xsi:schemaLocation="http://www.springframework.org/schema/beans
                http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
                http://www.springframework.org/schema/integration
                http://www.springframework.org/schema/integration/spring-integration-1.0.xsd
                http://www.springframework.org/schema/integration/stream
                http://www.springframework.org/schema/integration/stream/spring-integration-stream-1.0.xsd">
    
        <gateway id="cafe" service-interface="org.springframework.integration.samples.cafe.Cafe"/>
    
        <channel id="orders"/>
        <splitter input-channel="orders" ref="orderSplitter" method="split" output-channel="drinks"/>
    
        <channel id="drinks"/>
        <router input-channel="drinks" ref="drinkRouter" method="resolveOrderItemChannel"/>
    
        <channel id="coldDrinks">
            <queue capacity="10"/>
        </channel>
        <service-activator input-channel="coldDrinks" ref="barista"
                           method="prepareColdDrink" output-channel="preparedDrinks"/>
    
        <channel id="hotDrinks">
            <queue capacity="10"/>
        </channel>
        <service-activator input-channel="hotDrinks" ref="barista"
                           method="prepareHotDrink" output-channel="preparedDrinks"/>
    
        <channel id="preparedDrinks"/>
        <aggregator input-channel="preparedDrinks" ref="waiter"
                    method="prepareDelivery" output-channel="deliveries"/>
    
        <stream:stdout-channel-adapter id="deliveries"/>
    
        <beans:bean id="orderSplitter"
                    class="org.springframework.integration.samples.cafe.xml.OrderSplitter"/>
    
        <beans:bean id="drinkRouter"
                    class="org.springframework.integration.samples.cafe.xml.DrinkRouter"/>
    
        <beans:bean id="barista" class="org.springframework.integration.samples.cafe.xml.Barista"/>
    
        <beans:bean id="waiter" class="org.springframework.integration.samples.cafe.xml.Waiter"/>
    
        <poller id="poller" default="true">
            <interval-trigger interval="1000"/>
        </poller>
    
    </beans:beans>
    


    以下是参考文档中的示例描述图:



    CafeDemo代码创建了订单。这家咖啡店有两种饮料,一种是热的,一种是冷的,消息将这订单包装到一个"orders"的channel(频道)。一个endpoint侦听到订单频道并根据订单情况进行分开处理。

    完成分开处理后,程序交给DrinksRouter经过drink频道。而DrinkRouter一个职责就是将订单内容中的热咖啡和冷咖啡交给不同的channel处理。

    Xml代码 复制代码
    1. <gateway id="cafe" service-interface="org.springframework.integration.samples.cafe.Cafe"/>  
    	<gateway id="cafe" service-interface="org.springframework.integration.samples.cafe.Cafe"/>
    

    这里Gateway主要是根据接口生成代理类。

    Java代码 复制代码
    1. Cafe cafe = (Cafe) context.getBean("cafe");   
    2.                 DrinkOrder order = new DrinkOrder();   
    3.                 Drink hotDoubleLatte = new Drink(DrinkType.LATTE, 2false);   
    4.                 Drink icedTripleMocha = new Drink(DrinkType.MOCHA, 3true);   
    5.                 order.addDrink(hotDoubleLatte);   
    6.                 order.addDrink(icedTripleMocha);   
    7.                 for (int i = 0; i < 100; i++) {   
    8.                         cafe.placeOrder(order);   
    9.                 }  
    Cafe cafe = (Cafe) context.getBean("cafe");
                    DrinkOrder order = new DrinkOrder();
                    Drink hotDoubleLatte = new Drink(DrinkType.LATTE, 2, false);
                    Drink icedTripleMocha = new Drink(DrinkType.MOCHA, 3, true);
                    order.addDrink(hotDoubleLatte);
                    order.addDrink(icedTripleMocha);
                    for (int i = 0; i < 100; i++) {
                            cafe.placeOrder(order);
                    }
    



    Java代码 复制代码
    1. @MessageEndpoint(input="orders", output="drinks")   
    2. public class OrderSplitter {   
    3.   
    4.         @Splitter  
    5.         public List<Drink> split(Message<DrinkOrder> orderMessage) {   
    6.                 return orderMessage.getPayload().getDrinks();   
    7.         }   
    8.   
    9. }  
    @MessageEndpoint(input="orders", output="drinks")
    public class OrderSplitter {
    
            @Splitter
            public List<Drink> split(Message<DrinkOrder> orderMessage) {
                    return orderMessage.getPayload().getDrinks();
            }
    
    }
    


    Java代码 复制代码
    1. @MessageEndpoint(input="drinks")   
    2. public class DrinkRouter {   
    3.   
    4.         @Router  
    5.         public String resolveDrinkChannel(Drink drink) {   
    6.                 return (drink.isIced()) ? "coldDrinks" : "hotDrinks";   
    7.         }   
    8.   
    9. }  
    @MessageEndpoint(input="drinks")
    public class DrinkRouter {
    
            @Router
            public String resolveDrinkChannel(Drink drink) {
                    return (drink.isIced()) ? "coldDrinks" : "hotDrinks";
            }
    
    }
    


    Xml代码 复制代码
    1. <handler-endpoint handler="coldBarista" input-channel="coldDrinks"  
    2.         method="prepareColdDrink">  
    3. </handler-endpoint>  
    4.   
    5. <handler-endpoint handler="hotBarista" input-channel="hotDrinks"  
    6.         method="prepareHotDrink">  
    7. </handler-endpoint>  
    <handler-endpoint handler="coldBarista" input-channel="coldDrinks"
            method="prepareColdDrink">
    </handler-endpoint>
    
    <handler-endpoint handler="hotBarista" input-channel="hotDrinks"
            method="prepareHotDrink">
    </handler-endpoint>
    


    Java代码 复制代码
    1. public void prepareColdDrink(Message<Drink> drinkMessage) {   
    2.                 Drink drink = drinkMessage.getPayload();   
    3.                 //no changes to the rest of the code   
    4.         }  
  • 分享到:
    评论
    4 楼 sniciq 2012-08-22  
    git clone --recursive git://github.com/SpringSource/spring-integration.git
    3 楼 longlong850525 2012-03-12  
    Spring Integration 不能完全算作是一个esb,只能算作是一个集成框架而已,和camel完成的事情差不多,不过没有camel强大
    2 楼 longlong850525 2012-03-12  
    写得不错,顶曾经我上铺的兄弟一个
    1 楼 InnocentBoy 2011-08-22  
    spring integration官方的下载地址不能下载!

    相关推荐

      spring integration in action

      ### Spring Integration in Action #### Part 1 - 背景 **1: Spring Integration 的介绍** - **Spring Integration 概览:** Spring Integration 是一个基于 Spring 框架的企业集成解决方案,它提供了一种声明式...

      spring source spring integration in action 随书源码 example code

      通过这本书和随书源码的学习,你可以掌握如何利用Spring Integration实现系统间的无缝对接,将其作为轻量级的Enterprise Service Bus (ESB)使用,从而提高系统的集成效率和灵活性。无论是对于初学者还是有经验的...

      JBoss ESB 学习笔记

      ### JBoss ESB 学习笔记知识点概览 #### 一、搭建ESB开发环境 - **工具准备**: - Eclipse-JEE 3.5:集成开发环境,支持Java EE标准,适合企业级应用程序开发。 - jbossesb-server-4.7:JBoss ESB的具体版本,为...

      JBossESB学习笔记(1-16全)

      JBossESB学习笔记 收集了网上1-16系列教程,笔记详细介绍了JBossESB各个组件的特性及配置文件的说明

      Jboss_ESB学习笔记

      【JBoss ESB学习笔记】 JBoss ESB(Enterprise Service Bus)是Red Hat公司开发的一款开源企业服务总线,它是企业级应用集成的核心组件,用于连接不同系统、服务和应用程序,实现服务之间的通信和交互。本学习笔记...

      JBOSS_Esb学习资料

      4. **Spring整合**:《JBoss_ESB学习笔记13——第十个ESB应用Spring_AOP.doc》和《JBoss_ESB学习笔记12——第十个ESB应用Spring_helloworld.doc》涉及到Spring框架与ESB的结合,Spring AOP(面向切面编程)在ESB中的...

      JBossESB学习笔记.rar_Jboss_ESB_esb和aop

      【JBoss ESB 学习笔记】 JBoss ESB(Enterprise Service Bus,企业服务总线)是Red Hat公司开发的一款开源服务导向架构(SOA)平台,它为分布式应用程序提供了集成和互操作性。本笔记将深入探讨JBoss ESB的核心概念...

      pro_spring_integration.pdf (英文原版非扫描)

      ### Spring Integration核心知识点详解 #### 一、Spring Integration概述 ...通过系统学习本书中的内容,不仅可以获得Spring Integration的基础知识,还能了解到其在实际开发中的应用技巧和最佳实践。

      Pro Spring Integration (Apress)

      - **低门槛**:Spring Integration的设计使得开发者能够快速上手,无需深入了解复杂的企业服务总线(ESB)的概念。 - **灵活性**:Spring Integration允许开发者通过各种方式定制消息处理流程,满足不同的业务需求。...

      ESB应用Spring_Hello_World

      总结,这个ESB应用Spring_Hello_World实例是学习和理解如何在JBoss ESB中整合Spring框架进行服务开发的一个基础练习。通过这个示例,开发者可以了解到ESB中的消息传递机制、队列配置以及如何利用Spring进行服务实现...

      Spring学习笔记+学习源码.zip

      这份"Spring学习笔记+学习源码.zip"资源包含了深入学习Spring及其相关技术的知识点,以及实践代码,对提升Spring技能将大有裨益。 首先,我们来详细讨论Spring框架的主要组件和功能: 1. **依赖注入(Dependency ...

      Jboss-ESB学习笔记.doc

      本篇学习笔记主要围绕 JBoss ESB 的一个基础应用——“Hello World File Action”进行讲解,这个例子展示了如何利用 JBoss ESB 的 File Gateway 功能来监控文件系统变化,并通过 JMS(Java Message Service)消息...

      ESB应用Spring_AOP

      ESB应用Spring_AOP

      JBoss ESB学习笔记1-搭建ESB开发环境.docx

      本篇笔记将详细介绍如何搭建JBoss ESB的开发环境。 首先,我们需要准备的是Eclipse IDE,这里推荐使用Eclipse-JEE 3.5版本,因为该版本对Java EE开发有着良好的支持,同时包含了对各种服务器的集成。如果你还没有...

      Mule ESB 学习笔记(13)CSV数据文件到数据库

      在本篇“Mule ESB 学习笔记(13)CSV数据文件到数据库”中,我们将探讨如何使用Mule ESB(Enterprise Service Bus,企业服务总线)处理CSV(Comma Separated Values,逗号分隔值)数据,并将其有效地导入到数据库中...

      Pro Spring Integration

      - **集成框架比较**:本章比较了Spring Integration与其他流行的集成框架,如Apache Camel、Mule ESB等,帮助读者了解各种框架的特点和适用场景。 - **选择依据**:指导读者如何根据项目的具体需求来选择最适合的...

      Apress.Pro.Spring.Integration

      《专业Spring Integration》一书由Mark Lui、Mario Gray、Andy H. Chan和Josh Long共同撰写,旨在指导读者如何利用Spring Integration构建企业级集成解决方案。本书深入探讨了Spring Integration的核心概念与实践,...

      MuleESB学习笔记

      MuleESB是一个基于Java的轻量级企业服务总线和集成平台,允许开发人员快速便利地连接多个应用,并支持应用间的数据交换。MuleESB支持集成现有系统而无论其底层采用何种技术,如JMS、WebServices、JDBC、HTTP以及其他...

    Global site tag (gtag.js) - Google Analytics