Spring核心知识点 - 补充
Spring 三级缓存解决循环依赖
- Spring只能解决field和setter注入导致的循环依赖,无法解决构造器注入导致的循环依赖。
- Spring只处理了单例Bean对象之间的循环依赖,没有处理原型对象之间的循环依赖
三层缓存
// 三层缓存
public class DefaultSingletonBeanRegistry extends SimpleAliasRegistry implements SingletonBeanRegistry {
// 第一级缓存:初始化完成的完全单例对象 Map<beanname, beanInstance>
private final Map<String, Object> singletonObjects = new ConcurrentHashMap<>(256);
// 第二级缓存:提前暴露的单例对象引用(未完成依赖注入和初始化) Map<beanname, beanInstance>
private final Map<String, Object> earlySingletonObjects = new HashMap<>(16);
// 第三级缓存: 用于生成提前暴露的单例对象引用的工厂Bean对象 Map<beanname, objectFactory>
// factoryBean在getObject()方法中,对原生Bean添加后置处理器,判断是否需要提前生成代理对象并对外暴露
private final Map<String, ObjectFactory<?>> singletonFactories = new HashMap<>(16);
}
// DI : 先从缓存中取Bean --- 三层缓存依次判断(为解决循环依赖问题)
protected Object getSingleton(String beanName, boolean allowEarlyReference) {
Object singletonObject = this.singletonObjects.get(beanName);
if (singletonObject == null && isSingletonCurrentlyInCreation(beanName)) {
synchronized (this.singletonObjects) {
singletonObject = this.earlySingletonObjects.get(beanName);
if (singletonObject == null && allowEarlyReference) {
ObjectFactory<?> singletonFactory = this.singletonFactories.get(beanName);
if (singletonFactory != null) {
singletonObject = singletonFactory.getObject();
this.earlySingletonObjects.put(beanName, singletonObject);
this.singletonFactories.remove(beanName);
}
}
}
}
return singletonObject;
}
doGetBean阶段
// 核心代码 - AbstractBeanFactory#doGetBean():
...
// DI 3:这里使用了一个匿名内部类,创建Bean实例对象,并且存入正在创建的缓存池中
sharedInstance = getSingleton(beanName, () -> {
try {
// DI 3: 创建一个指定Bean实例对象,如果有父级继承,则合并子类和父类的定义
return createBean(beanName, mbd, args);
}
catch (BeansException ex) {
// Explicitly remove instance from singleton cache: It might have been put there
// eagerly by the creation process, to allow for circular reference resolution.
// Also remove any beans that received a temporary reference to the bean.
// 显式地从容器单例模式Bean缓存中清除实例对象
destroySingleton(beanName);
throw ex;
}
});
// 核心代码 - AbstractBeanFactory#getSingleton():
public Object getSingleton(String beanName, ObjectFactory<?> singletonFactory) {
Assert.notNull(beanName, "Bean name must not be null");
synchronized (this.singletonObjects) {
Object singletonObject = this.singletonObjects.get(beanName);
if (singletonObject == null) {
if (this.singletonsCurrentlyInDestruction) {
throw new BeanCreationNotAllowedException(beanName,
"Singleton bean creation not allowed while singletons of this factory are in destruction " +
"(Do not request a bean from a BeanFactory in a destroy method implementation!)");
}
if (logger.isDebugEnabled()) {
logger.debug("Creating shared instance of singleton bean '" + beanName + "'");
}
// 此处 singletonsCurrentlyInCreation.add(beanName) 添加到正在创建缓存池
beforeSingletonCreation(beanName);
boolean newSingleton = false;
boolean recordSuppressedExceptions = (this.suppressedExceptions == null);
if (recordSuppressedExceptions) {
this.suppressedExceptions = new LinkedHashSet<>();
}
try {
singletonObject = singletonFactory.getObject();
newSingleton = true;
}
catch (IllegalStateException ex) {
// Has the singleton object implicitly appeared in the meantime ->
// if yes, proceed with it since the exception indicates that state.
singletonObject = this.singletonObjects.get(beanName);
if (singletonObject == null) {
throw ex;
}
}
catch (BeanCreationException ex) {
if (recordSuppressedExceptions) {
for (Exception suppressedException : this.suppressedExceptions) {
ex.addRelatedCause(suppressedException);
}
}
throw ex;
}
finally {
if (recordSuppressedExceptions) {
this.suppressedExceptions = null;
}
// 此处,从正在创建缓存池移除
afterSingletonCreation(beanName);
}
if (newSingleton) {
// 创建完成,加入到第一级缓存
addSingleton(beanName, singletonObject);
}
}
return singletonObject;
}
}
doCreateBean阶段
// 核心代码 - AbstractAutowireCapableBeanFactory#doCreateBean():
...
// 向容器中缓存单例模式的Bean对象,以防循环引用
boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
isSingletonCurrentlyInCreation(beanName));
if (earlySingletonExposure) {
if (logger.isDebugEnabled()) {
logger.debug("Eagerly caching bean '" + beanName +
"' to allow for resolving potential circular references");
}
// this.singletonFactories.put(beanName, singletonFactory);
// 这里是一个匿名内部类(FactoryBean接口),完成Bean引用(可能是原生引用,也可能是代理引用)的提前暴露,防止循环引用
addSingletonFactory(beanName, () -> getEarlyBeanReference(beanName, mbd, bean));
}
// 核心代码 - AbstractAutowireCapableBeanFactory#getEarlyBeanReference():
// 获取提前暴露的引用 - 三层缓存的原因:
// factoryBean会调用getEarlyBeanReference方法,通过后置处理器尝试获取提前暴露的代理对象引用
protected Object getEarlyBeanReference(String beanName, RootBeanDefinition mbd, Object bean) {
Object exposedObject = bean;
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
for (BeanPostProcessor bp : getBeanPostProcessors()) {
if (bp instanceof SmartInstantiationAwareBeanPostProcessor) {
SmartInstantiationAwareBeanPostProcessor ibp = (SmartInstantiationAwareBeanPostProcessor) bp;
exposedObject = ibp.getEarlyBeanReference(exposedObject, beanName);
}
}
}
return exposedObject;
}
欢迎疑问、期待评论、感谢指点 -- kiqi,愿同您为友
-- 星河有灿灿,愿与之辉