Spring的循环引用
实力有限,如有勘误,请指出
1.Spring中的三级缓存
在创建Bean的过程中,Spring 会先去单例缓存中查找Bean是否已经被创建。
@Nullable
protected Object getSingleton(String beanName, boolean allowEarlyReference) {
//从单例缓存(一级缓存)如果有就返回
Object singletonObject = this.singletonObjects.get(beanName);
//如果不存在并且该Bean正在创建
if (singletonObject == null && isSingletonCurrentlyInCreation(beanName)) {
synchronized (this.singletonObjects) {
//查找二级缓存
singletonObject = this.earlySingletonObjects.get(beanName);
//二级缓存找不到 并且是允许循环引用的
if (singletonObject == null && allowEarlyReference) {
//ObjectFactory
ObjectFactory<?> singletonFactory = this.singletonFactories.get(beanName);
if (singletonFactory != null) {
singletonObject = singletonFactory.getObject();
//如果有存入到二级缓存当中。
this.earlySingletonObjects.put(beanName, singletonObject);
this.singletonFactories.remove(beanName);
}
}
}
}
return singletonObject;
}
- 第一级缓存singletonObjects 存储的是单例的完整的Bean对象。
- 第二级存储的是婴儿Bean就是比如属性没有赋值。
- 第三级缓存也是类似
一个先Bean从初始化到未给属性赋值的时候,先放到三级缓存当中。
AbstracAutowriedCapableBeanFactory#doCreateBean 方法中
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));
}
然后需要对属性设置populateBean:
protected void autowireByName(
String beanName, AbstractBeanDefinition mbd, BeanWrapper bw, MutablePropertyValues pvs) {
//非简单属性
String[] propertyNames = unsatisfiedNonSimpleProperties(mbd, bw);
//遍历
for (String propertyName : propertyNames) {
//如果是一个Bean
if (containsBean(propertyName)) {
//初始化Bean
Object bean = getBean(propertyName);
//属性名--> 属性值
pvs.add(propertyName, bean);
//属性依赖注入
registerDependentBean(propertyName, beanName);
if (logger.isTraceEnabled()) {
logger.trace("Added autowiring by name from bean name '" + beanName +
"' via property '" + propertyName + "' to bean named '" + propertyName + "'");
}
}
else {
if (logger.isTraceEnabled()) {
logger.trace("Not autowiring property '" + propertyName + "' of bean '" + beanName +
"' by name: no matching bean found");
}
}
}
}
举例:UserService 依赖 OrderService ,OrdeService 依赖UserService
UserService 先创建,初始化之后放入三级缓存,需要属性注入的时候发现存在依赖对象OrderService,那就先(getBean 方法 )创建OrderService,OrderService 先把自己放入三级缓存,属性注入的时候发现依赖UserService,就去GetBean创建,先查缓存中UserService,它在三级缓存中,把它拿到放入二级缓存,设置属性,然后OrderService 就到了一级缓存,整个递归结束返回。UserService拿到OrderService,把自己放入到一级缓存。
什么时候放入一级缓存呢?
// 如果是单例的Bean对象
if (mbd.isSingleton()) {
//创建完成之后放入一级缓存
sharedInstance = getSingleton(beanName, () -> {
try {
/**
* 创建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.
destroySingleton(beanName);
throw ex;
}
});
bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
}
这个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 + "'");
}
beforeSingletonCreation(beanName);
boolean newSingleton = false;
boolean recordSuppressedExceptions = (this.suppressedExceptions == null);
if (recordSuppressedExceptions) {
this.suppressedExceptions = new LinkedHashSet<>();
}
try {
/** <1> 如果在二级缓存中找到了 那就是新的单例对象 */
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) {
/**
*
* <2> 放入到缓存当中
*/
addSingleton(beanName, singletonObject);
}
}
return singletonObject;
}
}