Spring启动流程(一)

 我来答
户如乐9318
2022-06-21 · TA获得超过6689个赞
知道小有建树答主
回答量:2559
采纳率:100%
帮助的人:143万
展开全部

以java-config形式编写一个测试demo,新建一个 AnnotationConfigApplicationContext ,如果是XML形式使用 ClassPathXmlApplicationContext

两者都继承了 AbstractApplicationContext 类,详细看下面的层次图。

注意:在new AnnotationConfigApplicationContext()时如果未指定参数,会报运行时异常: org.springframework.context.annotation.AnnotationConfigApplicationContext@6ebc05a6 has not been refreshed yet

AnnotationConfigApplicationContext的有参构造执行了3个方法,分别是自己的无参构造、register()、refresh();

在描述前先从网上找了一个总体流程图方便了解一下大致流程,理清思路。

在执行 AnnotationConfigApplicationContext 的无参构造方法前会调用父类 GenericApplicationContext 的无参构造方法;

GenericApplicationContext中实例化一个 DefaultListableBeanFactory ,也就是说bean工厂实际上是应用上下文的一个属性;

从上面的类层次图可以看到:应用上下文和bean工厂又同时实现了BeanFactory接口。

前面讲到我们为了解IOC使用了Spring提供的AnnotationConfigApplicationContext作为入口展开,那Spring怎么对加了特定注解(如 @Service、@Repository)的类进行读取转化成 BeanDefinition 对象呢?

又如何对指定的包目录进行扫描查找 bean 对象呢?

所以我们需要new一个注解配置读取器和一个路径扫描器。

AnnotatedBeanDefinitionReader中执行了AnnotationConfigUtils中的registerAnnotationConfigProcessors(this.registry)方法,会向容器注册Sprign内置的处理器。

registerAnnotationConfigProcessors方法中通过 new RootBeanDefinition(XX.class) 新建一个RootBeanDefinition(BeanDefinition的一个实现),然后调用registerPostProcessor将内置bean对应的BeanDefinition保存到bean工厂中;

这里需要说明的是:我们刚刚一直在谈到注册bean,实际上就是将内置bean对应的beanDefinition保存到bean工厂中。那为什么要保存beanDefinition呢?因为Spring是跟据beanDefinition中对bean的描述,来实例化对象的,就算自己定义的bean也是要被解析成一个beanDefinition并注册的。

其中最主要的组件便是 ConfigurationClassPostProcessor 和 AutowiredAnnotationBeanPostProcessor ,前者是一个 beanFactory 后置处理器,用来完成 bean 的扫描与注入工作,后者是一个 bean 后置处理器,用来完成 @AutoWired 自动注入。

这个步骤主要是用来解析用户传入的 Spring 配置类,解析成一个 BeanDefinition 然后注册到容器中,主要源码如下:

通过生成AnnotatedGenericBeanDefinition,然后解析给BeanDefinition的其他属性赋值,然后将BeanDefinition和beanName封装成一个BeanDefinitionHolder对象注册到bean工厂中(就是将beanName与baenDefinition封装到Map中,将beanName放到list中。Map与list都是bean工厂DefaultListableBeanFactory所维护的属性),和前面内置bean的注册相同。

执行到这一步,register方法到此就结束了,通过断点观察BeanFactory中的beanDefinitionMap属性可以看出: this()和this.register(componentClasses)方法中就是将内置bean和我们传的配置bean的beanDefinition进行了注册,还没处理标记了@Component等注解的自定义bean。

已赞过 已踩过<
你对这个回答的评价是?
评论 收起
推荐律师服务: 若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询

为你推荐:

下载百度知道APP,抢鲜体验
使用百度知道APP,立即抢鲜体验。你的手机镜头里或许有别人想知道的答案。
扫描二维码下载
×

类别

我们会通过消息、邮箱等方式尽快将举报结果通知您。

说明

0/200

提交
取消

辅 助

模 式