1.前言
Demo中的beanFactory的引入,代码如下:
配置类:
@Configuration
public class Cap6MainConfig {
@Bean("testFactoryBean")
public TestFactoryBean testFactoryBean(){
return new TestFactoryBean();
}
}
TestFactoryBean类:
import cn.enjoy.cap6.Pig;
import org.springframework.beans.factory.FactoryBean;
public class TestFactoryBean implements FactoryBean<Pig> {
public Pig getObject() throws Exception {
return new Pig();
}
public Class<?> getObjectType() {
return Pig.class;
}
public boolean isSingleton() {
return true; //是一个单例的bean
}
}
测试类:
public class Cap6Test {
@Test
public void test() {
AnnotationConfigApplicationContext app = new AnnotationConfigApplicationContext(Cap6MainConfig.class); //解析配置文件
Object bean1 = app.getBean("testFactoryBean");
Object bean2 = app.getBean("testFactoryBean");
System.out.println("bean的类型="+bean1.getClass()); //Pig实例(1)
System.out.println(bean1 == bean2);
Object bean3 = app.getBean("&testFactoryBean");//取的是testFactoryBean实例,加了特殊字符(2)
}
}
2.问题描述
为什么上述代码块中的(1)和(2)处的实例是不一样的?
3.解惑一
进入debug模式,追踪app.getBean方法,如下:
@Override
public Object getBean(String name) throws BeansException {
assertBeanFactoryActive(); //上下文中的BeanFactory的激活断言
return getBeanFactory().getBean(name);//追踪如下代码块 ①
}
①:
@Override
public Object getBean(String name) throws BeansException {
return doGetBean(name, null, null, false); name: "testFactoryBean"
}
继续追踪-->②
②
@SuppressWarnings("unchecked")
protected <T> T doGetBean(final String name, @Nullable final Class<T> requiredType,
@Nullable final Object[] args, boolean typeCheckOnly) throws BeansException {
final String beanName = transformedBeanName(name);//获取去掉前缀的beanName,详见3.1
Object bean; //存放返回对象,懒汉单例模式
// Eagerly check singleton cache for manually registered singletons.
//在单例缓存中检查手动注册的单例
Object sharedInstance = getSingleton(beanName); //详见3.2,beanName=“testbeanFactory”
if (sharedInstance != null && args == null) { //为true
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);//详见3.3所示
}
else {
// Fail if we're already creating this bean instance:
// We're assumably within a circular reference.
if (isPrototypeCurrentlyInCreation(beanName)) {
throw new BeanCurrentlyInCreationException(beanName);
}
// Check if bean definition exists in this factory.
BeanFactory parentBeanFactory = getParentBeanFactory();
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.
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);
}
}
if (!typeCheckOnly) {
markBeanAsCreated(beanName);
}
try {
final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
checkMergedBeanDefinition(mbd, beanName, args);
// Guarantee initialization of beans that the current bean depends on.
String[] dependsOn = mbd.getDependsOn();
if (dependsOn != null) {
for (String dep : dependsOn) {
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.
if (mbd.isSingleton()) {
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);
prototypeInstance = createBean(beanName, mbd, args);
}
finally {
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.
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;
}
3.1 transformedBeanName(String name)方法详解
protected String transformedBeanName(String name) {
return canonicalName(BeanFactoryUtils.transformedBeanName(name));
}
//canonicalName(BeanFactoryUtils.transformedBeanName(name))见3.1.2
public static String transformedBeanName(String name) {
//非空检查
Assert.notNull(name, "'name' must not be null");
//判断是否不是以&前缀开头,在本例中返回为true
if (!name.startsWith(BeanFactory.FACTORY_BEAN_PREFIX)) {
return name;
}
//如果是以“&”前缀开头,这里使用到lambda表达式,假设此时的name=&testBeanFactory
//下面这个函数的逻辑为:
//transformedBeanNameCache是一个在Spring中申明的ConcurrentHashMap,以下简称Map
//如果map中name对应的值不为空,直接返回
//如果为空,则根据上述的映射函数进行计算,并put进入Map中
//总而言之,该Map中存储的都是没有&开头的名字
return transformedBeanNameCache.computeIfAbsent(name, beanName -> {
do {
beanName = beanName.substring(BeanFactory.FACTORY_BEAN_PREFIX.length());//参数为1
}
while (beanName.startsWith(BeanFactory.FACTORY_BEAN_PREFIX));
//该lambda表达式的意思是:去掉name之前所有的“&”前缀,直到不以&开头
return beanName;
});
}
//分析transformedBeanNameCache.computeIfAbsent()方法于3.1.1
3.1.1 computeIfAbsent方法详解
Map.class
//如果指定的key没有与value进行关联(或者映射到null),则试图通过给定的映射函数计算其值,并及那个该计算的结果映射到该map中,除非其值为null
default V computeIfAbsent(K key,
Function<? super K, ? extends V> mappingFunction) { //假设为key:&testBeanFactory
//非空检查
Objects.requireNonNull(mappingFunction);
V v; //申明v
if ((v = get(key)) == null) { //判断key对应的value值是否为空
V newValue; //申明新值
if ((newValue = mappingFunction.apply(key)) != null) { //通过新的映射关系获得newValue值
put(key, newValue); //newValue不为null,则插入map并返回
return newValue;
}
}
return v; //在key在map中映射的value不为空,则返回value
}
3.1.2 canonicalName方法详解
//确定原始名称,将别名解析为规范名称
public String canonicalName(String name) { //name="testFactoryBean"
String canonicalName = name;
// Handle aliasing... 处理别名
String resolvedName;
//循环,resolvedName为null,跳出循环,别名有待研究,里面的逻辑目前还不明确
//按照以下循环逻辑,别名中存的映射关系:a-->b--->c....x--->null,作用是取出x
do {
resolvedName = this.aliasMap.get(canonicalName); //取出aliasMap中的canonicalName对应的值
if (resolvedName != null) {
canonicalName = resolvedName;
}
}
while (resolvedName != null);
return canonicalName; //当前输出的是就是name值
}
3.2 getSingleton方法详解
@Nullable
protected Object getSingleton(String beanName, boolean allowEarlyReference) { //参数:“testBeanFactory” true
//singletonObjects是单例的缓存池,为一个hashMap的结构
Object singletonObject = this.singletonObjects.get(beanName); //取值,本例中该值不为null
//isSingletonCurrentlyInCreation方法底层,是判断一个set集合(存放正在创建的bean的集合)中是否包含beanName
//缓存为空且该set集合中包含beanName,向下执行
if (singletonObject == null && isSingletonCurrentlyInCreation(beanName)) {
//如果上面的singletonObjects缓存池中找不到,则去早期的缓存池中寻找
synchronized (this.singletonObjects) { //同步代码块
//从earlySingletonObjects这个存放早期单例对象的hashMap中取值
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; //直接返回singletonObjects单例的缓存池中的值,其实是一个TestBeanFactory类的实例对象
}
3.3 getObjectForBeanInstance(sharedInstance, name, beanName, null)方法详解
/**
* Overridden in order to implicitly register the currently created bean as
* dependent on further beans getting programmatically retrieved during a
* {@link Supplier} callback.
* @since 5.0
* @see #obtainFromSupplier
//重写,以隐式注册当前创建的bean,使其依赖于在回调期间以编程方式检索的其他bean
*/
@Override
protected Object getObjectForBeanInstance(
Object beanInstance, String name, String beanName, @Nullable RootBeanDefinition mbd) {
String currentlyCreatedBean = this.currentlyCreatedBean.get(); //详见3.3.1,结果返回为null
if (currentlyCreatedBean != null) { //不进入
registerDependentBean(beanName, currentlyCreatedBean);
}
return super.getObjectForBeanInstance(beanInstance, name, beanName, mbd); //详见3.3.2
}
3.3.1 this.currentlyCreatedBean.get()方法详解
/**
* Returns the value in the current thread's copy of this
* thread-local variable. If the variable has no value for the
* current thread, it is first initialized to the value returned
* by an invocation of the {@link #initialValue} method.
* 返回当前线程对此thread-local变量的拷贝
//如果当前线程对于此变量无值,则该值将会被第一次初始化为{@link #initialValue}反射方法返回
//的值
* @return the current thread's value of this thread-local
*/
public T get() {
Thread t = Thread.currentThread(); //获取当前线程
ThreadLocalMap map = getMap(t); //获取与当前线程的ThreadLocalMap静态类对象
//ThreadLocalMap是一个静态类,ThreadLocalMap is a customized hash map suitable only
// for maintaining thread local values.该结构中存在一个静态的Entry对象
//k---ThreadLocal v---Object
if (map != null) { //map不为null,向下执行
ThreadLocalMap.Entry e = map.getEntry(this); //this:当前的ThreadLocal对象
if (e != null) {
@SuppressWarnings("unchecked")
T result = (T)e.value; //获得entry中的当前ThreadLocal对象对应的value值
return result; //返回为null
}
}
return setInitialValue();
}
3.3.2 super.getObjectForBeanInstance(beanInstance, name, beanName, mbd)方法详解
protected Object getObjectForBeanInstance(
Object beanInstance, String name, String beanName, @Nullable RootBeanDefinition mbd) {
// Don't let calling code try to dereference the factory if the bean isn't a factory.
if (BeanFactoryUtils.isFactoryDereference(name)) {// //是否以“&”前缀开头,否
if (beanInstance instanceof NullBean) {
return beanInstance;
}
if (!(beanInstance instanceof FactoryBean)) {
throw new BeanIsNotAFactoryException(beanName, beanInstance.getClass());
}
if (mbd != null) {
mbd.isFactoryBean = true;
}
return beanInstance;
}
// Now we have the bean instance, which may be a normal bean or a FactoryBean.
// If it's a FactoryBean, we use it to create a bean instance, unless the
// caller actually wants a reference to the factory.
if (!(beanInstance instanceof FactoryBean)) { //false
return beanInstance;
}
Object object = null;
if (mbd != null) { //false
mbd.isFactoryBean = true;
}
else {
//在缓存中取beanname为testFactoryBean的value值,FactoryBean对象目前还没有创建,所以输出为nulL
object = getCachedObjectForFactoryBean(beanName);
}
if (object == null) {
// Return bean instance from factory.
FactoryBean<?> factory = (FactoryBean<?>) beanInstance;
// Caches object obtained from FactoryBean if it is a singleton.
if (mbd == null && containsBeanDefinition(beanName)) { //true
//containsBeanDefinition就是在判断spring底层的beanDifinitionMap中是否包含了beanName的键值
//在spring的register阶段,该Map中就已经被赋值,故而包含
mbd = getMergedLocalBeanDefinition(beanName); //包装TestFactoryBean为RootBeanDifinition
}
boolean synthetic = (mbd != null && mbd.isSynthetic());//false
object = getObjectFromFactoryBean(factory, beanName, !synthetic);//Pig@xxx,详见下
}
return object;//Pig@xxx
}
以上内容解释了第一个问题,对于第二个问题解释如下(当getBean方法中传入的字符串是“&xxx”的时候,程序获得的对象是TestFactoryBean实例bean)
protected Object getObjectFromFactoryBean(FactoryBean<?> factory, String beanName, boolean shouldPostProcess) {
//factory:TestFactory@xxx beanName:testFactoryBean shouldPostProcess:true
//containsSingleton()判断singletonObject这个Map中是否包含beanName这个键值,非懒加载的单例对象在Spring容器初始化的时候就创建
if (factory.isSingleton() && containsSingleton(beanName)) {
synchronized (getSingletonMutex()) { //同步代码块
Object object = this.factoryBeanObjectCache.get(beanName); //取出为null
if (object == null) {
object = doGetObjectFromFactoryBean(factory, beanName);//Pig@xxx,详见下代码块
// Only post-process and store if not put there already during getObject() call above
// (e.g. because of circular reference processing triggered by custom getBean calls)
Object alreadyThere = this.factoryBeanObjectCache.get(beanName);//取出为null
if (alreadyThere != null) {//false
object = alreadyThere;
}
else {
if (shouldPostProcess) {//true
if (isSingletonCurrentlyInCreation(beanName)) {//false
// Temporarily return non-post-processed object, not storing it yet..
return object;
}
//面向切片编程的思想
//单例bean创建的回调,底层是一个异常,可以忽略
beforeSingletonCreation(beanName);
try {
object = postProcessObjectFromFactoryBean(object, beanName);//object:Pig@xxx
}
catch (Throwable ex) {
throw new BeanCreationException(beanName,
"Post-processing of FactoryBean's singleton object failed", ex);
}
finally {
//单例创建之后的回调,底层也是一个异常信息,可忽略
afterSingletonCreation(beanName);
}
}
if (containsSingleton(beanName)) {//true
this.factoryBeanObjectCache.put(beanName, object);//向缓存中存入数据key:testFactoryBean value:Pig@xxx
}
}
}
return object; //返回Pig@xxx
}
}
else {
Object object = doGetObjectFromFactoryBean(factory, beanName);
if (shouldPostProcess) {
try {
object = postProcessObjectFromFactoryBean(object, beanName);
}
catch (Throwable ex) {
throw new BeanCreationException(beanName, "Post-processing of FactoryBean's object failed", ex);
}
}
return object;
}
}
private Object doGetObjectFromFactoryBean(FactoryBean<?> factory, String beanName) throws BeanCreationException {
Object object;
try {
if (System.getSecurityManager() != null) { //false
AccessControlContext acc = getAccessControlContext();
try {
object = AccessController.doPrivileged((PrivilegedExceptionAction<Object>) factory::getObject, acc);
}
catch (PrivilegedActionException pae) {
throw pae.getException();
}
}
else {
object = factory.getObject(); //调用上文中自定义的TestBeanFactory中的getObject方法,返回Pig@xxx
}
}
catch (FactoryBeanNotInitializedException ex) {
throw new BeanCurrentlyInCreationException(beanName, ex.toString());
}
catch (Throwable ex) {
throw new BeanCreationException(beanName, "FactoryBean threw exception on object creation", ex);
}
// Do not accept a null value for a FactoryBean that's not fully
// initialized yet: Many FactoryBeans just return null then.
if (object == null) { //false
if (isSingletonCurrentlyInCreation(beanName)) {
throw new BeanCurrentlyInCreationException(
beanName, "FactoryBean which is currently in creation returned null from getObject");
}
object = new NullBean();
}
return object; //返回Pig@xxx
}
4.解惑二
分析过程类似于解惑一中所示,这里将重要的方法描述下:
4.1 doGetBean方法追踪
protected <T> T doGetBean(
String name, @Nullable Class<T> requiredType, @Nullable Object[] args, boolean typeCheckOnly)
throws BeansException {
//name:&testFactoryBean requiredType:null args:null typeCheckOnly:false
String beanName = transformedBeanName(name);//如果有&前缀,去掉获得,beanName:testFactoryBean
Object bean; //申明返回值 bean:null
// Eagerly check singleton cache for manually registered singletons.
//sharedInstance:TestFactoryBean@xxx
Object sharedInstance = getSingleton(beanName);//详见4.2
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);//返回TestFactoryBean@xxx,详见4.3
}
else {
// Fail if we're already creating this bean instance:
// We're assumably within a circular reference.
if (isPrototypeCurrentlyInCreation(beanName)) {
throw new BeanCurrentlyInCreationException(beanName);
}
// Check if bean definition exists in this factory.
BeanFactory parentBeanFactory = getParentBeanFactory();
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.
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);
}
}
if (!typeCheckOnly) {
markBeanAsCreated(beanName);
}
try {
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
checkMergedBeanDefinition(mbd, beanName, args);
// Guarantee initialization of beans that the current bean depends on.
String[] dependsOn = mbd.getDependsOn();
if (dependsOn != null) {
for (String dep : dependsOn) {
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.
if (mbd.isSingleton()) {
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);
prototypeInstance = createBean(beanName, mbd, args);
}
finally {
afterPrototypeCreation(beanName);
}
bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);
}
else {
String scopeName = mbd.getScope();
if (!StringUtils.hasLength(scopeName)) {
throw new IllegalStateException("No scope name defined for bean ´" + beanName + "'");
}
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.
//false
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;//返回TestFactoryBean@xxx
}
4.2 getSingleton(String beanName)方法分析
@Override
@Nullable
public Object getSingleton(String beanName) {
return getSingleton(beanName, true);
}
--->
@Nullable
protected Object getSingleton(String beanName, boolean allowEarlyReference) {
// Quick check for existing instance without full singleton lock
singletonObjects为一个单例的concurrentHashMap获取单例对象,其中存放了所有已经实例化好的单例bean对象
//beanName这个key对应的value值为一个TestFactoryBean实例bean,记作TestFactoryBean@xxx
Object singletonObject = this.singletonObjects.get(beanName);
if (singletonObject == null && isSingletonCurrentlyInCreation(beanName)) { //false
singletonObject = this.earlySingletonObjects.get(beanName);
if (singletonObject == null && allowEarlyReference) {
synchronized (this.singletonObjects) {
// Consistent creation of early reference within full singleton lock
singletonObject = this.singletonObjects.get(beanName);
if (singletonObject == null) {
singletonObject = this.earlySingletonObjects.get(beanName);
if (singletonObject == null) {
ObjectFactory<?> singletonFactory = this.singletonFactories.get(beanName);
if (singletonFactory != null) {
singletonObject = singletonFactory.getObject();
this.earlySingletonObjects.put(beanName, singletonObject);
this.singletonFactories.remove(beanName);
}
}
}
}
}
}
return singletonObject;//返回TestFactoryBean@xxx
}
4.3 getObjectForBeanInstance方法分析
protected Object getObjectForBeanInstance(
Object beanInstance, String name, String beanName, @Nullable RootBeanDefinition mbd) {
//beanInstance:TestFactoryBean@xxx name:&testFactoryBean beanName:testFactoryBean mbd:null
// Don't let calling code try to dereference the factory if the bean isn't a factory.
//true
if (BeanFactoryUtils.isFactoryDereference(name)) {
if (beanInstance instanceof NullBean) { //false
return beanInstance;
}
if (!(beanInstance instanceof FactoryBean)) { //false
throw new BeanIsNotAFactoryException(beanName, beanInstance.getClass());
}
if (mbd != null) { //false
mbd.isFactoryBean = true;
}
return beanInstance; //返回TestFactoryBean@xxx
}