废话不多说,直接开始上源码
ClassPathXmlApplicationContext ioc = new ClassPathXmlApplicationContext(“classpath:spring.xml”);
public ClassPathXmlApplicationContext(
String[] configLocations, boolean refresh, @Nullable ApplicationContext parent)
throws BeansException {
//这个super方法会连续调用三次父类构造器,目的就是为了初始话父类,和获取资源加载器,和设置父子容器
super(parent);
// 根据提供的路径,处理成配置文件数组(以分号、逗号、空格、tab、换行符分割)
setConfigLocations(configLocations);
if (refresh) {
refresh();
}
}
继续跟进super方法可得
/**
* 这个this() 主要就是初始化资源加载器
* public AbstractApplicationContext() {
* this.resourcePatternResolver = getResourcePatternResolver();
* }
*/
this();
//设置父子容器,
setParent(parent);
最最重点的方法来了,refresh(); 该方法体现了整个ioc容器的生命周期
@Override
public void refresh() throws BeansException, IllegalStateException {
synchronized (this.startupShutdownMonitor) {
// Prepare this context for refreshing.
//准备刷新上下文环境
prepareRefresh();
// Tell the subclass to refresh the intern+al bean factory.
//获取告诉子类初始化Bean工厂
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后置处理器,留给子类去实现该接口
postProcessBeanFactory(beanFactory);
// Invoke factory processors registered as beans in the context.
//调用我们的bean工厂的后置处理器,1.将class扫描成bean定义,2.bean工厂的后置处理器调用
invokeBeanFactoryPostProcessors(beanFactory);
// Register bean processors that intercept bean creation
// 调用我们bean的后置处理器
registerBeanPostProcessors(beanFactory);
// Initialize message source for this context.
//初始化国际化资源处理器
initMessageSource();
// Initialize event multicaster for this context.
//创建事件多播器
initApplicationEventMulticaster();
// Initialize other special beans in specific context subclasses.
//这个方法同样也是留给子类实现的springboot也是从这个方法进行启动tomcat的
onRefresh();
// Check for listener beans and register them.
//把我们的事件监听器注册到多播器上
registerListeners();
// Instantiate all remaining (non-lazy-init) singletons.
//实例化我们剩余的单例bean ----该方法体现bean的加载过程
finishBeanFactoryInitialization(beanFactory);
// Last step: publish corresponding event.
//最后容器创建完成,容器刷新,主要发布刷新事件(spring cloud也是从这里启动的)
finishRefresh();
}
首先分析一下prepareRefresh(),都准备了哪些上下文环境
protected void prepareRefresh() {
// 设置当前系统时间,
this.startupDate = System.currentTimeMillis();
//设置关闭状态false
this.closed.set(false);
//设置容器正在激活true
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.
/**
* 初始化资源加载器,空方法,用于子类扩展
* protected void initPropertySources() {
* // For subclasses: do nothing by default.
* }
*/
initPropertySources();
// Validate that all properties marked as required are resolvable:
// see ConfigurablePropertyResolver#setRequiredProperties
//用于校验我们容器启动必须依赖的环境变量的值
getEnvironment().validateRequiredProperties();
// Store pre-refresh ApplicationListeners...
//如果不存在早期的事件监听器容器,则创建一个事件监听器容器
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...
//创建一个事件容器环境,注:earlyApplicationListeners是监听器容器,earlyApplicationEvents是事件容器
this.earlyApplicationEvents = new LinkedHashSet<>();
}
继续跟进validateRequiredProperties() 方法,可以看出主要是验证一些必要的属性是否为null
@Override
public void validateRequiredProperties() {
MissingRequiredPropertiesException ex = new MissingRequiredPropertiesException();
for (String key : this.requiredProperties) {
if (this.getProperty(key) == null) {
ex.addMissingRequiredProperty(key);
}
}
if (!ex.getMissingRequiredProperties().isEmpty()) {
throw ex;
}
}
由于篇幅原因,这篇文章就先介绍到这里,太长太冗余,你们也没心思看,懂得都懂。下篇再往下讲,有讲的不对的,欢迎大家指出更正。