首页 > 编程语言 >Spring源码-autowireByName

Spring源码-autowireByName

时间:2022-10-01 12:00:22浏览次数:49  
标签:return autowireByName Spring bean 源码 pd null type class

autowireByName

protected void autowireByName(
		String beanName, AbstractBeanDefinition mbd, BeanWrapper bw, MutablePropertyValues pvs) {

	String[] propertyNames = unsatisfiedNonSimpleProperties(mbd, bw);
	for (String propertyName : propertyNames) {
		if (containsBean(propertyName)) {
			Object bean = getBean(propertyName);
			pvs.add(propertyName, bean);
			registerDependentBean(propertyName, beanName);
			if (logger.isTraceEnabled()) {
				logger.trace("Added autowiring by name from bean name '" + beanName +
						"' via property '" + propertyName + "' to bean named '" + propertyName + "'");
			}
		}
		else {
			if (logger.isTraceEnabled()) {
				logger.trace("Not autowiring property '" + propertyName + "' of bean '" + beanName +
						"' by name: no matching bean found");
			}
		}
	}
}
  1. 获取bw中有setter方法 且 非简单类型属性 且 mbd的PropertyValues中没有该pd的属性名的 PropertyDescriptor 属性名数组

  2. 遍历属性名数组,如果该bean工厂有propertyName的beanDefinition,则获取该bean并设置到pvs中,同时注册bean依赖

unsatisfiedNonSimpleProperties

protected String[] unsatisfiedNonSimpleProperties(AbstractBeanDefinition mbd, BeanWrapper bw) {
	Set<String> result = new TreeSet<>();
	PropertyValues pvs = mbd.getPropertyValues();
	PropertyDescriptor[] pds = bw.getPropertyDescriptors();
	for (PropertyDescriptor pd : pds) {
		if (pd.getWriteMethod() != null && !isExcludedFromDependencyCheck(pd) && !pvs.contains(pd.getName()) &&
				!BeanUtils.isSimpleProperty(pd.getPropertyType())) {
			result.add(pd.getName());
		}
	}
	return StringUtils.toStringArray(result);
}

unsatisfiedNonSimpleProperties获取bw中有setter方法且非简单类型属性且mbd的PropertyValues中没有该pd的属性名的PropertyDescriptor属性名数组。

getWriteMethod

    public synchronized Method getWriteMethod() {
    Method writeMethod = this.writeMethodRef.get();
    if (writeMethod == null) {
        Class<?> cls = getClass0();
        if (cls == null || (writeMethodName == null && !this.writeMethodRef.isSet())) {
            // The write method was explicitly set to null.
            return null;
        }

        // We need the type to fetch the correct method.
        Class<?> type = getPropertyType0();
        if (type == null) {
            try {
                // Can't use getPropertyType since it will lead to recursive loop.
                type = findPropertyType(getReadMethod(), null);
                setPropertyType(type);
            } catch (IntrospectionException ex) {
                // Without the correct property type we can't be guaranteed
                // to find the correct method.
                return null;
            }
        }

        if (writeMethodName == null) {
            writeMethodName = Introspector.SET_PREFIX + getBaseName(); //     static final String SET_PREFIX = "set";
        }

        Class<?>[] args = (type == null) ? null : new Class<?>[] { type };
        writeMethod = Introspector.findMethod(cls, writeMethodName, 1, args);
        if (writeMethod != null) {
            if (!writeMethod.getReturnType().equals(void.class)) {
                writeMethod = null;
            }
        }
        try {
            setWriteMethod(writeMethod);
        } catch (IntrospectionException ex) {
            // fall through
        }
    }
    return writeMethod;
}

getWriteMethod获取set方法。

isExcludedFromDependencyCheck:

protected boolean isExcludedFromDependencyCheck(PropertyDescriptor pd) {
	return (AutowireUtils.isExcludedFromDependencyCheck(pd) ||
			this.ignoredDependencyTypes.contains(pd.getPropertyType()) ||     // ignoredDependencyTypes保存了忽略依赖检查的类型
			AutowireUtils.isSetterDefinedInInterface(pd, this.ignoredDependencyInterfaces)); // ignoredDependencyInterfaces保存了忽略依赖检查的接口
}

isExcludedFromDependencyCheck判断pd的属性是CGLIB定义的属性 或者 该工厂的忽略依赖类型列表中包含该pd的属性类型 或者 pd的属性是ignoredDependencyInterfaces里面的接口定义的方法。

isExcludedFromDependencyCheck:

public static boolean isExcludedFromDependencyCheck(PropertyDescriptor pd) {
	Method wm = pd.getWriteMethod();
	if (wm == null) {
		return false;
	}
	if (!wm.getDeclaringClass().getName().contains("$$")) {
		// Not a CGLIB method so it's OK.
		return false;
	}
	// It was declared by CGLIB, but we might still want to autowire it
	// if it was actually declared by the superclass.
	Class<?> superclass = wm.getDeclaringClass().getSuperclass();
	return !ClassUtils.hasMethod(superclass, wm);
}

isExcludedFromDependencyCheck判断是否是cglib代理对象,若不是返回false,若是判断cglib代理的对象是否存在set方法。

isSetterDefinedInInterface:

public static boolean isSetterDefinedInInterface(PropertyDescriptor pd, Set<Class<?>> interfaces) {
	Method setter = pd.getWriteMethod();
	if (setter != null) {
		Class<?> targetClass = setter.getDeclaringClass();
		for (Class<?> ifc : interfaces) {
			if (ifc.isAssignableFrom(targetClass) && ClassUtils.hasMethod(ifc, setter)) {
				return true;
			}
		}
	}
	return false;
}

isSetterDefinedInInterface方法判断set方法是否在接口中定义且有此方法。

isSimpleProperty:

public static boolean isSimpleProperty(Class<?> type) {
	Assert.notNull(type, "'type' must not be null");
	return isSimpleValueType(type) || (type.isArray() && isSimpleValueType(type.getComponentType()));
}

isSimpleProperty判断是否是简单值或者是简单值的数组。

isSimpleValueType

public static boolean isSimpleValueType(Class<?> type) {
	return (Void.class != type && void.class != type &&
			(ClassUtils.isPrimitiveOrWrapper(type) ||  // isPrimitiveOrWrapper判断是否是基本类型及其包装类
			Enum.class.isAssignableFrom(type) ||
			CharSequence.class.isAssignableFrom(type) ||
			Number.class.isAssignableFrom(type) ||
			Date.class.isAssignableFrom(type) ||
			Temporal.class.isAssignableFrom(type) ||
			URI.class == type ||
			URL.class == type ||
			Locale.class == type ||
			Class.class == type));
}

containsBean

	@Override
public boolean containsBean(String name) {
	String beanName = transformedBeanName(name);
	if (containsSingleton(beanName) || containsBeanDefinition(beanName)) {
		return (!BeanFactoryUtils.isFactoryDereference(name) || isFactoryBean(name));
	}
	// Not found -> check parent.
	BeanFactory parentBeanFactory = getParentBeanFactory();
	return (parentBeanFactory != null && parentBeanFactory.containsBean(originalBeanName(name)));
}

containsBean判断bean工厂有propertyName的beanDefinition或bean是否在singletonObjects中。

标签:return,autowireByName,Spring,bean,源码,pd,null,type,class
From: https://www.cnblogs.com/shigongp/p/16746957.html

相关文章

  • springboot+vue前后端分离项目搭建
    今天开始学习springboot+vue的前后端分离项目,跟着bili的视频开始做起。第一步安装node.js node.js自带npm插件,npm是node的一个包管理工具,安装好了node.js,就安装了npm......
  • Spring源码-populateBean填充bean属性
    一、bean属性注入模式AutowireCapableBeanFactory/***没有自动装配*/intAUTOWIRE_NO=0;/***按照名字自动装配*/intAUTOWIRE_BY_NAME=1;/***按......
  • 启动 Hello Spring Security Boot 应用
    本文章对如何快速启动一个启动HelloSpringSecurityBoot应用进行说明。下载代码在这个项目中,使用的是 spring.io 的项目生成程序,生成的地址为:https://start.sprin......
  • Spring
    Spring概念Spring框架概述Spring是轻量级的开源的EE框架轻量:依赖需求少,体积小,独立使用开源:提供源码框架Spring可以解决企业开发的复杂性两个核心:IOC和AOP......
  • springboot自动配置原理以及手动实现配置类
    springboot自动配置原理以及手动实现配置类1、原理spring有一个思想是“约定大于配置”。配置类自动配置可以帮助开发人员更加专注于业务逻辑开发,springboot在启动的时候......
  • springboot自动配置原理以及手动实现配置类
    springboot自动配置原理以及手动实现配置类1、原理spring有一个思想是“约定大于配置”。配置类自动配置可以帮助开发人员更加专注于业务逻辑开发,springboot在启动的时......
  • Spring源码-AbstractAutowireCapableBeanFactory的instantiateBean无参构造实例化bean
    instantiateBeanprotectedBeanWrapperinstantiateBean(StringbeanName,RootBeanDefinitionmbd){ try{ ObjectbeanInstance; if(System.getSecurityManager(......
  • Spring源码-AbstractAutowireCapableBeanFactory的autowireConstructor
    autowireConstructor:protectedBeanWrapperautowireConstructor( StringbeanName,RootBeanDefinitionmbd,@NullableConstructor<?>[]ctors,@NullableObject[......
  • 源码学习之MyBatis的底层查询原理
    导读本文通过MyBatis一个低版本的bug(3.4.5之前的版本)入手,分析MyBatis的一次完整的查询流程,从配置文件的解析到一个查询的完整执行过程详细解读MyBatis的一次查询流程,通过本......
  • Spring Security 在 Servlet 的作用区域
    SpringSecurity使用标准的Servlet 过滤器(Filter) 并与Servlet容器集成。这个意味着SpringSecurity可以在任何运行运行在Servlet容器(ServletContainer)中的应用......