分析mybatis 读取mybatis-config.xml文件的源码流程

代码见  GitHub:  https://github.com/tuyf/mybatisTest/tree/master/mybatisTest1

执行测试目录下的 UserTest 的 insertPerson方法, 进入MybatisUtil的静态方法块:

static{
    String resource="mybatis-config.xml";
    Reader reader =null;
    try {
        reader = Resources.getResourceAsReader(resource);
    } catch (IOException e) {
        e.printStackTrace();
    }
    sqlSessionFactory = new SqlSessionFactoryBuilder().build(reader);
}

主要看 new SqlSessionFactoryBuilder().build(reader); 看mybatis是怎么样 根据reader配置文件信息 来创建sqlSessionFactory对象的。

方法 一层一层 进入:

所以 主要逻辑还是在 XMLConfigBuilder.parse() 中,

可以看到 类XMLConfigBuilder 的 parseConfiguration(XNode root)  方法中 对于 mybatis-config.xml配置文件中的各种节点 都有解析。

根节点是  <configuration>

</configuration>

项目 https://github.com/tuyf/mybatisTest/tree/master/mybatisTest1  的mybatis-config.xml配置文件上包含的节点有

properties
typeAliases
environments
mappers

以 typeHandlerElement(root.evalNode("typeHandlers")); 为例, typeHandler 是类型转换处理接口。

XMLConfigBuilder 的代码:
 private void typeHandlerElement(XNode parent) throws Exception {
    if (parent != null) {
      for (XNode child : parent.getChildren()) {
        if ("package".equals(child.getName())) {
          String typeHandlerPackage = child.getStringAttribute("name");
          typeHandlerRegistry.register(typeHandlerPackage);
        } else {
          String javaTypeName = child.getStringAttribute("javaType");
          String jdbcTypeName = child.getStringAttribute("jdbcType");
          String handlerTypeName = child.getStringAttribute("handler");
          Class<?> javaTypeClass = resolveClass(javaTypeName);
          JdbcType jdbcType = resolveJdbcType(jdbcTypeName);
          Class<?> typeHandlerClass = resolveClass(handlerTypeName);
          if (javaTypeClass != null) {
            if (jdbcType == null) {
              typeHandlerRegistry.register(javaTypeClass, typeHandlerClass);
            } else {
              typeHandlerRegistry.register(javaTypeClass, jdbcType, typeHandlerClass);
            }
          } else {
            typeHandlerRegistry.register(typeHandlerClass);
          }
        }
      }
    }
  }
 private void register(Type javaType, JdbcType jdbcType, TypeHandler<?> handler) {
    if (javaType != null) {
      Map<JdbcType, TypeHandler<?>> map = TYPE_HANDLER_MAP.get(javaType);
      if (map == null) {
        map = new HashMap<JdbcType, TypeHandler<?>>();
        TYPE_HANDLER_MAP.put(javaType, map);
      }
      map.put(jdbcType, handler);
    }
    ALL_TYPE_HANDLERS_MAP.put(handler.getClass(), handler);
  }
从XMLConfigBuilder的以上代码可以知道, 类型转换处理接口 最终 会把javaTypeClass的类,JdbcType的JdbcType对象 以及 这两个对象的映射typeHandlerClass类 注册到  typeHandlerRegistry 中,最终保存到
    TYPE_HANDLER_MAP
   ALL_TYPE_HANDLERS_MAP 中 。

最后

XMLConfigBuilder 中的每种节点类型的读取和处理,如果是configuration里面的节点,都会set到

configuration的成员变量中。

在读取完 配置文件,并set到configuration中之后,

在SqlSessionFactoryBuilder中, 会有一个根据config配置信息,创建默认会话的方法:

return new DefaultSqlSessionFactory(config);

猜你喜欢

转载自blog.csdn.net/tuyf_hs/article/details/88142311