Mybatis初始化过程
Mybatis初始化过程
// 1. 读取配置文件,读成字节输入流,注意:现在还没解析
InputStream resourceAsStream = Resources.getResourceAsStream("sqlMapConfig.xml");
// 2. 解析配置文件,封装Configuration对象   创建DefaultSqlSessionFactory对象
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(resourceAsStream);

1.读取配置文件,读成字节输入流
//Resources.java
public static InputStream getResourceAsStream(String resource) throws IOException {
    return getResourceAsStream(null, resource);
}
public static InputStream getResourceAsStream(ClassLoader loader, String resource) throws IOException {
    InputStream in = classLoaderWrapper.getResourceAsStream(resource, loader);
    if (in == null) {
        throw new IOException("Could not find resource " + resource);
    }
    return in;
}
通过classLoad调用
getResourceAsStream()方法返回字节输入流,也就是得到了配置文件的字节输入流
2. 解析配置文件,封装Configuration对象 创建DefaultSqlSessionFactory对象
2.1 解析配置文件
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(resourceAsStream);
//SqlSessionFactoryBuilder.java
// 1.我们最初调用的build
public SqlSessionFactory build(InputStream inputStream) {
    //调用了重载方法
    return build(inputStream, null, null);
}
// 2.调用的重载方法
public SqlSessionFactory build(InputStream inputStream, String environment, Properties properties) {
    try {
        // 创建 XMLConfigBuilder, XMLConfigBuilder是专门解析mybatis的配置文件的类
        XMLConfigBuilder parser = new XMLConfigBuilder(inputStream, environment, properties);
        // 执行 XML 解析
        // 创建 DefaultSqlSessionFactory 对象
        return build(parser.parse());
    } catch (Exception e) {
        throw ExceptionFactory.wrapException("Error building SqlSession.", e);
    } finally {
        ErrorContext.instance().reset();
        try {
            inputStream.close();
        } catch (IOException e) {
            // Intentionally ignore. Prefer previous error.
        }
    }
}
1.传入配置文件的字节输入流,调用其重载方法。
2.创建 XMLConfigBuilder对象,它是用来解析mybatis的配置文件的类
3.执行parser.parse()
parser.parse()
//XMLConfigBuilder.java
/**
 * 解析 XML 成 Configuration 对象。
 *
 * @return Configuration 对象
 */
public Configuration parse() {
    // 若已解析,抛出 BuilderException 异常
    if (parsed) {
        throw new BuilderException("Each XMLConfigBuilder can only be used once.");
    }
    // 标记已解析
    parsed = true;
    ///parser是XPathParser解析器对象,读取节点内数据,<configuration>是MyBatis配置文件中的顶层标签
    // 解析 XML configuration 节点
    parseConfiguration(parser.evalNode("/configuration"));
    return configuration;
}
parse():
判断是否解析过,抛出异常或打标记
4.调用parseConfiguration()方法,开始解析XML configuration 节点,并返回configuration
//XMLConfigBuilder.java
/**
 * 解析 XML
 * 具体 MyBatis 有哪些 XML 标签,参见 《XML 映射配置文件》http://www.mybatis.org/mybatis-3/zh/configuration.html
 * @param root 根节点
 */
private void parseConfiguration(XNode root) {
    try {
        //issue #117 read properties first
        // 解析 <properties /> 标签
        propertiesElement(root.evalNode("properties"));
        // 解析 <settings /> 标签
        Properties settings = settingsAsProperties(root.evalNode("settings"));
        // 加载自定义的 VFS 实现类
        loadCustomVfs(settings);
        // 解析 <typeAliases /> 标签
        typeAliasesElement(root.evalNode("typeAliases"));
        // 解析 <plugins /> 标签
        pluginElement(root.evalNode("plugins"));
        // 解析 <objectFactory /> 标签
        objectFactoryElement(root.evalNode("objectFactory"));
        // 解析 <objectWrapperFactory /> 标签
        objectWrapperFactoryElement(root.evalNode("objectWrapperFactory"));
        // 解析 <reflectorFactory /> 标签
        reflectorFactoryElement(root.evalNode("reflectorFactory"));
        // 赋值 <settings /> 到 Configuration 属性
        settingsElement(settings);
        // read it after objectFactory and objectWrapperFactory issue #631
        // 解析 <environments /> 标签
        environmentsElement(root.evalNode("environments"));
        // 解析 <databaseIdProvider /> 标签
        databaseIdProviderElement(root.evalNode("databaseIdProvider"));
        // 解析 <typeHandlers /> 标签
        typeHandlerElement(root.evalNode("typeHandlers"));
        // 解析 <mappers /> 标签
        mapperElement(root.evalNode("mappers"));
    } catch (Exception e) {
        throw new BuilderException("Error parsing SQL Mapper Configuration. Cause: " + e, e);
    }
}
这些都是mybatis配置文件中的标签,开始逐个解析,注意最后一行 mapperElement(root.evalNode("mappers"))
说明在解析config*.xml的同时也解析了mapper.xml(映射配置)文件
一个映射配置文件中的每一个select、delete、update、insert都会封装成一个MappedStatement
2.2.创建DefaultSqlSessionFactory对象
return build(parser.parse());
public SqlSessionFactory build(Configuration config) {
   return new DefaultSqlSessionFactory(config); //构建者设计模式
}
5.执行build方法,接收到封装好的
Configuration对象,并根据这个对象构建一个DefaultSqlSessionFactory。DefaultSqlSessionFactory就是一个SqlSessionFactory的实现类。构建者设计模式:当构建一个复杂的对象时 可以把他拆成构建个很多的简单的对象,再由多个简单的对象构成复杂的对象
本文来自博客园,作者:邓晓晖,转载请注明原文链接:https://www.cnblogs.com/isdxh/p/13994822.html

                
            
        
浙公网安备 33010602011771号