导图社区 极客时间-小马哥讲Spring核心编程思想
极客时间-小马哥讲Spring核心编程思想个人学习总结,本图知识梳理清楚,非常实用,值得收藏。
编辑于2023-02-01 15:49:34极客时间-小马哥讲Spring核心编程思想
课程内容
第三章:Spring IoC容器概述
26.Spring IoC容器:BeanFactory和ApplicationContext谁才是Spring IoC容器?
BeanFactory
ApplicationContext
答案:ApplicationContext底层是通过BeanFactory来实现getBean方法来获取Bean对象的。 1.首先ApplicationContext是BeanFactory的子接口,因为ApplicationContext继承了ListableBeanFactory接口。(ApplicationContext是BeanFactory的子接口,说明ApplicationContext is BeanFactory。并且ApplicationContext 是BeanFactory的包装类,也就是它(AbstractRefreshableApplicationContext)内部组合了BeanFactory的实现-DefaultListableBeanFactory。为什么包装了DefaultListableBeanFactory,因为它需要简化且丰富功能来为企业开发提供更高的便捷性,也就是说ApplicationContext 是DefaultListableBeanFactory的超集。) 2.AbstractRefreshableApplicationContext类中组合了BeanFactory的实现DefaultListableBeanFactory,并通过组合的该BeanFactory对象实现getBeanFactory方法。而AbstractApplicationContext也就是通过子类AbstractRefreshableApplicationContext中组合的BeanFactory对象来实现getBean方法来获取Bean对象的逻辑。
思考:这里AbstractRefreshableApplicationContext通过继承BeanFactory加组合DefaultListableBeanFactory,达到了类似于代理设计模式的巧妙和思想。继承+组合=可以实现类似于代理设计模式
29.Spring IoC容器生命周期:IoC容器启停过程中发生了什么?
启动应用上下文:applicationContext.refresh()
关闭应用上下文:applicationContext.close()
第四章:Spring Bean基础
32.BeanDefinition元信息:除了Bean名称和类名,还有哪些Bean元信息值得关注?
BeanDefinition
BeanDefinitionBuilder
GenericBeanDefinition
33.命名Sping Bean:id和name属性命名Bean,哪个更好?
DefaultBeanNameGenerato
AnnotationBeanNameGenerator
36.实例化Spring Bean:Bean实例化的姿势多少种?
常规方式
通过构造器(配置元信息:XML、Java 注解和 Java API )
通过静态工厂方法(配置元信息:XML 和 Java API )
通过 Bean 工厂方法(配置元信息:XML和 Java API )
通过 FactoryBean(配置元信息:XML、Java 注解和 Java API )
特殊方式
通过 ServiceLoaderFactoryBean(配置元信息:XML、Java 注解和 Java API )
通过 AutowireCapableBeanFactory#createBean(java.lang.Class, int, boolean)
通过 BeanDefinitionRegistry#registerBeanDefinition(String,BeanDefinition)
37.初始化Spring Bean:Bean初始化有哪些方法?
@PostConstruct 标注方法
实现 InitializingBean 接口的 afterPropertiesSet() 方法
自定义初始化方法
XML 配置:<bean init-method=”init” ... />
Java 注解:@Bean(initMethod=”init”)
Java API:AbstractBeanDefinition#setInitMethodName(String)
假设以上三种方式均在同一 Bean 中定义,那么这些方法的执行顺序是:@PostConstruct->InitializingBean#afterPropertiesSet()->自定义初始化方法 (如果一个对象被标记为懒加载的,那么这个对象的这些初始化方法在Spring IoC容器启动的时候都不会执行,在这个对象被依赖查找的时候会被执行。)
38.延迟初始化Spring Bean:延迟初始化的Bean会影响依赖注入吗?
Bean 延迟初始化(Lazy Initialization)
XML 配置:<bean lazy-init=”true” ... />
Java 注解:@Lazy(true)
39.销毁Spring Bean:销毁Bean的基本操作有哪些?
Bean 销毁(Destroy)
@PreDestroy 标注方法
实现 DisposableBean 接口的 destroy() 方法
自定义销毁方法
XML 配置:<bean destroy=”destroy” ... />
Java 注解:@Bean(destroy=”destroy”)
Java API:AbstractBeanDefinition#setDestroyMethodName(String)
假设以上三种方式均在同一 Bean 中定义,那么这些方法的执行顺序是怎样? 答:@PreDestroy->DisposableBean#destroy()->自定义销毁方法
40.回收Spring Bean:Spring IoC容器管理的Bean能够被垃圾回收吗?
Bean 垃圾回收(GC)
1.关闭 Spring 容器(应用上下文)
2.执行 GC
3.Spring Bean 覆盖的 finalize() 方法被回调
第五章:Spring IoC以来查找(Dependency Lookup)
45.层次性以来查找:依赖查找也有双亲委派?
层次性依赖查找接口:HierarchicalBeanFactory
双亲 BeanFactory:getParentBeanFactory()
层次性查找
根据 Bean 名称查找:基于 containsLocalBean 方法实现
根据 Bean 类型查找实例列表
单一类型:BeanFactoryUtils#beanOfType
集合类型:BeanFactoryUtils#beansOfTypeIncludingAncestors
根据 Java 注解查找名称列表
BeanFactoryUtils#beanNamesForTypeIncludingAncestors
48.内建可查找的依赖:哪些Spring IoC容器内建依赖可供查找?
49.依赖查找中的经典异常:Bean找不到?Bean不是唯一的?Bean创建失败?
依赖查找中的经典异常
BeansException
NoSuchBeanDefinitionException
触发条件(举例)
当查找 Bean 不存在于 IoC 容器时
场景举例
BeanFactory#getBean
ObjectFactory#getObject
NoUniqueBeanDefinitionException
触发条件(举例)
类型依赖查找时,IoC 容器存在多个 Bean 实例
场景举例
BeanFactory#getBean(Class)
BeanInstantiationException
触发条件(举例)
当 Bean 所对应的类型非具体类时
场景举例
BeanFactory#getBean
BeanCreationException
触发条件(举例)
当 Bean 初始化过程中
场景举例
Bean 初始化方法执行异常时
BeanDefinitionStoreException
触发条件(举例)
当 BeanDefinition 配置元信息非法时
场景举例
XML 配置资源无法打开时
第六章:Spring IoC依赖注入(Dependency Injection)
55.Setter方法依赖注入:Setter注入的原理是什么?
56.构造器依赖注入:官方为什么推荐使用构造器注入?
57.字段注入:为什么Spring官方文档没有单独列举这种注入方式?
字段注入
@Autowired
@Resource
@Inject
58.方法注入:方法注入是@Autowired专利吗?
方法注入
@Autowired
@Resource
@Inject
@Bean
59.接口回调注入:回调注入的使用场景和限制有哪些?
Aware 系列接口回调(自动模式)
BeanFactoryAware
获取 IoC 容器 - BeanFactory
ApplicationContextAware
获取 Spring 应用上下文 - ApplicationContext 对象
EnvironmentAware
获取 Environment 对象
ResourceLoaderAware
获取资源加载器 对象 - ResourceLoader
BeanClassLoaderAware
获取加载当前 Bean Class 的 ClassLoader
BeanNameAware
获取当前 Bean 的名称
MessageSourceAware
获取 MessageSource 对象,用于 Spring 国际化
ApplicationEventPublisherAware
获取 ApplicationEventPublish 对象,用于 Spring 事件
EmbeddedValueResolverAware
获取 StringValueResolver 对象,用于占位符处理
63.限定注入:如何限定Bean名称注入?如何实现Bean逻辑分组注入?
使用注解 @Qualifier 限定
通过 Bean 名称限定
通过分组限定
基于注解 @Qualifier 扩展限定
自定义注解 - 如 Spring Cloud @LoadBalanced
64.延迟依赖注入:如何实现延迟执行依赖注入?与延迟依赖查找是类似的吗?
延迟依赖注入
使用 API ObjectFactory 延迟注入
单一类型
集合类型
使用 API ObjectProvider 延迟注入
单一类型
集合类型
65.依赖处理过程:依赖处理时会发生什么?其中与依赖查找的差异在哪?
基础知识
入口: DefaultListableBeanFactory#resolveDependency
依赖描述符:DependencyDescriptor
自定绑定候选对象处理器:AutowireCandidateResolver
66.@Autowired注入:@Autowired注入的规则和原理有哪些?
@Autowired 注入规则
非静态字段
非静态方法
构造器
@Autowired 注入过程
元信息解析
依赖查找
依赖注入(字段、方法)
源码分析关键入口
构建Bean对象元数据:org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor#postProcessMergedBeanDefinition
这个方法的逻辑是 将父类对象(这个父对象指<bean>标签中parent属性指定的对象)的属性合并到当前对象中,类似于属性拷贝。 AutowiredAnnotationBeanPostProcessor不仅可以处理@Autowired注解,还可以处理@Value和@Inject注解
注入Bean对象的依赖:org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor#postProcessProperties
这个方法主要是对对象注入的逻辑进行处理
68.Java通用注解注入原理:Spring是如何实现@Resource和@EJB等注解注入的?
CommonAnnotationBeanPostProcessor
注入注解
javax.xml.ws.WebServiceRef
javax.ejb.EJB
javax.annotation.Resource
生命周期注解
javax.annotation.PostConstruct
javax.annotation.PreDestroy
69.自定义依赖注入注解:如何最简化实现依赖注入注解?
自定义依赖注入注解
基于 AutowiredAnnotationBeanPostProcessor 实现
自定义实现
生命周期处理
InstantiationAwareBeanPostProcessor
MergedBeanDefinitionPostProcessor
元数据
InjectedElement
InjectionMetadata
第七章:Spring IoC依赖来源(Dependency Sources)
71.依赖查找的来源:除容器内建和自定义Spring Bean之外还有其他来源提供依赖查找吗?
Spring BeanDefinition
<bean id="user" class="org.geekbang...User">
@Bean public User user(){...}
BeanDefinitionBuilder
单例对象
通过SingletonBeanRegistry#registerSingleton注册的对象(这个注册单例对象方法的实现,一般是:DefaultListableBeanFactory#registerSingleton)
API 实现
72.依赖注入的来源:难道依赖注入的来源与依赖查找的不同吗?
Spring BeanDefinition
<bean id="user" class="org.geekbang...User">
@Bean public User user(){...}
BeanDefinitionBuilder
单例对象
通过SingletonBeanRegistry#registerSingleton注册的对象(这个注册单例对象方法的实现,一般是:DefaultListableBeanFactory#registerSingleton)
API 实现
非 Spring 容器管理对象
这类对象,指的是通过ConfigurableListableBeanFactory#registerResolvableDependency注册的resolvableDependency对象,例如:在AbstractApplicationContext#prepareBeanFactory方法中,就通过registerResolvableDependency方法注册了BeanFactory、ResourceLoader、ApplicationEventPublisher、ApplicationContext的对象。这个方法的实现,主要是:DefaultListableBeanFactory#registerResolvableDependency
74.Spring Bean Definition作为依赖来源:Spring Bean的来源
Spring BeanDefinition 作为依赖来源
要素
元数据:BeanDefinition
注册:BeanDefinitionRegistry#registerBeanDefinition
类型:延迟和非延迟
顺序:Bean 生命周期顺序按照注册顺序
75.单例对象作为依赖来源:单例对象与普通Spring Bean存在哪些差异?
单例对象作为依赖来源
要素
来源:外部普通 Java 对象(不一定是 POJO)
注册:SingletonBeanRegistry#registerSingleton
限制
无生命周期管理
无法实现延迟初始化 Bean
76.非Spring容器管理对象作为依赖来源:如何理解ResolvableDependency?
非 Spring 容器管理对象作为依赖来源
要素
注册:ConfigurableListableBeanFactory#registerResolvableDependency
限制
无生命周期管理
无法实现延迟初始化 Bean
无法通过依赖查找
第八章:Spring Bean作用域(Scopes)
86.课外资料:Spring Cloud RefreshScope是如何控制Bean的动态刷新?
第九章:Spring Bean生命周期(Bean Lifecycle)
88.Spring Bean元信息配置阶段:BeanDefinition配置与扩展
89.Spring Bean元信息解析阶段:BeanDefinition的解析
90.Spring Bean注册阶段:BeanDefinition与单体Bean注册
91.Spring BeanDefinition合并阶段:BeanDefinition合并过程是怎样出现的?
BeanDefinition 合并
父子 BeanDefinition 合并
当前 BeanFactory 查找
层次性 BeanFactory 查找
源码分析入口
org.springframework.beans.factory.support.AbstractBeanFactory#getMergedBeanDefinition(java.lang.String)
92.Spring Bean Class加载阶段:Bean ClassLoader能够被替换吗?
Spring Bean Class 加载阶段
ClassLoader 类加载
Java Security 安全控制
ConfigurableBeanFactory 临时 ClassLoader
源码分析入口
org.springframework.beans.factory.support.AbstractBeanFactory#doGetBean
93.Spring Bean实例化前阶段:Bean的实例化能否被绕开?
Spring Bean 实例化前阶段
非主流生命周期:Bean 实例化前阶段
InstantiationAwareBeanPostProcessor#postProcessBeforeInstantiation
94.Spring Bean实例化阶段:Bean实例化是通过Java反射创建吗?
Spring Bean 实例化阶段
实例化方式
传统实例化方式
实例化策略:InstantiationStrategy
构造器依赖注入
95.Spring Bean实例化后阶段:Bean实例化后是否一定被使用?
Spring Bean 实例化后阶段
Bean 属性赋值(Populate)判断
InstantiationAwareBeanPostProcessor#postProcessAfterInstantiation
本节视频,还讲了Bean对象依赖注入的顺序
96.Spring Bean属性赋值前阶段:配置后的PropertyValues还有机会修改吗?
Bean 属性值元信息
PropertyValues
Bean 属性赋值前回调
Spring 1.2 - 5.0
InstantiationAwareBeanPostProcessor#postProcessPropertyValues
Spring 5.1
InstantiationAwareBeanPostProcessor#postProcessProperties
源码分析入口
Spring Bean属性赋值或属性数据填充入口
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#populateBean
97.Aware接口回调阶段:众多Aware接口回调的顺序是怎样安排的?
这个阶段也属于Bean的初始化阶段
Spring Aware 接口回调先后顺序
从上到下,越前面的越优先被回调
BeanNameAware
BeanClassLoaderAware
BeanFactoryAware
这三个Aware接口的回调入口,参考这篇文章
EnvironmentAware
EmbeddedValueResolverAware
ResourceLoaderAware
ApplicationEventPublisherAware
MessageSourceAware
ApplicationContextAware
其它这6个Aware接口的回调入口,参考这篇文章
98.Spring Bean初始化前阶段:BeanPostProcessor
Spring Bean 初始化前阶段
已完成
Bean 实例化
Bean 属性赋值
Bean Aware 接口回调
方法回调
BeanPostProcessor#postProcessBeforeInitialization
99.Spring Bean初始化阶段:@PostConstruct、InitializingBean以及自定义初始化方法
Spring Bean 初始化阶段
Bean 初始化(Initialization)
@PostConstruct 标注方法
实现 InitializingBean 接口的 afterPropertiesSet() 方法
自定义初始化方法
100.Spring Bean初始化后阶段:BeanPostProcessor
Spring Bean 初始化后阶段
方法回调
BeanPostProcessor#postProcessAfterInitialization
101.Spring Bean初始化完成阶段:SmartInitializingSingleton
Spring Bean 初始化完成阶段
方法回调
Spring 4.1 +:SmartInitializingSingleton#afterSingletonsInstantiated
102.Spring Bean销毁前阶段:DestructionAwareBeanPostProcessor用在怎样的场景
这里的销毁是指从Spring IoC容器中销毁,而不是指GC垃圾回收掉这个对象。
Spring Bean 销毁前阶段
方法回调
DestructionAwareBeanPostProcessor#postProcessBeforeDestruction
103.Spring Bean销毁阶段:@PreDestroy、DisposableBean以及自定义方法
Spring Bean 销毁阶段
Bean 销毁(Destroy)
@PreDestroy 标注方法
实现 DisposableBean 接口的 destroy() 方法
自定义销毁方法
104.Spring Bean垃圾收集(GC):何时需要GC Spring Bean?
Spring Bean 垃圾收集
Bean 垃圾回收(GC)
关闭 Spring 容器(应用上下文)
执行 GC
Spring Bean 覆盖的 finalize() 方法被回调
第十章:Spring 配置元信息(Configuration Metadata)
106.Spring配置元信息:Spring存在哪些配置元信息?它们分别用在什么场景?
Spring 配置元信息
配置元信息
Spring Bean 配置元信息 - BeanDefinition
Spring Bean 属性元信息 - PropertyValues
Spring 容器配置元信息
Spring 外部化配置元信息 - PropertySource
Spring Profile 元信息 - @Profile
107.Spring Bean配置元信息:BeanDefinition
Bean 配置元信息:BeanDefinition
GenericBeanDefinition:通用型 BeanDefinition
RootBeanDefinition:无 Parent 的 BeanDefinition 或者合并后 BeanDefinition
AnnotatedBeanDefinition:注解标注的 BeanDefinition
108.Spring Bean属性元信息:PropertyValues
Spring Bean 属性元信息
Bean 属性元信息:PropertyValues
可修改实现:MutablePropertyValues
元素成员:PropertyValue
Bean 属性上下文存储:AttributeAccessor
Bean 元信息元素:BeanMetadataElement
109.Spring容器配置元信息
源码分析入口:org.springframework.beans.factory.xml.BeanDefinitionParserDelegate#populateDefaults
110.基于XML资源装载Spring Bean配置元信息
关键类:XmlBeanDefinitionReader#loadBeanDefinitions
111.基于Properties资源装载Spring Bean配置元信息:为什么Spring官方不推荐?
关键类:PropertiesBeanDefinitionReader#loadBeanDefinitions
112.基于Java注解装载Spring Bean配置元信息
113.Spring Bean配置元信息底层实现之XML资源
Spring XML资源BeanDefinition解析与注册
核心API:XmlBeanDefinitionReader
资源:Resource
底层:BeanDefinitionDocumentReader
XML 解析:Java DOM Level 3 API
BeanDefinition解析:BeanDefinitionParserDelegate
BeanDefinition注册:BeanDefinitionRegistry
114.Spring Bean配置元信息底层实现之Properties资源
Spring Properties资源BeanDefinition解析与注册
核心API:PropertiesBeanDefinitionReader
资源
字节流:Resource
字符流:EncodedResouce
底层
存储:java.util.Properties
BeanDefinition解析:API 内部实现
BeanDefinition注册:BeanDefinitionRegistry
115.Spring Bean配置元信息底层实现之Java注解
Spring Java注解BeanDefinition解析与注册
核心API:AnnotatedBeanDefinitionReader
资源
类对象:java.lang.Class
底层
条件评估:ConditionEvaluator
Bean范围解析:ScopeMetadataResolver
BeanDefinition解析:内部 API 实现
BeanDefinition处理:AnnotationConfigUtils.processCommonDefinitionAnnotations
BeanDefinition注册:BeanDefinitionRegistry
116.基于XML资源装载Spring IoC容器配置元信息
117.基于Java注解装载Spring IoC容器配置元信息
118.基于Extensible XML authoring扩展Spring XML元素
119.Extensible XML authoring扩展原理
120.基于Properties资源装载外部化配置
121.基于YAML资源装载外部化配置
第十一章:Spring资源管理(Resources)
第十二章:Spring国际化(i18n)
135.Spring国际化接口:MessageSource不是技术的创造者,只是技术的搬运工?
核心接口
org.springframework.context.MessageSource
ResourceBundleMessageSource
ReloadableResourceBundleMessageSource
主要概念
文案模板编码(code)
文案模板参数(args)
区域(Locale)
136.层次性MessageSource:双亲委派不是ClassLoader的专利吗?
Spring层次性接口回顾
org.springframework.beans.factory.HierarchicalBeanFactory
org.springframework.context.ApplicationContext
org.springframework.beans.factory.config.BeanDefinition
Spring层次性国际化接口
org.springframework.context.HierarchicalMessageSource
137.Java国际化标准实现:ResoueceBundle潜规则多?
Java 国际化标准实现
核心接口
抽象实现:java.util.ResourceBundle
Properties资源实现:java.util.PropertyResourceBundle
例举实现:java.util.ListResourceBundle
138.Java文本格式:MessageFormat脱离Spring场景,能力更强大?
Java文本格式化
核心接口
java.text.MessageFormat
基本用法
设置消息格式模式- new MessageFormat(...)
格式化 - format(new Object[]{...})
消息格式模式
格式元素:{ArgumentIndex (,FormatType,(FormatStyle))}
FormatType:消息格式类型,可选项,每种类型在 number、date、time 和 choice 类型选其一
FormatStyle:消息格式风格,可选项,包括:short、medium、long、full、integer、currency、percent
139.MessageSource开箱即用实现:ResourceBundle+MessageFormat组合拳
MessageSource开箱即用实现
基于ResourceBundle+MessageFormat组合MessageSource实现
org.springframework.context.support.ResourceBundleMessageSource
可重载Properties+MessageFormat组合MessageSource实现
org.springframework.context.support.ReloadableResourceBundleMessageSource
140.MessageSource内建依赖:到底“我”是谁?
MessageSource內建依赖
MessageSource內建Bean可能来源
预注册Bean名称为:“messageSource”,类型为:MessageSource Bean
默认內建实现:DelegatingMessageSource
层次性查找MessageSource对象
141.课外资料:SpringBoot为什么要新建MessageSource Bean?
AbstractApplicationContext的实现决定了MessageSource內建实现
Spring Boot通过外部化配置简化MessageSource Bean构建
Spring Boot基于Bean Validation校验非常普遍
第十三章:Spring校验(Validation)
148.Validator的救赎:如果没有Bean Validation,Validator将会在哪里?
Validator的救赎
Bean Validation与Validator 适配
核心组件: org.springframework.validation.beanvalidation.LocalValidatorFactoryBean
依赖Bean Validation:JSR-303 or JSR-349 provider
Bean 方法参数校验: org.springframework.validation.beanvalidation.MethodValidationPostProcessor
第十四章:Spring数据绑定(Data Binding)
150.Spring数据绑定使用场景:为什么官方文档描述一笔带过?
Spring数据绑定使用场景
Spring BeanDefinition到Bean实例创建
Spring数据绑定(DataBinder)
Spring Web参数绑定(WebDataBinder)
151.Spring数据绑定组件:DataBinder
Spring数据绑定组件
标准组件
org.springframework.validation.DataBinder
Web组件
org.springframework.web.bind.WebDataBinder
org.springframework.web.bind.ServletRequestDataBinder
org.springframework.web.bind.support.WebRequestDataBinder
org.springframework.web.bind.support.WebExchangeDataBinder(since 5.0)
152.DataBinder绑定元数据:PropertyValues不是Spring Bean属性元信息吗?
153.DataBinder绑定控制参数:ignoreUnknownFields和ignoreInvalidFields有什么作用?
154.Spring底层JavaBeans替换实现:BeanWapper源于JavaBeans而高于JavaBeans?
155.BeanWapperde使用场景:Spring数据绑定只是副业?
156.课外资料:标注JavaBeans是如何操作属性的?
157.DataBinder数据校验:又见Validator
第十五章:Spring类型转换(Type Conversion)
159.Spring类型转换的实现:Spring提供了哪几种类型转换的实现?
基于JavaBeans接口的类型转换实现
基于java.beans.PropertyEditor接口扩展
Spring 3.0+通用类型转换实现
160.使用场景:Spring类型转换各自的使用场景以及发展脉络是怎样的?
161.基于JavaBeans的接口的类型转换:Spring如何扩展PropertyEditor接口实现类型转换的?
核心职责
将 String 类型的内容转化为目标类型的对象
扩展原理
• Spring 框架将文本内容传递到 PropertyEditor 实现的 setAsText(String) 方法 • PropertyEditor#setAsText(String) 方法实现将 String 类型转化为目标类型的对象 • 将目标类型的对象传入 PropertyEditor#setValue(Object) 方法 • PropertyEditor#setValue(Object) 方法实现需要临时存储传入对象 • Spring 框架将通过 PropertyEditor#getValue() 获取类型转换后的对象
162.Spring内建PropertyEditor扩展:哪些常见类型被Spring内建PropertyEditor实现?
163.自定义PropertyEditor扩展:不尝试怎么知道它好不好用?
自定义PropertyEditor扩展
扩展模式
扩展 java.beans.PropertyEditorSupport 类
实现 org.springframework.beans.PropertyEditorRegistra
• 实现 registerCustomEditors(org.springframework.beans.PropertyEditorRegistry) 方法 • 将 PropertyEditorRegistrar 实现注册为 Spring Bean
向 org.springframework.beans.PropertyEditorRegistry 注册自定义 PropertyEditor 实现
• 通用类型实现 registerCustomEditor(Class<?>, PropertyEditor) • Java Bean 属性类型实现:registerCustomEditor(Class<?>, String, PropertyEditor)
164.Spring PropertyEditor的设计缺陷:为什么基于PropertyEditor扩展并不适合作为类型转换?
违反职责单一原则
java.beans.PropertyEditor 接口职责太多,除了类型转换,还包括 Java Beans 事件和 Java GUI 交互
java.beans.PropertyEditor 实现类型局限
来源类型只能为 java.lang.String 类型
java.beans.PropertyEditor 实现缺少类型安全
除了实现类命名可以表达语义,实现类无法感知目标转换类型
165.Spring 3通用类型转换接口:为什么Converter接口设计比PropertyEditor更合理?
166.Spring内建类型转换器:Spring内建类型转换器到底多丰富?
167.Converter接口的局限性:哪种类型转换场景Converter无法满足?有什么应对之策?
168.GenericConverter比Converter更通用?
169.优化GenericConverter接口:为什么GenericConverter需要补充条件判断?
170.扩展Spring类型转换器:为什么最终注册的都是ConditionalGenericConverter?
171.统一类型转换服务:ConversionService足够通用吗?
172.ConversionService作为依赖 能够同时作为依赖查找和依赖注入的来源吗?
第十六章:Spring泛型处理(Generic Resolution)
174.Java泛型基础:泛型参数信息在擦写后还会存在吗?
175.Java 5类型接口-Type:Java类型到底是Type还是Class?
176.Spring泛型类型辅助类:GenericTypeResolver
177.Spring泛型集合类型辅助类:GenericCollectionTypeResolver
178.Spring方法参数封装-MethodParameter:仅仅是方法参数
179.Spring 4.2泛型优化实现-ResolvableType
第十七章:Spring事件(Events)
182.Java事件/监听器编程模型:为什么Java中没有提供标准实现?
183.面向接口的事件/监听器设计模式:单事件监听和多事件监听怎么选?
185.Spring标准事件-ApplicationEvent:为什么不用EventObject?
187.基于注解的Spring事件监听器:@EventListener有哪些潜在规则?
188.注册Spring ApplicationListener:直接注册和间接注册有哪些差异?
方法一:ApplicationListener 作为 Spring Bean 注册
方法二:通过 ConfigurableApplicationContext API 注册
189.Spring事件发布器:Spring 4.2给ApplicationEventPublisher带来哪些变化?
190.Spring层次性上下文事件传播:这是一个Feature还是一个Bug?
191.Spring内建事件:为什么ContextStartedEvent和ContextStoppedEvent是鸡肋事件?
ContextRefreshedEvent :Spring 应用上下文就绪事件
ContextStartedEvent :Spring 应用上下文启动事件
ContextStoppedEvent :Spring 应用上下文停止事件
ContextClosedEvent :Spring 应用上下文关闭事件
192.Spring 4.2 Payload事件:为什么说PayloadApplicationEvent并非一个良好的设计?
193.自定义Spring事件:自定义事件业务用得上吗?
194.依赖注入ApplicationEventPublisher:事件推送还会引起Bug?
195.依赖查找ApplicationEventMulticaster:ApplicationEventMulticaster从何而来?
SimpleApplicationEventMulticaster
196.ApplicationEventPublisher底层实现:ApplicationEventMulticaster也是Java Observable的延伸?
197.同步和异步Spring事件广播:Spring对JUC Executor接口的理解不够?
198.Spring 4.1 事件异常处理:ErrorHandler使用有怎样的限制?
199.Spring事件/监听器实现原理:面向接口和注解的事件/监听器实现有区别吗?
Spring 事件/监听器实现原理
核心类
org.springframework.context.event.SimpleApplicationEventMulticaster
设计模式:观察者模式扩展
被观察者:org.springframework.context.ApplicationListener
通知对象:org.springframework.context.ApplicationEvent
执行模式:同步/异步
异常处理:org.springframework.util.ErrorHandler
泛型处理:org.springframework.core.ResolvableType
200.课外资料:Spring Boot和Spring Cloud事件也是Spring事件?
第十八章:Spring注解(Annotations)
202.Spring注解驱动编程发展历程
203.Spring核心注解场景分类
204.Spring注解编程模型
Spring注解编程模型
元注解(Meta-Annotations)
Spring 模式注解(Stereotype Annotations)
Spring 组合注解(Composed Annotations)
Spring 注解属性别名和覆盖(Attribute Aliases and Overrides)
205.Spring元注解
206.Spring模式注解
208.Spring注解属性别名
210.Spring @Enable模块驱动
211.Spring条件注解
212.课外资料:SpringBoot和SpringCloud是怎样在Spring注解内核上扩展的?
第十九章:Spring Environment抽象(Environment Abstraction)
220.依赖查找Environment
221.依赖注入@Value
226.基于注解扩展Spring配置属性源
227.基于API扩展Spring外部化配置属性源
228.课外资料:Spring 4.1测试配置属性源-@TestPropertySource
第二十章:Spring应用上下文生命周期(Container Lifecycle)
230.Spring应用上下文启动准备阶段
AbstractApplicationContext#prepareRefresh()方法
启动时间:startupDate
状态标识:closed(false)、active(true)
初始化PropertySources:initPropertySources()
检验Environment中必须属性
初始化事件监听器集合
初始化早期Spring事件集合
231.BeanFactory创建阶段
AbstractApplicationContext#obtainFreshBeanFactory()方法
刷新Spring应用上下文底层BeanFactory:refreshBeanFactory()
返回Spring应用上下文底层BeanFactory:getBeanFactory()
232.BeanFactory准备阶段
AbstractApplicationContext#prepareBeanFactory(ConfigurableListableBeanFactory)方法
233.BeanFactory后置处理阶段
AbstractApplicationContext#postProcessBeanFactory(ConfigurableListableBeanFactory)方法
AbstractApplicationContext#invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory)方法
调用BeanFactoryPostProcessor或BeanDefinitionRegistry后置处理方法
注册LoadTimeWeaverAwareProcessor对象
234.BeanFactory注册BeanPostProcessors阶段
AbstractApplicationContext#registerBeanPostProcessors(ConfigurableListableBeanFactory)方法
注册 PriorityOrdered 类型的 BeanPostProcessor Beans
注册 Ordered 类型的 BeanPostProcessor Beans
注册普通 BeanPostProcessor Beans
注册 MergedBeanDefinitionPostProcessor Beans
注册 ApplicationListenerDetector 对象
235.初始化内建Bean:MessageSource
AbstractApplicationContext#initMessageSource()方法
236.初始化内建Bean:Spring时间广播器
AbstractApplicationContext#initApplicationEventMulticaster()方法
237.Spring应用上下文刷新阶段
238.Spring事件监听器注册阶段
AbstractApplicationContext#registerListeners()方法
239.BeanFactory初始化完成阶段
240.Spring应用文上下刷新完成阶段
241.Spring应用上下文启动阶段
242.Spring应用上下文停止阶段
243.Spring应用上下文关闭阶段
245.结束语
加餐部分
加餐一:为什么说ObjectFactory提供的是延迟以来查找?
加餐二:依赖查找(注入)的Bean会被缓存吗?
单例Bean(Singleton)
会。缓存位置:org.springframework.beans.factory.support.DefaultSingletonBeanRegistry#singletonObjects 属性。
原型Bean(Prototype)
不会。当以来查询或依赖注入时,根据BeanDefinition每次创建。
其它Scope Bean
request:每个ServletRequest内部缓存,生命周期维持在每次HTTP请求。
session:每个HttpSession内部缓存,生命周期维持在每个用户HTTP会话。
application:当前Servlet应用内部缓存。
加餐三:@Bean的处理流程是怎样的?
解析范围
Configuration Class中的@Bean方法
方法类型
静态@Bean方法和实例@Bean方法
加餐四:BeanFactory如何处理循环依赖的?
预备知识
循环依赖开关(方法)
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#setAllowCircularReferences
单例工程(属性)
org.springframework.beans.factory.support.DefaultSingletonBeanRegistry#singletonFactories
获取早期未处理(未被初始化)的Bean对象(方法)
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#getEarlyBeanReference
早期未处理(未被初始化)的Bean(属性)
org.springframework.beans.factory.support.DefaultSingletonBeanRegistry#earlySingletonObjects
加餐五:MyBatis与Spring Framework是如何集成的?
课程内容-面试题
第三章面试题
996面试题:BeanFactory与FactoryBean有什么区别?
答: ①BeanFactory 是 IoC 底层容器 ②FactoryBean 是 创建 Bean 的一种方式,帮助实现复杂的初始化逻辑
劝退面试题:FactoryBean 是 创建 Bean 的一种方式,帮助实现复杂的初始化逻辑?
答: IoC 配置元信息读取和解析、IoC 容器生命周期、Spring 事件发布、 国际化等,更多答案将在后续专题章节逐一讨论
第四章面试题
沙雕面试题:如何注册一个 Spring Bean?
答: 通过 BeanDefinition 和外部单体对象来注册
996 面试题 :什么是 Spring BeanDefinition?
答: 回顾“定义 Spring Bean” 和 “BeanDefinition 元信息”
劝退面试题:Spring 容器是怎样管理注册 Bean
答: 答案将在后续专题章节详细讨论,如:IoC 配置元信息读取和解析、依 赖查找和注入以及 Bean 生命周期等。
第五章面试题
沙雕面试题:ObjectFactory 与 BeanFactory 的区别?
答: ObjectFactory 与 BeanFactory 均提供依赖查找的能力。 不过 ObjectFactory 仅关注一个或一种类型的 Bean 依赖查找,并 且自身不具备依赖查找的能力,能力则由 BeanFactory 输出。 BeanFactory 则提供了单一类型、集合类型以及层次性等多种依赖查 找方式。
996 面试题:BeanFactory.getBean 操作是否线程安全?
答: BeanFactory.getBean 方法的执行是线程安全的,操作过程中会增加互 斥锁
劝退面试题:Spring 依赖查找与注入在来源上的区别?
答: 答案将《Spring IoC依赖注入》以及《Spring IoC依赖来源》章节中继 续讨论。
第六章面试题
沙雕面试题:有多少种依赖注入的方式?
答: 构造器注入 Setter 注入 字段注入 方法注入 接口回调注入
996 面试题:你偏好构造器注入还是 Setter 注入?
答: 两种依赖注入的方式均可使用,如果是必须依赖的话,那么推荐使用构 造器注入,Setter 注入用于可选依赖。
劝退面试题:Spring 依赖注入的来源有哪些?
答: 答案将《Spring IoC依赖来源》章节中继续讨论。
第七章面试题
沙雕面试题:注入和查找的依赖来源是否相同?
答: 否,依赖查找的来源仅限于 Spring BeanDefinition 以及单例 对象,而依赖注入的来源还包括 Resolvable Dependency 以及 @Value 所标注的外部化配置
996 面试题:单例对象能在 IoC 容器启动后注册吗?
答: 可以的,单例对象的注册与 BeanDefinition 不同,BeanDefinition 会被 ConfigurableListableBeanFactory#freezeConfiguration() 方法影 响,从而冻结注册,单例对象则没有这个限制。
劝退面试题:Spring 依赖注入的来源有哪些?
答: Spring BeanDefinition 单例对象 Resolvable Dependency @Value 外部化配置
第八章面试题
沙雕面试题:Spring 內建的 Bean 作用域有几种?
答: singleton、prototype、request、session、application 以及 websocket
996 面试题:singleton Bean 是否在一个应用是唯一的
答: 否则,singleton bean 仅在当前 Spring IoC 容器(BeanFactory)中 是单例对象。
劝退面试题:“application”Bean 是否被其他方案替代
答: 可以的,实际上,“application” Bean 与“singleton” Bean 没有 本质区别
第九章面试题
沙雕面试题:BeanPostProcessor 的使用场景有哪些?
答: BeanPostProcessor 提供 Spring Bean 初始化前和初始化后的 生命周期回调,分别对应 postProcessBeforeInitialization 以及 postProcessAfterInitialization 方法,允许对关心的 Bean 进行 扩展,甚至是替换。 加分项: 其中,ApplicationContext 相关的 Aware 回调也是基于 BeanPostProcessor 实现,即 ApplicationContextAwareProcessor
996 面试题:BeanFactoryPostProcessor 与 BeanPostProcessor 的区别
答: BeanFactoryPostProcessor 是 Spring BeanFactory(实际为 ConfigurableListableBeanFactory) 的后置处理器,用于扩展 BeanFactory,或通过 BeanFactory 进行依赖查找和依赖注入。 加分项: BeanFactoryPostProcessor 必须有 Spring ApplicationContext 执行,BeanFactory 无法与其直接交互。 而 BeanPostProcessor 则直接与BeanFactory 关联,属于 N 对 1 的关系。
劝退面试题:BeanFactory 是怎样处理 Bean 生命周期?
答: BeanFactory 的默认实现为 DefaultListableBeanFactory,其中 Bean生命周期与方法映射如下: • BeanDefinition 注册阶段 - registerBeanDefinition • BeanDefinition 合并阶段 - getMergedBeanDefinition • Bean 实例化前阶段 - resolveBeforeInstantiation • Bean 实例化阶段 - createBeanInstance • Bean 实例化后阶段 - populateBean • Bean 属性赋值前阶段 - populateBean • Bean 属性赋值阶段 - populateBean • Bean Aware 接口回调阶段 - initializeBean • Bean 初始化前阶段 - initializeBean • Bean 初始化阶段 - initializeBean • Bean 初始化后阶段 - initializeBean • Bean 初始化完成阶段 - preInstantiateSingletons • Bean 销毁前阶段 - destroyBean • Bean 销毁阶段 - destroyBean
第十章面试题
沙雕面试题:Spring內建XML Schema常见有哪些?
996面试题:Spring配置元信息具体有哪些?
答: • Bean 配置元信息:通过媒介(如 XML、Proeprties 等),解析 BeanDefinition • IoC 容器配置元信息:通过媒介(如 XML、Proeprties 等),控制 IoC 容器行为 ,比如注解驱动、AOP 等 • 外部化配置:通过资源抽象(如 Proeprties、YAML 等),控制 PropertySource • Spring Profile:通过外部化配置,提供条件分支流程
劝退面试题:Extensible XML authoring 的缺点?
答: • 高复杂度:开发人员需要熟悉 XML Schema,spring.handlers,spring.schemas 以及 Spring API • 嵌套元素支持较弱:通常需要使用方法递归或者其嵌套解析的方式处理嵌套(子)元素 • XML 处理性能较差:Spring XML 基于 DOM Level 3 API 实现,该 API 便于理解,然而性能较差 • XML 框架移植性差:很难适配高性能和便利性的 XML 框架,如 JAXB
第十一章面试题
沙雕面试题:Spring 配置资源中有哪些常见类型?
答: • XML 资源 • Properties 资源 • YAML 资源
996面试题:请例举不同类型 Spring 配置资源?
答: • XML 资源 • 普通 Bean Definition XML 配置资源:*.xml • Spring Schema 资源:*.xsd • Properties 资源 • 普通 Properties 格式资源:*.properties • Spring Handler 实现类映射文件:META-INF/spring.handlers • Spring Schema 资源映射文件:META-INF/spring.schemas • YAML 资源 • 普通 YAML 配置资源:*.yaml 或 *.yml
劝退面试题:Java 标准资源管理扩展的步骤?
答: • 简易实现 • 实现 URLStreamHandler 并放置在 sun.net.www.protocol.$ {protocol}.Handler包下 • 自定义实现 • 实现URLStreamHandler • 添加 -Djava.protocol.handler.pkgs 启动参数,指向 URLStreamHandler实现 类的包下 • 高级实现 • 实现 URLStreamHandlerFactory 并传递到 URL 之中
第十二章面试题
沙雕面试题:Spring 国际化接口有哪些?
答: • 核心接口:MessageSource • 层次性接口:org.springframework.context.HierarchicalMessageSource
996面试题:Spring有哪些MessageSource內建实现?
答: •org.springframework.context.support.ResourceBundleMessageSource •org.springframework.context.support.ReloadableResourceBundleMessageSource •org.springframework.context.support.StaticMessageSource •org.springframework.context.support.DelegatingMessageSource
劝退面试题:如何实现配置自动更新 MessageSource?
答: • 主要技术 • Java NIO 2:java.nio.file.WatchService • Java Concurrency : java.util.concurrent.ExecutorService • Spring:org.springframework.context.support.AbstractMessageSource
第十三章面试题
沙雕面试题:Spring 校验接口是哪个?
答: org.springframework.validation.Validator
996 面试题:Spring 有哪些校验核心组件?
答: • 检验器:org.springframework.validation.Validator • 错误收集器:org.springframework.validation.Errors • Java Bean 错误描述:org.springframework.validation.ObjectError • Java Bean 属性错误描述:org.springframework.validation.FieldError • Bean Validation 适配: org.springframework.validation.beanvalidation.LocalValidatorFactoryBean
劝退面试题:请通过示例演示Spring Bean的校验?
答: 答案下章揭晓
第十四章面试题
沙雕面试题:Spring数据绑定API是什么?
答: org.springframework.validation.DataBinder
996 面试题:BeanWrapper与JavaBeans之间关系是?
答: • Spring 底层 JavaBeans 基础设施的中心化接口
劝退面试题:DataBinder是怎么完成属性类型转换的?
答: 答案下章揭晓
第十五章面试题
沙雕面试题:Spring 类型转换实现有哪些?
答: 1. 基于 JavaBeans PropertyEditor 接口实现 2. Spring 3.0+ 通用类型转换实现
996 面试题:Spring 类型转换器接口有哪些?
答: • 类型转换接口:org.springframework.core.convert.converter.Converter • 通用类型转换接口: org.springframework.core.convert.converter.GenericConverter • 类型条件接口: org.springframework.core.convert.converter.ConditionalConverter • 综合类型转换接口:org.springframework.core.convert.converter.ConditionalGenericConverter
劝退面试题:TypeDescriptor 是如何处理泛型?
答: 答案下章揭晓
第十六章面试题
沙雕面试题:Java 泛型擦写发生在编译时还是运行时?
答: 运行时
996 面试题:请介绍 Java 5 Type 类型的派生类或接口
答: • java.lang.Class • java.lang.reflect.GenericArrayType • java.lang.reflect.ParameterizedType • java.lang.reflect.TypeVariable • java.lang.reflect.WildcardType
劝退面试题:请说明 ResolvableType 的设计优势?
答: • 简化 Java 5 Type API 开发,屏蔽复杂 API 的运用,如 ParameterizedType • 不变性设计(Immutability) • Fluent API 设计(Builder 模式),链式(流式)编程
第十七章面试题
沙雕面试题:Spring 事件核心接口/组件?
答: • Spring 事件:org.springframework.context.ApplicationEvent • Spring 事件监听器:org.springframework.context.ApplicationListener • Spring 事件发布器:org.springframework.context.ApplicationEventPublisher • Spring 事件广播器: org.springframework.context.event.ApplicationEventMulticaster
996 面试题:Spring 同步和异步事件处理的使用场景?
答: • Spring 同步事件 - 绝大多数 Spring 使用场景,如 ContextRefreshedEvent • Spring 异步事件 - 主要 @EventListener 与 @Asyc 配合,实现异步处理,不阻塞主线程,比如长时间的数据计算任务等。不要轻易调整 SimpleApplicationEventMulticaster 中关联的taskExecutor 对象,除非使用者非常了解 Spring 事件机制,否则容易出现异常行为。
劝退面试题:@EventListener 的工作原理?
答:答案下章揭晓
第十八章面试题
沙雕面试题:Spring 模式注解有哪些?
答: • @org.springframework.stereotype.Component • @org.springframework.stereotype.Repository • @org.springframework.stereotype.Service • @org.springframework.stereotype.Controller • @org.springframework.context.annotation.Configuration
996面试题:@EventListener 的工作原理?
答: • 源码导读-org.springframework.context.event.EventListenerMethodProcessor
1.org.springframework.context.event.EventListenerMethodProcessor#postProcessBeanFactory
2.org.springframework.context.event.EventListenerFactory#createApplicationListener
org.springframework.context.event.DefaultEventListenerFactory#createApplicationListener
3.org.springframework.context.event.ApplicationListenerMethodAdapter#onApplicationEvent
劝退面试题:@PropertySource 的工作原理?
答:答案下章揭晓
第十九章面试题
沙雕面试题:简单介绍Spring Environment 接口?
答: • 核心接口:org.springframework.core.env.Environment • 父接口:org.springframework.core.env.PropertyResolver • 可配置接口:org.springframework.core.env.ConfigurableEnvironment • 职责: • 管理 Spring 配置属性源 • 管理 Profiles
996 面试题:如何控制 PropertySource 的优先级?
答:参考第227节《基于API扩展Spring外部化配置属性源》
劝退面试题:Environment 完整的生命周期是怎样的?
答:答案下章揭晓
第二十章面试题
沙雕面试题:Spring 应用上下文生命周期有哪些阶段?
答: • 刷新阶段 - ConfigurableApplicationContext#refresh() • 启动阶段 - ConfigurableApplicationContext#start() • 停止阶段 - ConfigurableApplicationContext#stop() • 关闭阶段 - ConfigurableApplicationContext#close()
996 面试题:Environment 完整的生命周期是怎样的?
答:代码演示
劝退面试题:Spring 应用上下文生命周期执行动作?
答:本章整体回顾
个人总结
Spring好用的工具类
ObjectUtils
StringUtils
RequestContextHolder
TransactionContextHolder
Assert
ReflectionUtils
ClassUtils
BeanUtils
StreamUtils
WebApplicationContextUtils
ApplicationContextInitializerUtils
Spring IoC容器启动主要步骤
1.创建 BeanFactory 容器
2.注册 Configuration Class(配置类)[SingletonBeanRegistry]
3.启动 Spring 应用上下文
4.关闭 Spring 应用上下文
Spring IoC容器关键类
BeanFactory
ConfigurableListableBeanFactory
ConfigurableListableBeanFactory是BeanFactory关键的子接口
BeanFactory关键的实现DefaultListableBeanFactory
ApplicationContext
AbstractRefreshableApplicationContext
AnnotationConfigWebApplicationContext
ClassPathXmlApplicationContext
FileSystemXmlApplicationContext
XmlWebApplicationContext
ConfigurableApplicationContext
AbstractApplicationContext
GenericApplicationContext
AnnotationConfigApplicationContext
GenericWebApplicationContext
WebApplicationContext
Spring Bean BeanDefinition关键类
Bean元信息BeanDefinition
BeanDefinition
AbstractBeanDefinition
RootBeanDefinition
GenericBeanDefinition
AnnotatedGenericBeanDefinition
手动构建BeanDefinition
BeanDefinitionBuilder
注册BeanDefinition
BeanDefinitionRegistry
AnnotationConfigApplicationContext
BeanDefinition注册入口
BeanDefinitionRegistry#registerBeanDefinition
BeanDefinition元信息读取
BeanDefinitionReader
AbstractBeanDefinitionReader
XmlBeanDefinitionReader
PropertiesBeanDefinitionReader
GroovyBeanDefinitionReader
AnnotatedBeanDefinitionReader
BeanDefinition解析
BeanDefinitionParser
AbstractBeanDefinitionParser
PropertiesBeanDefinitionParser
AnnotationBeanDefinitionParser
Spring Bean名字或id的生成
BeanNameGenerator
AnnotationBeanNameGenerator
DefaultBeanNameGenerator
Spring Bean注册入口
BeanDefinition注册入口
BeanDefinitionRegistry#registerBeanDefinition
单例对象注册入口
SingletonBeanRegistry#registerSingleton
Configuration类相关处理类
Configuration类的解析
ConfigurationClassParser
Configuration类的处理
ConfigurationClassPostProcessor
Spring IoC容器以来查找关键类
单一类型查找
BeanFactory#getBean【不安全】
ObjectFactory#getObjec【不安全】
ObjectProvider#getIfAvailable【安全】
集合类型查找
ListableBeanFactory#getBeansOfType【安全】
ObjectProvider#stream【安全】
Spring应用上下文关键类
AbstractApplicationContext
关键的子类
ClassPathXmlApplicationContext
GenericApplicationContext
AnnotationConfigApplicationContext
AbstractRefreshableApplicationContext
AnnotationConfigWebApplicationContext
关键的方法
refresh
prepareBeanFactory
注册BeanFactory、ResourceLoader、ApplicationEventPublisher、ApplicationContext类的对象
Spring 注解配置工具类
org.springframework.context.annotation.AnnotationConfigUtils
在这个类中可以看到这个类对@Lazy、@Primary、@DependsOn、@Role、@Description注解的简单处理,以及内建依赖的处理,如:internalConfigurationAnnotationProcessor、internalConfigurationBeanNameGenerator、internalAutowiredAnnotationProcessor、internalRequiredAnnotationProcessor。
注解处理器
CommonAnnotationBeanPostProcessor
@PostConstruct
@PreDestroy
@Resource
@WebServiceRef
@WebServiceClient
@EJB
依赖查找中的经典异常
BeansException
NoSuchBeanDefinitionException
触发条件(举例)
当查找 Bean 不存在于 IoC 容器时
场景举例
BeanFactory#getBean
ObjectFactory#getObject
NoUniqueBeanDefinitionException
触发条件(举例)
类型依赖查找时,IoC 容器存在多个 Bean 实例
场景举例
BeanFactory#getBean(Class)
BeanInstantiationException
触发条件(举例)
当 Bean 所对应的类型非具体类时
场景举例
BeanFactory#getBean
BeanCreationException
触发条件(举例)
当 Bean 初始化过程中
场景举例
Bean 初始化方法执行异常时
BeanDefinitionStoreException
触发条件(举例)
当 BeanDefinition 配置元信息非法时
场景举例
XML 配置资源无法打开时
Spring IoC依赖注入关键类
定义依赖注入有哪些类型
org.springframework.beans.factory.annotation.Autowire
AutowireCapableBeanFactory
AUTOWIRE_NO
AUTOWIRE_BY_NAME
AUTOWIRE_BY_TYPE
AUTOWIRE_CONSTRUCTOR
AUTOWIRE_AUTODETECT
Spring IoC依赖注入的方式
构造注入
Setter注入
字段注入
@Autowired
@Resource
@Inject
@Value
方法注入
@Autowired
@Resource
@Inject
@Bean
Spring IoC Bean依赖注入顺序的规则
要注入的Bean对象实例只有一个
直接根据类型查找到这个Bean并进行注入
要注入的Bean的对象实例有多个
1.首先根据@Qualifie来判断,首先根据看被注入的字段上是否有标记@Qualifier注解;如果有,则筛选出符合这个注解标注的名称的Bean对象
2.次之@Primary来判断,现在判断这个类型的多个Bean实例对象中是否有表示为@Primary的,有则注入标记为@Primary的Bean实例对象
3.次之根据@Priority来判断,那个Bean实例对象上标记的@Priority大 则注入那个Bean对象
4.次之根据名称来判断,如果发现没有名称相匹配的 那就会报错;如果有唯一一个名称相匹配的 则成功注入
依赖处理关键的类
入口: DefaultListableBeanFactory#resolveDependency
依赖描述符:DependencyDescriptor
自定绑定候选对象处理器:AutowireCandidateResolver
@Autowired注入逻辑处理的关键类
MergedBeanDefinitionPostProcessor
AutowiredAnnotationBeanPostProcessor
AutowiredAnnotationBeanPostProcessor不仅可以处理@Autowired注解,还可以处理@Value和@Inject注解
@Autowired
@Value
@Inject
Java通用注解注入原理关键类
InstantiationAwareBeanPostProcessor
DestructionAwareBeanPostProcessor
MergedBeanDefinitionPostProcessor
InitDestroyAnnotationBeanPostProcessor
CommonAnnotationBeanPostProcessor
1.首先CommonAnnotationBeanPostProcessor会在AutowiredAnnotationBeanPostProcessor前面进行处理,从这两个类的order属性的值可以得知(order的值越小越优先被执行)。 2.这个类除了处理@Resource注解的依赖注入外,还有对@PostConstruct、@PreDestroy注解标记的对象的生命周期的管理。
Aware系列接口
BeanNameAware
实现这个接口,可以获取Bean的名称
BeanClassLoaderAware
BeanFactoryAware
EnvironmentAware
EmbeddedValueResolverAware
ResourceLoaderAware
ApplicationEventPublisherAware
MessageSourceAware
ApplicationContextAware
这6个Aware接口,会在ApplicationContextAwareProcessor#postProcessBeforeInitialization中被回调
ResourceLoaderAware
LoadTimeWeaverAwareProcessor
ServletContextAware
BeanPostProcessor系列接口
AutowiredAnnotationBeanPostProcessor
处理@Autowired、@Value、@Inject等注解的注入逻辑
CommonAnnotationBeanPostProcessor
处理通用注入注解@Resource等注解的注入逻辑,以及@PostConstruct、@PreDestroy注解的bean的生命周期的管理
InstantiationAwareBeanPostProcessor
可以对Bean实例化前阶段进行扩展和处理
SmartInstantiationAwareBeanPostProcessor
ApplicationContextAwareProcessor
首先这个类也实现了BeanPostProcessor,所以也会有postProcessBeforeInitialization方法的回调 这个BeanPostProcessor是在org.springframework.context.support.AbstractApplicationContext#prepareBeanFactory方法的beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this));代码中被添加进去的。 这个类的postProcessBeforeInitialization方法中会对EnvironmentAware、EmbeddedValueResolverAware、ResourceLoaderAware、ApplicationEventPublisherAware、MessageSourceAware、ApplicationContextAware这6个Aware接口进行回调。
DestructionAwareBeanPostProcessor
Bean在销毁前阶段会执行DestructionAwareBeanPostProcessor#postProcessBeforeDestruction方法
MergedBeanDefinitionPostProcessor
处理BeanDefinitio的合并
ApplicationListenerDetector
ApplicationListenerDetector是ApplicationListener的探测器,并且同时实现了DestructionAwareBeanPostProcessor和MergedBeanDefinitionPostProcessor两个接口
MethodValidationPostProcessor
处理@Validated校验注解的校验逻辑
LoadTimeWeaverAwareProcessor
ServletContextAwareProcessor
BeanPostProcessorChecker
BeanFactoryPostProcessor系列接口
BeanDefinitionRegistryPostProcessor
Bean生命周期相关接口
DisposableBean
Bean对象的destroy回调。实现这个接口,当Spring IoC容器关闭或销毁时,会回调所有这个接口实现类的对象的destroy方法
Spring事件/事件监听关键类
Spring事件
ApplicationEvent
ContextRefreshedEvent
ApplicationStartedEvent
ContextStoppedEvent
ContextClosedEvent
事件发布器
ApplicationEventPublisher
ApplicationContext
AbstractApplicationContext
事件监听器
ApplicationListener
事件多路广播器
ApplicationEventMulticaster
AbstractApplicationEventMulticaster
SimpleApplicationEventMulticaster
事件监听探测器
ApplicationListenerDetector
Environment相关关键类
Environment
ConfigurableEnvironment
AbstractEnvironment
StandardEnvironment
StandardReactiveWebEnvironment
Lifecycle关键类
LifecycleProcessor
DefaultLifecycleProcessor
其它类
BeanFactory
ListableBeanFactory
HierarchicalBeanFactory
ConfigurableBeanFactory
ConfigurableListableBeanFactory
DefaultListableBeanFactory
这个类是BeanFactory、BeanDefinitionRegistry两个接口最根本的核心实现类
ObjectFactory
ObjectProvider
BeanDefinitionRegistry
DefaultListableBeanFactory
这个类是BeanDefinitionRegistry的一个重要实现
SingletonBeanRegistry
通过这个类可以将外部对象注册到Spring IoC容器中
BeanFactoryPostProcessor
BeanDefinitionRegistryPostProcessor
ConfigurationClassPostProcessor
使用位置:org.springframework.context.annotation.AnnotationConfigUtils#registerAnnotationConfigProcessors(org.springframework.beans.factory.support.BeanDefinitionRegistry, java.lang.Object)