spring1.0(一)spring初探

时间:2024-04-12 20:01:48

spring加载应用上下文的几种方式

1、AnnotationConfigApplicationContext:从一个或多个基于Java配置类中加载spring应用上下文,适用于Java注解方式;

如果想从Java配置中加载应用上线文,可以按照如下方式加载:

ApplicationContext context = new AnnotationConfigApplicationContext(com.springaction.knights.config.KnightCongig.class);
2、AnnotationConfigWebApplicationContext:从一个或多个基于Java配置类中加载Spring Web应用上下文,专门为web应用准备的,适用于注解方式;

3、ClassPathXmlApplicationContext:从类路径下的一个或者多个xml配置文件中加载上线文定义,把应用上下文的定义文件作为类资源,适用于xml配置方式;

ApplicationContext context = new ClassPathXmlApplicationContext("knight.xml");
4、FileSystemXmlApplicationContext:从文件系统下的一个或者多个xml配置文件中加载上下文定义

ApplicationContext context = new FileSystemXmlApplicationContext("c:/knight.xml");
5、XmlWebApplicationContext:从web应用的一个或者多个xml配置文件中加载上下文定义,适用于xml配置方式;

应用上下文准备好之后,我们就可以通过调用上下文的getBean()方法从spring容器中获取bean了。

bean的生命周期:

在spring中,从BeanFactory或ApplicationContext取得的实例为Singleton,也就是预设为每一个Bean的别名只能维持一个实例,而不是每次都产生一个新的对象使用Singleton模式产生单一实例,对单线程的程序说并不会有什么问题,但对于多线程的程序,就必须注意安全(Thread-safe)的议题,防止多个线程同时存取共享资源所引发的数据不同步问题。

然而在spring中 可以设定每次从BeanFactory或ApplicationContext指定别名并取得Bean时都产生一个新的实例:例如:

在spring中,singleton属性默认是true,只有设定为false,则每次指定别名取得的Bean时都会产生一个新的实例。

一个Bean从创建到销毁,如果是用BeanFactory来生成,管理Bean的话,会经历几个执行阶段(如图1.1):

spring1.0(一)spring初探

  1. Bean的建立 
    容器寻找Bean的定义信息并将其实例化。相当于:Object obj = new Object();
  2. 属性注入 
    使用依赖注入,Spring按照Bean定义信息配置Bean所有属性
  3. BeanNameAware的setBeanName() 
    如果Bean类有实现org.springframework.beans.BeanNameAware接口,工厂调用Bean的setBeanName()方法传递Bean的ID。
  4. BeanFactoryAware的setBeanFactory(): 
    如果Bean类有实现org.springframework.beans.factory.BeanFactoryAware接口,工厂调用setBeanFactory()方法传入工厂自身。
  5. BeanPostProcessors的ProcessBeforeInitialization(). 
    如果有org.springframework.beans.factory.config.BeanPostProcessors和Bean关联,那么其postProcessBeforeInitialization()方法将被将被调用。
  6. initializingBean的afterPropertiesSet(): 
    如果Bean类已实现org.springframework.beans.factory.InitializingBean接口,则执行他的afterProPertiesSet()方法
  7. Bean定义文件中定义init-method: 
    可以在Bean定义文件中使用”init-method”属性设定方法名称例如:如果有以上设置的话,则执行到这个阶段,就会执行initBean()方法
  8. BeanPostProcessors的ProcessaAfterInitialization() 
    如果有任何的BeanPostProcessors实例与Bean实例关联,则执行BeanPostProcessors实例的ProcessaAfterInitialization()方法

此时,Bean已经可以被应用系统使用,并且将保留在BeanFactory中知道它不在被使用。有两种方法可以将其从BeanFactory中删除掉

  1. DisposableBean的destroy() 
    在容器关闭时,如果Bean类有实现org.springframework.beans.factory.DisposableBean接口,则执行他的destroy()方法
  2. Bean定义文件中定义destroy-method 
    在容器关闭时,可以在Bean定义文件中使用”destroy-method”属性设定方法名称.

以上就是BeanFactory维护的一个Bean的生命周期。下面这个图可能更直观一些:

spring1.0(一)spring初探

如果使用ApplicationContext来维护一个Bean的生命周期,则基本上与上边的流程相同,只不过在执行BeanNameAware的setBeanName()后,若有Bean类实现了org.springframework.context.ApplicationContextAware接口,则执行其setApplicationContext()方法,然后再进行BeanPostProcessors的processBeforeInitialization()

实际上,ApplicationContext除了向BeanFactory那样维护容器外,还提供了更加丰富的框架功能,如Bean的消息,事件处理机制等