Spring 5 AutowireCapableBeanFactory -- resolveDependency源码分析(一)

Spring 5 AutowireCapableBeanFactory – resolveDependency源码分析(一)
Spring 5 AutowireCapableBeanFactory – resolveDependency源码分析(二)

相关源码注释

ApplicationContext

Spring 5 DefaultResourceLoader 源码注释
Spring 5 AbstractApplicationContext 源码注释

BeanFactory

Spring 5 SimpleAliasRegistry 源码注释
Spring 5 DefaultSingletonBeanRegistry 源码注释
Spring 5 FactoryBeanRegistrySupport 源码注释
Spring 5 AbstractBeanFactory 源码注释
Spring 5 AbstractAutowireCapableBeanFactory 源码注释
Spring 5 DefaultLisbaleBeanFactory 源码注释

resolveDependency

/**
	 *  <p>根据descriptor的依赖类型解析出与descriptor所包装的对象匹配的候选Bean对象</p>
	 * Resolve the specified dependency against the beans defined in this factory.
	 * <p>解析针对此工厂中定义的Bean的指定依赖关系</p>
	 * @param descriptor the descriptor for the dependency (field/method/constructor)
	 *                   -- 依赖项的描述符(字段/方法/构造函数)   
	 * @param requestingBeanName the name of the bean which declares the given dependency
	 *                            -- 声明给定依赖项的bean名,即需要Field/MethodParamter所对应的bean对象来构建的Bean对象的Bean名   
	 * @return the resolved object, or {@code null} if none found
	 * 		-- 解析的对象;如果找不到,则为null
	 * @throws NoSuchBeanDefinitionException if no matching bean was found
	 * 			-- 如果没有找到匹配的bean
	 * @throws NoUniqueBeanDefinitionException if more than one matching bean was found
	 * 			-- 如果找到多个匹配的bean
	 * @throws BeansException if dependency resolution failed for any other reason
	 * 			 -- 如果依赖项解析由于任何其他原因而失败
	 * @since 2.5
	 * @see #resolveDependency(DependencyDescriptor, String, Set, TypeConverter)
	 */
	@Nullable
	Object resolveDependency(DependencyDescriptor descriptor, @Nullable String requestingBeanName) throws BeansException;

	/**
	 * <p>根据descriptor的依赖类型解析出与descriptor所包装的对象匹配的候选Bean对象</p>
	 * Resolve the specified dependency against the beans defined in this factory.
	 * <p>解析针对此工厂中定义的Bean的指定依赖关系</p>
	 * @param descriptor the descriptor for the dependency (field/method/constructor)
	 *                   -- 依赖项的描述符(字段/方法/构造函数)
	 * @param requestingBeanName the name of the bean which declares the given dependency
	 *                           -- 声明给定依赖项的bean名,即需要Field/MethodParamter所对应的bean对象来构建的Bean对象的Bean名
	 * @param autowiredBeanNames a Set that all names of autowired beans (used for
	 * resolving the given dependency) are supposed to be added to
	 *     -- 一个集合,所有自动装配的bean名(用于解决给定依赖关系)都应添加.即自动注入匹配成功的候选Bean名集合。
	 *                              【当autowiredBeanNames不为null,会将所找到的所有候选Bean对象添加到该集合中,以供调用方使用】
	 * @param typeConverter the TypeConverter to use for populating arrays and collections
	 *    -- 用于填充数组和集合的TypeConverter
	 * @return the resolved object, or {@code null} if none found
	 *  -- 解析的对象;如果找不到,则为null
	 * @throws NoSuchBeanDefinitionException if no matching bean was found
	 *  -- 如果没有找到匹配的bean
	 * @throws NoUniqueBeanDefinitionException if more than one matching bean was found
	 *  -- 如果找到多个匹配的bean
	 * @throws BeansException if dependency resolution failed for any other reason
	 *  -- 如果依赖项解析由于任何其他原因而失败
	 * @since 2.5
	 * @see DependencyDescriptor
	 */
	@Nullable
	Object resolveDependency(DependencyDescriptor descriptor, @Nullable String requestingBeanName,
			@Nullable Set<String> autowiredBeanNames, @Nullable TypeConverter typeConverter) throws BeansException;

由 DefaultLisbableBeanFactory 实现。
根据descriptor的依赖类型解析出与descriptor所包装的对象匹配的候选Bean对象

  1. 获取工厂的参数名发现器,设置到descriptor中。使得descriptor初始化基础方法参数的参数名发现。
  2. 【当descriptor的依赖类型是Optional时】:
    1. 如果descriptor的依赖类型为Optional类,创建Optional类型的符合descriptor要求的候选Bean对象并返回 出去
  3. 【当decriptord的依赖类型是ObjectFactory或者是ObjectProvider】:
    1. 如果decriptord的依赖类型是ObjectFactory或者是ObjectProvider,新建一个 DependencyObjectProvider的实例并返回出去
  4. 【当decriptord的依赖类型是javax.inject.Provider】:
    1. 如果依赖类型是javax.inject.Provider类,新建一个专门用于构建 javax.inject.Provider对象的工厂来构建创建Jse330Provider对象
  5. 【当descriptor需要延迟加载时】:
    1. 尝试获取延迟加载代理对象【变量 result】
  6. 【当现在就需要得到候选Bean对象时】:
    1. 如果result为null,即表示现在需要得到候选Bean对象,解析出与descriptor所包装的对象匹配 的候选Bean对象
  7. 将与descriptor所包装的对象匹配的候选Bean对象【result】返回出去
/**
	 * 根据descriptor的依赖类型解析出与descriptor所包装的对象匹配的候选Bean对象:
	 * @param descriptor the descriptor for the dependency (field/method/constructor)
	 *                   -- 依赖项的描述符(字段/方法/构造函数)
	 * @param requestingBeanName the name of the bean which declares the given dependency
	 *                           -- 声明给定依赖项的bean名,即需要Field/MethodParamter所对应的bean对象来构建的Bean对象的Bean名
	 * @param autowiredBeanNames a Set that all names of autowired beans (used for
	 * resolving the given dependency) are supposed to be added to
	 *     一个集合,所有自动装配的bean名(用于解决给定依赖关系)都应添加.即自动注入匹配成功的候选Bean名集合。
	 *                              【当autowiredBeanNames不为null,会将所找到的所有候选Bean对象添加到该集合中,以供调用方使用】
	 * @param typeConverter the TypeConverter to use for populating arrays and collections
	 *    -- 用于填充数组和集合的TypeConverter
	 * @return  解析的对象;如果找不到,则为null
	 * @throws BeansException 如果依赖项解析由于任何其他原因而失败
	 */
	@Override
	@Nullable
	public Object resolveDependency(DependencyDescriptor descriptor, @Nullable String requestingBeanName,
			@Nullable Set<String> autowiredBeanNames, @Nullable TypeConverter typeConverter) throws BeansException {
    
    
		//获取工厂的参数名发现器,设置到descriptor中。使得descriptor初始化基础方法参数的参数名发现。此时,该方法实际上
		// 并没有尝试检索参数名称;它仅允许发现再应用程序调用getDependencyName时发生
		descriptor.initParameterNameDiscovery(getParameterNameDiscoverer());
		//如果descriptor的依赖类型为Optional类
		if (Optional.class == descriptor.getDependencyType()) {
    
    
			//创建Optional类型的符合descriptor要求的候选Bean对象
			return createOptionalDependency(descriptor, requestingBeanName);
		}
		//ObjectFactory则只是一个普通的对象工厂接口。在Spring中主要两处用了它:
		// 1. org.springframework.beans.factory.config.Scope.get(String, ObjectFactory).这个方法的目的
		// 就是从对于的域中获取到指定名称的对象。为什么要传入一个objectFactory呢?主要是为了方便我们扩展自定义的域,
		// 而不是仅仅使用request,session等域。
		// 2. {@link org.springframework.beans.factory.config.ConfigurableListableBeanFactory#registerResolvableDependency(Class, Object)}
		//  autowiredValue这个参数可能就是一个ObjectFactory,主要是为了让注入点能够被延迟注入
		//ObjectProvider:ObjectFactory的一种变体,专门为注入点设置,允许程序选择和扩展的非唯一处理。
		// 	具体用法参考博客:https://blog.csdn.net/qq_41907991/article/details/105123387
		//如果decriptord的依赖类型是ObjectFactory或者是ObjectProvider
		else if (ObjectFactory.class == descriptor.getDependencyType() ||
				ObjectProvider.class == descriptor.getDependencyType()) {
    
    
			//DependencyObjectProvider:依赖对象提供者,用于延迟解析依赖项
			//新建一个DependencyObjectProvider的实例
			return new DependencyObjectProvider(descriptor, requestingBeanName);
		}
		// javaxInjectProviderClass有可能导致空指针,不过一般情况下,我们引用Spirng包的时候都有引入该类以防止空旨在
		//如果依赖类型是javax.inject.Provider类。
		else if (javaxInjectProviderClass == descriptor.getDependencyType()) {
    
    
			//Jse330Provider:javax.inject.Provider实现类.与DependencyObjectProvoid作用一样,也是用于延迟解析依赖
			// 	项,但它是使用javax.inject.Provider作为依赖 对象,以减少与Springd耦合
			//新建一个专门用于构建javax.inject.Provider对象的工厂来构建创建Jse330Provider对象
			return new Jsr330Factory().createDependencyProvider(descriptor, requestingBeanName);
		}
		else {
    
    
			//尝试获取延迟加载代理对象
			Object result = getAutowireCandidateResolver().getLazyResolutionProxyIfNecessary(
					descriptor, requestingBeanName);
			//如果result为null,即表示现在需要得到候选Bean对象
			if (result == null) {
    
    
				//解析出与descriptor所包装的对象匹配的候选Bean对象
				result = doResolveDependency(descriptor, requestingBeanName, autowiredBeanNames, typeConverter);
			}
			//将与descriptor所包装的对象匹配的候选Bean对象【result】返回出去
			return result;
		}
	}

createOptionalDependency(descriptor, requestingBeanName);

创建Optional类型的符合descriptor要求的候选Bean对象:

  1. 新建一个NestedDependencyDescriptor实例,,该实例不要求一定要得到候选Bean对象,且可根据arg构建候选Bean对象且 可根据arg构建候选Bean对象(仅在Bean是SCOPE_PROTOTYPE时)。【变量 descriptorToUse】
  2. 解析出与descriptor所包装的对象匹配的后续Bean对象【变量 result】
  3. 如果result是Optional的实例,就将其强转为Optional后返回出去;否则将result包装到Optional对象中再返回出去
/**
	 * <p>创建Optional类型的符合descriptor要求的候选Bean对象
	 * </p>
	 * Create an {@link Optional} wrapper for the specified dependency.
	 * <p>为指定的依赖关系创建一个{@link Optional}包装器</p>
	 *
	 * @param descriptor   依赖项的描述符(字段/方法/构造函数)
	 * @param beanName  要依赖的Bean名,即需要Field/MethodParamter所对应的bean对象来构建的Bean对象的Bean名
	 * @param args 创建候选Bean对象所需的构造函数参数(仅在Bean是{@link #SCOPE_PROTOTYPE}时)
	 * @return Optional类型的符合descriptor要求的候选Bean对象,不会为null
	 */
	private Optional<?> createOptionalDependency(
			DependencyDescriptor descriptor, @Nullable String beanName, final Object... args) {
    
    
		//NestedDependencyDescriptor:嵌套元素的依赖项描述符标记,一般表示Optional类型依赖
		//新建一个NestedDependencyDescriptor实例,该实例不要求一定要得到候选Bean对象,且可根据arg构建候选Bean对象(当Bean是{@link #SCOPE_PROTOTYPE}时)
		DependencyDescriptor descriptorToUse = new NestedDependencyDescriptor(descriptor) {
    
    
			/**
			 * 不要求一定要得到候选Bean对象
			 */
			@Override
			public boolean isRequired() {
    
    
				return false;
			}

			/**
			 * 将指定的Bean名称解析为给定工厂的Bean实例,作为对此依赖项的匹配算法的候选结果:
			 * <p>重写该方法,使得该方法可以引用args来获取beanName的bean对象</p>
			 * @param beanName the bean name, as a candidate result for this dependency
			 *                 -- bean名,作为此依赖项的候选结果
			 * @param requiredType the expected type of the bean (as an assertion)
			 *                     -- bean的预期类型(作为断言)
			 * @param beanFactory the associated factory -- 相关工厂
			 * @return Bean名所对应的Bean对象
			 */
			@Override
			public Object resolveCandidate(String beanName, Class<?> requiredType, BeanFactory beanFactory) {
    
    
				//如果args不是空数组,就调用beanFactory.getBean(beanName, args)方法,即引用args来获取beanName的bean对象
				// 否则 调用父级默认实现;默认实现调用BeanFactory.getBean(beanName).
				return (!ObjectUtils.isEmpty(args) ? beanFactory.getBean(beanName, args) :
						super.resolveCandidate(beanName, requiredType, beanFactory));
			}
		};
		//解析出与descriptor所包装的对象匹配的后续Bean对象
		Object result = doResolveDependency(descriptorToUse, beanName, null, null);
		//如果result是Optional的实例,就将其强转为Optional后返回出去;否则将result包装到Optional对象中再返回出去
		return (result instanceof Optional ? (Optional<?>) result : Optional.ofNullable(result));
	}

super.resolveCandidate(beanName, requiredType, beanFactory)

由 DependencyDescriptor 实现.
将指定的Bean名称解析为给定工厂的Bean实例,作为对此依赖项的匹配算法的候选结果

/**
	 * Resolve the specified bean name, as a candidate result of the matching
	 * algorithm for this dependency, to a bean instance from the given factory.
	 * <p>将指定的Bean名称解析为给定工厂的Bean实例,作为对此依赖项的匹配算法的候选结果</p>
	 * <p>The default implementation calls {@link BeanFactory#getBean(String)}.
	 * Subclasses may provide additional arguments or other customizations.
	 * <p>默认实现调用BeanFactory.getBean(String).子类可以提供其他参数或其他自定义</p>
	 * @param beanName the bean name, as a candidate result for this dependency
	 *                 -- bean名,作为此依赖项的候选结果
	 * @param requiredType the expected type of the bean (as an assertion)
	 *                     -- bean的预期类型(作为断言)
	 * @param beanFactory the associated factory -- 相关工厂
	 * @return the bean instance (never {@code null}) -- bean实例(永远不为 null)
	 * @throws BeansException if the bean could not be obtained -- 如果无法获取bean
	 * @since 4.3.2
	 * @see BeanFactory#getBean(String)
	 */
	public Object resolveCandidate(String beanName, Class<?> requiredType, BeanFactory beanFactory)
			throws BeansException {
    
    

		return beanFactory.getBean(beanName);
	}

doResolveDependency

解析出与descriptor所包装的对象匹配的候选Bean对象:

  1. 设置新得当前切入点对象,得到旧的当前切入点对象【变量 previousInjectionPoint】
  2. 【尝试使用descriptor的快捷方法得到最佳候选Bean对象】:
    1. 获取针对该工厂的这种依赖关系的快捷解析最佳候选Bean对象【变量 shortcut】
    2. 如果shortcut不为null,返回该shortcut
  3. 获取descriptor的依赖类型【变量 type】
  4. 【尝试使用descriptor的默认值作为最佳候选Bean对象】:
    1. 使用此BeanFactory的自动装配候选解析器获取descriptor的默认值【变量 value】
    2. 如果value不为null:
      1. 如果value是String类型:
        1. 解析嵌套的值(如果value是表达式会解析出该表达式的值)【变量 strVal】
        2. 获取beanName的合并后RootBeanDefinition
        3. 让value引用评估bd中包含的value,如果strVal是可解析表达式,会对其进行解析.
      2. 如果没有传入typeConverter,则引用工厂的类型转换器【变量 converter】
      3. 将value转换为type的实例对象并返回出去
      4. 捕捉 不支持操作异常:
        1. 如果descriptor有包装成员属性,根据descriptor包装的成员属性来将值转换为type然后返回出去
        2. 否则,根据descriptor包装的方法参数对象来将值转换为type然后返回出去
  5. 【尝试针对desciptor所包装的对象类型是[stream,数组,Collection类型且对象类型是接口,Map]的情况, 进行解析与依赖类型匹配的候选Bean对象】:
    1. 针对desciptor所包装的对象类型是[stream,数组,Collection类型且对象类型是接口,Map]的情况,进行解析与依赖类型匹配的 候选Bean对象, 并将其封装成相应的依赖类型对象【resolveMultipleBeans(DependencyDescriptor, String, Set, TypeConverter)】
    2. 如果multpleBeans不为null,将multipleBeans返回出去
  6. 【尝试与type匹配的唯一候选bean对象】:
    1. 查找与type匹配的候选bean对象,构建成Map,key=bean名,val=Bean对象【变量 matchingBeans】
    2. 如果没有候选bean对象:
      1. 如果descriptor需要注入,抛出NoSuchBeanDefinitionException或BeanNotOfRequiredTypeException以解决不可 解决的依赖关系
      2. 返回null,表示么有找到候选Bean对象
    3. 定义用于存储唯一的候选Bean名变量【变量 autowiredBeanName】
    4. 定义用于存储唯一的候选Bean对象变量【变量 instanceCandidate】
    5. 如果候选Bean对象Map不止有一个:
      1. 让autowiredBeanName引用candidates中可以自动注入的最佳候选Bean名称
      2. 如果autowiredBeanName为null:
        1. 如果descriptor需要注入 或者 type不是数组/集合类型,让descriptor尝试选择其中一个实例,默认实现是 抛出NoUniqueBeanDefinitionException.
        2. 返回null,表示找不到最佳候选Bean对象
    6. 让instanceCandidate引用autowiredBeanName对应的候选Bean对象
    7. 如果候选bean名不为null,将autowiredBeanName添加到autowiredBeanNames中
    8. 如果instanceCandidate是Class实例,让instanceCandidate引用 descriptor对autowiredBeanName解析 为该工厂的Bean实例
    9. 定义一个result变量,用于存储最佳候选Bean对象
    10. 如果reuslt是NullBean的实例:
      1. 如果descriptor需要注入,抛出NoSuchBeanDefinitionException或BeanNotOfRequiredTypeException 以解决不可 解决的依赖关系
      2. 返回null,表示找不到最佳候选Bean对象
    11. 如果result不是type的实例,抛出Bean不是必需类型异常
    12. 返回最佳候选Bean对象【result】
  7. 返回最佳候选Bean对象【result】
/**
	 * 解析出与descriptor所包装的对象匹配的候选Bean对象
	 * @param descriptor 依赖项的描述符(字段/方法/构造函数)
	 * @param beanName 要依赖的Bean名,即需要Field/MethodParamter所对应的bean对象来构建的Bean对象的Bean名
	 * @param autowiredBeanNames 一个集合,所有自动装配的bean名(用于解决给定依赖关系)都应添加.即自动注入匹配成功的候选Bean名集合。
	 *                             【当autowiredBeanNames不为null,会将所找到的所有候选Bean对象添加到该集合中,以供调用方使用】
	 * @param typeConverter 用于填充数组和集合的TypeConverter
	 * @return 解析的对象;如果找不到,则为null
	 * @throws BeansException 如果依赖项解析由于任何其他原因而失败
	 */
	@Nullable
	public Object doResolveDependency(DependencyDescriptor descriptor, @Nullable String beanName,
			@Nullable Set<String> autowiredBeanNames, @Nullable TypeConverter typeConverter) throws BeansException {
    
    
		//设置新得当前切入点对象,得到旧的当前切入点对象
		InjectionPoint previousInjectionPoint = ConstructorResolver.setCurrentInjectionPoint(descriptor);
		try {
    
    
			//尝试使用descriptor的快捷方法得到最近候选Bean对象
			//resolveShortcut:解决针对给定工厂的这种依赖关系的快捷方式,例如,考虑一些预先解决的信息
			//尝试调用该工厂解决这种依赖关系的快捷方式来获取beanName对应的bean对象,默认返回null
			//获取针对该工厂的这种依赖关系的快捷解析最佳候选Bean对象
			Object shortcut = descriptor.resolveShortcut(this);
			//如果shortcut不为null,返回该shortcut
			if (shortcut != null) {
    
    
				return shortcut;
			}
			//获取descriptor的依赖类型
			Class<?> type = descriptor.getDependencyType();
			//尝试使用descriptor的默认值作为最近候选Bean对象
			//使用此BeanFactory的自动装配候选解析器获取descriptor的默认值
			Object value = getAutowireCandidateResolver().getSuggestedValue(descriptor);
			//如果默认值不为null
			if (value != null) {
    
    
				//如果value是String类型
				if (value instanceof String) {
    
    
					//解析嵌套的值(如果value是表达式会解析出该表达式的值)
					String strVal = resolveEmbeddedValue((String) value);
					//获取beanName的合并后RootBeanDefinition
					BeanDefinition bd = (beanName != null && containsBean(beanName) ?
							getMergedBeanDefinition(beanName) : null);
					//评估bd中包含的value,如果strVal是可解析表达式,会对其进行解析.
					value = evaluateBeanDefinitionString(strVal, bd);
				}
				//如果没有传入typeConverter,则引用工厂的类型转换器
				TypeConverter converter = (typeConverter != null ? typeConverter : getTypeConverter());
				try {
    
    
					//将value转换为type的实例对象
					return converter.convertIfNecessary(value, type, descriptor.getTypeDescriptor());
				}
				//捕捉 不支持操作异常
				catch (UnsupportedOperationException ex) {
    
    
					// A custom TypeConverter which does not support TypeDescriptor resolution...
					// 自定义TypeConverter,不支持TypeDesciptor解析
					//descriptor.getField():返回所包装的成员属性,仅在当前对象用于包装成员属性时返回非null<
					//如果descriptor有包装成员属性
					return (descriptor.getField() != null ?
							//根据包装的成员属性来将值转换为所需的类型
							converter.convertIfNecessary(value, type, descriptor.getField()) :
							//根据包装的方法参数对象来将值转换为所需的类型
							converter.convertIfNecessary(value, type, descriptor.getMethodParameter()));
				}
			}
			//尝试针对desciptor所包装的对象类型是[stream,数组,Collection类型且对象类型是接口,Map]的情况,进行解析与依赖类型匹配的候选Bean对象
			//针对desciptor所包装的对象类型是[stream,数组,Collection类型且对象类型是接口,Map]的情况,进行解析与依赖类型匹配的 候选Bean对象,
			// 并将其封装成相应的依赖类型对象
			Object multipleBeans = resolveMultipleBeans(descriptor, beanName, autowiredBeanNames, typeConverter);
			//如果multpleBeans不为null
			if (multipleBeans != null) {
    
    
				//将multipleBeans返回出去
				return multipleBeans;
			}
			//尝试与type匹配的唯一候选bean对象
			//查找与type匹配的候选bean对象,构建成Map,key=bean名,val=Bean对象
			Map<String, Object> matchingBeans = findAutowireCandidates(beanName, type, descriptor);
			//如果没有候选bean对象
			if (matchingBeans.isEmpty()) {
    
    
				//如果descriptor需要注入
				if (isRequired(descriptor)) {
    
    
					//抛出NoSuchBeanDefinitionException或BeanNotOfRequiredTypeException以解决不可 解决的依赖关系
					raiseNoMatchingBeanFound(type, descriptor.getResolvableType(), descriptor);
				}
				//返回null,表示么有找到候选Bean对象
				return null;
			}

			//定义用于存储唯一的候选Bean名变量
			String autowiredBeanName;
			//定义用于存储唯一的候选Bean对象变量
			Object instanceCandidate;

			//如果候选Bean对象Map不止有一个
			if (matchingBeans.size() > 1) {
    
    
				//确定candidates中可以自动注入的最佳候选Bean名称
				autowiredBeanName = determineAutowireCandidate(matchingBeans, descriptor);
				//如果autowiredBeanName为null
				if (autowiredBeanName == null) {
    
    
					//descriptor需要注入 或者 type不是数组/集合类型
					if (isRequired(descriptor) || !indicatesMultipleBeans(type)) {
    
    
						//让descriptor尝试选择其中一个实例,默认实现是抛出NoUniqueBeanDefinitionException.
						return descriptor.resolveNotUnique(descriptor.getResolvableType(), matchingBeans);
					}
					else {
    
    
						// In case of an optional Collection/Map, silently ignore a non-unique case:
						// possibly it was meant to be an empty collection of multiple regular beans
						// (before 4.3 in particular when we didn't even look for collection beans).
						// 如果是可选的Collection/Map,则静默忽略一个非唯一情况:
						// 可能是多个常规bean的空集合
						// (尤其是在4.3之前,设置在我们没有寻找collection bean的时候 )
						return null;
					}
				}
				//获取autowiredBeanName对应的候选Bean对象
				instanceCandidate = matchingBeans.get(autowiredBeanName);
			}
			else {
    
    
				// We have exactly one match. 我们刚好只有一个匹配
				//这个时候matchingBeans不会没有元素的,因为前面已经检查了
				//获取machingBeans唯一的元素
				Map.Entry<String, Object> entry = matchingBeans.entrySet().iterator().next();
				//让autowireBeanName引用该元素的候选bean名
				autowiredBeanName = entry.getKey();
				//让instanceCandidate引用该元素的候选bean对象
				instanceCandidate = entry.getValue();
			}
			//如果候选bean名不为null,
			if (autowiredBeanNames != null) {
    
    
				//将autowiredBeanName添加到autowiredBeanNames中,又添加一次?
				autowiredBeanNames.add(autowiredBeanName);
			}
			//如果instanceCandidate是Class实例
			if (instanceCandidate instanceof Class) {
    
    
				//让instanceCandidate引用 descriptor对autowiredBeanName解析为该工厂的Bean实例
				instanceCandidate = descriptor.resolveCandidate(autowiredBeanName, type, this);
			}
			//定义一个result变量,用于存储最佳候选Bean对象
			Object result = instanceCandidate;
			//如果reuslt是NullBean的实例
			if (result instanceof NullBean) {
    
    
				//如果descriptor需要注入
				if (isRequired(descriptor)) {
    
    
					//抛出NoSuchBeanDefinitionException或BeanNotOfRequiredTypeException以解决不可 解决的依赖关系
					raiseNoMatchingBeanFound(type, descriptor.getResolvableType(), descriptor);
				}
				//返回null,表示找不到最佳候选Bean对象
				result = null;
			}
			//如果result不是type的实例
			if (!ClassUtils.isAssignableValue(type, result)) {
    
    
				//抛出Bean不是必需类型异常
				throw new BeanNotOfRequiredTypeException(autowiredBeanName, type, instanceCandidate.getClass());
			}
			//返回最佳候选Bean对象【result】
			return result;
		}
		finally {
    
    
			//设置上一个切入点对象
			ConstructorResolver.setCurrentInjectionPoint(previousInjectionPoint);
		}
	}

ConstructorResolve

解析构造函数和工厂方法代表类

Spring 5 ConstructorResolver源码注释

getAutowireCandidateResolver()

自动装配候选解析器

Spring 5 AutowireCandidateResolver源码注释

resolveEmbeddedValue((String) value);

解析嵌套的值(如果value是表达式会解析出该表达式的值)

  1. 如果value为null,返回null
  2. 定义返回结果,默认引用value【变量 result】
  3. 遍历该工厂的所有字符串解析器【embeddedValueResolvers】:
    1. 解析result,将解析后的值重新赋值给result
    2. 如果result为null,结束该循环并返回null
  4. 将解析后的结果返回出去
/**
	 * 解析嵌套的值(如果value是表达式会解析出该表达式的值)
	 * @param value the value to resolve -- 要解析的值,
	 * @return 解析后的值(可能是原始值)
	 */
	@Override
	@Nullable
	public String resolveEmbeddedValue(@Nullable String value) {
    
    
		//如果value为null,返回null
		if (value == null) {
    
    
			return null;
		}
		//定义返回结果,默认引用value
		String result = value;
		//SpringBoot默认存放一个PropertySourcesPlaceholderConfigurer,该类注意用于针对当前
		// 	Spring Environment 及其PropertySource解析bean定义属性值和@Value注释中的${...}占位符
		//遍历该工厂的所有字符串解析器
		for (StringValueResolver resolver : this.embeddedValueResolvers) {
    
    
			//解析result,将解析后的值重新赋值给result
			result = resolver.resolveStringValue(result);
			//如果result为null,结束该循环,并返回null
			if (result == null) {
    
    
				return null;
			}
		}
		//将解析后的结果返回出去
		return result;
	}

getMergedBeanDefinition(beanName)

Spring 5 AbstractBeanFactory – getMergedLocalBeanDefinition 源码解析

evaluateBeanDefinitionString(strVal, bd)

评估benaDefinition中包含的value,如果value是可解析表达式,会对其进行解析,否则直接返回value:

  1. 如果该工厂没有设置bean定义值中表达式的解析策略【beanExpressionResolver】,就职返回value【默认情况下, 工厂是配置StandardBeanExpressionResolver作为beanExpressionResolver】
  2. 如果beanDefinition不为null,获取beanDefinition的当前目标作用域名,然后将其作用域名装换为Scope对象,赋值给 【scope】
  3. 使用beanExpressionResolver解析value,并返回其解析结果。在解析过程中,会判断value是否为表达式,如果不是 就会直接返回value作为其解析结果
/**
	 * Resolution strategy for expressions in bean definition values.
	 * <p>bean定义值中表达式的解析策略</p>
	 * <p>SpingBoot默认使用的是StandardBeanExpressionResolver</p>
	 * */
	@Nullable
	private BeanExpressionResolver beanExpressionResolver;
	
/**
	 * <p>评估benaDefinition中包含的value,如果value是可解析表达式,会对其进行解析,否则直接返回value </p>
	 * Evaluate the given String as contained in a bean definition,
	 * potentially resolving it as an expression.
	 * <p>评估bean定义中包含的给定String,可能将其解析为表达式</p>
	 * @param value the value to check -- 要检查的值
	 * @param beanDefinition the bean definition that the value comes from -- 值所来自的bean定义
	 * @return the resolved value -- 解析后的值
	 * @see #setBeanExpressionResolver
	 */
	@Nullable
	protected Object evaluateBeanDefinitionString(@Nullable String value, @Nullable BeanDefinition beanDefinition) {
    
    
		//如果该工厂没有设置bean定义值中表达式的解析策略
		if (this.beanExpressionResolver == null) {
    
    
			//直接返回要检查的值
			return value;
		}
		//值所来自的bean定义的当前目标作用域
		Scope scope = null;
		//如果有传入值所来自的bean定义
		if (beanDefinition != null) {
    
    
			//获取值所来自的bean定义的当前目标作用域名
			String scopeName = beanDefinition.getScope();
			//如果成功获得值所来自的bean定义的当前目标作用域名
			if (scopeName != null) {
    
    
				//获取scopeName对应的Scope对象
				scope = getRegisteredScope(scopeName);
			}
		}
		//评估value作为表达式(如果适用);否则按原样返回值
		return this.beanExpressionResolver.evaluate(value, new BeanExpressionContext(this, scope));
	}

getRegisteredScope(scopeName);

获取给定作用域名称对应的作用域对象(如果有):

  1. 如果scopeName为null,抛出异常
  2. 从映射的linkedHashMap【scopes】中获取scopeName对应的作用域对象并返回
/**
	 * 获取给定作用域名称对应的作用域对象(如果有)
	 * @param scopeName the name of the scope -- 作用域名
	 * @return scopeName对应的作用域对象
	 */
	@Override
	@Nullable
	public Scope getRegisteredScope(String scopeName) {
    
    
		//如果传入的作用域名为null,抛出异常
		Assert.notNull(scopeName, "Scope identifier must not be null");
		//从映射的linkedHashMap中获取传入的作用域名对应的作用域对象并返回
		return this.scopes.get(scopeName);
	}

getTypeConverter()

获取此BeanFactory使用的类型转换器。这可能是每次调用都有新实例,因TypeConverters通常 不是线程安全的.

  1. 获取自定义的TypeConverter【getCustomTypeConverter()】【变量 customConverter】
  2. 如果customConverter,返回该customConverter
  3. 新建一个SimpleTypeConverter对象【变量 typeConverter】
  4. 让typeConverter引用该工厂的类型转换的服务接口【getConversionService()】
  5. 将工厂中所有PropertyEditor注册到typeConverter中
  6. 返回SimpleTypeConverter作为该工厂的默认类型转换器。
/**
	 * 获取此BeanFactory使用的类型转换器。这可能是每次调用都有新实例,因TypeConverters通常 不是线程安全的.
	 * @return 此BeanFactory使用的类型转换器:默认情况下优先返回自定义的类型转换器【{@link #getCustomTypeConverter()}】;
	 * 	获取不到时,返回一个新的SimpleTypeConverter对象
	 */
	@Override
	public TypeConverter getTypeConverter() {
    
    
		//获取自定义的TypeConverter
		TypeConverter customConverter = getCustomTypeConverter();
		//如果有自定义的TypeConverter
		if (customConverter != null) {
    
    
			//返回该自定义的TypeConverter
			return customConverter;
		}
		else {
    
    
			// Build default TypeConverter, registering custom editors.
			// 构建默认的TypeConverter,注册自定义编辑器
			//SimpleTypeConverter:不在特定目标对象上运行的TypeConverter接口的简单实现。
			// 	这是使用完整的BeanWrapperImpl实例来实现 任意类型转换需求的替代方法,同时
			// 	使用相同的转换算法(包括委托给PropertyEditor和ConversionService)。
			//每次调用该方法都会新建一个类型转换器,因为SimpleTypeConverter不是线程安全的
			//新建一个SimpleTypeConverter对象
			SimpleTypeConverter typeConverter = new SimpleTypeConverter();
			//让typeConverter引用该工厂的类型转换的服务接口
			typeConverter.setConversionService(getConversionService());
			//将工厂中所有PropertyEditor注册到typeConverter中
			registerCustomEditors(typeConverter);
			//返回SimpleTypeConverter作为该工厂的默认类型转换器。
			return typeConverter;
		}
	}

Spring 5 SimpleTypeConverter 源码注释

篇幅过长,请看下一篇

Spring 5 AutowireCapableBeanFactory – resolveDependency源码分析(二)

猜你喜欢

转载自blog.csdn.net/qq_30321211/article/details/108358105
今日推荐