web项目中获取spring的bean对象

   Spring是一个轻量级的控制反转(IoC)和面向切面(AOP)的容器框架,如何在程序中不通过注解的形式(@Resource、@Autowired)获取Spring配置的bean呢?

   Bean工厂(com.springframework.beans.factory.BeanFactory)是Spring框架最核心的接口,它提供了高级IoC的配置机制。BeanFactory使管理不同类型的Java对象成为可能,应用上下文(com.springframework.context.ApplicationContext)建立在BeanFactory基础之上,提供了更多面向应用的功能,它提供了国际化支持和框架事件体系,更易于创建实际应用。我们一般称BeanFactory为IoC容器,而称ApplicationContext为应用上下文。但有时为了行文方便,我们也将ApplicationContext称为Spring容器。
   对于两者的用途,我们可以进行简单划分:BeanFactory是Spring框架的基础设施,面向Spring本身;ApplicationContext面向使用Spring框架的开发者,几乎所有的应用场合我们都直接使用ApplicationContext而非底层的BeanFactory。

工厂方式:

Resource resource = new ClassPathResource("applicationContext.xml");
BeanFactory factory = new XmlBeanFactory(resource);
factory.getBean(strName);

   ApplicationContext的初始化和BeanFactory有一个重大的区别:BeanFactory在初始化容器时,并未实例化Bean,直到第一次访问某个Bean时才实例目标Bean;而ApplicationContext则在初始化应用上下文时就实例化所有单实例的Bean。因此ApplicationContext的初始化时间会比BeanFactory稍长一些

    附加信息,简要说明Spring什么时候实例化bean,首先要分2种情况
  第一:如果你使用BeanFactory作为Spring Bean的工厂类,则所有的bean都是在第一次使用该Bean的时候实例化
  第二:如果你使用ApplicationContext作为Spring Bean的工厂类,则又分为以下几种情况:
       (1):如果bean的scope是singleton的,并且lazy-init为false(默认是false,所以可以不用设置),则 ApplicationContext启动的时候就实例化该Bean,并且将实例化的Bean放在一个map结构的缓存中,下次再使用该Bean的时候, 直接从这个缓存中取
       (2):如果bean的scope是singleton的,并且lazy-init为true,则该Bean的实例化是在第一次使用该Bean的时候进行实例化
       (3):如果bean的scope是prototype的,则该Bean的实例化是在第一次使用该Bean的时候进行实例化

要获取XML中配置的Bean,最关键的是获取org.springframework.context.ApplicationContext

方法一:获取ApplicationContext的方法(多用于java工程)

ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml" );
或者
ApplicationContext context = new FileSystemXmlApplicationContext("D:/Workspaces/MyEclipse Professional 2014/dubbo-customer/src/main/resources/applicationContext.xml" );
这种方式实例化applicationContext是非常耗时的,这种方式适用于采用Spring框架的独立应用程序,仅仅推荐使用在程序需要通过配置文件手工初始化Spring的情况。
   ApplicationContext的主要实现类是ClassPathXmlApplicationContext和FileSystemXmlApplicationContext,前者默认从类路径加载配置文件,后者默认从文件系统中装载配置文件。

方法二:获取ApplicationContext的方法(多用于web项目)

   通过Spring提供的工具类获取ApplicationContext对象,专为web工程定制的方法,推荐Web项目中使用。例如:
ServletContext sc = request.getSession().getServletContext(); 
ApplicationContext ac1 = WebApplicationContextUtils  .getRequiredWebApplicationContext(sc)   
ApplicationContext ac2 = WebApplicationContextUtils  .getWebApplicationContext(sc)  
ac1.getBean("beanId");  
ac2.getBean("beanId");

   其中,获取ServletContext对象时的request.getSession().getServletContext()可以改成this.getServletContext()。

   注意:当使用WebApplicationContextUtils获取ApplicationContext实例时,需要在web.xml配置文件中添加org.springframework.web.context.ContextLoaderListener监听器,否则获取不到ApplicationContext对象,返回Null。

  web.xml配置:

 

<listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>classpath:applicationContext.xml</param-value>
</context-param>

方法三:继承自抽象类ApplicationObjectSupport

说明:抽象类ApplicationObjectSupport提供getApplicationContext()方法,可以方便的获取到ApplicationContext。
Spring初始化时,会通过该抽象类的setApplicationContext(ApplicationContext context)方法将ApplicationContext 对象注入。

方法四:继承自抽象类WebApplicationObjectSupport

通过继承org.springframework.web.context.support.WebApplicationObjectSupport使用getWebApplicationContext() 获取到org.springframework.web.context.WebApplicationContext
   由于Web应用比一般的应用拥有更多的特性,因此WebApplicationContext扩展了ApplicationContext。WebApplicationContext定义了一个常量ROOT_WEB_APPLICATION_ CONTEXT_ATTRIBUTE,在上下文启动时,WebApplicationContext实例即以此为键放置在ServletContext的属性列表中,因此我们可以在java类中
直接通过以下语句从Web容器中获取WebApplicationContext:

ServletContext sc = this.getServletContext();
WebApplicationContext wac = (WebApplicationContext)sc.getAttribute(
WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE);
DemoService demoService = (DemoService)wac.getBean("demoService");

方法五:实现接口ApplicationContextAware(推荐)

实现该接口的setApplicationContext(ApplicationContext context)方法,并保存ApplicationContext 对象。Spring初始化时,会通过该方法将ApplicationContext 对象注入。

import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;

public class AppContext implements ApplicationContextAware{

    private static ApplicationContext applicationContext;
    /**
     * 当继承了ApplicationContextAware类之后,那么程序在调用
     * getBean(String)的时候会自动调用该方法,不用自己操作
     */
    @Override
    public void setApplicationContext(
            org.springframework.context.ApplicationContext applicationContext)
            throws BeansException {
        this.applicationContext= applicationContext;
    }

    public Object getBean(String beanName){
        return this.applicationContext.getBean(beanName);
    }
}

需要在配置文件中注入该类的bean

<bean class="com.cn.customer.AppContext"/>
然后在java类中获取spring的bean
AppContext aContext = new AppContext();
DemoService demoService = (DemoService)aContext.getBean("demoService");
原文地址:https://www.cnblogs.com/aqsunkai/p/6690605.html