相应注解包括:@Component、@Controller、@RestController、@Service、@Repository等。
Sping使用三级缓存模式主要是为了出于对IOC和AOP的考虑,三级缓存既能解决循环依赖,也能解决AOP(生成代理bean)。
注意:三级缓存只在单例bean中涉及,非单例bean不涉及三级缓存。
解决循环依赖和代理,其实使用二级缓存和三级缓存的方式都能做到。
二级缓存方式:不管有没有循环依赖,都提前创建好代理对象,并将代理对象放入二级缓存,出现循环依赖时,其他对象直接就可以取到代理对象并注入。
三级缓存方式:先只生成对象工厂,并放入到三级缓存,不提前创建好代理对象,在出现循环依赖被其他对象注入时,才通过三级缓存中的对象工厂生成代理对象,并将代理对象放入二级缓存。
这样在没有循环依赖的情况下,bean就可以按着Spring设计原则的步骤来创建。(Sping使用的就是这种方式)。这种情况下,早期的bean也不会真正暴露,不用提前执行代理过程,也不用重复执行代理过程。
下面从两点原因来分析:
如果要使用二级缓存解决循环依赖,意味着Bean在构造(实例化)完后就创建代理对象,这样违背了Spring设计原则。
Spring正常的代理应该是发生在bean初始化后,由AbstractAutoProxyCreator.postProcessAfterInitialization处理。而循环依赖要求bean在填充属性前就提前生成代理。
如果所有bean都提前生成代理,那AbstractAutoProxyCreator.postProcessAfterInitialization就直接没用了,相当于把原来生成代理的设计完全舍弃,但这么做只是为了解决循环依赖。这是得不尝试的,在非必要的情况下对核心代码大改甚至推翻重写是一种大忌。
所以Spring在原有设计的基础上做了扩展:
当循环依赖发生时,提前代理;
对象实例化后用ObjectFactory封装对象,并放到三级缓存(提前曝光的是ObjectFactory对象)。在遇到循环依赖,对象被注入时,才通过ObjectFactory.getObject方法生成代理对象,并把代理对象放入到第二级缓存。
为了防止对象在后面的初始化时重复代理,在生成代理对象时,earlyProxyReferences缓存会记录已代理的对象。
当没有循环依赖时,代理方式不变,依然是初始化后完成代理。
三级缓存中的第二级缓存(提前保留的半成品bean)只有在出现循环依赖的情况是才会用到,未出现循环依赖时并不会用到。
二级缓存在以下特殊情况下,无法解决循环依赖问题
缓存级别 | 缓存名称 | 描述 |
---|---|---|
一级缓存 | singletonObjects | 存放完成品bean对象(可能是原对象或代理对象) 从该缓存中取出的bean可以直接使用 |
二级缓存 | earlySingletonObjects | 存放半成品bean对象(可能是原对象或代理对象)早期曝光的bean对象 半成品bean对象是已实例化(但未注入属性和初始化),提早暴露的。 |
三级缓存 | singletonFactories | 存放bean的工厂对象 用来生成半成品的bean并放入到二级缓存中。 工厂对象封装了实例化(但未注入属性和初始化)的原对象。 |
三级缓存源码类:DefaultSingletonBeanRegistry
一级缓存:存放实例化+属性注入+初始化+代理(如果有代理)后的单例bean
private final Map<String, Object> singletonObjects = new ConcurrentHashMap<>(256);
二级缓存:存放实例化+代理(如果有代理)后的单例bean
private final Map<String, Object> earlySingletonObjects = new HashMap<>(16);
三级缓存:存放封装了单例bean(实例化的)的对象工厂
private final Map<String, ObjectFactory<?>> singletonFactories = new HashMap<>(16);
其它属性
// 已经完成注册的单例beanName
private final Set<String> registeredSingletons = new LinkedHashSet<>(256);
// 正在创建中的beanName
private final Set<String> singletonsCurrentlyInCreation = Collections.newSetFromMap(new ConcurrentHashMap<>(16));
// 当前不检查的bean的集合
private final Set<String> inCreationCheckExclusions = Collections.newSetFromMap(new ConcurrentHashMap<>(16));
// 存放异常出现的相关的原因的集合
private Set<Exception> suppressedExceptions;
// 标志,目前是否在销毁单例中
private boolean singletonsCurrentlyInDestruction = false;
// 存放一次性bean的缓存
private final Map<String, Object> disposableBeans = new LinkedHashMap<>();
// 外部bean与被包含在外部bean的所有内部bean集合包含关系的缓存
private final Map<String, Set<String>> containedBeanMap = new ConcurrentHashMap<>(16);
// 指定bean与依赖指定bean的所有bean的依赖关系的缓存
private final Map<String, Set<String>> dependentBeanMap = new ConcurrentHashMap<>(64);
// 指定bean与创建这个bean所需要依赖的所有bean的依赖关系的缓存
private final Map<String, Set<String>> dependenciesForBeanMap = new ConcurrentHashMap<>(64);
三级缓存源码详细描述可参考文章:Spring三级缓存源码
DefaultSingletonBeanRegistry.getSingleton(String beanName)
从缓存中获取单例bean。
/**
* 获取单例(从缓存中获取)
*/
@Override
@Nullable
public Object getSingleton(String beanName) {
// 允许早期依赖
return getSingleton(beanName, true);
}
/**
* 获取单例
* 1.如果一级缓存有直接返回
* 2.如果二级缓存有直接返回
* 3.如果三级缓存有,通过singletonFactory.getObject()的到未完成的单例对象,并移除三级缓存,返回未完成的单例对象
* @param allowEarlyReference true:允许早期依赖
* @return
*/
@Nullable
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);
// 三级缓存有,调用getObject方法创建bean并放入到二级缓存,并删除三级缓存
if (singletonFactory != null) {
singletonObject = singletonFactory.getObject();
this.earlySingletonObjects.put(beanName, singletonObject);
this.singletonFactories.remove(beanName);
}
}
}
}
return singletonObject;
}
DefaultSingletonBeanRegistry.getSingleton(String beanName, ObjectFactory> singletonFactory)
获取单例bean。
/**
* 获取单例(没有则创建)
*/
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) {
// 当前正在销毁bean,不能创建
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 {
// 调用getObject方法创建bean
singletonObject = singletonFactory.getObject();
newSingleton = true;
}
catch (IllegalStateException ex) {
// 有可能是其他方式创建的bean
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);
}
// 如果是新创建的bean,添加到一级缓存(并移除二级、三级缓存)
if (newSingleton) {
addSingleton(beanName, singletonObject);
}
}
return singletonObject;
}
}
AbstractAutowireCapableBeanFactory.createBeanInstance(String beanName, RootBeanDefinition mbd, Object[] args)
实例化。
protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) {
// 解析class
Class<?> beanClass = resolveBeanClass(mbd, beanName);
//确保class不为空,并且访问权限为public
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());
}
//配置的一种特殊的callback回调方法,通过这个callback创建bean
Supplier<?> instanceSupplier = mbd.getInstanceSupplier();
if (instanceSupplier != null) {
return obtainFromSupplier(instanceSupplier, beanName);
}
//通过工厂方法创建
if (mbd.getFactoryMethodName() != null) {
return instantiateUsingFactoryMethod(beanName, mbd, args);
}
// 一个类可能有多个构造器,所以Spring得根据参数个数、类型确定需要调用的构造器
// 在使用构造器创建实例后,Spring会将解析过后确定下来的构造器或工厂方法保存在缓存中,避免再次创建相同bean时再次解析
boolean resolved = false;
boolean autowireNecessary = false;
if (args == null) {
synchronized (mbd.constructorArgumentLock) {
if (mbd.resolvedConstructorOrFactoryMethod != null) {
//已经解析过class的构造器
resolved = true;
autowireNecessary = mbd.constructorArgumentsResolved;
}
}
}
if (resolved) {
//已经解析过class的构造器,使用已经解析好的构造器
if (autowireNecessary) {
//构造函数自动注入
return autowireConstructor(beanName, mbd, null, null);
}
else {
//使用默认构造器
return instantiateBean(beanName, mbd);
}
}
// 需要根据参数解析、确定构造函数
Constructor<?>[] ctors = determineConstructorsFromBeanPostProcessors(beanClass, beanName);
// 解析的构造器不为空 || 注入类型为构造函数自动注入 || bean定义中有构造器参数 || 传入参数不为空
if (ctors != null ||
mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_CONSTRUCTOR ||
mbd.hasConstructorArgumentValues() || !ObjectUtils.isEmpty(args)) {
//构造函数自动注入
return autowireConstructor(beanName, mbd, ctors, args);
}
// 使用默认构造器
return instantiateBean(beanName, mbd);
}
DefaultSingletonBeanRegistry.addSingletonFactory(String beanName, ObjectFactory> singletonFactory)
添加bean的对象工厂到三级缓存。
/**
* 添加到三级级缓存
*/
protected void addSingletonFactory(String beanName, ObjectFactory<?> singletonFactory) {
Assert.notNull(singletonFactory, "Singleton factory must not be null");
synchronized (this.singletonObjects) {
// 如果一级缓存没有,添加对象工厂到三级缓存
if (!this.singletonObjects.containsKey(beanName)) {
this.singletonFactories.put(beanName, singletonFactory);
this.earlySingletonObjects.remove(beanName);
this.registeredSingletons.add(beanName);
}
}
}
AbstractAutowireCapableBeanFactory.populateBean(String beanName, RootBeanDefinition mbd, BeanWrapper bw)
属性注入。
protected void populateBean(String beanName, RootBeanDefinition mbd, @Nullable BeanWrapper bw) {
/*
* 1 校验bw为null的情况
* 如果此bean定义中定义了标签,那么抛出异常,其他情况则直接返回
*/
//如果bw为null
if (bw == null) {
//如果mbd存在propertyValues属性,即定义了标签
//因为BeanWrapper都为null了,不能进行依赖注入,那么抛出异常
if (mbd.hasPropertyValues()) {
throw new BeanCreationException(
mbd.getResourceDescription(), beanName, "Cannot apply property values to null instance");
} else {
//跳过null实例的属性装配阶段
return;
}
}
/*
* 2 在bean实例化之后,属性填充(初始化)之前,回调InstantiationAwareBeanPostProcessor后处理器的
* postProcessAfterInstantiation方法,可用于修改bean实例的状态
*
* Spring在这个扩展点方法中没有任何额外操作,但是我们可以自定义后处理器,重写该方法定义自己的逻辑。
*/
// 确保mbd不是合成的,并且具有InstantiationAwareBeanPostProcessor这个后处理器
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
//遍历所有注册的BeanPostProcessor后处理器
for (BeanPostProcessor bp : getBeanPostProcessors()) {
//如果属于InstantiationAwareBeanPostProcessor类型
if (bp instanceof InstantiationAwareBeanPostProcessor) {
//强制转型
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
//回调postProcessAfterInstantiation方法,传递的参数就是此前获取的bean实例以及beanName
//该方法可用于在bean实例化之后,初始化之前,修改bean实例的状态
//如果返回false,则不会继续应用后续的处理同时也会结束后续的属性填充流程,该方法结束,否则继续向后调用
if (!ibp.postProcessAfterInstantiation(bw.getWrappedInstance(), beanName)) {
return;
}
}
}
}
//获取bean定义的PropertyValues集合,在此前的parsePropertyElement方法中,我们说过
//所有的标签标签都被解析为PropertyValue对象并存入PropertyValues集合中了
PropertyValues pvs = (mbd.hasPropertyValues() ? mbd.getPropertyValues() : null);
/*
* 3 根据名称或者类型进行setter自动注入,适用于基于XML的配置autowire自动注入,现在很少基于XML配置了
* 并没有真正的注入,而是将可以自动注入的属性名和bean实例存入新建的newPvs中,后面会统一注入
*/
//获取已解析的自动注入模式,默认就是0,即不自动注入,可以设置,对应XML的autowire属性
int resolvedAutowireMode = mbd.getResolvedAutowireMode();
//如果是1(就是byName),或者如果是2(就是byType),单纯使用注解注入就是0
if (resolvedAutowireMode == AUTOWIRE_BY_NAME || resolvedAutowireMode == AUTOWIRE_BY_TYPE) {
//根据原来的属性新建一个属性集合
MutablePropertyValues newPvs = new MutablePropertyValues(pvs);
// 基于byName的setter自动注入
//并没有真正的注入,而是将可以自动注入的属性名和bean实例存入新建的newPvs中,后面会统一注入
if (resolvedAutowireMode == AUTOWIRE_BY_NAME) {
autowireByName(beanName, mbd, bw, newPvs);
}
// 基于byType的setter自动注入
//并没有真正的注入,而是将可以自动注入的属性名和bean实例存入新建的newPvs中,后面会统一注入
if (resolvedAutowireMode == AUTOWIRE_BY_TYPE) {
autowireByType(beanName, mbd, bw, newPvs);
}
//pvs赋值为newPvs
//现在pvs中包括了我们定义的标签属性,以及找到的byName和byType的setter自动注入属性
pvs = newPvs;
}
//是否具有InstantiationAwareBeanPostProcessor这个后处理器
boolean hasInstAwareBpps = hasInstantiationAwareBeanPostProcessors();
//是否需要进行依赖检查,即是否设置dependencyCheck属性,表示属性强制检查,就是XML的dependency-check属性
//然而这个属性早在spring3.0的时候就被废弃了,代替它的就是构造器注入或者@Required,默认就是0,不进行强制检查,因此为false
boolean needsDepCheck = (mbd.getDependencyCheck() != AbstractBeanDefinition.DEPENDENCY_CHECK_NONE);
PropertyDescriptor[] filteredPds = null;
/*
* 4 查找全部InstantiationAwareBeanPostProcessor后处理器,回调postProcessProperties方法
* 解析此前通过applyMergedBeanDefinitionPostProcessors方法找到的自动注入注解,这里进行了注解的真正的注入
*/
if (hasInstAwareBpps) {
//如果为null,初始化一个空的MutablePropertyValues对象
if (pvs == null) {
pvs = mbd.getPropertyValues();
}
//获取、遍历全部注册的后处理器
for (BeanPostProcessor bp : getBeanPostProcessors()) {
//如果属于SmartInstantiationAwareBeanPostProcessor类型
if (bp instanceof InstantiationAwareBeanPostProcessor) {
//强转
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
/*
* 回调postProcessProperties方法,传递的参数就是目前的pvs、bean实例、beanName,解析、注入此前通过
* applyMergedBeanDefinitionPostProcessors方法找到的自动注入注解,返回PropertyValues
*
* CommonAnnotationBeanPostProcessor -> 解析注入@WebServiceRef、@EJB、@Resource注解,默认直接返回参数pvs
* AutowiredAnnotationBeanPostProcessor -> 解析注入@Autowired、@Value、@Inject注解,默认直接返回参数pvs
*
* 在Spring 5.1 之前使用的是postProcessPropertyValues回调方法,Spring 5.1开始该方法被不推荐使用,推荐使用postProcessProperties来替代
*/
PropertyValues pvsToUse = ibp.postProcessProperties(pvs, bw.getWrappedInstance(), beanName);
//如果pvsToUse为null,那么调用此前的已被放弃的postProcessPropertyValues方法继续尝试
if (pvsToUse == null) {
//获取属性描述符
if (filteredPds == null) {
filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
}
//调用postProcessPropertyValues方法,该方法已被丢弃
//实际上CommonAnnotationBeanPostProcessor和AutowiredAnnotationBeanPostProcessor的方法内部就是直接调用的postProcessProperties方法
//只有RequiredAnnotationBeanPostProcessor有自己的逻辑,但是我们知道RequiredAnnotationBeanPostProcessor已经整体丢弃了
pvsToUse = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
//还是返回null,那什么直接结束这个方法
if (pvsToUse == null) {
return;
}
}
//从新设置pvs,对于CommonAnnotationBeanPostProcessor和AutowiredAnnotationBeanPostProcessor来说具有同一批数据
pvs = pvsToUse;
}
}
}
//如果需要进行依赖检查,默认不需要,Spring3.0之后没法设置设置
if (needsDepCheck) {
if (filteredPds == null) {
filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
}
checkDependencies(beanName, mbd, filteredPds, pvs);
}
/*
* 5 如果pvs不为null,这里默认的pvs就是标签和byName或者byType找到的属性值的汇总
* 这里将所有PropertyValues中的属性继续填充到bean实例中
*/
if (pvs != null) {
applyPropertyValues(beanName, mbd, bw, pvs);
}
}
AbstractAutowireCapableBeanFactory.initializeBean(final String beanName, final Object bean, RootBeanDefinition mbd)
初始化、生成代理对象(如果有代理且对象还未被代理)。
对象有代理,但可能因为循环依赖,已经提前通过对象工厂生成代理对象放入了二级缓存。
生成代理对象的具体逻辑在applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName)方法中。
protected Object initializeBean(final String beanName, final Object bean, @Nullable RootBeanDefinition mbd) {
if (System.getSecurityManager() != null) { // 安全模式
AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
// <1> 激活 Aware 方法,对特殊的 bean 处理:Aware、BeanClassLoaderAware、BeanFactoryAware
invokeAwareMethods(beanName, bean);
return null;
}, getAccessControlContext());
}
else {
invokeAwareMethods(beanName, bean);
}
// 后处理器,before
Object wrappedBean = bean;
if (mbd == null || !mbd.isSynthetic()) {
wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
}
// 激活用户自定义的 init 方法
try {
invokeInitMethods(beanName, wrappedBean, mbd);
}
catch (Throwable ex) {
throw new BeanCreationException(
(mbd != null ? mbd.getResourceDescription() : null),
beanName, "Invocation of init method failed", ex);
}
// 后处理器,after
if (mbd == null || !mbd.isSynthetic()) {
wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
}
return wrappedBean;
}
DefaultSingletonBeanRegistry.addSingleton(String beanName, Object singletonObject)
放入一级缓存,清除其他级的缓存。
/**
* 添加到一级缓存(并移除二级、三级缓存)
*/
protected void addSingleton(String beanName, Object singletonObject) {
synchronized (this.singletonObjects) {
// 加入单例对象到一级缓存
this.singletonObjects.put(beanName, singletonObject);
// 删除三级缓存
this.singletonFactories.remove(beanName);
// 删除二级缓存
this.earlySingletonObjects.remove(beanName);
// 加入已注册的bean
this.registeredSingletons.add(beanName);
}
}
AbstractBeanFactory.getObjectForBeanInstance(
Object beanInstance, String name, String beanName, RootBeanDefinition mbd)
得到最终完整的可以使用的单例bean对象(原对象或代理对象)。
protected Object getObjectForBeanInstance(Object beanInstance, String name, String beanName, @Nullable RootBeanDefinition mbd) {
// 如果Bean不是工厂,不要让调用代码尝试取消对工厂的引用
// 如果 name为FactoryBean的解引用.name是以'&'开头,就是FactoryBean的解引用
if (BeanFactoryUtils.isFactoryDereference(name)) {
//如果beanInstance是NullBean实例
if (beanInstance instanceof NullBean) {
//返回beanInstance
return beanInstance;
}
//如果beanInstance不是FactoryBean实例
if (!(beanInstance instanceof FactoryBean)) {
//抛出Bean不是一个Factory异常
throw new BeanIsNotAFactoryException(beanName, beanInstance.getClass());
}
//如果mbd不为null
if (mbd != null) {
//设置mbd是否是FactoryBean标记为true
mbd.isFactoryBean = true;
}
//返回beanInstance
return beanInstance;
}
// 现在我们有了Bean实例,他可能是一个普通的Bean或FactoryBean。
// 如果它是FactoryBean,我们使用它来创建一个Bean实例,除非调用者确实需要对工厂的引用。
//如果beanInstance不是FactoryBean实例
if (!(beanInstance instanceof FactoryBean)) {
return beanInstance;
}
//定义为bean公开的对象,初始化为null
Object object = null;
//如果mbd不为null
if (mbd != null) {
//更新mbd的是否是FactoryBean标记为true
mbd.isFactoryBean = true;
}
else {
//从FactoryBean获得的对象缓存集中获取beanName对应的Bean对象
object = getCachedObjectForFactoryBean(beanName);
}
//如果object为null
if (object == null) {
// 从工厂返回Bean实例
//将beanInstance强转为FactoryBean对象
FactoryBean<?> factory = (FactoryBean<?>) beanInstance;
// 如果是单例对象,则缓存从FactoryBean获得的对象、
//如果mbd为null && 该BeanFactory包含beanName的BeanDefinition对象。
if (mbd == null && containsBeanDefinition(beanName)) {
//获取beanName合并后的本地RootBeanDefintiond对象
mbd = getMergedLocalBeanDefinition(beanName);
}
//是否是'synthetic'标记:mbd不为null && 返回此bean定义是否是"synthetic"【一般是指只有AOP相关的prointCut配置或者
// Advice配置才会将 synthetic设置为true】
boolean synthetic = (mbd != null && mbd.isSynthetic());
//从BeanFactory对象中获取管理的对象.如果不是synthetic会对其对象进行该工厂的后置处理
object = getObjectFromFactoryBean(factory, beanName, !synthetic);
}
//返回为bean公开的对象
return object;
}
涉及循环依赖和代理的Bean加载
例子:对象A和对象B相互循环依赖,且都有代理。