spring源码解析 -- 构造bean

Spring源码解析 -- 读取bean元数据
spring源码解析 -- 构造bean
spring源码解析 -- 注入属性
spring源码解析 -- Spring Context
Spring源码解析 -- AOP原理(1)
Spring源码解析 -- AOP原理(2)
Spring源码解析 -- SpringMvc原理java

源码分析基于spring 4.3.xspring

前面文章已经分析了spring如何加载xml配置中的bean元数据,如今来分析一下spring构造bean的过程。
关于阅读源码的思路,可参考 -- 如何阅读java源码 缓存

BeanFactory xmlBeanFactory = new XmlBeanFactory(new ClassPathResource("application.xml"));
Blog bean = (Blog)xmlBeanFactory.getBean("blog");
复制代码

XmlBeanFactory的父类AbstractBeanFactory是spring中一个很重要的类,他为BeanFactory提供基础服务。构造bean就是由该类实现的。
AbstractBeanFactory#doGetBeanbash

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);
	Object bean;

	Object sharedInstance = getSingleton(beanName);	// #1
	if (sharedInstance != null && args == null) {
		...
		bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);	// #2
	}

	else {
		if (isPrototypeCurrentlyInCreation(beanName)) {	// #3
			throw new BeanCurrentlyInCreationException(beanName);
		}

		BeanFactory parentBeanFactory = getParentBeanFactory();
		if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {	// #4
			...
		}

		if (!typeCheckOnly) {
			markBeanAsCreated(beanName);	// #5
		}

		try {
			final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);	// #6
			checkMergedBeanDefinition(mbd, beanName, args);

			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);	// #7
					}
					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, () -> {		// #8
					try {
						return createBean(beanName, mbd, args);	// #9
					}
					catch (BeansException ex) {
						destroySingleton(beanName);
						throw ex;
					}
				});
				bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
			}

			... 
		}
		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)) {	// #10
		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;
}

复制代码

#1 单例的bean,先从缓冲中查询
getSingleton方法会查询 singletonObject,earlySingletonObjects,singletonFactories等缓存,它们都是简单的map,缓存了单例的bean,正在建立的bean和ObjectFactory对象。微信

#2 若是构造的bean是FactoryBean,进行对应的处理
getObjectForBeanInstance方法会根据参数beanInstance进行处理,若是beanInstance是FactoryBean,会调用其getObject()方法建立bean,若是不是,返回直接返回该beanInstance参数。 FactoryBean是spring提供的一个扩展接口,用户实现该接口能够自定义bean的建立。app

#3 若是如今正在建立这个bean,则直接报错,这时极可能陷入循环引用了
#4 当前BeanFactory不存在对应的BeanDefinition,尝试经过父BeanFactory构造bean
#5 标记这个bean正在构造中
#6 获取BeanDefinition
前面解析spring加载bean数据的文章中说过,spring会将bean元数据转化为BeanDefinition,存入DefaultListableBeanFactory#beanDefinitionMap属性中。
getMergedLocalBeanDefinition方法会获取对应BeanDefinition,若是BeanDefinition存在ParentName,会获取父BeanDefinition,再合并元数据。ide

#7 先构造依赖的bean
#8 使用ObjectFactory构造并注册一个bean,getSingleton方法也要完成构造bean的准备和蔼后工做
#9 匿名的ObjectFactory,调用AbstractAutowireCapableBeanFactory#createBean进行实际的构造bean工做
#10 bean类型转换函数

spring中bean有singleton,prototype等范围,这里只关注singleton类型的bean的构造过程。源码分析

#8步骤,DefaultSingletonBeanRegistry#getSingleton(注意getSingleton有重载方法)post

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) {
				...
				beforeSingletonCreation(beanName);	// #1
				boolean newSingleton = false;
				boolean recordSuppressedExceptions = (this.suppressedExceptions == null);
				if (recordSuppressedExceptions) {
					this.suppressedExceptions = new LinkedHashSet<>();
				}
				try {
					singletonObject = singletonFactory.getObject();	// #2
					newSingleton = true;
				}
				...
				finally {
					if (recordSuppressedExceptions) {
						this.suppressedExceptions = null;
					}
					afterSingletonCreation(beanName);
				}
				if (newSingleton) {
					addSingleton(beanName, singletonObject);	// #3
				}
			}
			return singletonObject;
		}
	}
复制代码

#1 仅作错误检查,也是提供给子类的扩展方法
#2 真正构造bean的方法,调用AbstractBeanFactory#doGetBean方法#9步骤的匿名类处理,实际调用AbstractAutowireCapableBeanFactory#createBean
#3 单例的bean,加入缓冲中

真正的构造bean方法
AbstractAutowireCapableBeanFactory#createBean

protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) throws BeanCreationException {

		if (logger.isTraceEnabled()) {
			logger.trace("Creating instance of bean '" + beanName + "'");
		}
		RootBeanDefinition mbdToUse = mbd;

		Class<?> resolvedClass = resolveBeanClass(mbd, beanName);	// #1
		if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
			mbdToUse = new RootBeanDefinition(mbd);
			mbdToUse.setBeanClass(resolvedClass);
		}

		try {
			mbdToUse.prepareMethodOverrides();	// #2
		}
		...

		try {
			Object bean = resolveBeforeInstantiation(beanName, mbdToUse);	// #3
			if (bean != null) {
				return bean;
			}
		}
		...

		try {
			Object beanInstance = doCreateBean(beanName, mbdToUse, args);	// #4
			if (logger.isTraceEnabled()) {
				logger.trace("Finished creating instance of bean '" + beanName + "'");
			}
			return beanInstance;
		}
		...
	}

复制代码

#1 确保jdk已加载bean的class
#2 对bean的lookup-method和replace-method作检查工做
#3 spring的扩展机制,调用BeanPostProcessor#postProcessBeforeInstantiation方法
注意,若是resolveBeforeInstantiation返回非null对象,这里将直接返回该对象做为bean,spring再也不构造该bean。
#4 继续构造bean

AbstractAutowireCapableBeanFactory#doCreateBean

protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final @Nullable Object[] args) throws BeanCreationException {

	BeanWrapper instanceWrapper = null;
	if (mbd.isSingleton()) {
		instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);	// #1
	}
	if (instanceWrapper == null) {
		instanceWrapper = createBeanInstance(beanName, mbd, args);	// #2
	}
	final Object bean = instanceWrapper.getWrappedInstance();
	Class<?> beanType = instanceWrapper.getWrappedClass();
	if (beanType != NullBean.class) {
		mbd.resolvedTargetType = beanType;
	}

	// Allow post-processors to modify the merged bean definition.
	synchronized (mbd.postProcessingLock) {
		if (!mbd.postProcessed) {
			try {
				applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);	// #3
			}
			catch (Throwable ex) {
				throw new BeanCreationException(mbd.getResourceDescription(), beanName,
						"Post-processing of merged bean definition failed", ex);
			}
			mbd.postProcessed = true;
		}
	}

	...

	// Initialize the bean instance.
	Object exposedObject = bean;
	try {
		populateBean(beanName, mbd, instanceWrapper);	// #4
		exposedObject = initializeBean(beanName, exposedObject, mbd);	// #5
	}
	catch (Throwable ex) {
		if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {
			throw (BeanCreationException) ex;
		}
		else {
			throw new BeanCreationException(
					mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);
		}
	}

	...

	// Register bean as disposable.
	try {
		registerDisposableBeanIfNecessary(beanName, bean, mbd);		// #6
	}
	catch (BeanDefinitionValidationException ex) {
		throw new BeanCreationException(
				mbd.getResourceDescription(), beanName, "Invalid destruction signature", ex);
	}

	return exposedObject;
}
复制代码

#1 查询BeanWrapper缓冲
#2 构造一个空的(属性未注入)bean,生成BeanWrapper
#3 spring扩展机制,调用MergedBeanDefinitionPostProcessor#postProcessMergedBeanDefinition
#4 populateBean负责注入属性到bean中,后面有对应文章解析该步骤
#5 spring扩展机制,调用Aware方法和init方法,并调用BeanPostProcessor#postProcessAfterInitialization方法。
#6 若是bean存在Destroy方法,或存在对应的DestructionAwareBeanPostProcessor,注册该bean为disposable。(该bean销毁时要调用对应的销毁机制)

这里涉及到循环引用的处理,比较繁琐,因此省略了不少代码,只保留bean建立相关的代码。

BeanWrapper是对bean的包装类,提供了对bean的class,property进行操做的方法。

#2步骤,AbstractAutowireCapableBeanFactory#createBeanInstance

protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, Object[] args) {
		Class<?> beanClass = resolveBeanClass(mbd, beanName);	// #1

		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());
		}

		if (mbd.getFactoryMethodName() != null)  {	// #2
			return instantiateUsingFactoryMethod(beanName, mbd, args);
		}

		boolean resolved = false;
		boolean autowireNecessary = false;
		if (args == null) {
			synchronized (mbd.constructorArgumentLock) {
				if (mbd.resolvedConstructorOrFactoryMethod != null) {	// #3
					resolved = true;
					autowireNecessary = mbd.constructorArgumentsResolved;
				}
			}
		}
		if (resolved) {	
			if (autowireNecessary) {
				return autowireConstructor(beanName, mbd, null, null);	// #4
			}
			else {
				return instantiateBean(beanName, mbd);	// #5
			}
		}

		Constructor<?>[] ctors = determineConstructorsFromBeanPostProcessors(beanClass, beanName);	// #6
		if (ctors != null ||
				mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_CONSTRUCTOR ||
				mbd.hasConstructorArgumentValues() || !ObjectUtils.isEmpty(args))  {
			return autowireConstructor(beanName, mbd, ctors, args);
		}

		// No special handling: simply use no-arg constructor.
		return instantiateBean(beanName, mbd);
	}


复制代码

#1 获取bean的class
#2 若是存在factoryMethod,经过factoryMethod构造bean
#3 判断该class已经构造过bean了
#4 使用以前选择好的构造函数构造bean
#5 使用无参构造函数构造bean
#6 spring根据构造函数的参数,自行选择构造函数,逻辑较复杂。

下面看看使用无参构造方法构造bean,AbstractAutowireCapableBeanFactory#instantiateBean -> SimpleInstantiationStrategy#instantiate

public Object instantiate(RootBeanDefinition bd, String beanName, BeanFactory owner) {
		if (bd.getMethodOverrides().isEmpty()) {
			Constructor<?> constructorToUse;
			synchronized (bd.constructorArgumentLock) {
				constructorToUse = (Constructor<?>) bd.resolvedConstructorOrFactoryMethod;
				if (constructorToUse == null) {
					final Class<?> clazz = bd.getBeanClass();
					if (clazz.isInterface()) {
						throw new BeanInstantiationException(clazz, "Specified class is an interface");
					}
					try {
						if (System.getSecurityManager() != null) {
							...
						}
						else {
							constructorToUse =	clazz.getDeclaredConstructor((Class[]) null);	// #1
						}
						bd.resolvedConstructorOrFactoryMethod = constructorToUse;	// #2
					}
					catch (Throwable ex) {
						throw new BeanInstantiationException(clazz, "No default constructor found", ex);
					}
				}
			}
			return BeanUtils.instantiateClass(constructorToUse);	// #3
		}
		else {
			return instantiateWithMethodInjection(bd, beanName, owner);		// #4
		}
	}
复制代码

#1 获取无参构造函数
#2 添加无参构造函数加入到BeanDefinition缓存中
#2 BeanUtils#instantiateClass经过构造函数构造bean
#3 bean中存在lookup-method或replace-method,必须使用CGLIB构造bean

到这里,bean已经构造完成,下一步就是注入属性了。

若是您以为本文不错,欢迎关注个人微信公众号,您的关注是我坚持的动力!

相关文章
相关标签/搜索