文章目录
populateBean一流程图
- 存在InstantiationAwareBeanPostProcessor自定义依赖注入,则调用postProcessAfterInstantiation;根据postProcessAfterInstantiation返回Boolean值决定是否完成spring自带DI
- 如果配置了autowired_by_name,则根据名称进行注入
- 如果配置了autowired_by_type,则根据类型进行注入
- 通过InstantiationAwareBeanPostProcessor处理注解注入
- 处理xml等方式配置的properties注入

populateBean-源码分析
- 1 InstantiationAwareBeanPostProcessor注入
- 2 spring 自动注入autowired By Name or Type
- 3 注解注入
- 4 xml注入
protected void populateBean(String beanName, RootBeanDefinition mbd, @Nullable BeanWrapper bw) {
......删除其他代码
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
for (BeanPostProcessor bp : getBeanPostProcessors()) {
if (bp instanceof InstantiationAwareBeanPostProcessor) {
* 如果返回false则终止DI注入
* -----------------------
* 如果你定义一个InstantiationAwareBeanPostProcessor
* 在postProcessAfterInstantiation里完成了DI 并返回false 则完成自定义的DI过程 或者直接返回false
* 说明你期望终止特定bean的注入过程
* 而如果返回true说明你期望自定义DI与springDI共同作用
* -----------------------
step-1: postProcessAfterInstantiation表示实例化之后 Initialization表示初始化之后 实例化之后未加入bean容器管理 初始化之后已经加入singletonObjects被bean容器管理
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
if (!ibp.postProcessAfterInstantiation(bw.getWrappedInstance(), beanName)) {
return;
}
}
}
}
取容器在解析bean定义资源时为bd设置的PropertyValues,一般我们在xml中配置
PropertyValues pvs = (mbd.hasPropertyValues() ? mbd.getPropertyValues() : null);
int resolvedAutowireMode = mbd.getResolvedAutowireMode();
step-2:判断是根据名称注入还是类型注入 =如果是默认则跳过这里 一般情况下我们采用AUTOWIRE_NO[spring不自动注入而是通过注解注入]
注入方式 分为 AUTOWIRE_BY_NAME AUTOWIRE_BY_TYPE AUTOWIRE_NO等[也就是采用名称注入 type注入 还是no依赖注解或者xml配置注入]
if (resolvedAutowireMode == AUTOWIRE_BY_NAME || resolvedAutowireMode == AUTOWIRE_BY_TYPE) {
MutablePropertyValues newPvs = new MutablePropertyValues(pvs);
if (resolvedAutowireMode == AUTOWIRE_BY_NAME) {
autowireByName(beanName, mbd, bw, newPvs);
}
if (resolvedAutowireMode == AUTOWIRE_BY_TYPE) {
autowireByType(beanName, mbd, bw, newPvs);
}
pvs = newPvs;
}
...... 删除其他代码
if (hasInstAwareBpps || needsDepCheck) {
step-3: 获取所有getter/setter对应的属性值 不仅仅是@autowired等spring注解的属性而是这个bean的所有属性值比如通用的getClass对应的class属性值
PropertyDescriptor[] filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
if (hasInstAwareBpps) {
for (BeanPostProcessor bp : getBeanPostProcessors()) {
* AutowiredAnnotationBeanPostProcessor 處理@Autowired @Value @Inject等
* CommonAnnotationBeanPostProcessor 負責@Resource | @PostConstruct @PreDestroy(交給父类处理)等
*
if (bp instanceof InstantiationAwareBeanPostProcessor) {
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
pvs = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
if (pvs == null) {
return;
}
}
}
}
...... 删除依赖检查
}
if (pvs != null) {
step-4: 属性DI注入 PropertyValues是一般值xml配置的properties
采用set注入
applyPropertyValues(beanName, mbd, bw, pvs);
}
结合这个流程可以看出 存在多个对相同的属性的注入 比如同时配置注解与xml 最终生效流程如下
自定义注入--> AUTOWIRE_BY_NAME-->AUTOWIRE_BY_TYPE->注解注入[CommonAnnotationBeanPostProcessor -> AutowiredAnnotationBeanPostProcessor]--> xml注入
}
总结
- 依赖注入中存在一个核心问题,单例bean的循环依赖[参见二十一篇]
- postProcessProperties和postProcessPropertyValues的功能一致,区别在于前者依赖Metadata ,后者依赖PropertyDescriptor,后者未来版本应该会被淘汰
- 注解注入的两个核心BPP如下
CommonAnnotationBeanPostProcessor | AutowiredAnnotationBeanPostProcessor |
---|
处理@Resource @PostConstruct @PreDestroy 等 | @Autowired @Value @Inject等 |
- 注入方式有构造注入 名称注入 类型注入 注解注入以及自定义等多种方式
autowired_by_name | autowired_by_type | autowire_constructor | autowire_no注解注入 |
---|
- 如果存在一个属性值多次注入,最后执行DI的覆盖前置,顺序如下