internalAutowiredAnnotationProcessor在哪冒出来的?
读spring源码的时候,跳过了一些自认为不是很重要的过程,在loadBeanDefinitions完成的时候,出现了几个奇怪的身影,这些internal-XXXXXXXX-Processor哪来的,和后面的@Autowired又有什么关系?
带着这个疑问,来一行一行的啃一下相关的源码。
创建一个测试类
@Test
public void test() {
ClassPathXmlApplicationContext applicationContext = new ClassPathXmlApplicationContext("spring-test.xml");
}
直接进入
public ClassPathXmlApplicationContext(String configLocation) throws BeansException {
this(new String[] {configLocation}, true, null);
}
继续跟进,找到核心入口refresh()方法
public ClassPathXmlApplicationContext(
String[] configLocations, boolean refresh, @Nullable ApplicationContext parent)
throws BeansException {
super(parent);
setConfigLocations(configLocations);
if (refresh) {
refresh();// 入口
}
}
来到AbstractApplicationContext#refresh(),忽略掉prepareRefresh的过程,直接进入obtainFreshBeanFactory
@Override
public void refresh() throws BeansException, IllegalStateException {
synchronized (this.startupShutdownMonitor) {
StartupStep contextRefresh = this.applicationStartup.start("spring.context.refresh");
// Prepare this context for refreshing.
prepareRefresh();//做容器刷新前的准备工作
// Tell the subclass to refresh the internal bean factory.
ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();// 核心
…………………………
在AbstractApplicationContext#obtainFreshBeanFactory()中,将进行beanFactory的创建和beanDefinition的解析工作
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
// 初始化BeanFactory,并进行XML文件的读取,并将得到的BeanFactory记录在当前的属性中
refreshBeanFactory();
return getBeanFactory();//返回当前实体的BeanFactory
}
进入AbstractRefreshableApplicationContext#refreshBeanFactory()
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
refreshBeanFactory();// 创建beanFactroy并解析xml
return getBeanFactory();
}
@Override
protected final void refreshBeanFactory() throws BeansException {
if (hasBeanFactory()) {
destroyBeans();
closeBeanFactory();
}
try {
DefaultListableBeanFactory beanFactory = createBeanFactory();
beanFactory.setSerializationId(getId());
customizeBeanFactory(beanFactory);
// 初始化documentReader,并进行XML文件读取以及解析
loadBeanDefinitions(beanFactory);
this.beanFactory = beanFactory;
}
catch (IOException ex) {
throw new ApplicationContextException("I/O error parsing bean definition source for " + getDisplayName(), ex);
}
}
进入 AbstractXmlApplicationContext#loadBeanDefinitions (DefaultListableBeanFactory beanFactory)
开始迷宫般的load之旅,这里的代码不要想着走读就能读通,必须逐行debug,不然就在里面绕圈圈……
终于到了真正干活的地方,doLoadBeanDefinitions
doLoadBeanDefinitions调doLoadDocument,doLoadDocument会将xml文件解析成一个 Document对象,里面具体的解析过程就不再细究了
主要看返回之后,registerBeanDefinitions
将Document对象里的键值对解析成BeanDefinition
根据标签类型的不同,进行不同的解析
我的xml里面第一个标签是 component-scan
属于CustomElement
调用自定义的NamespaceHandler 进行解析
解析完的标签信息,最终放在一个Set集合里,但随后做的一件事情很关键——registerComponents
就是这这个registerComponents里,完成了那些 internal xxxxxxxxxxxxxProcessor的注册
在此完成的添加,beanDefs.add(registerPostProcessor(registry, def, XXXX_YYYYY_BEAN_NAME));
这些正是前文对应的那些internal-XXXXXXXX-Processor
转载自:https://juejin.cn/post/7112343617850572836