首页 > 代码库 > 详解contextConfigLocation ---摘
详解contextConfigLocation ---摘
spring的应用初始化流程一直没有搞明白,刚刚又碰到了相关的问题。决定得好好看看这个流程。我们在开发spring的项目当中基本上都会在web.xml通过:
[html] view plaincopy
- <context-param>
- <param-name>contextConfigLocation</param-name>
- <param-value>
- /WEB-INF/conf/application-*.xml
- </param-value>
- </context-param>
来初始化各个spring的配置文件,但是我们只是知道这段代码的功能, 并不是很清楚我们配置了这段代码之后为什么就能去初始化配置文件。当然我们还会加上:
[html] view plaincopy
- <listener>
- <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
- </listener>
这一个listener,我首先就会想contextConfigLocation这个一定能在ContextLoaderListener这个类当中找到,打开了源码,这个listener是实现了ServletContextListener这个接口的,这个接口只有两个方法:
[html] view plaincopy
- public interface ServletContextListener
- extends EventListener
- {
- public abstract void contextInitialized(ServletContextEvent servletcontextevent);
- public abstract void contextDestroyed(ServletContextEvent servletcontextevent);
- }
而且它是继承了EventListener这个接口的,打开这个接口的代码让我大吃一惊,里面没有方法啥都没有:
[html] view plaincopy
- package java.util;
- public interface EventListener
- {
- }
这样找了之后没有找到,往回退到ContextLoaderListener这个类的方法上,contextInitialized方法是用来初始化上下文的:
[html] view plaincopy
- public void contextInitialized(ServletContextEvent event)
- {
- contextLoader = createContextLoader();
- contextLoader.initWebApplicationContext(event.getServletContext());
- }
[html] view plaincopy
- protected ContextLoader createContextLoader()
- {
- return new ContextLoader();
- }
[html] view plaincopy
- protected WebApplicationContext createWebApplicationContext(ServletContext servletContext, ApplicationContext parent)
- throws BeansException
- {
- Class contextClass = determineContextClass(servletContext);
- if(!(org.springframework.web.context.ConfigurableWebApplicationContext.class).isAssignableFrom(contextClass))
- {
- throw new ApplicationContextException("Custom context class [" + contextClass.getName() + "] is not of type [" + (org.springframework.web.context.ConfigurableWebApplicationContext.class).getName() + "]");
- } else
- {
- ConfigurableWebApplicationContext wac = (ConfigurableWebApplicationContext)BeanUtils.instantiateClass(contextClass);
- wac.setParent(parent);
- wac.setServletContext(servletContext);
- wac.setConfigLocation(servletContext.getInitParameter("<span style="color:#ff0000;">contextConfigLocation</span>"));
- customizeContext(servletContext, wac);
- wac.refresh();
- return wac;
- }
- }
[html] view plaincopy
- public void setConfigLocation(String configLocation)
- {
- if(configLocation != null)
- throw new UnsupportedOperationException("StaticWebApplicationContext does not support config locations");
- else
- return;
- }
StaticWebApplicationContext
class does not support this method.说是此类不支持这个方法,这下子又卡住了。又要退回去,看这句:[html] view plaincopy
- ConfigurableWebApplicationContext wac = (ConfigurableWebApplicationContext)BeanUtils.instantiateClass(contextClass);
[html] view plaincopy
- protected Class determineContextClass(ServletContext servletContext)
- throws ApplicationContextException
- {
- String contextClassName = servletContext.getInitParameter("contextClass");
- if(contextClassName != null)
- try
- {
- return ClassUtils.forName(contextClassName);
- }
- catch(ClassNotFoundException ex)
- {
- throw new ApplicationContextException("Failed to load custom context class [" + contextClassName + "]", ex);
- }
- contextClassName = defaultStrategies.getProperty((org.springframework.web.context.WebApplicationContext.class).getName());
- try
- {
- return ClassUtils.forName(contextClassName, (org.springframework.web.context.ContextLoader.class).getClassLoader());
- }
- catch(ClassNotFoundException ex)
- {
- throw new ApplicationContextException("Failed to load default context class [" + contextClassName + "]", ex);
- }
- }
[html] view plaincopy
- return instantiateClass(clazz.getDeclaredConstructor((Class[])null), null);
通过反射得到contextClass的构造方法。下面是instantiateClass方法的重载,主要是下面两句代码:
[html] view plaincopy
- ReflectionUtils.makeAccessible(ctor);
- return ctor.newInstance(args);
这时又要退回到determineContextClass 这个方法中,我们主要看:
[html] view plaincopy
- contextClassName = defaultStrategies.getProperty((org.springframework.web.context.WebApplicationContext.class).getName());
总结:通过查看这几个类的源代码,java的反射使用范围之广再次体现出来。如看了之后觉得有错误或者不同意见,欢迎提出来,我也是第一次才研究这个问题。
详解contextConfigLocation ---摘
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。