我是靠谱客的博主 花痴水蜜桃,最近开发中收集的这篇文章主要介绍准备依赖注入,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

在前面的分析中我们已经了解到Bean 的依赖注入主要分为两个步骤,首先调用createBeanInstance()方法生成Bean 所包含的Java 对象实例。然后,调用populateBean()方法,对Bean 属性的依赖注入进行处理。

上面我们已经分析了容器初始化生成Bean 所包含的Java 实例对象的过程,现在我们继续分析生成对象后,Spring IOC 容器是如何将Bean 的属性依赖关系注入Bean 实例对象中并设置好的,回到AbstractAutowireCapableBeanFactory 的populateBean()方法,对属性依赖注入的代码如下:

//将Bean属性设置到生成的实例对象上
protected void populateBean(String beanName, RootBeanDefinition mbd, @Nullable BeanWrapper bw) {
	if (bw == null) {
		if (mbd.hasPropertyValues()) {
			throw new BeanCreationException(
					mbd.getResourceDescription(), beanName, "Cannot apply property values to null instance");
		}
		else {
			// Skip property population phase for null instance.
			return;
		}
	}

	// Give any InstantiationAwareBeanPostProcessors the opportunity to modify the
	// state of the bean before properties are set. This can be used, for example,
	// to support styles of field injection.
	boolean continueWithPropertyPopulation = true;

	if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
		for (BeanPostProcessor bp : getBeanPostProcessors()) {
			if (bp instanceof InstantiationAwareBeanPostProcessor) {
				InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
				if (!ibp.postProcessAfterInstantiation(bw.getWrappedInstance(), beanName)) {
					continueWithPropertyPopulation = false;
					break;
				}
			}
		}
	}

	if (!continueWithPropertyPopulation) {
		return;
	}
	//获取容器在解析Bean定义资源时为BeanDefiniton中设置的属性值
	PropertyValues pvs = (mbd.hasPropertyValues() ? mbd.getPropertyValues() : null);

	//对依赖注入处理,首先处理autowiring自动装配的依赖注入
	if (mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_NAME ||
			mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_TYPE) {
		MutablePropertyValues newPvs = new MutablePropertyValues(pvs);

		// Add property values based on autowire by name if applicable.
		//根据Bean名称进行autowiring自动装配处理
		if (mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_NAME) {
			autowireByName(beanName, mbd, bw, newPvs);
		}

		// Add property values based on autowire by type if applicable.
		//根据Bean类型进行autowiring自动装配处理
		if (mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_TYPE) {
			autowireByType(beanName, mbd, bw, newPvs);
		}

		pvs = newPvs;
	}

	//对非autowiring的属性进行依赖注入处理

	boolean hasInstAwareBpps = hasInstantiationAwareBeanPostProcessors();
	boolean needsDepCheck = (mbd.getDependencyCheck() != RootBeanDefinition.DEPENDENCY_CHECK_NONE);

	if (hasInstAwareBpps || needsDepCheck) {
		if (pvs == null) {
			pvs = mbd.getPropertyValues();
		}
		PropertyDescriptor[] filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
		if (hasInstAwareBpps) {
			for (BeanPostProcessor bp : getBeanPostProcessors()) {
				if (bp instanceof InstantiationAwareBeanPostProcessor) {
					InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
					pvs = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
					if (pvs == null) {
						return;
					}
				}
			}
		}
		if (needsDepCheck) {
			checkDependencies(beanName, mbd, filteredPds, pvs);
		}
	}

	if (pvs != null) {
		//对属性进行注入
		applyPropertyValues(beanName, mbd, bw, pvs);
	}
}
//解析并注入依赖属性的过程
protected void applyPropertyValues(String beanName, BeanDefinition mbd, BeanWrapper bw, PropertyValues pvs) {
	if (pvs.isEmpty()) {
		return;
	}

	//封装属性值
	MutablePropertyValues mpvs = null;
	List<PropertyValue> original;

	if (System.getSecurityManager() != null) {
		if (bw instanceof BeanWrapperImpl) {
			//设置安全上下文,JDK安全机制
			((BeanWrapperImpl) bw).setSecurityContext(getAccessControlContext());
		}
	}

	if (pvs instanceof MutablePropertyValues) {
		mpvs = (MutablePropertyValues) pvs;
		//属性值已经转换
		if (mpvs.isConverted()) {
			// Shortcut: use the pre-converted values as-is.
			try {
				//为实例化对象设置属性值
				bw.setPropertyValues(mpvs);
				return;
			}
			catch (BeansException ex) {
				throw new BeanCreationException(
						mbd.getResourceDescription(), beanName, "Error setting property values", ex);
			}
		}
		//获取属性值对象的原始类型值
		original = mpvs.getPropertyValueList();
	}
	else {
		original = Arrays.asList(pvs.getPropertyValues());
	}

	//获取用户自定义的类型转换
	TypeConverter converter = getCustomTypeConverter();
	if (converter == null) {
		converter = bw;
	}
	//创建一个Bean定义属性值解析器,将Bean定义中的属性值解析为Bean实例对象的实际值
	BeanDefinitionValueResolver valueResolver = new BeanDefinitionValueResolver(this, beanName, mbd, converter);

	// Create a deep copy, resolving any references for values.

	//为属性的解析值创建一个拷贝,将拷贝的数据注入到实例对象中
	List<PropertyValue> deepCopy = new ArrayList<>(original.size());
	boolean resolveNecessary = false;
	for (PropertyValue pv : original) {
		//属性值不需要转换
		if (pv.isConverted()) {
			deepCopy.add(pv);
		}
		//属性值需要转换
		else {
			String propertyName = pv.getName();
			//原始的属性值,即转换之前的属性值
			Object originalValue = pv.getValue();
			//转换属性值,例如将引用转换为IOC容器中实例化对象引用
			Object resolvedValue = valueResolver.resolveValueIfNecessary(pv, originalValue);
			//转换之后的属性值
			Object convertedValue = resolvedValue;
			//属性值是否可以转换
			boolean convertible = bw.isWritableProperty(propertyName) &&
					!PropertyAccessorUtils.isNestedOrIndexedProperty(propertyName);
			if (convertible) {
				//使用用户自定义的类型转换器转换属性值
				convertedValue = convertForProperty(resolvedValue, propertyName, bw, converter);
			}
			// Possibly store converted value in merged bean definition,
			// in order to avoid re-conversion for every created bean instance.
			//存储转换后的属性值,避免每次属性注入时的转换工作
			if (resolvedValue == originalValue) {
				if (convertible) {
					//设置属性转换之后的值
					pv.setConvertedValue(convertedValue);
				}
				deepCopy.add(pv);
			}
			//属性是可转换的,且属性原始值是字符串类型,且属性的原始类型值不是
			//动态生成的字符串,且属性的原始值不是集合或者数组类型
			else if (convertible && originalValue instanceof TypedStringValue &&
					!((TypedStringValue) originalValue).isDynamic() &&
					!(convertedValue instanceof Collection || ObjectUtils.isArray(convertedValue))) {
				pv.setConvertedValue(convertedValue);
				//重新封装属性的值
				deepCopy.add(pv);
			}
			else {
				resolveNecessary = true;
				deepCopy.add(new PropertyValue(pv, convertedValue));
			}
		}
	}
	if (mpvs != null && !resolveNecessary) {
		//标记属性值已经转换过
		mpvs.setConverted();
	}

	// Set our (possibly massaged) deep copy.
	//进行属性依赖注入
	try {
		bw.setPropertyValues(new MutablePropertyValues(deepCopy));
	}
	catch (BeansException ex) {
		throw new BeanCreationException(
				mbd.getResourceDescription(), beanName, "Error setting property values", ex);
	}
}

分析上述代码,我们可以看出,对属性的注入过程分以下两种情况:

1)、属性值类型不需要强制转换时,不需要解析属性值,直接准备进行依赖注入。

2)、属性值需要进行类型强制转换时,如对其他对象的引用等,首先需要解析属性值,然后对解析后的属性值进行依赖注入。

对属性值的解析是在BeanDefinitionValueResolver 类中的resolveValueIfNecessary()方法中进行的,对属性值的依赖注入是通过bw.setPropertyValues()方法实现的,在分析属性值的依赖注入之前,我们先分析一下对属性值的解析过程。

 

最后

以上就是花痴水蜜桃为你收集整理的准备依赖注入的全部内容,希望文章能够帮你解决准备依赖注入所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(29)

评论列表共有 0 条评论

立即
投稿
返回
顶部