请注意,Aware被Bean实现,作用于单个Bean , BeanPostProcessor被注册到Bean工厂中,作用于工厂中的每个Bean 。实例化Bean&属性设置#这图里所描述的是,创建Bean时先从BeanDefinition开始,然后实例化Bean,在实例化前后,
InstantiationAwareBeanPostProcessor
会被调用 。文章插图
下面从
doGetBean
方法开始(getBean
方法实际调用的方法 , 它已经是AbstractBeanFactory
中的方法了),看下面的代码需要注意,Spring中Bean的作用域可以分为Singleton、Prototype和其它,其中Singleton和Prototype是Spring框架原生支持的,其它作用域需要自行扩展,比如SpringWebMVC扩展了Session等作用域 。所以你看下面的代码时也要在脑袋里把它们分成Singleton、Prototype和其它作用域,要不然你可能就被这很长很长的代码搞迷糊了:protected <T> T doGetBean(String name, @Nullable Class<T> requiredType, @Nullable Object[] args, boolean typeCheckOnly)throws BeansException {String beanName = transformedBeanName(name);Object beanInstance;// ...try {// 根据BeanName获取BeanDefinition// MergedBeanDefinition是将它和它的祖先Bean整合,这里可以先忽略,就当作普通的BeanDefinitionRootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);checkMergedBeanDefinition(mbd, beanName, args);// 如果是Singleton,按Singleton的方法创建if (mbd.isSingleton()) {sharedInstance = getSingleton(beanName, () -> {try {// [+] 实际创建Beanreturn createBean(beanName, mbd, args);}catch (BeansException ex) {}});beanInstance = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);}// 如果是Prototype,按Prototype的方法创建else if (mbd.isPrototype()) {Object prototypeInstance = null;try {beforePrototypeCreation(beanName);// [+] 实际创建BeanprototypeInstance = createBean(beanName, mbd, args);}finally {afterPrototypeCreation(beanName);}beanInstance = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);}// 如果是其它作用域,那么就放到其它作用域中创建// 这里的逻辑和Singleton很像,在Singleton创建中// Bean放到SingletonBeanRegistry中管理,而这个// 放到对应的作用域中管理else {String scopeName = mbd.getScope();Scope scope = this.scopes.get(scopeName);try {Object scopedInstance = scope.get(beanName, () -> {beforePrototypeCreation(beanName);try {// [+] 实际创建Beanreturn createBean(beanName, mbd, args);}finally {afterPrototypeCreation(beanName);}});beanInstance = getObjectForBeanInstance(scopedInstance, name, beanName, mbd);}catch (IllegalStateException ex) {}}}catch (BeansException ex) {}}return adaptBeanInstance(name, beanInstance, requiredType);}
所以 , 不管是哪个作用域,它们都调用了createBean
来创建Bean,AbstractBeanFactory
中并没有实现这个方法,createBean
是AbstractAutowireCapableBeanFactory
抽象类实现的:@Overrideprotected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)throws BeanCreationException {RootBeanDefinition mbdToUse = mbd;try {// 在Bean实例化之前 , 让一些关心实例化阶段的BeanPostProcessor得到执行Object bean = resolveBeforeInstantiation(beanName, mbdToUse);// 如果返回的bean不是null,那么结束整个阶段,直接返回这个值作为beanif (bean != null) {return bean;}}catch (Throwable ex) {}try {// 实例化BeanObject beanInstance = doCreateBean(beanName, mbdToUse, args);return beanInstance;}catch (BeanCreationException | ImplicitlyAppearedSingletonException ex) {}catch (Throwable ex) {}}
所以,resolveBeforeInstantiation
方法应该就是查找那些InstantiationAwareBeanPostProcessor
,然后调用它们 。InstantiationAwareBeanPostProcessor的before hook#
protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {Object bean = null;if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {Class<?> targetType = determineTargetType(beanName, mbd);if (targetType != null) {// 应用BeanPostProcessor的beforeInstantiationbean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);if (bean != null) {// 调用BeanPostProcessors的初始化后方法,注意是初始化后不是实例化后// 前提是before方法返回了一个对象bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);}}}mbd.beforeInstantiationResolved = (bean != null);}return bean;}
我们可以看到,这个方法的代码非常简单,虽然还没写明 , 但是99%就是调用所有的InstantiationAwareBeanPostProcessor
了,两个apply
应该就是做这个工作的 。我们不妨点进去看一个:
推荐阅读
- 详解AQS中的condition源码原理
- 怎么去巴基斯坦去巴基斯坦时需要注意什么(从中国去巴基斯坦怎么去)
- 有到过伊拉克的人吗应该怎么去(从国内怎样到伊拉克)
- 从ObjectPool到CAS指令
- 蜘蛛的丝是从哪里吐出来的?
- .net 温故知新:【8】.NET 中的配置从xml转向json
- iqoo7电池多大_iqoo7电池多少毫安
- 【lwip】08-ARP协议一图笔记及源码实现
- <一>从指令角度了解函数堆栈调用过程
- 【lwip】07-链路层收发以太网数据帧源码分析