Mybatis-ObjectFactory,ObjectWrapperFactory源码分析

Mybatis3.5.1源码分析

  1. Mybatis-SqlSessionFactoryBuilder,XMLConfigBuilder,XPathParser源码解析
  2. Mybatis-Configuration源码解析
  3. Mybatis-事务对象源码解析
  4. Mybatis-数据源源码解析
  5. Mybatis缓存策略源码解析
  6. Mybatis-DatabaseIdProvider源码解析
  7. Mybatis-TypeHandler源码解析
  8. Mybatis-Reflector源码解析
  9. Mybatis-ObjectFactory,ObjectWrapperFactory源码分析
  10. Mybatis-Mapper各类标签封装类源码解析
  11. Mybatis-XMLMapperBuilder,XMLStatmentBuilder源码分析
  12. Mybatis-MapperAnnotationBuilder源码分析
  13. [Mybatis-MetaObject,MetaClass源码解析]https://www.jianshu.com/p/f51fa552f30a)
  14. Mybatis-LanguageDriver源码解析
  15. Mybatis-SqlSource源码解析
  16. Mybatis-SqlNode源码解析
  17. Mybatis-KeyGenerator源码解析
  18. Mybatis-Executor源码解析
  19. Mybatis-ParameterHandler源码解析
  20. Mybatis-StatementHandler源码解析
  21. Mybatis-DefaultResultSetHandler(一)源码解析
  22. Mybatis-DefaultResultSetHandler(二)源码解析
  23. Mybatis-ResultHandler,Cursor,RowBounds 源码分析
  24. Mybatis-MapperProxy源码解析
  25. Mybatis-SqlSession源码解析
  26. Mybatis-Interceptor源码解析

ObjectFactory

/**
 *    Copyright 2009-2019 the original author or authors.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */
package org.apache.ibatis.reflection.factory;

import java.util.List;
import java.util.Properties;

/**
 * MyBatis uses an ObjectFactory to create all needed new Objects.
 * 在 MyBatis 中,当其 sql 映射配置文件中的 sql 语句所得到的查询结果,
 * 被动态映射到 resultType 或其他处理结果集的参数配置对应的 Java 类型,其中就有 JavaBean 等封装类
 * 而 objectFactory 对象工厂就是用来创建实体对象的类。
 * @author Clinton Begin
 */
public interface ObjectFactory {

  /**
   * 处理参数
   * Sets configuration properties.
   * @param properties configuration properties
   */
  void setProperties(Properties properties);

  /**
   * 处理默认构造方法
   * Creates a new object with default constructor.
   * @param type Object type
   * @return
   */
   T create(Class type);

  /**
   * 处理有参构造方法
   * Creates a new object with the specified constructor and params.
   * @param type Object type
   * @param constructorArgTypes Constructor argument types
   * @param constructorArgs Constructor argument values
   * @return
   */
   T create(Class type, List> constructorArgTypes, List constructorArgs);

  /**
   * Returns true if this object can have a set of other objects.
   * It's main purpose is to support non-java.util.Collection objects like Scala collections.
   * 判断集合类型参数
   * @param type Object type
   * @return whether it is a collection or not
   * @since 3.1.0
   */
   boolean isCollection(Class type);

}


DefaultObjectFactory

/**
 *    Copyright 2009-2019 the original author or authors.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */
package org.apache.ibatis.reflection.factory;

import java.io.Serializable;
import java.lang.reflect.Constructor;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.Properties;
import java.util.Set;
import java.util.SortedSet;
import java.util.TreeSet;
import java.util.stream.Collectors;

import org.apache.ibatis.reflection.ReflectionException;
import org.apache.ibatis.reflection.Reflector;

/**
 * 默认的ObjectFactory
 * 

* 简单的通过反射方式调用目标类的构造方法构建出对应实例,如果是创建常用集合或者Map是, * 可以直接传集合进去{@link DefaultObjectFactory#create(Class)}或者{@link DefaultObjectFactory#create(Class, List, List)}. * 详情可查看{@link DefaultObjectFactory#resolveInterface(Class)} *

* @author Clinton Begin */ public class DefaultObjectFactory implements ObjectFactory, Serializable { private static final long serialVersionUID = -8855120656740914948L; @Override public T create(Class type) { return create(type, null, null); } @SuppressWarnings("unchecked") @Override public T create(Class type, List> constructorArgTypes, List constructorArgs) { Class classToCreate = resolveInterface(type); // we know types are assignable return (T) instantiateClass(classToCreate, constructorArgTypes, constructorArgs); } @Override public void setProperties(Properties properties) { // no props for default } /** * 实例化类对象 * @param type 需要实例化的类 * @param constructorArgTypes 构造函数参数类型集合 * @param constructorArgs 构造函数参数对象集合 * @param 需要实例化的类型 * @return */ private T instantiateClass(Class type, List> constructorArgTypes, List constructorArgs) { try { Constructor constructor; //通过无参构造方法实例化对象 if (constructorArgTypes == null || constructorArgs == null) { constructor = type.getDeclaredConstructor(); try { return constructor.newInstance(); } catch (IllegalAccessException e) { if (Reflector.canControlMemberAccessible()) { constructor.setAccessible(true); return constructor.newInstance(); } else { throw e; } } } //通过指定参数构造方法实例化对象 constructor = type.getDeclaredConstructor(constructorArgTypes.toArray(new Class[constructorArgTypes.size()])); try { return constructor.newInstance(constructorArgs.toArray(new Object[constructorArgs.size()])); } catch (IllegalAccessException e) { if (Reflector.canControlMemberAccessible()) { constructor.setAccessible(true); return constructor.newInstance(constructorArgs.toArray(new Object[constructorArgs.size()])); } else { throw e; } } } catch (Exception e) { //将map转换成以','分割的字符串 String argTypes = Optional.ofNullable(constructorArgTypes).orElseGet(Collections::emptyList) .stream().map(Class::getSimpleName).collect(Collectors.joining(",")); String argValues = Optional.ofNullable(constructorArgs).orElseGet(Collections::emptyList) .stream().map(String::valueOf).collect(Collectors.joining(",")); throw new ReflectionException("Error instantiating " + type + " with invalid types (" + argTypes + ") or values (" + argValues + "). Cause: " + e, e); } } /** * 判断type是否只是集合接口,该方法会改成对应的实体类 *
    *
  • type==List.class||type=Collection.class||type==Iterable.class,返回ArrayList.class
  • *
  • type==Map.class,返回HashMap.class
  • *
  • type==SortedSet.class,返回TreeSet.class
  • *
  • type==Set.class,返回HashSet.class
  • *
  • default:返回(参数type)
  • *
*/ protected Class resolveInterface(Class type) { Class classToCreate; if (type == List.class || type == Collection.class || type == Iterable.class) { classToCreate = ArrayList.class; } else if (type == Map.class) { classToCreate = HashMap.class; } else if (type == SortedSet.class) { // issue #510 Collections Support classToCreate = TreeSet.class; } else if (type == Set.class) { classToCreate = HashSet.class; } else { classToCreate = type; } return classToCreate; } /** * 判断 (参数type)是否是 {@link Collection} 的 子类 * @param type Object type * @param * @return */ @Override public boolean isCollection(Class type) { return Collection.class.isAssignableFrom(type); } }

ObjectWrapperFactory

/**
 *    Copyright 2009-2016 the original author or authors.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */
package org.apache.ibatis.reflection.wrapper;

import org.apache.ibatis.reflection.MetaObject;

/**
* 对象包装工厂
 * @author Clinton Begin
 *
 */
public interface ObjectWrapperFactory {

  /**
   * 是否有为(参数object)进行包装
   */
  boolean hasWrapperFor(Object object);

  /**
   * 返回类对象包装类对象
   */
  ObjectWrapper getWrapperFor(MetaObject metaObject, Object object);

}

DefaultObjectWrapperFactory

/**
 *    Copyright 2009-2015 the original author or authors.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */
package org.apache.ibatis.reflection.wrapper;

import org.apache.ibatis.reflection.MetaObject;
import org.apache.ibatis.reflection.ReflectionException;

/**
 * 默认对象包装工厂
 * 

* 默认不会对对象进行包装 *

* @author Clinton Begin */ public class DefaultObjectWrapperFactory implements ObjectWrapperFactory { /** * 是否有为(参数object)进行包装 *

* 这里写死返回false,因为该类的业务就是不对任何类对象进行包装 *

*/ @Override public boolean hasWrapperFor(Object object) { return false; } /** * 返回类对象包装类对象 *

* 这里调用该方法会抛出异常,因为该类的业务就是不对任何类对象进行包装 *

*/ @Override public ObjectWrapper getWrapperFor(MetaObject metaObject, Object object) { //默认对象包装器工厂不应该被称为对象提供一个包装器。; throw new ReflectionException("The DefaultObjectWrapperFactory should never be called to provide an ObjectWrapper."); } }

ObjectWrapper

/**
 *    Copyright 2009-2019 the original author or authors.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */
package org.apache.ibatis.reflection.wrapper;

import java.util.List;

import org.apache.ibatis.reflection.MetaObject;
import org.apache.ibatis.reflection.factory.ObjectFactory;
import org.apache.ibatis.reflection.property.PropertyTokenizer;

/**
 *https://blog.csdn.net/weixin_34075551/article/details/91402679
 * @author Clinton Begin
 */
public interface ObjectWrapper {


  /**
   * 获取对应(参数prop)当前类中属性对象
   */
  Object get(PropertyTokenizer prop);

  /**
   *对 对应(参数prop)当前类中属性的对象 赋上(参数value)
   */
  void set(PropertyTokenizer prop, Object value);

  /**
   * 查找属性并返回
   * @param name 属性名
   * @param useCamelCaseMapping 是否使用驼峰命名
   */
  String findProperty(String name, boolean useCamelCaseMapping);

  /***
   * 返回类的所有get方法名
   */
  String[] getGetterNames();

  /**
   * 返回类的所有set方法名
   */
  String[] getSetterNames();

  /**
   * 返回对应(参数name)当前类中属性的setter方法的参数类型
   */
  Class getSetterType(String name);

  /**
   * 返回对应(参数name)当前类中属性的getter方法的参数类型
   */
  Class getGetterType(String name);

  /**
   * 是否有对应(参数name)的当前类属性的set方法
   */
  boolean hasSetter(String name);

  /**
   * 是否有对应(参数name)的当前类属性的get方法
   */
  boolean hasGetter(String name);

  /**
   * 实例化属性对象
   */
  MetaObject instantiatePropertyValue(String name, PropertyTokenizer prop, ObjectFactory objectFactory);

  /**
   * 是否是集合
   * @return
   */
  boolean isCollection();

  /**
   * 添加元素
   * @param element
   */
  void add(Object element);

  /**
   * 添加元素
   */
   void addAll(List element);

}

BaseWrapper

/**
 *    Copyright 2009-2017 the original author or authors.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */
package org.apache.ibatis.reflection.wrapper;

import java.util.List;
import java.util.Map;

import org.apache.ibatis.reflection.MetaObject;
import org.apache.ibatis.reflection.ReflectionException;
import org.apache.ibatis.reflection.property.PropertyTokenizer;

/**
 * 抽象类,实现ObjectWrapper接口
 * 为子类BeanWrapper和MapWrapper提供公共的方法和属性
 * @author Clinton Begin
 */
public abstract class BaseWrapper implements ObjectWrapper {

  /**
   * 无参
   */
  protected static final Object[] NO_ARGUMENTS = new Object[0];
  /**
   * 当前的元类对象
   */
  protected final MetaObject metaObject;

  protected BaseWrapper(MetaObject metaObject) {
    this.metaObject = metaObject;
  }

  /**
   * 处理集合,根据(参数prop)获取对应属性的集合(Array、List、Map)对象,最终调用{@link MetaObject#getValue(String)}获取
   *
   * @param prop   PropertyTokenizer 对象
   * @param object 指定 Object 对象
   * @return 值
   */
  protected Object resolveCollection(PropertyTokenizer prop, Object object) {
    if ("".equals(prop.getName())) {//这里加上prop是'[0]',那么其实可以认为他是指object本身,类似于this的用法。
      return object;
    } else {
      return metaObject.getValue(prop.getName());
    }
  }

  /**
   * 获取在(参数collection)中对应(参数prop)的属性对象。(处理集合(Array、List、Map)
   * @param prop PropertyTokenizer 对象
   * @param collection 集合(Array、List、Map)
   * @return 对应下标或key的值
   */
  protected Object getCollectionValue(PropertyTokenizer prop, Object collection) {
    if (collection instanceof Map) {
      // 如果是Map类型,则index为key
      return ((Map) collection).get(prop.getIndex());
    } else {
      // 如果是其他集合类型,则index为下标
      int i = Integer.parseInt(prop.getIndex());
      if (collection instanceof List) {
        return ((List) collection).get(i);
      } else if (collection instanceof Object[]) {
        return ((Object[]) collection)[i];
      } else if (collection instanceof char[]) {
        return ((char[]) collection)[i];
      } else if (collection instanceof boolean[]) {
        return ((boolean[]) collection)[i];
      } else if (collection instanceof byte[]) {
        return ((byte[]) collection)[i];
      } else if (collection instanceof double[]) {
        return ((double[]) collection)[i];
      } else if (collection instanceof float[]) {
        return ((float[]) collection)[i];
      } else if (collection instanceof int[]) {
        return ((int[]) collection)[i];
      } else if (collection instanceof long[]) {
        return ((long[]) collection)[i];
      } else if (collection instanceof short[]) {
        return ((short[]) collection)[i];
      } else {
        // 不是集合对象抛ReflectionException异常
        throw new ReflectionException("The '" + prop.getName() + "' property of " + collection + " is not a List or Array.");
      }
    }
  }

  /**
   * 获取在(参数collection)中对应(参数prop)的属性对象,并对象赋上(参数value),(处理集合(Array、List、Map)
   * @param prop PropertyTokenizer 对象
   * @param collection 集合(Array、List、Map)
   * @param value 值
   */
  protected void setCollectionValue(PropertyTokenizer prop, Object collection, Object value) {
    if (collection instanceof Map) {
      ((Map) collection).put(prop.getIndex(), value);
    } else {
      int i = Integer.parseInt(prop.getIndex());
      if (collection instanceof List) {
        ((List) collection).set(i, value);
      } else if (collection instanceof Object[]) {
        ((Object[]) collection)[i] = value;
      } else if (collection instanceof char[]) {
        ((char[]) collection)[i] = (Character) value;
      } else if (collection instanceof boolean[]) {
        ((boolean[]) collection)[i] = (Boolean) value;
      } else if (collection instanceof byte[]) {
        ((byte[]) collection)[i] = (Byte) value;
      } else if (collection instanceof double[]) {
        ((double[]) collection)[i] = (Double) value;
      } else if (collection instanceof float[]) {
        ((float[]) collection)[i] = (Float) value;
      } else if (collection instanceof int[]) {
        ((int[]) collection)[i] = (Integer) value;
      } else if (collection instanceof long[]) {
        ((long[]) collection)[i] = (Long) value;
      } else if (collection instanceof short[]) {
        ((short[]) collection)[i] = (Short) value;
      } else {
        throw new ReflectionException("The '" + prop.getName() + "' property of " + collection + " is not a List or Array.");
      }
    }
  }

}

BeanWrapper

/**
 *    Copyright 2009-2017 the original author or authors.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */
package org.apache.ibatis.reflection.wrapper;

import java.util.List;

import org.apache.ibatis.reflection.*;
import org.apache.ibatis.reflection.factory.ObjectFactory;
import org.apache.ibatis.reflection.invoker.Invoker;
import org.apache.ibatis.reflection.property.PropertyTokenizer;

/**
 * 普通Java类包装
 * @author Clinton Begin
 */
public class BeanWrapper extends BaseWrapper {

  /**
   * 当前的类对象
   */
  private final Object object;
  /**
   * 当前元类
   */
  private final MetaClass metaClass;

  public BeanWrapper(MetaObject metaObject, Object object) {
    super(metaObject);
    this.object = object;
    this.metaClass = MetaClass.forClass(object.getClass(), metaObject.getReflectorFactory());
  }

  /**
   * 假设是prop是order[0],prop的index!=null,调用resolveCollection(prop,object)方法:resolveCollection(prop,object)里
   * 又会重新调用MetaObject.getValue(String)方法,String参数值为order。MetaObject.getValue(String)又会调用BeanWrapper.
   * get(PropertyTokenizer),此时PropertyTokenizer的参数为order,这个时候PropertyTokenizer的index为空,就会调用
   * getBeanProperty(PropertyTokenizer,Object)获取object的order属性的getter方法的返回值,此时resolveCollection(prop,object)
   * 方法就执行完了,返回结果就是取当前对象object的order属性的getter方法的返回值,再简单的说就是当前对象object中的order属性的对象,再调用
   * getCollectionValue(PropertyTokenizer,Object),这里的PropertyTokenizer参数为'order[0]',index='0',name='order',
   * Object参数是当前对象object中的order属性的对象,getCollectionValue(PropertyTokenizer,Object)方法会,将order对象
   * 转换成成Map,或者集合,或者数组(前提是order对象时能转换成Map,或者集合,或者数组,否则会抛出异常),然后以'order[0]'的index
   * 作为数组下班取其元素并返回给get(PropertyTokenizer)方法,get(PropertyTokenizer)返回其结果出去。
   * 此时以prop为’order[0]‘为参数的get(PropertyTokenizer)方法的执行程过就到此结束了。
   *
   */
  @Override
  public Object get(PropertyTokenizer prop) {
    if (prop.getIndex() != null) {
      Object collection = resolveCollection(prop, object);
      return getCollectionValue(prop, collection);
    } else {
      return getBeanProperty(prop, object);
    }
  }

  /**
   * 对对应(参数prop)的当前类对象object的属性附上(参数value)的值
   * 

* 假设是prop是order[0],prop的index!=null,调用resolveCollection(prop,object)方法:resolveCollection(prop,object)里 * 又会重新调用MetaObject.getValue(String)方法,String参数值为order。MetaObject.getValue(String)又会调用BeanWrapper. * get(PropertyTokenizer),此时PropertyTokenizer的参数为order,这个时候PropertyTokenizer的index为空,就会调用 * getBeanProperty(PropertyTokenizer,Object)获取object的order属性的getter方法的返回值,此时resolveCollection(prop,object) * 方法就执行完了,返回结果就是取当前对象object的order属性的getter方法的返回值,再简单的说就是当前对象object中的order属性的对象,再调用 * setCollectionValue(PropertyTokenizer,Object,Object),这里的PropertyTokenizer参数为'order[0]',index='0',name='order', * 第二个Object参数是当前对象object中的order属性的对象,第三个Object是需要设置的值,就是方法set(PropertyTokenizer,Object)的第二参数。 * ,然后setCollectionValue(PropertyTokenizer,Object,Object)方法会,将order对象 * 转换成成Map,或者集合,或者数组(前提是order对象时能转换成Map,或者集合,或者数组,否则会抛出异常),然后以'order[0]'的index * 作为数组下标第三个参数Object其元素。 * 此时以prop为’order[0]‘为参数的set(PropertyTokenizer prop, Object value)方法的执行程过就到此结束了。 *

* */ @Override public void set(PropertyTokenizer prop, Object value) { if (prop.getIndex() != null) { Object collection = resolveCollection(prop, object); setCollectionValue(prop, collection, value); } else { setBeanProperty(prop, object, value); } } /** * 实际是直接调用 {@link MetaClass#findProperty(String, boolean)} * @param name 属性名 * @param useCamelCaseMapping 是否使用驼峰命名 * @return */ @Override public String findProperty(String name, boolean useCamelCaseMapping) { return metaClass.findProperty(name, useCamelCaseMapping); } /** * 实际直接调用 {@link MetaClass#getGetterNames()} */ @Override public String[] getGetterNames() { return metaClass.getGetterNames(); } /** * 实际直接调用 {@link MetaClass#getSetterNames()} */ @Override public String[] getSetterNames() { return metaClass.getSetterNames(); } /** * 获取参数name在metaClass对应的setter方法的参数类型。 *

* 以name='order[0].name'为参数调用该方法:首先将name封装成 {@link PropertyTokenizer} * 并赋值给(变量prop,prop={name='order',index='0',children='name'}),调用prop的 * {@link PropertyTokenizer#hasNext()}得到true,通过prop的{@link PropertyTokenizer#getIndexedName()} * 方法得到'order[0]',再'order[0]'作为参数调用当前类中成员变量metaObject的{@link MetaObject#metaObjectForProperty(String)}, * 得到封装 当前类对象的对应'order[0]'属性对象 的 {@link MetaObject} 并附值给metaValue变量, * 判断metaValue是否等于 {@link SystemMetaObject#NULL_META_OBJECT} ,若等于,调用当前类中成员变量metaClass的 * {@link MetaClass#getSetterType(String)}得到(参数name)对应的属性的setter方法的参数类型。 * 若不等于,调用Prop的{@link PropertyTokenizer#getChildren()} 得到'name',再以'name'为参数, * 递归调用metaValue的 {@link MetaObject#getSetterType(String)},将'name'封装成 {@link PropertyTokenizer} * 并赋值给(prop变量,prop={name='name',index=null,children=null}),调用(变量prop)的 * {@link PropertyTokenizer#hasNext()}得到false,然后以(参数name='name')作为参数,调用(当前类中成员变量metaClass)的 * {@link MetaClass#getSetterType(String)}得到当前声明在metaClass的对应于(参数name='name')的setter方法的参数类型 * *

*/ @Override public Class getSetterType(String name) { PropertyTokenizer prop = new PropertyTokenizer(name); if (prop.hasNext()) { MetaObject metaValue = metaObject.metaObjectForProperty(prop.getIndexedName()); if (metaValue == SystemMetaObject.NULL_META_OBJECT) { return metaClass.getSetterType(name); } else { return metaValue.getSetterType(prop.getChildren()); } } else { return metaClass.getSetterType(name); } } /** * 获取name对应的getter方法的返回类型。 *

* 以name='order[0].name'为参数调用该方法:首先将name封装成 {@link PropertyTokenizer} * 并赋值给(变量prop,prop={name='order',index='0',children='name'}),调用prop的 * {@link PropertyTokenizer#hasNext()}得到true,通过prop的{@link PropertyTokenizer#getIndexedName()} * 方法得到'order[0]',再'order[0]'作为参数调用当前类中成员变量metaObject的{@link MetaObject#metaObjectForProperty(String)}, * 得到封装 当前类对象的对应'order[0]'属性对象 的 {@link MetaObject} 并附值给metaValue变量, * 判断metaValue是否等于 {@link SystemMetaObject#NULL_META_OBJECT} ,若等于,调用当前类中成员变量metaClass的 * {@link MetaClass#getGetterType(String)}得到(参数name)对应的属性的setter方法的参数类型。 * 若不等于,调用Prop的{@link PropertyTokenizer#getChildren()} 得到'name',再以'name'为参数, * 递归调用metaValue的 {@link MetaObject#getGetterType(String)},将'name'封装成 {@link PropertyTokenizer} * 并赋值给(prop变量,prop={name='name',index=null,children=null}),调用(变量prop)的 * {@link PropertyTokenizer#hasNext()}得到false,然后以(参数name='name')作为参数,调用(当前类中成员变量metaClass)的 * {@link MetaClass#getGetterType(String)}得到当前声明在metaClass的对应于(参数name='name')的setter方法的参数类型 * *

*/ @Override public Class getGetterType(String name) { PropertyTokenizer prop = new PropertyTokenizer(name); if (prop.hasNext()) { MetaObject metaValue = metaObject.metaObjectForProperty(prop.getIndexedName()); if (metaValue == SystemMetaObject.NULL_META_OBJECT) { return metaClass.getGetterType(name); } else { return metaValue.getGetterType(prop.getChildren()); } } else { return metaClass.getGetterType(name); } } /** * 判断是否存在对应(参数name)类中属性的setter方法 *

* 以(参数name='order[0].name')调用该方法,先将name封装成 {@link PropertyTokenizer}, * 并赋值给(变量prop,prop={name='order',index='0',name='name'}),调用(变量prop)的 * {@link PropertyTokenizer#hasNext()}方法得到true,将 (变量prop)的调用{@link PropertyTokenizer#getIndexedName()} * 得到'order[0]'传入进(成员变量metaClass)的{@link MetaClass#hasSetter(String)}得到true,再将 * 变量prop)的调用{@link PropertyTokenizer#getIndexedName()}得到'order[0]', * 传入{@link MetaObject#metaObjectForProperty(String)}得到封装着对应'order'的类中属性对象的 {@link MetaObject} * 并赋值给(变量metaValue),如果(变量metaValue)等于{@link SystemMetaObject#NULL_META_OBJECT},会调用将(参数name) * 传入 {@link MetaClass#hasSetter(String)} 判断;否则,将 从(变量prop)调用 {@link PropertyTokenizer#getChildren()}得到 * 'name' 传入(变量metaValue)的 {@link MetaObject#hasSetter(String)} 最终还是有可能调用回该方法:将'name'传入 * {@link PropertyTokenizer}并赋值给(变量prop,prop={name='name',index=null,children=null}),调用(变量prop)的 * {@link PropertyTokenizer#hasNext()}得到false,然后直接返回 {@link MetaClass#hasSetter(String)}的结果 * *

*/ @Override public boolean hasSetter(String name) { PropertyTokenizer prop = new PropertyTokenizer(name); if (prop.hasNext()) { if (metaClass.hasSetter(prop.getIndexedName())) { MetaObject metaValue = metaObject.metaObjectForProperty(prop.getIndexedName()); if (metaValue == SystemMetaObject.NULL_META_OBJECT) { return metaClass.hasSetter(name); } else { return metaValue.hasSetter(prop.getChildren()); } } else { return false; } } else { return metaClass.hasSetter(name); } } /** * 判断是否存在对应(参数name)类中属性的getter方法 *

* 以(参数name='order[0].name')调用该方法,先将name封装成 {@link PropertyTokenizer}, * 并赋值给(变量prop,prop={name='order',index='0',name='name'}),调用(变量prop)的 * {@link PropertyTokenizer#hasNext()}方法得到true,将 (变量prop)的调用{@link PropertyTokenizer#getIndexedName()} * 得到'order[0]'传入进(成员变量metaClass)的{@link MetaClass#hasGetter(String)}得到true,再将 * 变量prop)的调用{@link PropertyTokenizer#getIndexedName()}得到'order[0]', * 传入{@link MetaObject#metaObjectForProperty(String)}得到封装着对应'order'的类中属性对象的 {@link MetaObject} * 并赋值给(变量metaValue),如果(变量metaValue)等于{@link SystemMetaObject#NULL_META_OBJECT},会调用将(参数name) * 传入 {@link MetaClass#hasGetter(String)} 判断;否则,将 从(变量prop)调用 {@link PropertyTokenizer#getChildren()}得到 * 'name' 传入(变量metaValue)的 {@link MetaObject#hasGetter(String)} 最终还是有可能调用回该方法:将'name'传入 * {@link PropertyTokenizer}并赋值给(变量prop,prop={name='name',index=null,children=null}),调用(变量prop)的 * {@link PropertyTokenizer#hasNext()}得到false,然后直接返回 {@link MetaClass#hasSetter(String)}的结果 * *

*/ @Override public boolean hasGetter(String name) { PropertyTokenizer prop = new PropertyTokenizer(name); if (prop.hasNext()) { if (metaClass.hasGetter(prop.getIndexedName())) { MetaObject metaValue = metaObject.metaObjectForProperty(prop.getIndexedName()); if (metaValue == SystemMetaObject.NULL_META_OBJECT) { return metaClass.hasGetter(name); } else { return metaValue.hasGetter(prop.getChildren()); } } else { return false; } } else { return metaClass.hasGetter(name); } } /** * 实例化属性对象 *

* 以(参数name='order[0].name',参数prop={name='order',index='0',children='name'}, * 参数objectFactory={@link org.apache.ibatis.reflection.factory.DefaultObjectFactory})调用该方法, * 调用(参数prop)的 {@link PropertyTokenizer#getName()} 得到'order',再将'order'插入{@link BeanWrapper#getSetterType(String)} * 方法得到 在metaClass对应的setter方法的参数类型 并赋值给(变量type),将(变量type)传入(参数objectFactory)的 * {@link org.apache.ibatis.reflection.factory.DefaultObjectFactory#create(Class)}的(变量type)的对象并 * 赋值给(变量newObject)。再将(变量newObject)传入 {@link MetaObject#forObject(Object, ObjectFactory, ObjectWrapperFactory, ReflectorFactory)} * 得到 {@link MetaObject} 赋值给(变量metaValue),再将(变量newObject)和(参数prop)传入 {@link BeanWrapper#set(PropertyTokenizer, Object)} * 进行对(变量prop)所描述的属性附上(变量newObject),最后返回(变量metaValue) *

* @return */ @Override public MetaObject instantiatePropertyValue(String name, PropertyTokenizer prop, ObjectFactory objectFactory) { MetaObject metaValue; Class type = getSetterType(prop.getName());// try { Object newObject = objectFactory.create(type); metaValue = MetaObject.forObject(newObject, metaObject.getObjectFactory(), metaObject.getObjectWrapperFactory(), metaObject.getReflectorFactory()); set(prop, newObject); } catch (Exception e) { throw new ReflectionException("Cannot set value of property '" + name + "' because '" + name + "' is null and cannot be instantiated on instance of " + type.getName() + ". Cause:" + e.toString(), e); } return metaValue; } /** * 获取在(参数object)中的对应(参数prop)的属性对象。 *

* 假设prop为'order',该方法调用 {@link MetaClass#getGetInvoker(String)} 获取'order'的对应Getter方法, * 然后通过object执行Getter并返回结果 *

* * * @param object 带有对应与prop.getName的返回值的属性名,一般是当前对象 */ private Object getBeanProperty(PropertyTokenizer prop, Object object) { try { Invoker method = metaClass.getGetInvoker(prop.getName()); try { return method.invoke(object, NO_ARGUMENTS); } catch (Throwable t) { throw ExceptionUtil.unwrapThrowable(t); } } catch (RuntimeException e) { throw e; } catch (Throwable t) { throw new ReflectionException("Could not get property '" + prop.getName() + "' from " + object.getClass() + ". Cause: " + t.toString(), t); } } /** * 获取在(参数object)中的对应(参数prop)的属性对象。 *

* 假设(参数prop)的{@link PropertyTokenizer#getName()}为'order',该方法调用 * {@link MetaClass#getSetInvoker(String)} 获取'order'的对应setter方法并赋值(变量method) * 然后传入(参数object)和(参数value)到(变量method)的{@link java.lang.reflect.Method#invoke(Object, Object...)} * 进行对 在(参数object)中对应'order'的属性对象赋上(参数value) *

* * @param object 带有对应与prop.getName的返回值的属性名,一般是当前对象 * @param value 对应属性的值、对象 */ private void setBeanProperty(PropertyTokenizer prop, Object object, Object value) { try { Invoker method = metaClass.getSetInvoker(prop.getName()); Object[] params = {value}; try { method.invoke(object, params); } catch (Throwable t) { throw ExceptionUtil.unwrapThrowable(t); } } catch (Throwable t) { throw new ReflectionException("Could not set property '" + prop.getName() + "' of '" + object.getClass() + "' with value '" + value + "' Cause: " + t.toString(), t); } } /** * 普通Java类不可能是集合,永远返回false */ @Override public boolean isCollection() { return false; } /** * 普通Java类并不知add方法,会抛出异常 */ @Override public void add(Object element) { throw new UnsupportedOperationException(); } /** * 普通Java类并不知addAll方法,会抛出异常 */ @Override public void addAll(List list) { throw new UnsupportedOperationException(); } }

MapWrapper

/**
 *    Copyright 2009-2018 the original author or authors.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */
package org.apache.ibatis.reflection.wrapper;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.ibatis.reflection.MetaObject;
import org.apache.ibatis.reflection.ReflectorFactory;
import org.apache.ibatis.reflection.SystemMetaObject;
import org.apache.ibatis.reflection.factory.ObjectFactory;
import org.apache.ibatis.reflection.property.PropertyTokenizer;

/**
 * Map包装类
 * 

* 对Map对象进行包装 *

* * @author Clinton Begin */ public class MapWrapper extends BaseWrapper { private final Map map; public MapWrapper(MetaObject metaObject, Map map) { super(metaObject); this.map = map; } /** * 获取对应(参数prop)当前类中属性的对象 *

* 判断(参数prop)的{@link PropertyTokenizer#getIndex()}是否为空:不为空表示该属性可能是集合类型对象, * 所以调用{@link BaseWrapper#resolveCollection(PropertyTokenizer, Object)}进行获取,该属性对象并 * 赋值给(变量collection),然后将(变量prop)和(变量collection)传入 * {@link BaseWrapper#getCollectionValue(PropertyTokenizer, Object)}获取属性对象;否则直接调用 * (成员变量map)的{@link Map#get(Object)}获取属性对象 *

*/ @Override public Object get(PropertyTokenizer prop) { if (prop.getIndex() != null) { Object collection = resolveCollection(prop, map); return getCollectionValue(prop, collection); } else { return map.get(prop.getName()); } } /** * 对 对应(参数prop)当前类中属性的对象 赋上(参数value) *

* 判断(参数prop)的{@link PropertyTokenizer#getIndex()}是否为空:不为空表示该属性可能是集合类型对象, * 所以调用{@link BaseWrapper#resolveCollection(PropertyTokenizer, Object)}进行获取,该属性对象并 * 赋值给(变量collection),然后将(变量prop)和(变量collection)传入 * {@link BaseWrapper#setCollectionValue(PropertyTokenizer, Object,Object)}赋上(参数value);否则直接调用 * (成员变量map)的{@link Map#put(Object, Object)}赋上(参数value) *

*/ @Override public void set(PropertyTokenizer prop, Object value) { if (prop.getIndex() != null) { Object collection = resolveCollection(prop, map); setCollectionValue(prop, collection, value); } else { map.put(prop.getName(), value); } } /** * 查找属性并返回 *

* 实际直接返回(参数name) *

* @param name 属性名 * @param useCamelCaseMapping 是否使用驼峰命名 */ @Override public String findProperty(String name, boolean useCamelCaseMapping) { return name; } /** * 返回类的所有get方法名 *

* 实际返回(成员变量map)的keySet *

*/ @Override public String[] getGetterNames() { return map.keySet().toArray(new String[map.keySet().size()]); } /** * 返回类的所有set方法名 *

* 实际返回(成员变量map)的keySet *

*/ @Override public String[] getSetterNames() { return map.keySet().toArray(new String[map.keySet().size()]); } /** * 返回对应(参数name)当前类中属性的setter方法的参数类型 *

* 以name='order[0].name'为参数调用该方法:首先将name封装成 {@link PropertyTokenizer} * 并赋值给(变量prop,prop={name='order',index='0',children='name'}),调用prop的 * {@link PropertyTokenizer#hasNext()}得到true,通过prop的{@link PropertyTokenizer#getIndexedName()} * 方法得到'order[0]',再'order[0]'作为参数调用当前类中成员变量metaObject的{@link MetaObject#metaObjectForProperty(String)}, * 得到封装 当前类对象的对应'order[0]'属性对象 的 {@link MetaObject} 并附值给metaValue变量, * 判断metaValue是否等于 {@link SystemMetaObject#NULL_META_OBJECT} ,若等于,直接返回Object.class; * 若不等于,调用Prop的{@link PropertyTokenizer#getChildren()} 得到'name',再以'name'为参数, * 递归调用metaValue的 {@link MetaObject#getSetterType(String)}:将'name'封装成 {@link PropertyTokenizer} * 并赋值给(prop变量,prop={name='name',index=null,children=null}),调用(变量prop)的 * {@link PropertyTokenizer#hasNext()}得到false,就会调用(成员变量map)的{@link Map#get(Object)}获得 * 对象不为null就返回该对象类型,否则返回Object.class。 * *

*/ @Override public Class getSetterType(String name) { PropertyTokenizer prop = new PropertyTokenizer(name); if (prop.hasNext()) { MetaObject metaValue = metaObject.metaObjectForProperty(prop.getIndexedName()); if (metaValue == SystemMetaObject.NULL_META_OBJECT) { return Object.class; } else { return metaValue.getSetterType(prop.getChildren()); } } else { if (map.get(name) != null) { return map.get(name).getClass(); } else { return Object.class; } } } /** * 返回对应(参数name)当前类中属性的getter方法的参数类型 *

* 以name='order[0].name'为参数调用该方法:首先将name封装成 {@link PropertyTokenizer} * 并赋值给(变量prop,prop={name='order',index='0',children='name'}),调用prop的 * {@link PropertyTokenizer#hasNext()}得到true,通过prop的{@link PropertyTokenizer#getIndexedName()} * 方法得到'order[0]',再'order[0]'作为参数调用当前类中成员变量metaObject的{@link MetaObject#metaObjectForProperty(String)}, * 得到封装 当前类对象的对应'order[0]'属性对象 的 {@link MetaObject} 并附值给metaValue变量, * 判断metaValue是否等于 {@link SystemMetaObject#NULL_META_OBJECT} ,若等于,直接返回Object.class; * 若不等于,调用Prop的{@link PropertyTokenizer#getChildren()} 得到'name',再以'name'为参数, * 递归调用metaValue的 {@link MetaObject#getGetterType(String)}:将'name'封装成 {@link PropertyTokenizer} * 并赋值给(prop变量,prop={name='name',index=null,children=null}),调用(变量prop)的 * {@link PropertyTokenizer#hasNext()}得到false,就会调用(成员变量map)的{@link Map#get(Object)}获得 * 对象不为null就返回该对象类型,否则返回Object.class。 * *

*/ @Override public Class getGetterType(String name) { PropertyTokenizer prop = new PropertyTokenizer(name); if (prop.hasNext()) { MetaObject metaValue = metaObject.metaObjectForProperty(prop.getIndexedName()); if (metaValue == SystemMetaObject.NULL_META_OBJECT) { return Object.class; } else { return metaValue.getGetterType(prop.getChildren()); } } else { if (map.get(name) != null) { return map.get(name).getClass(); } else { return Object.class; } } } /** * 是否有对应(参数name)的当前类属性的set方法 *

* 因为是Map,所以肯定有key的setter方法。setter方法就是指{@link Map#put(Object, Object)}, * 这里写死了返回true *

*/ @Override public boolean hasSetter(String name) { return true; } /** * 是否有对应(参数name)的当前类属性的get方法 *

* 以name='order[0].name'为参数调用该方法:首先将name封装成 {@link PropertyTokenizer} * 并赋值给(变量prop,prop={name='order',index='0',children='name'}),调用prop的 * {@link PropertyTokenizer#hasNext()}得到true,通过prop的{@link PropertyTokenizer#getIndexedName()} * 方法得到'order[0]',再'order[0]'作为参数调用当前类中成员变量metaObject的{@link MetaObject#metaObjectForProperty(String)}, * 得到封装 当前类对象的对应'order[0]'属性对象 的 {@link MetaObject} 并附值给metaValue变量, * 判断metaValue是否等于 {@link SystemMetaObject#NULL_META_OBJECT} ,若等于,直接返回true; * 否则,从(变量prop)调用 {@link PropertyTokenizer#getChildren()}得到'name' 传入 * (变量metaValue)的 {@link MetaObject#hasSetter(String)} 最终还是有可能调用回该方法:将'name'传入 * {@link PropertyTokenizer}并赋值给(变量prop,prop={name='name',index=null,children=null}),调用(变量prop)的 * {@link PropertyTokenizer#hasNext()}得到false,然后直接返回 {@link Map#containsKey(Object)}的结果 *

*/ @Override public boolean hasGetter(String name) { PropertyTokenizer prop = new PropertyTokenizer(name); if (prop.hasNext()) { if (map.containsKey(prop.getIndexedName())) { MetaObject metaValue = metaObject.metaObjectForProperty(prop.getIndexedName()); if (metaValue == SystemMetaObject.NULL_META_OBJECT) { return true; } else { return metaValue.hasGetter(prop.getChildren()); } } else { return false; } } else { return map.containsKey(prop.getName()); } } /** * 实例化对象 *

* 先实例化一个{@link HashMap}赋值给(变量map),将(参数prop)和(变量map)传入{@link MapWrapper#set(PropertyTokenizer, Object)} * 对 对应(参数prop)当前类中属性的对象 赋上(变量map),然后将(变量map),(成员变量metaObject的{@link ObjectFactory}, * {@link ObjectWrapperFactory},{@link org.apache.ibatis.reflection.ReflectorFactory}) 传入 * {@link MetaObject#forObject(Object, ObjectFactory, ObjectWrapperFactory, ReflectorFactory)} * 得到 {@link MetaObject} 并返回出去 *

*/ @Override public MetaObject instantiatePropertyValue(String name, PropertyTokenizer prop, ObjectFactory objectFactory) { HashMap map = new HashMap<>(); set(prop, map); return MetaObject.forObject(map, metaObject.getObjectFactory(), metaObject.getObjectWrapperFactory(), metaObject.getReflectorFactory()); } /** * Map肯定不是集合,所以写死返回false */ @Override public boolean isCollection() { return false; } /** * Map肯定不存在集合的添加方法,所以这里一旦调用就会抛出异常 */ @Override public void add(Object element) { throw new UnsupportedOperationException(); } /** * Map肯定不存在集合的添加方法,所以这里一旦调用就会抛出异常 */ @Override public void addAll(List element) { throw new UnsupportedOperationException(); } }

CollectionWrapper

/**
 *    Copyright 2009-2017 the original author or authors.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */
package org.apache.ibatis.reflection.wrapper;

import java.util.Collection;
import java.util.List;

import org.apache.ibatis.reflection.MetaObject;
import org.apache.ibatis.reflection.factory.ObjectFactory;
import org.apache.ibatis.reflection.property.PropertyTokenizer;

/**
 * 集合包装类,这里注意了,除了isCollection(),add(Object),addAll(List)以外,调用其他方法都会抛出UnsupportedOperationException
 * @author Clinton Begin
 */
public class CollectionWrapper implements ObjectWrapper {

  private final Collection object;

  public CollectionWrapper(MetaObject metaObject, Collection object) {
    this.object = object;
  }


  @Override
  public Object get(PropertyTokenizer prop) {
    throw new UnsupportedOperationException();
  }

  @Override
  public void set(PropertyTokenizer prop, Object value) {
    throw new UnsupportedOperationException();
  }

  @Override
  public String findProperty(String name, boolean useCamelCaseMapping) {
    throw new UnsupportedOperationException();
  }

  @Override
  public String[] getGetterNames() {
    throw new UnsupportedOperationException();
  }

  @Override
  public String[] getSetterNames() {
    throw new UnsupportedOperationException();
  }

  @Override
  public Class getSetterType(String name) {
    throw new UnsupportedOperationException();
  }

  @Override
  public Class getGetterType(String name) {
    throw new UnsupportedOperationException();
  }

  @Override
  public boolean hasSetter(String name) {
    throw new UnsupportedOperationException();
  }

  @Override
  public boolean hasGetter(String name) {
    throw new UnsupportedOperationException();
  }

  @Override
  public MetaObject instantiatePropertyValue(String name, PropertyTokenizer prop, ObjectFactory objectFactory) {
    throw new UnsupportedOperationException();
  }

  @Override
  public boolean isCollection() {
    return true;
  }


  @Override
  public void add(Object element) {
    object.add(element);
  }


  @Override
  public  void addAll(List element) {
    object.addAll(element);
  }

}







你可能感兴趣的:(Mybatis-ObjectFactory,ObjectWrapperFactory源码分析)