这篇文章主要是源码的一个整理:将来要是忘了可以看看:
这是spring的启动listener:
/*** Eclipse Class Decompiler plugin, copyright (c) 2012 Chao Chen (cnfree2000@hotmail.com) ***/
package org.springframework.web.context;
import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
public class ContextLoaderListener extends ContextLoader implements
ServletContextListener {
private ContextLoader contextLoader;
public ContextLoaderListener() {
}
public ContextLoaderListener(WebApplicationContext context) {
super(context);
}
public void contextInitialized(ServletContextEvent event) {
this.contextLoader = createContextLoader();
if (this.contextLoader == null) {
this.contextLoader = this;
}
this.contextLoader.initWebApplicationContext(event.getServletContext());
}
@Deprecated
protected ContextLoader createContextLoader() {
return null;
}
@Deprecated
public ContextLoader getContextLoader() {
return this.contextLoader;
}
public void contextDestroyed(ServletContextEvent event) {
if (this.contextLoader != null) {
this.contextLoader.closeWebApplicationContext(event
.getServletContext());
}
ContextCleanupListener.cleanupAttributes(event.getServletContext());
}
}
这是初始化方法
/*** Eclipse Class Decompiler plugin, copyright (c) 2012 Chao Chen (cnfree2000@hotmail.com) ***/
package org.springframework.web.context;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Properties;
import java.util.concurrent.ConcurrentHashMap;
import javax.servlet.ServletContext;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.access.BeanFactoryLocator;
import org.springframework.beans.factory.access.BeanFactoryReference;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextException;
import org.springframework.context.ApplicationContextInitializer;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.access.ContextSingletonBeanFactoryLocator;
import org.springframework.core.GenericTypeResolver;
import org.springframework.core.annotation.AnnotationAwareOrderComparator;
import org.springframework.core.env.ConfigurableEnvironment;
import org.springframework.core.io.ClassPathResource;
import org.springframework.core.io.support.PropertiesLoaderUtils;
import org.springframework.util.Assert;
import org.springframework.util.ClassUtils;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.context.support.WebApplicationContextUtils;
public class ContextLoader {
public static final String CONTEXT_CLASS_PARAM = "contextClass";
public static final String CONTEXT_ID_PARAM = "contextId";
public static final String CONTEXT_INITIALIZER_CLASSES_PARAM = "contextInitializerClasses";
public static final String CONFIG_LOCATION_PARAM = "contextConfigLocation";
public static final String LOCATOR_FACTORY_SELECTOR_PARAM = "locatorFactorySelector";
public static final String LOCATOR_FACTORY_KEY_PARAM = "parentContextKey";
private static final String DEFAULT_STRATEGIES_PATH = "ContextLoader.properties";
private static final Properties defaultStrategies;
private static final Map<ClassLoader, WebApplicationContext> currentContextPerThread;
private static volatile WebApplicationContext currentContext;
private WebApplicationContext context;
private BeanFactoryReference parentContextRef;
static {
try {
ClassPathResource resource = new ClassPathResource(
"ContextLoader.properties", ContextLoader.class);
defaultStrategies = PropertiesLoaderUtils.loadProperties(resource);
} catch (IOException ex) {
throw new IllegalStateException(
"Could not load 'ContextLoader.properties': "
+ ex.getMessage());
}
currentContextPerThread = new ConcurrentHashMap(1);
}
public ContextLoader() {
}
public ContextLoader(WebApplicationContext context) {
this.context = context;
}
<span style="color:#ff0000;">public WebApplicationContext initWebApplicationContext(
ServletContext servletContext) {
if (servletContext
.getAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE) != null) {
throw new IllegalStateException(
"Cannot initialize context because there is already a root application context present - check whether you have multiple ContextLoader* definitions in your web.xml!");
}
Log logger = LogFactory.getLog(ContextLoader.class);
servletContext.log("Initializing Spring root WebApplicationContext");
if (logger.isInfoEnabled()) {
logger.info("Root WebApplicationContext: initialization started");
}
long startTime = System.currentTimeMillis();
try {
if (this.context == null) {
this.context = createWebApplicationContext(servletContext);
}
if (this.context instanceof ConfigurableWebApplicationContext) {
configureAndRefreshWebApplicationContext(
(ConfigurableWebApplicationContext) this.context,
servletContext);
}
servletContext
.setAttribute(
WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE,
this.context);
ClassLoader ccl = Thread.currentThread().getContextClassLoader();
if (ccl == ContextLoader.class.getClassLoader()) {
currentContext = this.context;
} else if (ccl != null) {
currentContextPerThread.put(ccl, this.context);
}
if (logger.isDebugEnabled()) {
logger.debug("Published root WebApplicationContext as ServletContext attribute with name ["
+ WebApplicationContext.<span style="background-color: rgb(192, 192, 192);">ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE</span>
+ "]");
}
if (logger.isInfoEnabled()) {
long elapsedTime = System.currentTimeMillis() - startTime;
logger.info("Root WebApplicationContext: initialization completed in "
+ elapsedTime + " ms");
}
return this.context;
} catch (RuntimeException ex) {
logger.error("Context initialization failed", ex);
servletContext
.setAttribute(
WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE,
ex);
throw ex;
} catch (Error err) {
logger.error("Context initialization failed", err);
servletContext
.setAttribute(
WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE,
err);
throw err;
}
}
</span>
protected WebApplicationContext createWebApplicationContext(
ServletContext sc) {
Class contextClass = determineContextClass(sc);
if (!(ConfigurableWebApplicationContext.class
.isAssignableFrom(contextClass))) {
throw new ApplicationContextException("Custom context class ["
+ contextClass.getName() + "] is not of type ["
+ ConfigurableWebApplicationContext.class.getName() + "]");
}
ConfigurableWebApplicationContext wac = (ConfigurableWebApplicationContext) BeanUtils
.instantiateClass(contextClass);
return wac;
}
@Deprecated
protected WebApplicationContext createWebApplicationContext(
ServletContext sc, ApplicationContext parent) {
return createWebApplicationContext(sc);
}
protected void configureAndRefreshWebApplicationContext(
ConfigurableWebApplicationContext wac, ServletContext sc) {
if (ObjectUtils.identityToString(wac).equals(wac.getId())) {
String idParam = sc.getInitParameter("contextId");
if (idParam != null) {
wac.setId(idParam);
} else if ((sc.getMajorVersion() == 2)
&& (sc.getMinorVersion() < 5)) {
wac.setId(ConfigurableWebApplicationContext.APPLICATION_CONTEXT_ID_PREFIX
+ ObjectUtils.getDisplayString(sc
.getServletContextName()));
} else {
wac.setId(ConfigurableWebApplicationContext.APPLICATION_CONTEXT_ID_PREFIX
+ ObjectUtils.getDisplayString(sc.getContextPath()));
}
}
ApplicationContext parent = loadParentContext(sc);
wac.setParent(parent);
wac.setServletContext(sc);
String initParameter = sc.getInitParameter("contextConfigLocation");
if (initParameter != null) {
wac.setConfigLocation(initParameter);
}
customizeContext(sc, wac);
wac.refresh();
}
protected Class<?> determineContextClass(ServletContext servletContext) {
String contextClassName = servletContext
.getInitParameter("contextClass");
if (contextClassName != null) {
try {
return ClassUtils.forName(contextClassName,
ClassUtils.getDefaultClassLoader());
} catch (ClassNotFoundException ex) {
throw new ApplicationContextException(
"Failed to load custom context class ["
+ contextClassName + "]", ex);
}
}
contextClassName = defaultStrategies
.getProperty(WebApplicationContext.class.getName());
try {
return ClassUtils.forName(contextClassName,
ContextLoader.class.getClassLoader());
} catch (ClassNotFoundException ex) {
throw new ApplicationContextException(
"Failed to load default context class [" + contextClassName
+ "]", ex);
}
}
protected List<Class<ApplicationContextInitializer<ConfigurableApplicationContext>>> determineContextInitializerClasses(
ServletContext servletContext) {
String classNames = servletContext
.getInitParameter("contextInitializerClasses");
List classes = new ArrayList();
if (classNames != null) {
for (String className : StringUtils.tokenizeToStringArray(
classNames, ",")) {
try {
Class clazz = ClassUtils.forName(className,
ClassUtils.getDefaultClassLoader());
Assert.isAssignable(
ApplicationContextInitializer.class,
clazz,
"class ["
+ className
+ "] must implement ApplicationContextInitializer");
classes.add(clazz);
} catch (ClassNotFoundException ex) {
throw new ApplicationContextException(
"Failed to load context initializer class ["
+ className + "]", ex);
}
}
}
return classes;
}
protected void customizeContext(ServletContext servletContext,
ConfigurableWebApplicationContext applicationContext) {
List initializerClasses = determineContextInitializerClasses(servletContext);
if (initializerClasses.size() == 0) {
return;
}
ArrayList initializerInstances = new ArrayList();
for (Class initializerClass : initializerClasses) {
Class contextClass = applicationContext.getClass();
Class initializerContextClass = GenericTypeResolver
.resolveTypeArgument(initializerClass,
ApplicationContextInitializer.class);
Assert.isAssignable(
initializerContextClass,
contextClass,
String.format(
"Could not add context initializer [%s] as its generic parameter [%s] is not assignable from the type of application context used by this context loader [%s]",
new Object[] { initializerClass.getName(),
initializerContextClass, contextClass }));
initializerInstances.add((ApplicationContextInitializer) BeanUtils
.instantiateClass(initializerClass));
}
Collections.sort(initializerInstances,
new AnnotationAwareOrderComparator());
WebApplicationContextUtils.initServletPropertySources(
applicationContext.getEnvironment().getPropertySources(),
servletContext);
for (ApplicationContextInitializer initializer : initializerInstances)
initializer.initialize(applicationContext);
}
protected ApplicationContext loadParentContext(ServletContext servletContext) {
ApplicationContext parentContext = null;
String locatorFactorySelector = servletContext
.getInitParameter("locatorFactorySelector");
String parentContextKey = servletContext
.getInitParameter("parentContextKey");
if (parentContextKey != null) {
BeanFactoryLocator locator = ContextSingletonBeanFactoryLocator
.getInstance(locatorFactorySelector);
Log logger = LogFactory.getLog(ContextLoader.class);
if (logger.isDebugEnabled()) {
logger.debug("Getting parent context definition: using parent context key of '"
+ parentContextKey + "' with BeanFactoryLocator");
}
this.parentContextRef = locator.useBeanFactory(parentContextKey);
parentContext = (ApplicationContext) this.parentContextRef
.getFactory();
}
return parentContext;
}
public void closeWebApplicationContext(ServletContext servletContext) {
servletContext.log("Closing Spring root WebApplicationContext");
label34: ClassLoader ccl;
try {
if (!(this.context instanceof ConfigurableWebApplicationContext)) break label34;
((ConfigurableWebApplicationContext)this.context).close();
}
finally
{
ClassLoader ccl = Thread.currentThread().getContextClassLoader();
if (ccl == ContextLoader.class.getClassLoader()) {
currentContext = null;
}
else if (ccl != null) {
currentContextPerThread.remove(ccl);
}
servletContext.removeAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE);
if (this.parentContextRef != null)
this.parentContextRef.release();
}
}
public static WebApplicationContext getCurrentWebApplicationContext() {
ClassLoader ccl = Thread.currentThread().getContextClassLoader();
if (ccl != null) {
WebApplicationContext ccpt = (WebApplicationContext) currentContextPerThread
.get(ccl);
if (ccpt != null) {
return ccpt;
}
}
return currentContext;
}
}
想要跟清楚的了解,把tomcat的listener,fliter弄明白就可以了