Spring源码分析のBean创建流程(下)
文章目录
- 前言
- 一、createBean
- 1.1、resolveBeanClass
- 1.2、resolveBeforeInstantiation
- 二、doCreateBean
- 2.1、createBeanInstance
- 2.2、applyMergedBeanDefinitionPostProcessors
- 2.3、initializeBean
- 2.4 registerDisposableBeanIfNecessary
- 总结
前言
在doGetBean
方法中,如果即将获取的bean不存在,无论是何种作用域的bean,最终都会调用createBean
方法去创建bean。createBean
方法是bean创建流程中的重要方法。
一、createBean
createBean
有三个参数,而主要参数:参数一是bean的名称,而参数二是合并后的bean定义。在方法中主要完成了:
- 将beanName转换为bean的class对象,并且赋值给bean定义的BeanClass属性。
- 处理当前 Bean 配置了方法重写的情况。
- bean实例化前的处理
- 在doCreateBean中进行bean实例化等一系列操作。
@Override
protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
throws BeanCreationException {
if (logger.isTraceEnabled()) {
logger.trace("Creating instance of bean '" + beanName + "'");
}
RootBeanDefinition mbdToUse = mbd;
// Make sure bean class is actually resolved at this point, and
// clone the bean definition in case of a dynamically resolved Class
// which cannot be stored in the shared merged bean definition.
//1.1、resolveBeanClass将bean定义和bean的名称传入resolveBeanClass,得到bean的class对象
Class<?> resolvedClass = resolveBeanClass(mbd, beanName);
if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
mbdToUse = new RootBeanDefinition(mbd);
//将bean定义中的beanClass属性设置为加载后的类
mbdToUse.setBeanClass(resolvedClass);
}
// Prepare method overrides.
try {
//处理当前 Bean 配置了方法重写(可能是通过 XML 配置、注解或代码配置)的情况
mbdToUse.prepareMethodOverrides();
}
catch (BeanDefinitionValidationException ex) {
throw new BeanDefinitionStoreException(mbdToUse.getResourceDescription(),
beanName, "Validation of method overrides failed", ex);
}
try {
// Give BeanPostProcessors a chance to return a proxy instead of the target bean instance.
//1.2、resolveBeforeInstantiation bean实例化前的处理
Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
if (bean != null) {
return bean;
}
}
catch (Throwable ex) {
throw new BeanCreationException(mbdToUse.getResourceDescription(), beanName,
"BeanPostProcessor before instantiation of bean failed", ex);
}
try {
//实例化bean
Object beanInstance = doCreateBean(beanName, mbdToUse, args);
if (logger.isTraceEnabled()) {
logger.trace("Finished creating instance of bean '" + beanName + "'");
}
//返回bean的实例
return beanInstance;
}
catch (BeanCreationException | ImplicitlyAppearedSingletonException ex) {
// A previously detected exception with proper bean creation context already,
// or illegal singleton state to be communicated up to DefaultSingletonBeanRegistry.
throw ex;
}
catch (Throwable ex) {
throw new BeanCreationException(
mbdToUse.getResourceDescription(), beanName, "Unexpected exception during bean creation", ex);
}
}
1.1、resolveBeanClass
resolveBeanClass
方法是利用jvm去加载类,如果发现当前bean定义的beanClass属性已经是class类型,就直接返回,不去重复加载。
在doResolveBeanClass
方法中,主要考虑到了AOP的场景,以及类名是表达式的场景。
类名是动态表达式的案例:
applicationContext.xml
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<!-- 定义动态类名 -->
<bean id="dynamicClass" class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
<property name="properties" value="classpath:dynamic.properties"/>
</bean>
<!-- 使用 SpEL 表达式动态解析类名 -->
<bean id="myBean" class="#{ T(java.lang.Class).forName('${dynamic.class.name}') }"/>
</beans>
dynamic.properties
# dynamic.properties
dynamic.class.name=com.example.MyDynamicClass
package com.example;
public class MyDynamicClass {
public void greet() {
System.out.println("Hello from MyDynamicClass!");
}
}
resolveBeanClass
&doResolveBeanClass
详解:
@Nullable
protected Class<?> resolveBeanClass(RootBeanDefinition mbd, String beanName, Class<?>... typesToMatch)
throws CannotLoadBeanClassException {
try {
//如果当前bean定义的beanClass属性已经是class类型,就直接返回,不去重复加载
if (mbd.hasBeanClass()) {
return mbd.getBeanClass();
}
//无论是否开启了安全检查,最终都会去调用doResolveBeanClass方法
if (System.getSecurityManager() != null) {
return AccessController.doPrivileged((PrivilegedExceptionAction<Class<?>>)
() -> doResolveBeanClass(mbd, typesToMatch), getAccessControlContext());
}
else {
return doResolveBeanClass(mbd, typesToMatch);
}
}
catch (PrivilegedActionException pae) {
ClassNotFoundException ex = (ClassNotFoundException) pae.getException();
throw new CannotLoadBeanClassException(mbd.getResourceDescription(), beanName, mbd.getBeanClassName(), ex);
}
catch (ClassNotFoundException ex) {
throw new CannotLoadBeanClassException(mbd.getResourceDescription(), beanName, mbd.getBeanClassName(), ex);
}
catch (LinkageError err) {
throw new CannotLoadBeanClassException(mbd.getResourceDescription(), beanName, mbd.getBeanClassName(), err);
}
}
/**
* 真正去加载类的方法
* 参数一:合并后的bean定义
**/
private Class<?> doResolveBeanClass(RootBeanDefinition mbd, Class<?>... typesToMatch) throws ClassNotFoundException {
// 获取默认的类加载器,用于加载 Bean 类。
ClassLoader beanClassLoader = getBeanClassLoader();
// 将动态加载器初始化为默认的 Bean 类加载器
ClassLoader dynamicLoader = beanClassLoader;
// 记录是否需要重新解析的标志,默认为 false
boolean freshResolve = false;
// 如果传入的 typesToMatch 不为空,表示需要进行类型检查(AOP的场景)
if (!ObjectUtils.isEmpty(typesToMatch)) {
ClassLoader tempClassLoader = getTempClassLoader();
if (tempClassLoader != null) {
dynamicLoader = tempClassLoader;
freshResolve = true;
if (tempClassLoader instanceof DecoratingClassLoader) {
DecoratingClassLoader dcl = (DecoratingClassLoader) tempClassLoader;
for (Class<?> typeToMatch : typesToMatch) {
dcl.excludeClass(typeToMatch.getName());
}
}
}
}
// 获取 Bean 定义中的类名
String className = mbd.getBeanClassName();
// 如果类名不为空
if (className != null) {
// 如果类名是一个表达式,可能会被解析成实际的类名
Object evaluated = evaluateBeanDefinitionString(className, mbd);
// 类名与原始类名不同,表示类名是动态解析出来的
if (!className.equals(evaluated)) {
// 结果是一个 Class 对象
if (evaluated instanceof Class) {
// 直接返回 Class 对象
return (Class<?>) evaluated;
}
// 如果结果是一个字符串
else if (evaluated instanceof String) {
// 将动态解析后的类名赋值给 className
className = (String) evaluated;
// 标记需要重新解析
freshResolve = true;
}
else {
throw new IllegalStateException("Invalid class name expression result: " + evaluated);
}
}
// 如果需要重新解析
if (freshResolve) {
// 如果使用临时类加载器进行解析,则提前返回,不将结果缓存到 Bean 定义中
if (dynamicLoader != null) {
try {
// 尝试用动态加载器加载该类
return dynamicLoader.loadClass(className);
} catch (ClassNotFoundException ex) {
if (logger.isTraceEnabled()) {
logger.trace("Could not load class [" + className + "] from " + dynamicLoader + ": " + ex);
}
}
}
// 使用默认的类加载器加载类并返回
return ClassUtils.forName(className, dynamicLoader);
}
}
// 如果没有找到类名,或者没有重新解析,最终会使用Class.forName加载类
return mbd.resolveBeanClass(beanClassLoader);
}
一般场景下通过org.springframework.util.ClassUtils#forName的Class.forName方法加载类
1.2、resolveBeforeInstantiation
在resolveBeforeInstantiation
方法中,重点会判断目标bean是否实现了InstantiationAwareBeanPostProcessor
接口,当一个类实现了InstantiationAwareBeanPostProcessor
接口时,可以选择重写其中的postProcessAfterInstantiation
(实例化后)、postProcessBeforeInstantiation
(实例化前)方法,以及其父类BeanPostProcessor
的postProcessAfterInitialization
(初始化后)、postProcessBeforeInitialization
(初始化前)的方法(接口中有default关键字):
@Component
public class MyInstantiationAwareBeanPostProcessor implements InstantiationAwareBeanPostProcessor {
/**
* bean实例化前的处理
* 可以在方法中利用反射直接创建对象
* @param beanClass the class of the bean to be instantiated
* @param beanName the name of the bean
* @return
* @throws BeansException
*/
public Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) throws BeansException {
Object bean = null;
try {
bean = beanClass.newInstance();
} catch (InstantiationException e) {
throw new RuntimeException(e);
} catch (IllegalAccessException e) {
throw new RuntimeException(e);
}
return bean;
}
/**
* hasInstantiationAwareBeanPostProcessors() 的判断依据
* @param bean the bean instance created, with properties not having been set yet
* @param beanName the name of the bean
* @return
* @throws BeansException
*/
public boolean postProcessAfterInstantiation(Object bean, String beanName) throws BeansException {
return beanName.equals("orderService");
}
/**
* bean初始化前的处理
* @param bean the new bean instance
* @param beanName the name of the bean
* @return
* @throws BeansException
*/
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
return null;
}
/**
* bean初始化后的处理
* @param bean the new bean instance
* @param beanName the name of the bean
* @return
* @throws BeansException
*/
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
return null;
}
}
可以在applyBeanPostProcessorsBeforeInstantiation
方法中,通过反射创建对象。这样的对象,生命周期就不归Spring容器去统一管理了,直接跳转到初始化后的方法,然后返回bean。
@Nullable
protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
Object bean = null;
if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
// Make sure bean class is actually resolved at this point.
//有自定义的bean实现了InstantiationAwareBeanPostProcessor接口
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
Class<?> targetType = determineTargetType(beanName, mbd);
if (targetType != null) {
//调用实例化前的方法,在该方法中,可以自己通过反射创建对象
bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
//如果自己通过反射创建了对象,直接执行初始化后的方法
if (bean != null) {
bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
}
}
}
mbd.beforeInstantiationResolved = (bean != null);
}
return bean;
}
二、doCreateBean
在doCreateBean
方法中,主要做了:
- 通过反射创建一个bean的实例,并且包装成BeanWrapper。
- 遍历所有实现了
MergedBeanDefinitionPostProcessor
接口的类,执行其中的postProcessMergedBeanDefinition
方法(在创建了实例后,修改bean定义) - 进行bean的属性填充。
- 进行bean的初始化操作。
- 确保在Spring容器销毁Bean时,能够正确地调用其销毁方法。
protected Object doCreateBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
throws BeanCreationException {
// Instantiate the bean.
//定义一个BeanWrapper 对象
BeanWrapper instanceWrapper = null;
//如果当前需要实例化的bean是单例的
if (mbd.isSingleton()) {
//尝试从缓存中获取
//k:bean的名称 value 对应的BeanWrapper 对象
//private final ConcurrentMap<String, BeanWrapper> factoryBeanInstanceCache = new ConcurrentHashMap<>();
instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
}
//缓存中获取不到
if (instanceWrapper == null) {
//2.1、createBeanInstance 创建一个bean的实例,并且包装成BeanWrapper
instanceWrapper = createBeanInstance(beanName, mbd, args);
}
//获取创建完成的bean的实例
Object bean = instanceWrapper.getWrappedInstance();
//得到bean实例的class 例:class org.ragdollcat.OrderService
Class<?> beanType = instanceWrapper.getWrappedClass();
//当前的bean 不是 nullbean
if (beanType != NullBean.class) {
//设置bean定义的解析目标类型
mbd.resolvedTargetType = beanType;
}
//允许后处理器修改合并的 bean 定义。
synchronized (mbd.postProcessingLock) {
if (!mbd.postProcessed) {
try {
//2.2 applyMergedBeanDefinitionPostProcessors
applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
}
catch (Throwable ex) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName,
"Post-processing of merged bean definition failed", ex);
}
mbd.postProcessed = true;
}
}
// Eagerly cache singletons to be able to resolve circular references
// even when triggered by lifecycle interfaces like BeanFactoryAware.
//这一段和解决循环依赖有关 单独开一篇分析
boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
isSingletonCurrentlyInCreation(beanName));
if (earlySingletonExposure) {
if (logger.isTraceEnabled()) {
logger.trace("Eagerly caching bean '" + beanName +
"' to allow for resolving potential circular references");
}
addSingletonFactory(beanName, () -> getEarlyBeanReference(beanName, mbd, bean));
}
// Initialize the bean instance.
Object exposedObject = bean;
try {
//进行bean的属性填充 单独开一篇分析
populateBean(beanName, mbd, instanceWrapper);
//2.3、initializeBean 进行bean的初始化
exposedObject = initializeBean(beanName, exposedObject, mbd);
}
catch (Throwable ex) {
if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {
throw (BeanCreationException) ex;
}
else {
throw new BeanCreationException(
mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);
}
}
//解决循环依赖 单独开一篇说明
if (earlySingletonExposure) {
Object earlySingletonReference = getSingleton(beanName, false);
if (earlySingletonReference != null) {
if (exposedObject == bean) {
exposedObject = earlySingletonReference;
}
else if (!this.allowRawInjectionDespiteWrapping && hasDependentBean(beanName)) {
String[] dependentBeans = getDependentBeans(beanName);
Set<String> actualDependentBeans = new LinkedHashSet<>(dependentBeans.length);
for (String dependentBean : dependentBeans) {
if (!removeSingletonIfCreatedForTypeCheckOnly(dependentBean)) {
actualDependentBeans.add(dependentBean);
}
}
if (!actualDependentBeans.isEmpty()) {
throw new BeanCurrentlyInCreationException(beanName,
"Bean with name '" + beanName + "' has been injected into other beans [" +
StringUtils.collectionToCommaDelimitedString(actualDependentBeans) +
"] in its raw version as part of a circular reference, but has eventually been " +
"wrapped. This means that said other beans do not use the final version of the " +
"bean. This is often the result of over-eager type matching - consider using " +
"'getBeanNamesForType' with the 'allowEagerInit' flag turned off, for example.");
}
}
}
}
// Register bean as disposable.
try {
//2.4 registerDisposableBeanIfNecessary 用于处理可能存在的bean销毁回调
registerDisposableBeanIfNecessary(beanName, bean, mbd);
}
catch (BeanDefinitionValidationException ex) {
throw new BeanCreationException(
mbd.getResourceDescription(), beanName, "Invalid destruction signature", ex);
}
return exposedObject;
}
2.1、createBeanInstance
这段代码根据不同的条件(是否有工厂方法、是否有构造函数、是否需要自动装配等)决定使用何种方式来实例化一个 Bean。最终将结果包装成BeanWrapper
返回。
- 如果定义了工厂方法,则通过工厂方法来创建 Bean。
- 如果定义了 Supplier,则通过该提供者获取 Bean 实例。
- 如果 Bean 需要通过构造函数进行自动装配,则选择合适的构造函数。
- 最常见的情况:如果没有特殊的要求,直接使用无参构造函数创建 Bean。
protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) {
// Make sure bean class is actually resolved at this point.
//这一步会看mbd.hasBeanClass()是否有值
Class<?> beanClass = resolveBeanClass(mbd, beanName);
//检查Bean类是否是公共的,若不是则抛出异常(除非允许非公共访问)
if (beanClass != null && !Modifier.isPublic(beanClass.getModifiers()) && !mbd.isNonPublicAccessAllowed()) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName,
"Bean class isn't public, and non-public access not allowed: " + beanClass.getName());
}
//获取Bean定义中的实例提供者
Supplier<?> instanceSupplier = mbd.getInstanceSupplier();
if (instanceSupplier != null) {
//如果定义了实例提供者,直接通过实例提供者获取Bean实例(通常用于通过 Lambda 或其他外部工厂方法提供 Bean 实例的情况。)
return obtainFromSupplier(instanceSupplier, beanName);
}
//如果定义了工厂方法,则使用工厂方法来实例化Bean
//使用 @Bean 注解的情况,或者显式定义工厂方法的场景。
if (mbd.getFactoryMethodName() != null) {
return instantiateUsingFactoryMethod(beanName, mbd, args);
}
// 如果 args 为空(即没有显式传入构造函数参数)
// 并且 Bean 的构造函数或工厂方法已经解析过(resolvedConstructorOrFactoryMethod != null),则直接根据解析结果创建 Bean 实例。
boolean resolved = false;
boolean autowireNecessary = false;
if (args == null) {
synchronized (mbd.constructorArgumentLock) {
检查Bean定义中是否已经解析了构造函数或者工厂方法
if (mbd.resolvedConstructorOrFactoryMethod != null) {
resolved = true;
autowireNecessary = mbd.constructorArgumentsResolved;
}
}
}
if (resolved) {
if (autowireNecessary) {
// 如果需要自动装配,则调用autowireConstructor来处理自动装配
return autowireConstructor(beanName, mbd, null, null);
}
else {
// 如果不需要自动装配,直接使用无参构造器创建Bean
return instantiateBean(beanName, mbd);
}
}
//进行构造方法推论
//如果 Bean 需要通过构造函数进行自动装配(例如通过 @Autowired 注解自动注入构造函数参数),则会进入这个分支。
Constructor<?>[] ctors = determineConstructorsFromBeanPostProcessors(beanClass, beanName);
if (ctors != null || mbd.getResolvedAutowireMode() == AUTOWIRE_CONSTRUCTOR ||
mbd.hasConstructorArgumentValues() || !ObjectUtils.isEmpty(args)) {
return autowireConstructor(beanName, mbd, ctors, args);
}
// 某些情况下,Bean 定义中可能指定了首选的构造函数,这时候就会选择这些构造函数来创建 Bean。
ctors = mbd.getPreferredConstructors();
if (ctors != null) {
return autowireConstructor(beanName, mbd, ctors, null);
}
// 最常见的情况,Bean 没有复杂的构造函数或特殊要求时,会通过无参构造函数创建实例。
return instantiateBean(beanName, mbd);
}
instantiateBean 利用反射创建对象
补充:三种情况案例
- 使用工厂方法创建 Bean:
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class AppConfig {
@Bean
public Person person() {
return new Person("John", 30);
}
}
- 使用实例提供者获取 Bean 实例:
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.function.Supplier;
@Configuration
public class AppConfig {
// 使用 Supplier 提供一个 Person 实例
@Bean
public Person person() {
Supplier<Person> personSupplier = () -> new Person("Tom", 40);
return personSupplier.get();
}
}
- 使用自动装配构造函数创建 Bean:
public class Person {
private String name;
private int age;
private Address address;
// 通过构造函数自动装配
public Person(String name, int age, Address address) {
this.name = name;
this.age = age;
this.address = address;
}
// getter 和 setter 省略
}
public class Address {
private String city;
private String street;
public Address(String city, String street) {
this.city = city;
this.street = street;
}
// getter 和 setter 省略
}
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class AppConfig {
// 通过构造函数自动装配 Address 和 Person
@Bean
public Person person(Address address) {
return new Person("Jack", 35, address);
}
// Address Bean
@Bean
public Address address() {
return new Address("New York", "5th Avenue");
}
}
2.2、applyMergedBeanDefinitionPostProcessors
applyMergedBeanDefinitionPostProcessors
方法主要的作用:遍历所有实现了MergedBeanDefinitionPostProcessor
接口的类,执行其中的postProcessMergedBeanDefinition
方法:
@Component
public class MyMergedBeanDefinitionPostProcessor implements MergedBeanDefinitionPostProcessor {
public void postProcessMergedBeanDefinition(RootBeanDefinition beanDefinition, Class<?> beanType, String beanName) {
//允许在bean创建实例后,对bean定义再次进行修改
}
}
protected void applyMergedBeanDefinitionPostProcessors(RootBeanDefinition mbd, Class<?> beanType, String beanName) {
//遍历所有实现了MergedBeanDefinitionPostProcessor接口的类,执行其中的postProcessMergedBeanDefinition方法
for (MergedBeanDefinitionPostProcessor processor : getBeanPostProcessorCache().mergedDefinition) {
processor.postProcessMergedBeanDefinition(mbd, beanType, beanName);
}
}
BeanPostProcessorCache getBeanPostProcessorCache() {
BeanPostProcessorCache bpCache = this.beanPostProcessorCache;
if (bpCache == null) {
bpCache = new BeanPostProcessorCache();
//下面的各种BeanPostProcessor都是BeanPostProcessor 的子类
for (BeanPostProcessor bp : this.beanPostProcessors) {
//该类型的 BeanPostProcessor 用于在 Bean 实例化时进行处理,通常是在 Bean 的实例化前后做一些操作,比如属性填充、依赖注入等。
if (bp instanceof InstantiationAwareBeanPostProcessor) {
bpCache.instantiationAware.add((InstantiationAwareBeanPostProcessor) bp);
//是 InstantiationAwareBeanPostProcessor 的子接口
if (bp instanceof SmartInstantiationAwareBeanPostProcessor) {
bpCache.smartInstantiationAware.add((SmartInstantiationAwareBeanPostProcessor) bp);
}
}
//该接口用于处理 Bean 销毁时的回调。实现该接口的 BeanPostProcessor 可以在 Bean 销毁时做一些清理工作。
if (bp instanceof DestructionAwareBeanPostProcessor) {
bpCache.destructionAware.add((DestructionAwareBeanPostProcessor) bp);
}
//用于处理合并后的 Bean 定义的后处理器。合并后的 Bean 定义通常是在多个配置或多个容器中对 Bean 的定义进行合并时使用的。
if (bp instanceof MergedBeanDefinitionPostProcessor) {
bpCache.mergedDefinition.add((MergedBeanDefinitionPostProcessor) bp);
}
}
this.beanPostProcessorCache = bpCache;
}
//最后返回构建好的 BeanPostProcessorCache,该缓存包含了按照不同类型分类的 BeanPostProcessor。
return bpCache;
}
2.3、initializeBean
initializeBean
是进行bean的初始化操作:
- 调用 Aware 接口方法:首先根据是否存在
SecurityManager
,安全地调用 bean 的 Aware 接口方法。 - 应用初始化前的
BeanPostProcessor
:在 bean 初始化前,执行所有的BeanPostProcessor
,对 bean 进行增强或修改。 - 执行初始化方法:调用
InitializingBean
的afterPropertiesSet()
方法以及init-method
配置的自定义初始化方法。 - 应用初始化后的
BeanPostProcessor
:在初始化后,执行所有的BeanPostProcessor
,对 bean 进行进一步的增强。 - 返回处理后的 bean:返回可能经过修改或增强的最终 bean 实例。
protected Object initializeBean(String beanName, Object bean, @Nullable RootBeanDefinition mbd) {
//无论是否安全检查,执行各种Aware回调
if (System.getSecurityManager() != null) {
AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
invokeAwareMethods(beanName, bean);
return null;
}, getAccessControlContext());
}
else {
invokeAwareMethods(beanName, bean);
}
Object wrappedBean = bean;
//当前的 bean 不是由框架内部合成或创建的(即用户定义的正常 bean)
if (mbd == null || !mbd.isSynthetic()) {
//执行bean初始化前的操作
wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
}
try {
//调用自定义的初始化方法,以及实现了 InitializingBean 接口的afterPropertiesSet方法
invokeInitMethods(beanName, wrappedBean, mbd);
}
catch (Throwable ex) {
throw new BeanCreationException(
(mbd != null ? mbd.getResourceDescription() : null),
beanName, "Invocation of init method failed", ex);
}
if (mbd == null || !mbd.isSynthetic()) {
//执行bean初始化后的操作
wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
}
//最终返回的是经过所有处理(初始化前、初始化、初始化后)后的 wrappedBean 对象。这个对象可能经过了一些增强或修改,通常是通过 AOP 等方式。
return wrappedBean;
}
2.4 registerDisposableBeanIfNecessary
registerDisposableBeanIfNecessary
确保在Spring容器销毁Bean时,能够正确地调用其销毁方法。
protected void registerDisposableBeanIfNecessary(String beanName, Object bean, RootBeanDefinition mbd) {
AccessControlContext acc = (System.getSecurityManager() != null ? getAccessControlContext() : null);
//1.只有单例bean才需要由spring容器去管理销毁操作
//2.当前Bean是否需要销毁(即它是否实现了 DisposableBean 接口或者有自定义的销毁方法)
if (!mbd.isPrototype() && requiresDestruction(bean, mbd)) {
if (mbd.isSingleton()) {
// Register a DisposableBean implementation that performs all destruction
// work for the given bean: DestructionAwareBeanPostProcessors,
// DisposableBean interface, custom destroy method.
registerDisposableBean(beanName, new DisposableBeanAdapter(
bean, beanName, mbd, getBeanPostProcessorCache().destructionAware, acc));
}
//其他作用范围(非单例非多例)
else {
// A bean with a custom scope...
Scope scope = this.scopes.get(mbd.getScope());
if (scope == null) {
throw new IllegalStateException("No Scope registered for scope name '" + mbd.getScope() + "'");
}
scope.registerDestructionCallback(beanName, new DisposableBeanAdapter(
bean, beanName, mbd, getBeanPostProcessorCache().destructionAware, acc));
}
}
}
总结
在解析xml或注解扫描将对应的bean转换为bean定义后,剩余的步骤以及扩展点:
- 将beanName转换为bean的class对象(通过jvm加载类得到class)
- 处理当前 bean 配置了方法重写的情况
- 通过反射将bean 实例化,并且包装成BeanWrapper。
- 如果定义了工厂方法,则通过工厂方法来创建 Bean。
- 如果定义了 Supplier,则通过该提供者获取 Bean 实例。
- 如果 Bean 需要通过构造函数进行自动装配,则选择合适的构造函数。
- 最常见的情况:如果没有特殊的要求,直接使用无参构造函数创建 Bean。
- 遍历所有实现了
MergedBeanDefinitionPostProcessor
接口的类,执行其中的postProcessMergedBeanDefinition
方法(在创建了实例后,修改bean定义) - 进行bean的属性填充。
- 自动装配:Spring 会根据配置(如 @Autowired 注解或 XML 配置的自动装配策略)将依赖注入到 Bean 中。如果未明确配置注入策略,Spring 会默认使用按类型自动装配。
- 属性填充的优先级:如果 Bean 中有多个候选依赖项,Spring 会根据类型和名称来决定注入的优先级,避免出现多个匹配时的冲突。 - 进行bean的初始化操作
- 调用 Aware 接口方法:首先根据是否存在
SecurityManager
,安全地调用 bean 的 Aware 接口方法。 - 应用初始化前的
BeanPostProcessor
:在 bean 初始化前,执行所有的BeanPostProcessor
,对 bean 进行增强或修改。 - 执行初始化方法:调用
InitializingBean
的afterPropertiesSet()
方法以及init-method
配置的自定义初始化方法。 - 应用初始化后的
BeanPostProcessor
:在初始化后,执行所有的BeanPostProcessor
,对 bean 进行进一步的增强。 - 返回处理后的 bean:返回可能经过修改或增强的最终 bean 实例。
- 调用 Aware 接口方法:首先根据是否存在
- 确保在Spring容器销毁Bean时,能够正确地调用其销毁方法。
- 在容器关闭或销毁时,Spring 会检查是否配置了销毁方法(如@PreDestroy
注解或 destroy-method)。如果配置了销毁方法,Spring 会在销毁 Bean 时自动调用该方法。
- 销毁操作通常包括关闭资源、清理状态、释放锁等操作,确保容器在销毁时不会漏掉重要的资源释放。 - 果 Bean 被 AOP 代理(如通过
@Transactional
注解),Spring 会在实例化后对 Bean 进行增强。所有的增强逻辑会通过代理对象进行,而实际的业务逻辑通常在原始 Bean 中。