1、进入如下核心构造方法
public ClassPathXmlApplicationContext(
String[] configLocations, boolean refresh, @Nullable ApplicationContext parent)
throws BeansException {
//调用父类构造方法,进行相关的对象创建操作,初始化一些父类成员属性
super(parent);
setConfigLocations(configLocations);
if (refresh) {
refresh();
}
}
2、super
2.1、几层步入super(parent)
public AbstractApplicationContext(@Nullable ApplicationContext parent) {
this();
setParent(parent);
}
2.2、步入this()
public AbstractApplicationContext() {
//创建资源模式处理器(解析系统允许时需要的资源)
this.resourcePatternResolver = getResourcePatternResolver();
}
2.3、步入getResourcePatternResolver()
protected ResourcePatternResolver getResourcePatternResolver() {
//创建一个资源模式解析器(其实就是用来解析xml配置文件)
return new PathMatchingResourcePatternResolver(this);
}
实际上就是创建了一个PathMatchingResourcePatternResolver(this)对象。
public class PathMatchingResourcePatternResolver implements ResourcePatternResolver {
private static final Log logger = LogFactory.getLog(PathMatchingResourcePatternResolver.class);
@Nullable
private static Method equinoxResolveMethod;
private final ResourceLoader resourceLoader;
//创建ant方式的路径匹配器
private PathMatcher pathMatcher = new AntPathMatcher();
......
}
查看类图
只需要搞明白ResourceLoader就行,就是个资源加载器,就是加载xml文件、yml文件等资源的加载器,这些东西在加载时候都要实现这个接口ResourceLoader,它提供了某些统一规范。
public interface ResourceLoader {
/** Pseudo URL prefix for loading from the class path: "classpath:". */
String CLASSPATH_URL_PREFIX = ResourceUtils.CLASSPATH_URL_PREFIX;
Resource getResource(String location);
@Nullable
ClassLoader getClassLoader();
}
2.4、进入setParent(parent)方法
public void setParent(@Nullable ApplicationContext parent) {
this.parent = parent;
if (parent != null) {
//获取父容器的环境对象
Environment parentEnvironment = parent.getEnvironment();
//如果当前环境对象是可配置的环境
if (parentEnvironment instanceof ConfigurableEnvironment) {
//进行相关的合并工作
getEnvironment().merge((ConfigurableEnvironment) parentEnvironment);
}
}
}
2.5、F7往下走
public abstract class AbstractXmlApplicationContext extends AbstractRefreshableConfigApplicationContext {
//设置xml文件的验证标志,默认true
private boolean validating = true;
xml格式文件有一些规范要求,比如 dtd,xsd
3、步入setConfigLocations方法
setConfigLocations(configLocations);
作用是把路径设置到某个成员对象里面,方便后续能直接进行调用。
public void setConfigLocations(@Nullable String... locations) {
if (locations != null) {
Assert.noNullElements(locations, "Config locations must not be null");
this.configLocations = new String[locations.length];
for (int i = 0; i < locations.length; i++) {
//解析给定路径,比如路径名是spring-${username}.xml时,对文件名进行解析替换
this.configLocations[i] = resolvePath(locations[i]).trim();
}
}
else {
this.configLocations = null;
}
}
3.1、进入resolvePath方法
protected String resolvePath(String path) {
//将当前系统环境变量的属性值进行替换工作
return getEnvironment().resolveRequiredPlaceholders(path);
}
里面的方法可以看懂
记住一个类名AbstractRefreshableConfigApplicationContext,里面有个属性是
//定义配置路径
String[] configLocations;
4、refresh()核心流程
public void refresh() throws BeansException, IllegalStateException {
//同步监视器,表示刷新和销毁的操作
synchronized (this.startupShutdownMonitor) {
//忽略掉,不重要,启动阶段做标记,初始化是标记位为false,执行refresh完毕后修改为true(最后的end方法)
StartupStep contextRefresh = this.applicationStartup.start("spring.context.refresh");
// Prepare this context for refreshing.
//准备刷新上下文环境,作用就是初始化一些状态和属性,为后面的工作做准备
//程序启动标志位、上下文拓展资源加载、上下文环境准备情况验证、监听器监听事件容器初始化准备
//前戏,做容器刷前的准备工作
//1、设置容器启动时间
//2、设置活跃状态为true
//3、设置关闭状态为false
//4、获取Environment对象,并加载当前系统的属性值到Environment对象中
//准备监听器和事件的集合对象,默认为空的集合
prepareRefresh();
// Tell the subclass to refresh the internal bean factory.
//初始化beanFactory
//加载xml配置文件的属性值到当前工厂,最重要的是BeanDefinition
ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
// Prepare the bean factory for use in this context.
//完成bean工厂的某些初始化操作
prepareBeanFactory(beanFactory);
try {
// Allows post-processing of the bean factory in context subclasses.
//beanfactory配置好的后置拓展操作,由子类实现,
//可在这里提前加入自定义的beanfactorypostprocess
postProcessBeanFactory(beanFactory);
//也是启动阶段的标记操作
StartupStep beanPostProcess = this.applicationStartup.start("spring.context.beans.post-process");
// Invoke factory processors registered as beans in the context.
//执行beanfactor后置处理,spring的spi机制报障
invokeBeanFactoryPostProcessors(beanFactory);
// Register bean processors that intercept bean creation.
//注册beanpostprocessors到beanfactory中并排序,并未执行,涉及到bean生命周期执行
registerBeanPostProcessors(beanFactory);
beanPostProcess.end();
// Initialize message source for this context.
//初始化messagesource,用于消息国际化处理
initMessageSource();
// Initialize event multicaster for this context.
//初始化上下文事件广播器
initApplicationEventMulticaster();
// Initialize other special beans in specific context subclasses.
//子类实现,初始化特殊上下文子类的其他特殊bean,默认无实现
onRefresh();
// Check for listener beans and register them.
//给广播器中注册监听器,执行初期事件
registerListeners();
// Instantiate all remaining (non-lazy-init) singletons.
//初始化所有非懒加载的单例bean
finishBeanFactoryInitialization(beanFactory);
// Last step: publish corresponding event.
//完成刷新、发布上下文刷新完毕事件
finishRefresh();
}
catch (BeansException ex) {
if (logger.isWarnEnabled()) {
logger.warn("Exception encountered during context initialization - " +
"cancelling refresh attempt: " + ex);
}
// Destroy already created singletons to avoid dangling resources.
//销毁以及创建的单例bean,防止资源悬空
destroyBeans();
// Reset 'active' flag.
//取消刷新,重装active标志位为false
cancelRefresh(ex);
// Propagate exception to caller.
throw ex;
}
finally {
// Reset common introspection caches in Spring's core, since we
// might not ever need metadata for singleton beans anymore...
resetCommonCaches();
//刷新结束,设置标志位为true
contextRefresh.end();
}
}
}
4.1、准备刷新上下文方法prepareRefresh()
protected void prepareRefresh() {
// Switch to active.
//设置基础属性,设置启动日期、设置当前活跃状态
this.startupDate = System.currentTimeMillis();
this.closed.set(false);
this.active.set(true);
//日志记录
if (logger.isDebugEnabled()) {
if (logger.isTraceEnabled()) {
logger.trace("Refreshing " + this);
}
else {
logger.debug("Refreshing " + getDisplayName());
}
}
// Initialize any placeholder property sources in the context environment.
//加载初始化资源属性,交由子类实现
initPropertySources();
// Validate that all properties marked as required are resolvable:
// see ConfigurablePropertyResolver#setRequiredProperties
//校验所需要的环境变量是否都以及加载进来
getEnvironment().validateRequiredProperties();
// Store pre-refresh ApplicationListeners...
//保留未生成context时加载的listeners监听器
if (this.earlyApplicationListeners == null) {
this.earlyApplicationListeners = new LinkedHashSet<>(this.applicationListeners);
}
else {
// Reset local application listeners to pre-refresh state.
this.applicationListeners.clear();
this.applicationListeners.addAll(this.earlyApplicationListeners);
}
// Allow for the collection of early ApplicationEvents,
// to be published once the multicaster is available...
//创建applicationEvent监听事件容器
this.earlyApplicationEvents = new LinkedHashSet<>();
}
4.2、尝试扩展一下,initPropertySources();
4.2.1、创建如下类
public class MyClassPathXmlApplicationContext extends ClassPathXmlApplicationContext {
/**
* Create a new ClassPathXmlApplicationContext, loading the definitions
* from the given XML files and automatically refreshing the context.
*
* @param configLocations array of resource locations
* @throws BeansException if context creation failed
*/
public MyClassPathXmlApplicationContext(String... configLocations) throws BeansException {
super(configLocations);
}
@Override
protected void initPropertySources() {
System.out.println("扩展initPropertySources");
getEnvironment().setRequiredProperties("abc");
}
}
4.2.2、用自定义类创建容器
ApplicationContext context = new MyClassPathXmlApplicationContext("applicationContext.xml");
4.2.3、调用initPropertySources()
通过打断点的方式查看是否进入子类实现的initPropertySources()
//todo
获取beanfactory
//这俩方法均交由子类实现,大致是设置beanfactory的序列化id号,
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
refreshBeanFactory();
return getBeanFactory();
}
初始化beanfactory各种属性和容器内容
//配置工厂的标准上下文特征,例如上下文的 ClassLoader 和后处理器。
protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
// Tell the internal bean factory to use the context's class loader etc.
//设置beanfactory的类加载器
beanFactory.setBeanClassLoader(getClassLoader());
//判断是否需要加载spring-spel表达式解析,默认加载
if (!shouldIgnoreSpel) {
beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader()));
}
//添加属性编辑器用于自定义属性设置覆盖
beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, getEnvironment()));
// Configure the bean factory with context callbacks.
//添加默认注册bean前加入beanpostprocessor用于bean初始化前的操作
beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this));
//忽略一些系统级接口依赖,这些方法在上面的processor中检查回调中执行
beanFactory.ignoreDependencyInterface(EnvironmentAware.class);
beanFactory.ignoreDependencyInterface(EmbeddedValueResolverAware.class);
beanFactory.ignoreDependencyInterface(ResourceLoaderAware.class);
beanFactory.ignoreDependencyInterface(ApplicationEventPublisherAware.class);
beanFactory.ignoreDependencyInterface(MessageSourceAware.class);
beanFactory.ignoreDependencyInterface(ApplicationContextAware.class);
beanFactory.ignoreDependencyInterface(ApplicationStartupAware.class);
// BeanFactory interface not registered as resolvable type in a plain factory.
// MessageSource registered (and found for autowiring) as a bean.
//设置注册不能自动创建的bean依赖
beanFactory.registerResolvableDependency(BeanFactory.class, beanFactory);
beanFactory.registerResolvableDependency(ResourceLoader.class, this);
beanFactory.registerResolvableDependency(ApplicationEventPublisher.class, this);
beanFactory.registerResolvableDependency(ApplicationContext.class, this);
// Register early post-processor for detecting inner beans as ApplicationListeners.
//添加bean初始化后操作,如果有该单例监听器bean,就加入到上下文监听器容器中
beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(this));
// Detect a LoadTimeWeaver and prepare for weaving, if found.
//加入AspectJ支持
if (!NativeDetector.inNativeImage() && beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
// Set a temporary ClassLoader for type matching.
beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
}
// Register default environment beans.
//检查并加入一些默认的初始化环境bean
if (!beanFactory.containsLocalBean(ENVIRONMENT_BEAN_NAME)) {
beanFactory.registerSingleton(ENVIRONMENT_BEAN_NAME, getEnvironment());
}
if (!beanFactory.containsLocalBean(SYSTEM_PROPERTIES_BEAN_NAME)) {
beanFactory.registerSingleton(SYSTEM_PROPERTIES_BEAN_NAME, getEnvironment().getSystemProperties());
}
if (!beanFactory.containsLocalBean(SYSTEM_ENVIRONMENT_BEAN_NAME)) {
beanFactory.registerSingleton(SYSTEM_ENVIRONMENT_BEAN_NAME, getEnvironment().getSystemEnvironment());
}
if (!beanFactory.containsLocalBean(APPLICATION_STARTUP_BEAN_NAME)) {
beanFactory.registerSingleton(APPLICATION_STARTUP_BEAN_NAME, getApplicationStartup());
}
}
SpEL的支持
SpEL使用#{…}作为界定符,所有在大括号中的字符都可认为是spel
invokeBeanFactoryPostProcessors():激活beanfactory的后置处理器
beanFactory作为spring中容器功能的基础,用于存放已经加载的bean,为了保证程序的可扩展性,spring对beanfactory做了很多扩展,比如这个后置处理器。
这一步的功能主要时激活各种beanFactoryPostProcessors()
registerBeanPostProcessors:注册各种beanpostprocessor
initMessageSource:初始化各种消息资源。
提取配置中定义的各种messagesource,并将其记录在spring容器中,也就是abstractApplicationContext中。如果用户没有设置资源属性文件,spring提供了默认的配置delegatingMessageSource。
protected void initMessageSource() {
ConfigurableListableBeanFactory beanFactory = getBeanFactory();
if (beanFactory.containsLocalBean(MESSAGE_SOURCE_BEAN_NAME)) {
//获取自定义资源文件。这里使用了硬编码,默认资源文件为MessageSource,否则获取不到
this.messageSource = beanFactory.getBean(MESSAGE_SOURCE_BEAN_NAME, MessageSource.class);
// Make MessageSource aware of parent MessageSource.
//
if (this.parent != null && this.messageSource instanceof HierarchicalMessageSource) {
HierarchicalMessageSource hms = (HierarchicalMessageSource) this.messageSource;
if (hms.getParentMessageSource() == null) {
// Only set parent context as parent MessageSource if no parent MessageSource
// registered already.
hms.setParentMessageSource(getInternalParentMessageSource());
}
}
if (logger.isTraceEnabled()) {
logger.trace(“Using MessageSource [” + this.messageSource + “]”);
}
}
else {
// Use empty MessageSource to be able to accept getMessage calls.
//如果用户没有定义就使用默认的资源文件
DelegatingMessageSource dms = new DelegatingMessageSource();
dms.setParentMessageSource(getInternalParentMessageSource());
this.messageSource = dms;
beanFactory.registerSingleton(MESSAGE_SOURCE_BEAN_NAME, this.messageSource);
if (logger.isTraceEnabled()) {
logger.trace(“No '” + MESSAGE_SOURCE_BEAN_NAME + “’ bean, using [” + this.messageSource + “]”);
}
}
}
initAplicationEventMulticaster:初始化事件监听
protected void initApplicationEventMulticaster() {
ConfigurableListableBeanFactory beanFactory = getBeanFactory();
//如果用户自定义了事件广播器,就使用用户自定义的
if (beanFactory.containsLocalBean(APPLICATION_EVENT_MULTICASTER_BEAN_NAME)) {
this.applicationEventMulticaster =
beanFactory.getBean(APPLICATION_EVENT_MULTICASTER_BEAN_NAME, ApplicationEventMulticaster.class);
if (logger.isTraceEnabled()) {
logger.trace(“Using ApplicationEventMulticaster [” + this.applicationEventMulticaster + “]”);
}
}
else {
//否则使用默认的事件广播器SimpleApplicationEventMulticaster
this.applicationEventMulticaster = new SimpleApplicationEventMulticaster(beanFactory);
beanFactory.registerSingleton(APPLICATION_EVENT_MULTICASTER_BEAN_NAME, this.applicationEventMulticaster);
if (logger.isTraceEnabled()) {
logger.trace(“No '” + APPLICATION_EVENT_MULTICASTER_BEAN_NAME + "’ bean, using " +
“[” + this.applicationEventMulticaster.getClass().getSimpleName() + “]”);
}
}
}
SimpleApplicationEventMulticaster里面有一段代码,如下:
public void multicastEvent(final ApplicationEvent event, @Nullable ResolvableType eventType) {
ResolvableType type = (eventType != null ? eventType : resolveDefaultEventType(event));
Executor executor = getTaskExecutor();
for (ApplicationListener<?> listener : getApplicationListeners(event, type)) {
if (executor != null) {
executor.execute(() -> invokeListener(listener, event));
}
else {
invokeListener(listener, event);
}
}
}
当spring事件产生的时候,默认使用multicastEvent方法来广播事件,遍历所有的监听器,并使用监听器中的onapplicationevent方法来进行监听事件的处理(通过invokelistener()方法激活监听方法)。而对于每个监听器来说,其实都可以获取到产生的事件。
onfresh()
registerlistener():注册监听器
分为如下三步:
一、注册硬编码注册的监听器
二、注册配置注册的监听器
三、发布之前的监听事件
代码如下:
protected void registerListeners() {
// Register statically specified listeners first.
//注册硬编码方式注册的监听器
for (ApplicationListener<?> listener : getApplicationListeners()) {
getApplicationEventMulticaster().addApplicationListener(listener);
}
// Do not initialize FactoryBeans here: We need to leave all regular beans
// uninitialized to let post-processors apply to them!
//配置文件注册的监听处理器
String[] listenerBeanNames = getBeanNamesForType(ApplicationListener.class, true, false);
for (String listenerBeanName : listenerBeanNames) {
getApplicationEventMulticaster().addApplicationListenerBean(listenerBeanName);
}
// Publish early application events now that we finally have a multicaster…
//发布前保存的待发布事件
Set earlyEventsToProcess = this.earlyApplicationEvents;
this.earlyApplicationEvents = null;
if (!CollectionUtils.isEmpty(earlyEventsToProcess)) {
for (ApplicationEvent earlyEvent : earlyEventsToProcess) {
getApplicationEventMulticaster().multicastEvent(earlyEvent);
}
}
}
finishbeanfactoryinitialization:beanfactory的收尾工作
目的:结束beanfactory的初始化工作,初始化所有剩余的单例bean
protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) {
// Initialize conversion service for this context.
//对conversionservice进行设置,
//如果beanfactory加载了beanname为conversionservice的bean并且类型为conversionservice,
//则设置为beanfactory的conversionservice
if (beanFactory.containsBean(CONVERSION_SERVICE_BEAN_NAME) &&
beanFactory.isTypeMatch(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class)) {
beanFactory.setConversionService(
beanFactory.getBean(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class));
}
// Register a default embedded value resolver if no BeanFactoryPostProcessor
// (such as a PropertySourcesPlaceholderConfigurer bean) registered any before:
// at this point, primarily for resolution in annotation attribute values.
if (!beanFactory.hasEmbeddedValueResolver()) {
beanFactory.addEmbeddedValueResolver(strVal -> getEnvironment().resolvePlaceholders(strVal));
}
// Initialize LoadTimeWeaverAware beans early to allow for registering their transformers early.
String[] weaverAwareNames = beanFactory.getBeanNamesForType(LoadTimeWeaverAware.class, false, false);
for (String weaverAwareName : weaverAwareNames) {
getBean(weaverAwareName);
}
// Stop using the temporary ClassLoader for type matching.
beanFactory.setTempClassLoader(null);
// Allow for caching all bean definition metadata, not expecting further changes.
//冻结所有bean的定义,说明注册的bean定义将不再被修改或任何进一步处理
beanFactory.freezeConfiguration();
// Instantiate all remaining (non-lazy-init) singletons.
//初始化所有剩余的非懒加载单例bean
beanFactory.preInstantiateSingletons();
}
finishRefresh()完成刷新
protected void finishRefresh() {
// Clear context-level resource caches (such as ASM metadata from scanning).
//清除资源缓存
clearResourceCaches();
// Initialize lifecycle processor for this context.
//应用启动或停止时,通过lifestyleprocessor来与所有声明的bean周期做状态更新
//而在lifecycleprocessor的使用前首先需要初始化,这里进行初始化
initLifecycleProcessor();
// Propagate refresh to lifecycle processor first.
//启动所有实现lifecycleprocessor接口的bean
getLifecycleProcessor().onRefresh();
// Publish the final event.
//当完成applicationcontext初始化后,通过spring中的事件发布机制来发出ContextRefreshedEvent中的事件,
//以保证对应的事件监听器可以做进一步的逻辑处理
publishEvent(new ContextRefreshedEvent(this));
// Participate in LiveBeansView MBean, if active.
//注册ApplicationContext
if (!NativeDetector.inNativeImage()) {
LiveBeansView.registerApplicationContext(this);
}
}