zoukankan      html  css  js  c++  java
  • java-Sping-IOC

    1.IoC容器建立

    BeanFactory是一个最基本的接口规范,其中包含getBean,containsBean,getAliases等方法

    Spring提供了一个BeanFactory的基本实现,XmlBeanFactory同样的通过使用模板模式来得到对IOC容器的抽象- 
    AbstractBeanFactory,DefaultListableBeanFactory这些抽象类为其提供模板服务。其中通过resource 接口来抽象bean定义数据,对Xml定义文件的解析通过委托给XmlBeanDefinitionReader来完成。下面的例子,简单的演示IOC容器的创建过程:

    ClassPathResource res = new ClassPathResource("beans.xml");   
    DefaultListableBeanFactory factory = new DefaultListableBeanFactory(); 
    XmlBeanDefinitionReader reader = new XmlBeanDefinitionReader(factory);
    reader.loadBeanDefinitions(res);
      
    

      

    这些代码演示了以下几个步骤:   
        1. 创建IOC配置文件的抽象资源     

      2. 创建一个BeanFactory  
        3. 把读取配置信息的BeanDefinitionReader,这里是XmlBeanDefinitionReader配置给BeanFactory  
        4. 从定义好的资源位置读入配置信息,具体的解析过程由XmlBeanDefinitionReader来完成,这样完成整个载入bean定义的过程。我们的IoC容器就建立起来了。

       public class XmlBeanFactory extends DefaultListableBeanFactory {   
        //这里为容器定义了一个默认使用的bean定义读取器   
        private final XmlBeanDefinitionReader reader = new XmlBeanDefinitionReader(this);   
        public XmlBeanFactory(Resource resource) throws BeansException {   
             this(resource, null);   
       }   
        //在初始化函数中使用读取器来对资源进行读取,得到bean定义信息。   
        public XmlBeanFactory(Resource resource, BeanFactory parentBeanFactory) throws BeansException {   
              super(parentBeanFactory);   
              this.reader.loadBeanDefinitions(resource);  
        }

    备注( XmlBeanFactory[已废弃] 和 ApplicationContext 是两种IOC容器,其中实现的功能ApplicationContext 要多一点,BeanFactory往往不具备对资源定义的能力,而上下文可以自己完成资源定义)

    2.ApplicationContext

    仔细分析Spring BeanFactory的结构,我们来看看在BeanFactory基础上扩展出的ApplicationContext - 我们最常使用的上下文。除了具备BeanFactory的全部能力,上下文为应用程序又增添了许多便利:   
          * 可以支持不同的信息源,我们看到ApplicationContext扩展了MessageSource  

       * 访问资源 , 体现在对ResourceLoader和Resource的支持上面,这样我们可以从不同地方得到bean定义资源     

       * 支持应用事件,继承了接口ApplicationEventPublisher,这样在上下文中引入了事件机制而BeanFactory是没有的。

    ApplicationContext提供IoC容器的主要接口,在其体系中有许多抽象子类比如AbstractApplicationContext为具体的BeanFactory的实现,比如FileSystemXmlApplicationContext和 ClassPathXmlApplicationContext提供上下文的模板,使得他们只需要关心具体的资源定
    位问题。当应用程序代码实例化 FileSystemXmlApplicationContext的时候,得到IoC容器的一种具体表现 - ApplicationContext,从而应用程序通过ApplicationContext来管理对bean的操作。 BeanFactory 是一个接口,在实际应用中我们一般使用ApplicationContext来使用IOC容器,它们也是IOC容器展现给应用开发者的使用接口。对应用程序开发者来说,可以认为BeanFactory和ApplicationFactory在不同的使用层面上代表了SPRING提供的IOC容器服务。 下面我们具体看看通过FileSystemXmlApplicationContext是怎样建立起IOC容器的, 显而易见我们可以通过new来得到IoC容器:

    ApplicationContext = new FileSystemXmlApplicationContext(xmlPath);
    

    调用的是它初始化代码:

    public FileSystemXmlApplicationContext(String[] configLocations, boolean refresh, ApplicationContext parent)   throws BeansException {   
         super(parent);   
         this.configLocations = configLocations;   
         if (refresh) {   
           //这里是IoC容器的初始化过程,其初始化过程的大致步骤由AbstractApplicationContext来定义   
            refresh();   
        }   
    }

    refresh的模板在AbstractApplicationContext:

     

    public void refresh() throws BeansException, IllegalStateException {  

        synchronized (this.startupShutdownMonitor) {    

           synchronized (this.activeMonitor) {        

             this.active = true;      

          }       
       // 这里需要子类来协助完成资源位置定义,bean载入和向IOC容器注册的过程         refreshBeanFactory();        

      ............  

     }  

      

    这个方法包含了整个BeanFactory初始化的过程,对于特定的FileSystemXmlBeanFactory,我们看到定位资源位置由refreshBeanFactory()来实现:  
    在AbstractXmlApplicationContext中定义了对资源的读取过程,默认由XmlBeanDefinitionReader来读取;

        * 初始化的入口在容器实现中的refresh()调用来完成  
        * 对bean 定义载入IOC容器使用的方法是loadBeanDefinition,其中的大致过程如下:通过ResourceLoader来完成资源文件位置的定位,DefaultResourceLoader是默认的实现,同时上下文本身就给出了ResourceLoader的实现,可以从类路径,文件系统, URL等方式来定为资源位置。如果是XmlBeanFactory作为IOC容器,那么需要为它指定bean定义的资源,也就是说bean定义文件时通过抽象成Resource来被IOC容器处理的,容器通过BeanDefinitionReader来完成定义信息的解析和Bean信息的注册,往往使用的是XmlBeanDefinitionReader来解析bean的xml定义文件 - 实际的处理过程是委托给BeanDefinitionParserDelegate来完成的,从而得到bean的定义信息,这些信息在Spring中使用BeanDefinition对象来表示 - 这个名字可以让我们想到
    loadBeanDefinition,RegisterBeanDefinition这些相关的方法 - 他们都是为处理BeanDefinitin服务的,IoC容器解析得到BeanDefinition以后,需要把它在IOC容器中注册,这由IOC实现 BeanDefinitionRegistry接口来实现。注册过程就是在IOC容器内部维护的一个HashMap来保存得到的 BeanDefinition的过程。这个HashMap是IoC容器持有bean信息的场所,以后对bean的操作都是围绕这个HashMap来实现的。  
        * 然后我们就可以通过BeanFactory和ApplicationContext来享受到Spring IOC的服务了. 

      

  • 相关阅读:
    年度回忆录(2012.102013.01)
    Java中的Annotation(1)三个基本Annotation
    Java7中的文件和目录管理Path类
    Struts1和Struts2核心控制器的执行原理
    java中的IO基础3
    动态代理(2)动态代理和AOP
    java中的IO基础
    《嫌疑犯x的献身》看完了。。。
    像NHibernate致敬ado.net entity framework的范型DAO和open session in view实现
    我的MBTI职业性格测试
  • 原文地址:https://www.cnblogs.com/wonder2636/p/5541703.html
Copyright © 2011-2022 走看看