澄澈的眼|这Spring注入对象处理过程也太细了,收藏了,什么神仙( 三 )
不同的后置处理器的postProcessProperties()方法对应的是不同的处理逻辑 。
4、@Autowired注解属性4.1处理过程
首先 , 通过findAutowiringMetadata()方法获取被注入的元数据 。 以上述:「情形一」 , 为例:
对于@Autowired注解的其他使用方式 , 最终都会调用element.inject(target,beanName,pvs);
接下来将分析resolveDependency()方法 , 通过该方法可以发现 , 最终调用的是doResolveDependency() 。 看到了doXXXX()的方法 , 就又到了Spring惯用的套路了 , 这里这方法就是真正做事的方式 。 下面就来看看在doResolveDependency()中做了什么事情...
publicObjectdoResolveDependency(DependencyDescriptordescriptor,@NullableStringbeanName,@NullableSetautowiredBeanNames,@NullableTypeConvertertypeConverter)throwsBeansException{InjectionPointpreviousInjectionPoint=ConstructorResolver.setCurrentInjectionPoint(descriptor);try{Objectshortcut=descriptor.resolveShortcut(this);if(shortcut!=null){returnshortcut;}/***根据类型获取 , @Autowired默认根据type*/Class>type=descriptor.getDependencyType();/***支持@value注解*/Objectvalue=https://pcff.toutiao.jxnews.com.cn/p/20200906/getAutowireCandidateResolver().getSuggestedValue(descriptor);if(value!=null){if(valueinstanceofString){StringstrVal=resolveEmbeddedValue((String)value);BeanDefinitionbd=(beanName!=null&&containsBean(beanName)?getMergedBeanDefinition(beanName):null);value=evaluateBeanDefinitionString(strVal,bd);}TypeConverterconverter=(typeConverter!=null?typeConverter:getTypeConverter());try{/**通过转换器将Bean的值转换为对应的type类型*/returnconverter.convertIfNecessary(value,type,descriptor.getTypeDescriptor());}catch(UnsupportedOperationExceptionex){//AcustomTypeConverterwhichdoesnotsupportTypeDescriptorresolution...return(descriptor.getField()!=null?converter.convertIfNecessary(value,type,descriptor.getField()):converter.convertIfNecessary(value,type,descriptor.getMethodParameter()));}}ObjectmultipleBeans=resolveMultipleBeans(descriptor,beanName,autowiredBeanNames,typeConverter);if(multipleBeans!=null){returnmultipleBeans;}/***根据属性类型找到beanFactory中所有类型匹配的Bean*返回值的结构为:*key:匹配的BeanName;*value:beanName对应的实例化后的bean通过getBean(beanName)返回*/MapmatchingBeans=findAutowireCandidates(beanName,type,descriptor);if(matchingBeans.isEmpty()){/***如果autowire的require属性为true*找到的匹配项为空则抛出异常*/if(isRequired(descriptor)){raiseNoMatchingBeanFound(type,descriptor.getResolvableType(),descriptor);}returnnull;}StringautowiredBeanName;ObjectinstanceCandidate;//根据类型匹配到的数量大于1个if(matchingBeans.size()>1){//确定自动注入的beanNameautowiredBeanName=determineAutowireCandidate(matchingBeans,descriptor);if(autowiredBeanName==null){if(isRequired(descriptor)||!indicatesMultipleBeans(type)){returndescriptor.resolveNotUnique(descriptor.getResolvableType(),matchingBeans);}else{returnnull;}}instanceCandidate=matchingBeans.get(autowiredBeanName);}else{//Wehaveexactlyonematch.Map.Entryentry=matchingBeans.entrySet().iterator().next();autowiredBeanName=entry.getKey();instanceCandidate=entry.getValue();}if(autowiredBeanNames!=null){autowiredBeanNames.add(autowiredBeanName);}if(instanceCandidateinstanceofClass){//实例化对象instanceCandidate=descriptor.resolveCandidate(autowiredBeanName,type,this);}Objectresult=instanceCandidate;if(resultinstanceofNullBean){if(isRequired(descriptor)){raiseNoMatchingBeanFound(type,descriptor.getResolvableType(),descriptor);}result=null;}if(!ClassUtils.isAssignableValue(type,result)){thrownewBeanNotOfRequiredTypeException(autowiredBeanName,type,instanceCandidate.getClass());}returnresult;}finally{ConstructorResolver.setCurrentInjectionPoint(previousInjectionPoint);}}分析上述代码 , 可以发现其中主要做了如下的几件事:
推荐阅读
- 科技资讯眺望|Boot 12 国际化,Spring
- 澄澈的眼|余承东成背后主要“推手”,错在华为?华为手机涨价的原因曝光
- spring|某Java程序员在外包公司每天读写删改几年后,发现跳不出来了
- 澄澈的眼|的那些事(二),关于国密HTTPS
- mybatis|java新手教程: springboot集成mybatis-plus上篇的学习
- 芯片|成功突破离子注入关键技术,率先开发铌酸锂薄膜芯,厉害了我的国
- 澄澈的眼|自学一个月跳槽计算机视觉,其实入门很简单,网友:Java岗
- 管掌柜|管掌柜平台为长沙管道交易行业注入新动能
- spring|SpringBoot使用起来太简单了,真香!
- 澄澈的眼|余承东正式宣布,联想也没想到发展这么快,4年做到中国电脑第二