社区微信群开通啦,扫一扫抢先加入社区官方微信群
社区微信群
创建单例bean的代码在getSingleton中实现:
//省略了日志打印和异常捕获的代码
public Object getSingleton(String beanName, ObjectFactory<?> singletonFactory) {
//单例模式下创建bena需要加锁同步
synchronized (this.singletonObjects) {
//如果bean已经创建,则直接返回就好
Object singletonObject = this.singletonObjects.get(beanName);
if (singletonObject == null) {
if (this.singletonsCurrentlyInDestruction) {
throw new BeanCreationNotAllowedException(beanName,"...");
}
//这一步是将正在创建的bean记录在缓存中,以便对循环依赖进行检查
beforeSingletonCreation(beanName);
boolean newSingleton = false;
try {
//创建单例
singletonObject = singletonFactory.getObject();
newSingleton = true;
}
//省略异常捕获
finally {
//移除正在加载的bean记录,与beforeSingletonCreation相对应
afterSingletonCreation(beanName);
}
if (newSingleton) {
//将bean添加到缓存,并且移除加载过程中记录的各种辅助状态
addSingleton(beanName, singletonObject);
}
}
return singletonObject;
}
}
因为考虑到多线程获取bean的原因,单例bean的创建是全程加锁的,下面是方法的大致流程:
protected void addSingleton(String beanName, Object singletonObject) {
synchronized (this.singletonObjects) {
this.singletonObjects.put(beanName, singletonObject);
this.singletonFactories.remove(beanName);
this.earlySingletonObjects.remove(beanName);
this.registeredSingletons.add(beanName);
}
}
从上面创建单例的代码可以看到,真正创建bean的功能委托给了ObjectFactory,通过它的getObject方法来创建,那么这个ObjectFactory是在哪里创建的?回顾上一节的doGetBean方法:
// Create bean instance.
if (mbd.isSingleton()) {
sharedInstance = getSingleton(beanName, () -> {
try {
//调用createBean方法
return createBean(beanName, mbd, args);
}
catch (BeansException ex) {
// 创建失败会删除中间状态
destroySingleton(beanName);
throw ex;
}
});
bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
}
再看一下其他scope的bean创建:
else {
String scopeName = mbd.getScope();
final Scope scope = this.scopes.get(scopeName);
if (scope == null) {
throw new IllegalStateException("No Scope registered for scope name '" + scopeName + "'");
}
try {
Object scopedInstance = scope.get(beanName, () -> {
beforePrototypeCreation(beanName);
try {
//调用createBean方法
return createBean(beanName, mbd, args);
}
finally {
afterPrototypeCreation(beanName);
}
});
bean = getObjectForBeanInstance(scopedInstance, name, beanName, mbd);
}
//省略catch。。。
}
可以看到,不管是哪种类型的bean,都是通过createBean方法创建的。不一样的是,不同scope的bean在创建前后会有不一样的状态保存工作。
在AbstractBeanFactory中,createBean的方法并未实现,而是将具体创建bean的工作留给了子类,是一个典型的模版方法:
在AbstractAutowireCapableBeanFactory 中实现了该方法:
protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
throws BeanCreationException {
RootBeanDefinition mbdToUse = mbd;
// 确定并加载bean的class
Class<?> resolvedClass = resolveBeanClass(mbd, beanName);
if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
mbdToUse = new RootBeanDefinition(mbd);
mbdToUse.setBeanClass(resolvedClass);
}
// 验证以及准备需要覆盖的方法
mbdToUse.prepareMethodOverrides();
try {
// 给BeanPostProcessors 一个机会来返回代理对象来代替真正的实例,在这里实现创建代理对象功能
Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
if (bean != null) {
return bean;
}
}
//catch...
try {
//创建bean
Object beanInstance = doCreateBean(beanName, mbdToUse, args);
return beanInstance;
}
//catch
}
上面代码对应步骤:
createBean方法中调用了resolveBeforeInstantiation 方法做些前置处理,并且如果在这个方法中返回了bean的话(AOP代理对象或者自定义对象),就直接返回这个bean,不再继续后面的创建步骤,方法实现:
protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
Object bean = null;
//bean还未被解析
if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
// Make sure bean class is actually resolved at this point.
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
Class<?> targetType = determineTargetType(beanName, mbd);
if (targetType != null) {
//应用实例化前的后处理器
bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
if (bean != null) {
//如果bean不为空,则应用实例化后的后处理器
bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
}
}
}
//标记当前bean是否被解析过
mbd.beforeInstantiationResolved = (bean != null);
}
return bean;
}
protected Object applyBeanPostProcessorsBeforeInstantiation(Class<?> beanClass, String beanName) {
//遍历所有的后处理器
for (BeanPostProcessor bp : getBeanPostProcessors()) {
if (bp instanceof InstantiationAwareBeanPostProcessor) {
//应用其中类型为 InstantiationAwareBeanPostProcessor 的后处理器
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
Object result = ibp.postProcessBeforeInstantiation(beanClass, beanName);
//如果后处理器中创建了代理bean,则直接返回
if (result != null) {
return result;
}
}
}
return null;
}
如果实例化前的后处理器创建了一个代理对象,才会继续应用实例化后的后处理器:
bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
if (bean != null) {
bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
}
应用后处理器的方法与a中类似,只不过调用的是 postProcessBeforeInstantiation ,而后者调用的是 postProcessAfterInstantiation
public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName)
throws BeansException {
Object result = existingBean;
for (BeanPostProcessor beanProcessor : getBeanPostProcessors()) {
Object current = beanProcessor.postProcessAfterInitialization(result, beanName);
//当其中一个后处理器返回null时,就会中断处理器的调用链,直接返回
if (current == null) {
return result;
}
result = current;
}
return result;
}
终于到了Spring创建bean的地方,下面是代码实现:
protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final @Nullable Object[] args)
throws BeanCreationException {
// 先从factoryBeanInstanceCache缓存中尝试获取
BeanWrapper instanceWrapper = null;
if (mbd.isSingleton()) {
instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
}
//如果缓存中不存在,则根据bean对应的策略创建新的实例,如:工厂方法、构造器自动注入、简单初始化
if (instanceWrapper == null) {
instanceWrapper = createBeanInstance(beanName, mbd, args);
}
final Object bean = instanceWrapper.getWrappedInstance();
Class<?> beanType = instanceWrapper.getWrappedClass();
if (beanType != NullBean.class) {
mbd.resolvedTargetType = beanType;
}
// 应用MergedBeanDefinitionPostProcessor 后处理器,合并bean的定义信息
// Autowire等注解信息就是在这一步完成预解析,并且将注解需要的信息放入缓存
synchronized (mbd.postProcessingLock) {
if (!mbd.postProcessed) {
try {
applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
}
//catch..
mbd.postProcessed = true;
}
}
// 是否需要提前曝光=单例&允许循环依赖&bean正在创建中
boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
isSingletonCurrentlyInCreation(beanName));
if (earlySingletonExposure) {
//为了避免循环依赖,在bean初始化完成前,就将创建bean实例的ObjectFactory放入工厂缓存(singletonFactories)
addSingletonFactory(beanName, () -> getEarlyBeanReference(beanName, mbd, bean));
}
// 对bean属性进行填充,注入bean中的属性,会递归初始化依赖的bean
Object exposedObject = bean;
try {
populateBean(beanName, mbd, instanceWrapper);
//调用初始化方法,比如init-method、注入Aware对象、应用后处理器
exposedObject = initializeBean(beanName, exposedObject, mbd);
}
//catch
if (earlySingletonExposure) {
//从提前曝光的bean缓存中查询bean,目的是验证是否有循环依赖存在
//如果存在循环依赖,也就是说该bean已经被其他bean递归加载过,放入了提早曝光的bean缓存中
Object earlySingletonReference = getSingleton(beanName, false);
//只有检测到循环依赖的情况下,earlySingletonReference才不会为null
if (earlySingletonReference != null) {
//如果exposedObject没有在 initializeBean 初始化方法中改变,也就是没有被增强
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);
}
}
//因为bean创建后,其依赖的bean一定也是已经创建的
//如果actualDependentBeans不为空,则表示依赖的bean并没有被创建完,即存在循环依赖
if (!actualDependentBeans.isEmpty()) {
throw new BeanCurrentlyInCreationException("...");
}
}
}
}
// 根据scope注册bean
try {
registerDisposableBeanIfNecessary(beanName, bean, mbd);
}
//catch。。。
return exposedObject;
}
如果觉得我的文章对您有用,请随意打赏。你的支持将鼓励我继续创作!