在分析Spring Bean 初始化之前,先来到 DefaultSingletonBeanRegistry 查看三个cache混个眼熟。
/** Cache of singleton objects: bean name to bean instance. */
private final Map singletonObjects = new ConcurrentHashMap<>(256);
/** Cache of singleton factories: bean name to ObjectFactory. */
private final Map> singletonFactories = new HashMap<>(16);
/** Cache of early singleton objects: bean name to bean instance. */
private final Map earlySingletonObjects = new HashMap<>(16);
Spring 提供了多种重载和getBean的方法
当我们在执行 beanFactory.getBean("XXBean") 时,其实是在调用 AbstractBeanFactory 中的实现:
public Object getBean(String name) throws BeansException {
return this.doGetBean(name, null, null, false);
}
最终几乎所有的操作都交给doGetBean 去实现的,那下面来看看真正干干活的doGetBean
public T getBean(String name, @Nullable Class requiredType, @Nullable Object... args) throws BeansException {
return doGetBean(name, requiredType, args, false);
}
/**
* Return an instance, which may be shared or independent, of the specified bean.
*
* @param name the name of the bean to retrieve
* @param requiredType the required type of the bean to retrieve
* @param args arguments to use when creating a bean instance using explicit arguments
* (only applied when creating a new instance as opposed to retrieving an existing one)
* @param typeCheckOnly whether the instance is obtained for a type check,
* not for actual use
* @return an instance of the bean
* @throws BeansException if the bean could not be created
*/
@SuppressWarnings("unchecked")
protected T doGetBean(final String name, @Nullable final Class requiredType, @Nullable final Object[] args,
boolean typeCheckOnly) throws BeansException {
/**
* 获取对应Bean的真正beanName
* 怎么说?
* 因为传入的name 可能是 bean的 别名 也可能是 FactoryBean的name
* 解析 如下:
* 如果是FactoryBean,则去掉修饰符“&”
* 沿着引用链获取alias对应的最终name(从 aliasMap中获取)
*/
final String beanName = transformedBeanName(name);
Object bean;
/**
* 检查 缓存或者实例工厂中 是否 有对应的bean(单例)
* 为什么刚开始需要这么做?
* 因为在 创建单例Bean的时候会存在依赖注入的情况。
* 因而在创建bean的时候为了避免循环依赖,所以这么干
*
* Spring 创建bean的时候,先去singletonObjects 中获取
* Spring创建bean的原则是不等bean创建完成就将创建bean的ObjectFactory提早曝光(将对应的ObjectFactory加入到缓存)
* 一旦下一个bean创建需要依赖上一个bean,则直接使用ObjectFactory对象
*/
//直接尝试从缓存中获取,或者singletonfacotory中获取,
// 如果是从singletonFactories中获取的 且准许提前曝光 就将 获取到的Bean 放在提前曝光缓存 earlySingletonObjects
Object sharedInstance = getSingleton(beanName); // 获取单例实例
if (sharedInstance != null && args == null) {
if (logger.isTraceEnabled()) {
if (isSingletonCurrentlyInCreation(beanName)) {
logger.trace("Returning eagerly cached instance of singleton bean '" + beanName
+ "' that is not fully initialized yet - a consequence of a circular reference");
} else {
logger.trace("Returning cached instance of singleton bean '" + beanName + "'");
}
}
//返回对应的实例
bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);
}
// 单例实例不存在
else {
// Fail if we're already creating this bean instance:
// We're assumably within a circular reference.
/**
* 只有在单例情况才会尝试解决循环依赖
* 原型模式下如果存在 A class中有B Class,B class 中有A Class
* 即满足 isPrototypeCurrentlyInCreation z则跑出循环依赖异常
*/
if (isPrototypeCurrentlyInCreation(beanName)) {
throw new BeanCurrentlyInCreationException(beanName);
}
// Check if bean definition exists in this factory.
// 获取parentBeanFactory实例
BeanFactory parentBeanFactory = getParentBeanFactory();
// 如果在beanDefinitionMap中(已加载的类定义)不包含目标bean,则尝试从parentBeanFactory中获取
if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {
// Not found -> check parent.
String nameToLookup = originalBeanName(name);
if (parentBeanFactory instanceof AbstractBeanFactory) {
return ((AbstractBeanFactory) parentBeanFactory)
.doGetBean(nameToLookup, requiredType, args, typeCheckOnly);
} else if (args != null) {
// Delegation to parent with explicit args.
// 递归到BeanFactory中寻找
return (T) parentBeanFactory.getBean(nameToLookup, args);
} else if (requiredType != null) {
// No args -> delegate to standard getBean method.
return parentBeanFactory.getBean(nameToLookup, requiredType);
} else {
return (T) parentBeanFactory.getBean(nameToLookup);
}
}
//如果不是仅仅做类型检查而是创建bean这里要进行记录,即将beanName加入alreadyCreated集合中
if (!typeCheckOnly) {
markBeanAsCreated(beanName);
}
try {
/**
* 将存储XML配置文件的GericBeanDefinition转换为RootBeanDefinition
* 如果存在父bean,则同时合并父bean的相关属性
*/
final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
/**
* 检查bean的类定义 , 如果是 抽象类 则跑出异常
*/
checkMergedBeanDefinition(mbd, beanName, args);
// Guarantee initialization of beans that the current bean depends on.
// 加载当前bean依赖的bean
String[] dependsOn = mbd.getDependsOn();
//若存在依赖则要递归实例化依赖的bean
if (dependsOn != null) {
for (String dep : dependsOn) {
// 检查dep是否依赖beanName,从而导致循环依赖
if (isDependent(beanName, dep)) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName,
"Circular depends-on relationship between '" + beanName + "' and '" + dep + "'");
}
//注册
registerDependentBean(dep, beanName);
try {
// 缓存依赖调用
getBean(dep);
} catch (NoSuchBeanDefinitionException ex) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName,
"'" + beanName + "' depends on missing bean '" + dep + "'", ex);
}
}
}
// Create bean instance.
// 完成加载依赖的bean后,实例化mbd自身
if (mbd.isSingleton()) {
//singleton模式的创建
sharedInstance = getSingleton(beanName, () -> {
try {
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);
} else if (mbd.isPrototype()) {
// It's a prototype -> create a new instance.
Object prototypeInstance = null;
try {
// 设置正在创建的状态
beforePrototypeCreation(beanName);
// 创建bean ,addSingletonFactory
prototypeInstance = createBean(beanName, mbd, args);
} finally {
// prototypesCurrentlyInCreation 清理
afterPrototypeCreation(beanName);
}
// 返回对应的实例
bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);
} 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 {
return createBean(beanName, mbd, args);
} finally {
afterPrototypeCreation(beanName);
}
});
bean = getObjectForBeanInstance(scopedInstance, name, beanName, mbd);
} catch (IllegalStateException ex) {
throw new BeanCreationException(beanName,
"Scope '" + scopeName + "' is not active for the current thread; consider "
+ "defining a scoped proxy for this bean if you intend to refer to it from a singleton",
ex);
}
}
} catch (BeansException ex) {
cleanupAfterBeanCreationFailure(beanName);
throw ex;
}
}
// Check if required type matches the type of the actual bean instance.
//检查需要的类型是否符合bean的实际类型 ,对应getBean时指定的requireType
if (requiredType != null && !requiredType.isInstance(bean)) {
try {
// 执行类型转换,转换成期望的类型
T convertedBean = getTypeConverter().convertIfNecessary(bean, requiredType);
if (convertedBean == null) {
throw new BeanNotOfRequiredTypeException(name, requiredType, bean.getClass());
}
return convertedBean;
} catch (TypeMismatchException ex) {
if (logger.isTraceEnabled()) {
logger.trace("Failed to convert bean '" + name + "' to required type '" + ClassUtils
.getQualifiedName(requiredType) + "'", ex);
}
throw new BeanNotOfRequiredTypeException(name, requiredType, bean.getClass());
}
}
return (T) bean;
}
代码 贴了name多,看起来也有点转悠,那再来简单概括doGetBean 到底干了啥活
setp 1;
根据参数name 获取真正beanName
step2;
检查缓存/实例工厂中是否有对应的单例(getSingleton),若存在则进行实例化并返回对象,否则继续往下执行
step3:
原型模式,循环依赖检查。
step4:
如果当前 beanFactory 中不存在目标 bean,则尝试从 parentBeanFactory 递归获取
step5:
getMergedLocalBeanDefinition(将之前解析过程返得到的 GenericBeanDefinition 对象合并为 RootBeanDefinition 对象,同事合并父类属性)
step6:
若存在依赖则要递归实例化依赖的bean
step7:
根据不同作用域对bean实例化
step8:
检查bean的类型要求,如有要求则做类型转换
step9::
返回bean 实例。