在路上

          路上有驚慌,路上有理想

            BlogJava :: 首頁 :: 聯系 :: 聚合  :: 管理
            28 Posts :: 1 Stories :: 10 Comments :: 0 Trackbacks

          寫在前面的話:spring的監聽事件模型應該是觀察者模式。本人項目里的應用在process方法按日期同步某個庫的數據,在方法最后publish一個event事件,這個事件用于后續同步過來的數據處理。事件處理采用了spring的監聽模型.這樣可以做到process方法與event可以異步分離執行。(注:這個事件模型缺省使用SyncTaskExecutor來執行listener的注冊event,所有該listener注冊的event事件為同步執行的)。

          當然,spring的這個機制還有很多應用的場景,就不一一列舉了。

          ApplicationEvent

          事件抽象類,里面只有一個構造函數和一個timestamp。

          ApplicationListener

          監聽接口,里面只有一個onApplicationEvent方法。需要用戶自己編寫ApplicationListener的實現。

          ApplicationContext

          spring上下文,其publishEvent方法用于通知監聽器(ApplicationListener的實現)注冊event時間.

          publishEvent

          void publishEvent(ApplicationEvent event)

          Notify all listeners registered with this application of an application event.

          源碼解讀:
          1.作為ApplicationContext的實現AbstractApplicationContext.java的成員變量applicationListeners,是一個ArrayList,保存了所有的ApplicationListener
          2.利用ApplicationEventMulticaster接口里的方法來完成注冊監聽addApplicationListener,移除監聽removeApplicationListener,removeAllListeners,以及通知監聽注冊事件event:multicastEvent(ApplicationEvent event);
          上面說到的publishEvent方法即使用了multicastEvent方法

          SimpleApplicationEventMultucaster作為ApplicationEventMulticaster的一個實現,提供了multicastEvent的實現代碼,其實就是迭代所有的監聽器,用SyncTaskExecutor同步執行listener的onApplicationEvent

          public void multicastEvent(final ApplicationEvent event) {

          for (Iterator it = getApplicationListeners().iterator(); it

          .hasNext();) {

          final ApplicationListener listener = (ApplicationListener) it

          .next();

          getTaskExecutor().execute(new Runnable() {

          public void run() {

          listener.onApplicationEvent(event);
          }
          });
          }

          3.注意事項:自己編寫ApplicationListener的實現時,要注意不同的監聽器處理不同的事件(復寫onApplicationEvent)。原因就是multicastEvent的執行原理。它是迭代執行所有的監聽器onApplicationEvent

          這里是ApplicationEventMulticaster的類分布圖



          abstract public class AbstractApplicationEventMulticaster implements ApplicationEventMulticaster(Code)(Java Doc)
          public interface ApplicationEventMulticaster (Code)(Java Doc)

          public class SimpleApplicationEventMulticaster extends

          這里是ApplicationContext的類分布圖
          public class DefaultResourceLoader implements ResourceLoader(Code)(Java Doc)
          public interface ResourceLoader (Code)(Java Doc)

          abstract public class AbstractApplicationContext extends DefaultResourceLoader implements ConfigurableApplicationContext,DisposableBean(Code)(Java Doc)
          public interface ConfigurableApplicationContext extends ApplicationContext,Lifecycle(Code)(Java Doc)
          public interface DisposableBean (Code)(Java Doc)

          public class GenericApplicationContext extends AbstractApplicationContext implements BeanDefinitionRegistry(Code)(Java Doc)
          public interface BeanDefinitionRegistry (Code)(Java Doc)

          abstract public class AbstractRefreshableApplicationContext extends
          下面是spring自身的事件應用
          1) ContextRefreshedEvent:當ApplicationContext初始化或者刷新時觸發該事件。
          2) ContextClosedEvent:當ApplicationContext被關閉時觸發該事件。容器被關閉時,其管理的所有單例Bean都被銷毀。
          3) RequestHandleEvent:在Web應用中,當一個http請求(request)結束觸發該事件。
          4) ContestStartedEvent:當容器調用ConfigurableApplicationContext的Start()方法開始/重新開始容器時觸發該事件。
          5) ContestStopedEvent:當容器調用ConfigurableApplicationContext的Stop()方法停止容器時觸發該事件。

          posted on 2010-09-01 10:41 阮步兵 閱讀(5352) 評論(6)  編輯  收藏 所屬分類: OpenSource

          Feedback

          # re: Spring之事件監聽 2010-09-01 10:54 @joe
          都有啥有用場景?  回復  更多評論
            

          # re: Spring之事件監聽[未登錄] 2010-09-01 11:30 毛掌柜
          @@joe
          比如在facebook中,一般上傳一張照片都會對于一個activity的產生,這個時候就可以用這個東西。
          記得SimpleApplicationEventMultucaster的listener都是同步執行,需要再瞧瞧代碼。。。  回復  更多評論
            

          # re: Spring之事件監聽 2010-09-01 11:41 阮步兵
          getTaskExecutor().execute(new Runnable() {

          public void run() {

          listener.onApplicationEvent(event);
          }
          });
          以上是SimpleApplicationEventMultucaster的部分代碼,它選擇的是new Runnable來執行listener  回復  更多評論
            

          # re: Spring之事件監聽 2010-09-01 11:43 阮步兵
          @@joe
          一個任務里面,比如包括上傳文件和數據處理,如果文件不必立刻相應給客戶,可以通過事件監聽的方式來實現。另外,業務流程中有郵件處理以及日志處理的,都可以在主流程結束后執行,可以選擇事件監聽方式處理。  回復  更多評論
            

          # re: Spring之事件監聽[未登錄] 2010-09-01 13:20 毛掌柜
          @阮步兵
          看了下Spring 3的代碼,確實是同步的。
          可以看下SyncTaskExecutor的代碼。  回復  更多評論
            

          # re: Spring之事件監聽 2010-09-01 21:24 阮步兵
          SimpleApplicationEventMultucaster確實采用的是SyncTaskExecutor同步executor,也就是說SimpleApplicationEventMultucaster的listener都是同步執行。當一個listener有多個事件需要處理時,同步執行。  回復  更多評論
            

          主站蜘蛛池模板: 东阿县| 奈曼旗| 巩义市| 孝感市| 盐城市| 嘉鱼县| 遂平县| 柘城县| 寿光市| 石首市| 义乌市| 吕梁市| 泾阳县| 天门市| 锡林郭勒盟| 邹平县| 高平市| 康定县| 绍兴县| 左贡县| 富锦市| 邛崃市| 湖州市| 巫山县| 安新县| 武夷山市| 宜兰县| 嘉定区| 大渡口区| 珲春市| 西充县| 出国| 黑龙江省| 尉氏县| 永兴县| 仁寿县| 灵宝市| 洛浦县| 定日县| 荥经县| 武穴市|