zoukankan      html  css  js  c++  java
  • 怎么获取Spring的ApplicationContext

    在 WEB 开发中,可能会非常少须要显示的获得 ApplicationContext 来得到由 Spring 进行管理的某些 Bean, 今天我就遇到了,在这里和大家分享一下, WEB 开发中,怎么获取 ApplicationContext 

    一       要想怎么获取 ApplicationContext, 首先必须明确 Spring 内部 ApplicationContext 是如何存储的。以下我们来跟踪一下源代码 

    首先:从大家最熟悉的地方開始 

    Java代码  收藏代码
    1. <listener>  
    2.      <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>  
    3.   </listener>  

     上面这一段,大家非常熟悉吧。好,让我们看一看它究竟实现了些啥。

     

     

    Java代码  收藏代码
    1. public class ContextLoaderListener<span style="color: #ff0000;"> <span style="color: #000000;">implements ServletContextListener</span></span> {  
    2.   
    3.     private ContextLoader contextLoader;  
    4.   
    5.     /** 
    6.      * Initialize the root web application context. 
    7.      */  
    8.     public void <span style="color: #000000;">contextInitialized</span>(ServletContextEvent event) {  
    9.         this.contextLoader = createContextLoader();  
    10.         this.contextLoader.<span style="color: #000000;">initWebApplicationContext</span>(event.getServletContext());  
    11.     }//以下的略  

     
    显然,ContextLoaderListener实现了ServeletContextListenet,在ServletContext初始化的时候,会进行Spring的初始化,大家肯定会想,Spring的初始化应该与ServletContext有一定关系吧?有关系吗?接下来让我们进入

    ContextLoader.initWebApplicationContext方法

     

     

    Java代码  收藏代码
    1. public WebApplicationContext initWebApplicationContext(ServletContext servletContext)  
    2.             throws IllegalStateException, BeansException {  
    3.   
    4.         //从ServletContext中查找,是否存在以<span style="color: #000000;">WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE为Key的值</span>  
    Java代码  收藏代码
    1. if (servletContext.getAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE) != null){  
    2.     throw new IllegalStateException(  
    3.             "Cannot initialize context because there is already a root application context present - " +  
    4.             "check whether you have multiple ContextLoader* definitions in your web.xml!");  
    5. }  
    6.   
    7.           
    8. try {  
    9.     // Determine parent for root web application context, if any.  
    10.     ApplicationContext parent = loadParentContext(servletContext);  
    11.   
    12.     // it is available on ServletContext shutdown.  
    13.     this.context = createWebApplicationContext(servletContext, parent);  
    14.     //将ApplicationContext放入ServletContext中,其key为<span style="color: #000000;">WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE</span>  
    Java代码  收藏代码
    1. servletContext.setAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE, this.context);
    2.             //将ApplicationContext放入ContextLoader的全局静态常量Map中,当中key为:<span style="color: #000000;">Thread.currentThread().getContextClassLoader()即当前线程类载入器</span>  
    Java代码  收藏代码
    1.     currentContextPerThread.put(Thread.currentThread().getContextClassLoader(), this.context);  
    2.   
    3.     return this.context;  
    4. }  

     从上面的代码大家应该明确了Spring初始化之后,将ApplicationContext存到在了两个地方,那么是不是意味着我们能够通过两种方式取得ApplicationContext?

     

    第一种获取方式:


     注意:WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE = WebApplicationContext.class.getName() + ".ROOT";

    即为 "org.springframework.web.context.WebApplicationContext.ROOT"

     

    那么咱们是不是能够这样获得ApplicationContext:

      

    Java代码  收藏代码
    1. request.getSession().getServletContext().getAttribute("org.springframework.web.context.WebApplicationContext.ROOT")  

     确实能够,并且我们想到这样的方法的时候,Spring早就提供给我们接口了:

     

    Java代码  收藏代码
    1. public abstract class WebApplicationContextUtils {  
    2.       
    3.            
    4. public static WebApplicationContext getRequiredWebApplicationContext(ServletContext sc)  
    5.         throws IllegalStateException {  
    6.   
    7.        WebApplicationContext wac = getWebApplicationContext(sc);
    8.         if (wac == null) {  
    9.             throw new IllegalStateException("No WebApplicationContext found: no ContextLoaderListener registered?");  
    10.         }  
    11.         return wac;  
    12.     }  

     getWebApplicationContext方法例如以下:

     

     

    Java代码  收藏代码
    1. public static WebApplicationContext getWebApplicationContext(ServletContext sc) {  
    2.         return getWebApplicationContext(sc, WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE);  
    3.     }  

     哈哈,明确了吧,它和我们自己实现的方法是一样的。

    这样的方法一般用在你自定义了一个Listener而且实现了ServletContextListener接口,在web.xml中你须要把这个Listener配置好

    	<!--
    		用于做初始化工作的监听器,一定要配置到Spring的ContextLoaderListener之后,由于要用到Spring的容器对象
    	-->
    
    	<listener>
    	  <listener-class>cn.itcast.oa.Utils.InitListener</listener-class>
    	</listener>
    实现这个监听器的类例如以下:

    public class InitListener implements ServletContextListener {
    
    //启动时,为最大的作用于初始化
    	public void contextInitialized(ServletContextEvent sce) {
    		// 获取容器与相关的Service对象
    		ApplicationContext ac = WebApplicationContextUtils.getWebApplicationContext(sce.getServletContext());
    		PrivilegeService privilegeService = (PrivilegeService) ac.getBean("privilegeServiceImpl");
    
    		// 准备数据:topPrivilegeList
    		List<Privilege> topPrivilegeList = privilegeService.findTopList();
    		sce.getServletContext().setAttribute("topPrivilegeList", topPrivilegeList);
    		System.out.println("------------> 已准备数据 <------------");
    	}
    
    	public void contextDestroyed(ServletContextEvent arg0) {
    
    	}
    }
    


    另一种简单的

    代码:
    ApplicationContext ac = new FileSystemXmlApplicationContext("applicationContext.xml");
    ac.getBean("beanId");
    说明:这样的方式适用于採用Spring框架的独立应用程序,须要程序通过配置文件手工初始化Spring的情况。

    然后。。。。。获取的这个ApplicationContext对象后你就能够getBean()了。。。。。啦啦

    參考  http://www.blogjava.net/Todd/archive/2010/04/22/295112.html


  • 相关阅读:
    深入浅出Blazor webassembly之程序配置
    深入浅出Blazor webassembly之通过CascadingValue组件实现向子级组件传值
    深入浅出Blazor webassembly之数据绑定写法
    深入浅出Blazor webassembly之浏览器WSAM性能测试
    重构的秘诀:消除重复,清晰意图
    在多数据源中对部分数据表使用shardingsphere进行分库分表
    logstach http input
    Addax 备忘
    WIN10下面0x00000bcb共享打印机无法连接怎么办?
    Calcite(二): 从list到tree的转换1
  • 原文地址:https://www.cnblogs.com/yxwkf/p/4067248.html
Copyright © 2011-2022 走看看