<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    Dict.CN 在線詞典, 英語(yǔ)學(xué)習(xí), 在線翻譯

    都市淘沙者

    荔枝FM Everyone can be host

    統(tǒng)計(jì)

    留言簿(23)

    積分與排名

    優(yōu)秀學(xué)習(xí)網(wǎng)站

    友情連接

    閱讀排行榜

    評(píng)論排行榜

    Spring 源碼分析:ApplicationContext

    Spring 源碼分析:ApplicationContext

    關(guān)鍵詞Spring    ApplicationCont                                          

    分析ApplicationContext
           Spring的bean包支持通過(guò)編碼方式管理和操作bean的基本功能,ApplicationContext
    則以Framework的方式提供BeanFactory的所有功能。使用ApplicationContext,你可以讓
    系統(tǒng)加載你的bean(例如,在Servlet容器初始化ContextLoaderServlet時(shí),通過(guò)
    ContextLoader類加載Spring Framework),而不是使用編碼方式來(lái)加載。
           ApplicationContext接口是context包的基礎(chǔ),位于
    org.springframework.context包里,提供了BeanFactory的所有功能。除此之外, 
    ApplicationContext為了支持Framework的工作方式,提供了以下的功能:
          l.MessageSource,提供了語(yǔ)言信息的國(guó)際化支持
          2.提供資源(如URL和文件系統(tǒng))的訪問(wèn)支持
          3.為實(shí)現(xiàn)了ApplicationListener接口的bean提供了事件傳播支持
          4.為不同的應(yīng)用環(huán)境提供不同的context,例如支持web應(yīng)用的XmlWebApplicationContext類
    
          下面的源代碼分析主要集中在ApplicationContext接口特有的功能上,如國(guó)際化支持,
    資源訪問(wèn)和bean的事件傳播。
    
    我的問(wèn)題
           現(xiàn)在我的問(wèn)題是,ApplicationContext是如何實(shí)現(xiàn)上面提到的功能的?下面的分析
    將作出回答。
    
    準(zhǔn)備測(cè)試用例
           1. 首先在類路徑根目錄編寫測(cè)試國(guó)際化支持的testmsg.xml,并將它加入Spring IDE
    的管理范圍:
           <beans>
                <bean id="messageSource" 
               class="org.springframework.context.support.ResourceBundleMessageSource">
                     <property name="basenames">
                          <list>
                                <value>message</value>
                          </list>
                     </property>
                </bean>
           </beans>
    
           2. 編寫測(cè)試用例,測(cè)試國(guó)際化支持和資源訪問(wèn)的功能。
               public class MsgTest extends TestCase {
                     ApplicationContext ctx = null;
                     public MsgTest(String arg0) {
                           super(arg0);
                     }
                     protected void setUp() throws Exception {
                           super.setUp();
                           ctx = new FileSystemXmlApplicationContext("testmsg.xml");
                     }
                     public void testMessageResource() {
                           Object[] args = {"我", "你"};
                           String msg = ctx.getMessage("hello", args, Locale.CHINA);
                           //System.out.println("msg=" + msg);
                           assertEquals("我和你", msg);
                           Resource rs = ctx.getResource("classpath:log4j.properties");
                           assertTrue(rs.exists());
                    }
               }
    
           3. 在類路徑根目錄創(chuàng)建屬性文件message.properties,內(nèi)容為hello={0}和{1}。
     
           此時(shí)運(yùn)行TestCase,果然不出所料,Junit視圖的測(cè)試狀態(tài)是紅條。將打印msg變量的
    語(yǔ)句打開(kāi),重新測(cè)試,發(fā)現(xiàn)"和"字是亂碼。
           在message.properties文件中將"和"字改為ASCII碼\u548c,重新運(yùn)行TestCase,
    綠條,測(cè)試通過(guò)。
           將testmsg.xml中bean的id改為messageSource1,重新運(yùn)行測(cè)試,出現(xiàn)紅條,
    測(cè)試失敗,說(shuō)明bean的名稱必須是messageSource,這點(diǎn)值得注意。至于其中的原因稍后
    說(shuō)明。
    
           ApplicationContext接口通過(guò)繼承BeanFactory,MessageSource和ResourceLoader
    三個(gè)接口,分別支持管理和操作bean的功能,語(yǔ)言信息的國(guó)際化支持以及對(duì)資源訪問(wèn)的支持。
           AbstractApplicationContect是ApplicationContext的抽象實(shí)現(xiàn)類,它的繼承層次較
    為紊亂,我覺(jué)得這里應(yīng)該進(jìn)行代碼重構(gòu)。AbstractXmlApplicationContext是
    AbstractApplicationContext的子類,提供了對(duì)XML配置文件的支持,它有三個(gè)子類,分別
    用于不同的應(yīng)用環(huán)境。
           對(duì)于MessageSource,Spring提供了兩個(gè)bean實(shí)現(xiàn),ResourceBundleMessageSource和
    ReloadableResourceBundleMessageSource。前者提供了訪問(wèn)Properties文件的支持,后者
    添加了無(wú)需重啟JVM,重新加載Properties文件的支持。
    ApplicationContext的國(guó)際化和資源訪問(wèn)支持
           1. 如類層次圖所示,在我們的例子中,F(xiàn)ileSystemXmlApplicationContext使用
    DefaultListableBeanFactory裝載和解釋testmsg.xml配置文件(參見(jiàn)代碼分析的
    BeanFactory部分)。
    
           2. FileSystemXmlApplicationContext根據(jù)配置文件的BeanDefinition創(chuàng)建
    ResourceBundleMessageSource,加載<list>元素定義的Properties文件,并保存在
    AbstractApplicationContext的屬性中。當(dāng)客戶程序調(diào)用getMessage方法時(shí),
    AbstractApplicationContext調(diào)用ResourceBundleMessageSource的getMessage方法返回
    Message信息。
    
           3. 至于上節(jié)提到的MessageSource的id只能是messageSource,是因?yàn)?/FONT>
    AbstractApplicationContext的initMessageSource()方法中,有這樣一段代碼:
                       this.messageSource = (MessageSource) 
                       getBean(MESSAGE_SOURCE_BEAN_NAME);
               其中MESSAGE_SOURCE_BEAN_NAME的定義為:
                       static final String MESSAGE_SOURCE_BEAN_NAME = "messageSource";
               原因找到了,其實(shí)只要稍做代碼重構(gòu),即可消除這個(gè)缺陷。
           4. 如類層次圖所示,AbstractApplicationContext繼承了DefaultResourceLoader,
    當(dāng)客戶程序調(diào)用getResource方法時(shí),使用父類中實(shí)現(xiàn)的方法來(lái)處理。
     
    ApplicationContext的事件傳播
    準(zhǔn)備測(cè)試用例
           1. 首先編寫測(cè)試用例。
               public class SenderBeanTest extends TestCase {
                    ApplicationContext ctx = null;
                    protected void setUp() throws Exception {
                        super.setUp();
                        ctx = new FileSystemXmlApplicationContext("testlistener.xml");
                    }
                    public void testSendEmail() {
                        SenderBean sender = (SenderBean)ctx.getBean("sender");
                        String msg = sender.sendMessage("test message");
                        assertEquals("test message", msg);
                    }
               }
           2. 接著編寫testlistener.xml配置文件。
               <beans>
                   <bean id="sender" class="unittest.SenderBean"/>
                   <bean id="listener" class="unittest.MessageListener"/>
               </beans>
           3. 最后編寫SenderBean,MessageListener和MessageEvent類。
               public class SenderBean implements ApplicationContextAware {
                      private ApplicationContext applicationContext;
                      public void setApplicationContext(ApplicationContext applicationContext)
                                throws BeansException {
                            this.applicationContext = applicationContext;
                      }
                      public String sendMessage(String msg) {
                            MessageEvent event = new MessageEvent(msg);
                            this.applicationContext.publishEvent(event);
                            return msg;
                      }
                }
     
                public class MessageListener implements ApplicationListener {
                      public void onApplicationEvent(ApplicationEvent event) {
                            if (event instanceof MessageEvent) {
                                  System.out.println("I got the message:" + event.getSource());
                            }
                      }
                }
     
                public class MessageEvent extends ApplicationEvent {
                      public MessageEvent(Object source) {
                            super(source);
                            System.out.println(this.getTimestamp() + ":" + source);
                      }
                }
               運(yùn)行測(cè)試案例SenderBeanTest,綠條,測(cè)試通過(guò)。Console窗口出現(xiàn)以下DEBUG
    信息:
               ……
               796 DEBUG support.DefaultListableBeanFactory - Returning 
    cached instance of singleton bean 'sender'
               1085553911796:test message
               796 DEBUG support.FileSystemXmlApplicationContext - Publishing event 
    in context [org.springframework.context.support.FileSystemXmlApplicationContext;hashCode=13549765]: 
    unittest.MessageEvent[source=test message]
               I got the message:test message
    
     
    事件傳播的實(shí)現(xiàn)
           1. FileSystemXmlApplicationContext的構(gòu)造器調(diào)用AbstractApplicationContext的
    refresh方法。如圖所示,refresh方法調(diào)用refreshListeners方法。
           2. AbstractApplicationContext的refreshListeners方法使用BeanFactory的
    getBeanOfType方法得到所有ApplicationListener類(本例中是MessageListener),并使用
    addListener方法把它們都放入ApplicationEventMulticasterImpl的Set容器中
    (eventListeners變量)。
           3. 如圖所示,SenderBean實(shí)現(xiàn)ApplicationContextAware接口,并通過(guò)
    setApplicationContext方法注入ApplicationContext對(duì)象實(shí)例。
           4. 當(dāng)調(diào)用SenderBean類sendMessage方法時(shí),AbstractApplicationContext調(diào)用
    publishEvent方法。
           5. AbstractApplicationContext類的publishEvent方法調(diào)用
    ApplicationEventMulticasterImpl類的onApplicationEvent方法。
           6. ApplicationEventMulticasterImpl通知Set容器中所有的ApplicationListener
    對(duì)象,調(diào)用它們的onApplicationEvent方法。
     
           從以上的過(guò)程可以看出,ApplicationContext將事件通知所有的
    ApplicationListener。如果ApplicationListener的子類(如MessageListener)只想接受
    指定的事件類型,需要自己編寫過(guò)濾代碼,如例子中的if (event instanceof MessageEvent)。

    posted on 2006-03-02 17:09 都市淘沙者 閱讀(1481) 評(píng)論(0)  編輯  收藏 所屬分類: Spring+Struts+Hibernate

    主站蜘蛛池模板: 免费国产va视频永久在线观看| 亚洲国产精品无码久久青草| 中文字幕在线免费播放| 亚洲一线产区二线产区区| 久久亚洲精品成人综合| 亚洲国产中文字幕在线观看| 性盈盈影院免费视频观看在线一区| 久久免费视频精品| 91精品全国免费观看青青| 在线亚洲v日韩v| 亚洲综合一区无码精品| 亚洲国产综合自在线另类| 亚洲av丰满熟妇在线播放| 国产精品亚洲二区在线观看| 日产乱码一卡二卡三免费| 色婷婷7777免费视频在线观看| 国产高清不卡免费视频| 免费无码又爽又刺激网站| www免费插插视频| 黄色网页免费观看| 噜噜综合亚洲AV中文无码| 亚洲人成色77777在线观看| 激情亚洲一区国产精品| 亚洲国产成人精品无码区在线秒播| 亚洲人成网站在线播放影院在线 | 亚洲人成网站在线播放影院在线| 国产亚洲日韩在线三区| 亚洲男人的天堂一区二区| 亚洲国产成人影院播放| 亚洲国产专区一区| 国产精品亚洲产品一区二区三区| 亚洲人成网站色在线入口| 亚洲欧洲久久久精品| 不卡精品国产_亚洲人成在线| 综合亚洲伊人午夜网| 亚洲国产精品无码专区影院 | 朝桐光亚洲专区在线中文字幕| 久久亚洲AV成人无码国产电影| 国产午夜亚洲精品不卡| 农村寡妇一级毛片免费看视频| www在线观看免费视频|