spring scope prototype_java的properties类

(1) 2024-07-20 12:23

Hi,大家好,我是编程小6,很荣幸遇见你,我把这些年在开发过程中遇到的问题或想法写出来,今天说一说
spring scope prototype_java的properties类,希望能够帮助你!!!。

一、jdk中类PropertyDescriptor获取

 jdk中Introspector类为工具提供了一种标准的方法来了解目标Java Bean支持的属性、事件和方法。 java.beans.Introspector#getTargetPropertyInfo private PropertyDescriptor[] getTargetPropertyInfo() { // Apply some reflection to the current class. // First get an array of all the public methods at this level Method methodList[] = getPublicDeclaredMethods(beanClass); // Now analyze each method. //遍历所有方法看是否是符合PropertyDescriptor for (int i = 0; i < methodList.length; i++) { Method method = methodList[i]; if (method == null) { continue; } // skip static methods. int mods = method.getModifiers(); if (Modifier.isStatic(mods)) { continue; } String name = method.getName(); Class<?>[] argTypes = method.getParameterTypes(); Class<?> resultType = method.getReturnType(); int argCount = argTypes.length; PropertyDescriptor pd = null; if (name.length() <= 3 && !name.startsWith(IS_PREFIX)) { // Optimization. Don't bother with invalid propertyNames. continue; } try { if (argCount == 0) { /** * 方法没有参数:方法有readMethod没有writeMehtod * 1、普通get开头方法 * 2、返回值boolean 以is开头的 */ if (name.startsWith(GET_PREFIX)) { // Simple getter pd = new PropertyDescriptor(this.beanClass, name.substring(3), method, null); } else if (resultType == boolean.class && name.startsWith(IS_PREFIX)) { // Boolean getter pd = new PropertyDescriptor(this.beanClass, name.substring(2), method, null); } } else if (argCount == 1) { /** * 有一个参数 * 1、有一个参数且int类型,方法get开头的,没有readMethod writeMehtod等属性 * 2、没有返回值、set方法开头的,具有writeMethod */ if (int.class.equals(argTypes[0]) && name.startsWith(GET_PREFIX)) { pd = new IndexedPropertyDescriptor(this.beanClass, name.substring(3), null, null, method, null); } else if (void.class.equals(resultType) && name.startsWith(SET_PREFIX)) { // Simple setter pd = new PropertyDescriptor(this.beanClass, name.substring(3), null, method); if (throwsException(method, PropertyVetoException.class)) { pd.setConstrained(true); } } } else if (argCount == 2) { /** * 两个参数 * 1、返回值void ,第一个参数int类型,set开头的会生成PropertyDescriptor(注意此时没有writeMethod) */ if (void.class.equals(resultType) && int.class.equals(argTypes[0]) && name.startsWith(SET_PREFIX)) { pd = new IndexedPropertyDescriptor(this.beanClass, name.substring(3), null, null, null, method); if (throwsException(method, PropertyVetoException.class)) { pd.setConstrained(true); } } } } catch (IntrospectionException ex) { pd = null; } if (pd != null) { if (propertyChangeSource) { pd.setBound(true); } addPropertyDescriptor(pd); } } processPropertyDescriptors(); } 

总结满足以下条件才会生成PropertyDescriptor(注意读写方法是否为空,spring中by_type类型注入会筛选出具有写方法不为空的PropertyDescriptor):
1、参数个数必须2个以内、方法不是static
2、 方法没有参数:方法有readMethod没有writeMehtod
1、普通get开头方法
2、返回值boolean 以is开头的
3、 有一个参数
1、有一个参数且int类型,方法get开头的,没有readMethod writeMehtod等属性
2、没有返回值、set方法开头的,具有writeMethod
4、两个参数
1、返回值void ,第一个参数int类型,set开头的会生成PropertyDescriptor(注意此时没有writeMethod)

综上所述:具有写方法的必须返回值void 且set开头一个参数的的才有写方法(spring中by_type类型注入会筛选出具有写方法不为空的)

demo 具有写方法的PropertyDescriptor演示:

//@Component public class UserService { 
    private OrderService orderService; //返回值不为void public OrderService setOrderService(OrderService orderService){ 
    //this.orderService=orderService; return orderService; } //返回值不为void public OrderService setOrderService(int test,OrderService orderService){ 
    this.orderService=orderService; return orderService; } //返回值void 一个参数满足要求 public void setService12123(OrderService orderService1){ 
    System.out.println("1231"+orderService); } //返回值void 参数个数大于2不满足 public void setOrderService(int test,OrderService orderService,StockService stockService){ 
    this.orderService=orderService; } } public class Test { 
    public static void main(String[] args) throws IntrospectionException { 
    BeanInfo beanInfo= Introspector.getBeanInfo(UserService.class); PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors(); for(PropertyDescriptor propertyDescriptor:propertyDescriptors){ 
    System.out.println(propertyDescriptor.getWriteMethod()); } } } 
此时满足条件方法有getClass(继承父类的Object) 、setService12123会生成PropertyDescriptor且具有写方法 

spring scope prototype_java的properties类_https://bianchenghao6.com/blog__第1张

存在问题:
方法有返回值、且静态的方法是不具备生成PropertyDescriptor属性描述器,spring中org.springframework.beans.ExtendedBeanInfo#isCandidateWriteMethod拓展有返回值、或者static也会生成
PropertyDescriptor**
满足以下条件:
return methodName.length() > 3 && methodName.startsWith(“set”) && Modifier.isPublic(method.getModifiers()) && (!Void.TYPE.isAssignableFrom(method.getReturnType()) || Modifier.isStatic(method.getModifiers())) && (nParams == 1 || nParams == 2 && Integer.TYPE == method.getParameterTypes()[0]);

二、spring针对jdk进行拓展,ExtendedBeanInfo对jdk不满足的方法进行扩展(有返回值、static)生成PropertyDescriptor

 **满足以下条件才会生成PropertyDescriptor 1、set开头方法 2、public方法 3、返回值不是void或者是静态 4、参数一个或者2个(2个实话第一个参数必须为int类型)** 
 //1、set开头方法 2public方法 3、返回值不是void或者是静态 4、参数一个或者2个(2个实话第一个参数必须为int类型) public static boolean isCandidateWriteMethod(Method method) { 
    String methodName = method.getName(); int nParams = method.getParameterCount(); return methodName.length() > 3 && methodName.startsWith("set") && Modifier.isPublic(method.getModifiers()) && (!Void.TYPE.isAssignableFrom(method.getReturnType()) || Modifier.isStatic(method.getModifiers())) && (nParams == 1 || nParams == 2 && Integer.TYPE == method.getParameterTypes()[0]); } 

三、总结

spring依赖注入(@Bean(autowire=Autowire.BY_TYPE)实话会找到该类所有PropertyDescriptor满足条件的方法
1、从jdk中Introspector中获取
2、扩展ExtendedBeanInfo获取

今天的分享到此就结束了,感谢您的阅读,如果确实帮到您,您可以动动手指转发给其他人。

上一篇

已是最后文章

下一篇

已是最新文章

发表回复