SpringBoot 启动流程
2021-07-21 23:02:02 0 举报
SpringBoot 启动流程
作者其他创作
大纲/内容
InstantiationAwareBeanPostProcessor.postProcessPropertyValues()
invokeInitMethods()
第一次进入getSingleton()
AbstractRefreshableApplicationContext.refreshBeanFactory()
prepareEnvironment()
2.createSpringFactoriesInstances获取类名后,反射创建对象
构造时,初始化
AnnotationConfigApplicationContext实现,里面的逻辑
createApplicationContext()
触发BootstrapApplicationListener
容器加入new ApplicationContextAwareProcessor(this),并beanFactory.ignoreDependencyInterface(忽略这个processor处理的Aware接口setter方法注入
loadBeanDefinitions(beanFactory);
1.初始化ConfigurableEnvironment:MutablePropertySources,主要是系统变量和环境变量
进入createBean
判断,Bean类型是否是指定类型
initMethod
AbstractApplicationContext 867
ConfigurableEnvironment environment = getOrCreateEnvironment();
BeanPostProcessor.postProcessAfterInitialization()
AbstractAutowireCapableBeanFactory 542
第二次进入getSingleton()
初始化BeanDefinitionLoader,加载的是SpringApplication的primarySources、sources字段中的类注册进容器,在父级容器(AnnotationConfigApplicationContext)这个阶段sources是spring.factories中的BootstrapConfiguration类,子容器中这里sources是main()方法的启动类
其他ApplicationContext最终实现,里面的逻辑
MergedBeanDefinitionPostProcessor.postProcessMergedBeanDefinition()
AnnotatedBeanDefinitionReader实例化时AnnotationConfigUtils.registerAnnotationConfigProcessors(this.registry)初始化了若干RootBeanDefinition
ConfigFileApplicationListener
refreshContext(context)
getSingleton(beanName):从当前容器三个缓存中获取
InstantiationAwareBeanPostProcesso.postProcessAfterInstantiation()
doGetBean()
applyPropertyValues():填充属性值
BeanPostProcessor的五大接口https://www.cnblogs.com/zhangjianbin/p/10059191.html
ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory()
触发了EnvironmentPostProcessor执行
AbstractBeanFactory 306
容器注入environment、systemProperties、systemEnvironment单利bean
|垂直关系|应用容器| 水平关系|启动容器|类型|| :---- | :---- | :---- | :---- | :---- ||内置子容器|serializationId:***-***-***(DefaultListableBeanFactory): |子 --> 父|serializationId: application (DefaultListableBeanFactory)|BeanFactory||外置容器|id:application-1 (AnnotationConfigServletWebServerApplicationContext) | 子 --> 父| id: bootstrap (AnnotationConfigApplicationContext)|ApplicationContext|
invokeAwareMethods()
AbstractAutowireCapableBeanFactory 483
执行BeanDefinitionRegistryPostProcessor(先PriorityOrdered,再Ordered)
getBean(beanName);
同时父类GenericApplicationContext构造方法中实例化 beanFactory = DefaultListableBeanFactory
1.设置环境激活的profile2.判断设置两个propertySource:defaultProperties、springApplicationCommandLineArgs
没取到
AbstractApplicationContext.refresh();
AbstractBeanFactory.createBean()
ConfigurationClassPostProcessor在此时会被执行,去解析@Configuration @Bean @ComponentScan @Import @ImportResource(加载XML等形式中的Bean)注解形式指定的Class及其父类,注入容器
根据webApplicationType实例化:ConfigurableApplicationContext,默认对象是AnnotationConfigApplicationContext
取到
1.SpringFactoriesLoader.loadFactoryNames()从classpath下META-INF/spring.factories获取所有指定的类名,并缓存
prepareContext()
getBean()
postProcessBeanFactory(beanFactory)(AnnotationConfigApplicationContext是空实现)
finishBeanFactoryInitializatio():实例化所有剩余的(非lazy-init)单例。触发所有非懒加载的单例bean初始化(即应用中自定义的各种controller、service等Bean的实例化初始化)
initMessageSource():初始化注册一个名为messageSource的 DelegatingMessage Source单例对象,并赋给AbstractApplicationContext(初始化国际化信息源)
实例化Bean:封装成BeanWraper
1
使用SpringAppilcationBuilder创建了新的SpringApplication,调用run()方法,按照spring容器构建流程,生成了父容器(Bootstrap容器)AnnotationConfigApplicationContext,随后放入AncestorInitializer,在触发(应用容器)执行ApplicationContextInitializer时,设置为应用容器的父容器。(run()方法构建容器时还会触发BootstrapApplicationListener,由于构建前environment,已经设置了名:bootstrap的PropertySource,检测这个变量如果存在,就返回,而不会死循环无限构建)解析https://blog.csdn.net/wangwei19871103/article/details/105728553/
applyInitializers(context):遍历执行ApplicationContextInitializer
getSpringFactoriesInstances
顺序执行了BeanNameAware、BeanClassLoaderAware、BeanFactoryAware 的set方法
触发Bean代理对象的创建AnnotationAwareAspectJAutoProxyCreator (AOP)
new SpringApplication()
registerBeanPostProcessors(beanFactory);注册相关BeanPostProcessor,供Bean生成前后调用。
为什么需要三个map呢?先来了解这三个map到底都缓存了什么 * 第一个map singletonObjects 存放的单例的bean * 第二个map singletonFactories 存放的临时对象的工厂类(没有完整springBean生命周期的对象的工厂类) * 第三个map earlySingletonObjects 存放的临时对象(没有完整springBean生命周期的对象)
DefaultListableBeanFactory 761
X
从所有spring.factory实例化获取SpringApplicationRunListener列表到SpringApplicationRunListeners 然后starting
AbstractBeanFactory
(√)GenericApplicationContext.refreshBeanFactory()只设置了serializationId
处理Autowire依赖的PropertyValue
容器加入new ApplicationListenerDetector(this)
refreshContext():最重要的流程
DefaultSingletonBeanRegistry
getOrCreateEnvironment()
afterRefresh()
初始化了:ConfigurationClassPostProcessor(处理@Configuration@Bean)AutowiredAnnotationBeanPostProcessor(处理@Autowired@Value@Inject)RequiredAnnotationBeanPostProcessor(处理@Required)CommonAnnotationBeanPostProcessor(处理@PostConstruct@PreDestroy@Resource)PersistenceAnnotationBeanPostProcessor(要存在JPA)EventListenerMethodProcessor(处理@EventListener)
DefaultListableBeanFactory beanFactory = createBeanFactory();
待理解
onRefresh():启动容器这一步没操作,应用容器在一步创建启动了tomcat(或jetty...)容器
refresh(context);
run()
refreshBeanFactory();刷新内部的DefaultListableBeanFactory对象,设置serializationId
上层大致流程
printBanner()(打印banner)
doGetBean
populateBean():使用BeanDefination中的属性值填充给定BeanWrapper中的Bean实例
进入getBean()
父类AbstractApplicationContext构造方法中实例化 PathMatchingResourcePatternResolver(this)
EventPublishingRunListener中是空方法,未实现
。。。
prepareRefresh():设置容器开启启动时间、状态、初始化propertySources如果有、验证Environment属性
beanFactory.preInstantiateSingletons();
invokeBeanFactoryPostProcessors(beanFactory);
注册BeanNameGenerator的单例bean(if判断跳过了)设置context的classloader(if判断跳过了)
触发ApplicationContext准备好了的通知listeners.contextPrepared(context);
createApplicationContext
getBeanFactory();获取GenericApplicationContext内部的DefaultListableBeanFactory对象
initApplicationEventMulticaster():初始化一个SimpleApplicationEventMulticaster如果容器中没有的话
postProcessApplicationContext(context)
触发了AutowiredAnnotationBeanPostProcessor的执行,注入依赖
initializeBean()
InitializingBean
触发
customizeBeanFactory(beanFactory):设置允许循环引用&BeanDefination覆盖
context.registerShutdownHook()
listeners.environmentPrepared(environment);
从所有spring.factory1.实例化ApplicationContextInitializer(扩展点)2.实例化ApplicationListener
prepareBeanFactory(beanFactory);
设置ConfigurableApplicationContext的environment
同时构造方法中实例化 new AnnotatedBeanDefinitionReader(this); new ClassPathBeanDefinitionScanner(this);
InstantiationAwareBeanPostProcessor.postProcessBeforeInstantiation()
bindToSpringApplication(environment);
getRunListeners
BeanPostProcessor.postProcessBeforeInitialization()
收藏
0 条评论
回复 删除
下一页