mybatis架构

159 阅读4分钟

MyBatis 架构分为接口层、核心处理层和基础支持层,通过 SqlSession 提供操作入口,核心层实现 SQL 解析、执行及结果映射,支持动态 SQL 和插件扩展,基础层整合数据源、事务与缓存,适用于复杂查询和高性能场景。

image.png

一、接口层

核心模块SqlSession 作用

  • 作为 MyBatis 对外的核心 API,提供操作数据库的入口(如 selectOne(), insert())。
  • 通过 getMapper() 方法动态生成 Mapper 接口的代理对象,将接口方法与 SQL 映射绑定。 协作流程
// 示例:通过 SqlSession 获取 Mapper 并执行查询
try (SqlSession session = sqlSessionFactory.openSession()) {
    UserMapper mapper = session.getMapper(UserMapper.class); // 动态代理生成实现类
    User user = mapper.selectUserById(1); // 调用接口方法触发 SQL 执行
}

二、核心处理层

包含 SQL 生命周期管理的核心模块,具体如下:

1. 配置解析
  • 作用:解析全局配置文件(mybatis-config.xml)和 Mapper XML 文件,构建 Configuration 对象。

  • 关键内容

    • 数据源、事务管理器、插件等全局配置。
    • Mapper 接口与 XML 的绑定关系。
2. SQL 解析
  • 作用:将动态 SQL 标签(如 <if>, <foreach>)解析为可执行的静态 SQL。

  • 示例

    <!-- 动态 SQL 解析为静态 SQL -->
    <select id="findUser">
      SELECT * FROM user 
      <where>
        <if test="name != null">name = #{name}</if>
      </where>
    </select>
    

    解析后生成:SELECT * FROM user WHERE name = ?

3. 参数映射
  • 作用:将 Java 方法的参数转换为 SQL 中的占位符(#{param})。

  • 支持类型

    • 基本类型、POJO、Map、集合等。
    • 通过 @Param 注解指定参数名。
4. SQL 执行
  • 执行器(Executor)

    • 类型SimpleExecutor(默认)、ReuseExecutor(复用 Statement)、BatchExecutor(批量执行)。

    • 流程

      1. 调用 StatementHandler 创建 PreparedStatement
      2. 通过 ParameterHandler 设置参数。
      3. 执行 SQL 并返回结果。
5. 结果集映射
  • 作用:将 JDBC 的 ResultSet 转换为 Java 对象。

  • 关键组件ResultSetHandler

  • 映射方式

    • 自动映射(字段名与属性名一致)。
    • 手动配置 ResultMap(处理复杂嵌套对象)。
6. 插件(Plugin)
  • 作用:通过拦截器扩展功能,如分页、SQL 日志、性能监控。

  • 拦截点ExecutorStatementHandlerResultSetHandlerParameterHandler

  • 示例

    @Intercepts({
        @Signature(type = Executor.class, method = "query", args = {...})
    })
    public class LogPlugin implements Interceptor {
        @Override
        public Object intercept(Invocation invocation) {
            System.out.println("SQL 执行日志...");
            return invocation.proceed();
        }
    }
    

三、基础支持层

为上层提供底层基础设施,包含以下模块:

1. 数据源模块
  • 作用:管理数据库连接池(如 Druid、HikariCP)。

  • 配置示例

    <dataSource type="POOLED">
      <property name="driver" value="com.mysql.jdbc.Driver"/>
      <property name="url" value="jdbc:mysql://localhost:3306/test"/>
    </dataSource>
    
2. 事务管理模块
  • 作用:控制事务提交与回滚。

  • 实现类

    • JdbcTransaction:基于 JDBC 的本地事务。
    • ManagedTransaction:由容器(如 Spring)管理事务。
3. 缓存模块
  • 一级缓存SqlSession 级别的缓存,默认开启。
  • 二级缓存:需手动开启,跨 SqlSession 共享。
  • 自定义缓存:支持集成 Redis、Ehcache 等。
4. Binding 模块
  • 作用:将 Mapper 接口与 XML 文件或注解中的 SQL 绑定。
  • 实现原理:动态代理 + 方法签名匹配。
5. 反射模块
  • 作用:动态操作 Java 对象属性,用于参数设置和结果映射。
  • 工具类MetaObjectReflector
6. 类型转换
  • 作用:处理 Java 类型与 JDBC 类型的转换(如 StringVARCHAR)。
  • 组件TypeHandler(如 StringTypeHandlerDateTypeHandler)。
7. 日志模块
  • 作用:记录 SQL 执行日志,支持集成 Log4j、SLF4J 等日志框架。
8. 资源加载
  • 作用:加载配置文件、Mapper XML 等资源文件。
  • 工具类Resources
9. 解析器模块
  • 作用:解析 XML 配置文件(如 mybatis-config.xml)和注解中的 SQL。
  • 关键类XPathParserXMLMapperBuilder

四、架构协作流程图

接口层: SqlSession
核心处理层
配置解析
SQL 解析
参数映射
SQL 执行
结果集映射
插件
基础支持层
数据源模块
事务管理模块
缓存模块
Binding 模块
反射模块
类型转换
日志模块
资源加载
解析器模块

五、架构优势总结

  1. 分层解耦:接口层、核心层、支持层职责清晰,便于扩展和维护。
  2. 灵活控制 SQL:动态 SQL 和手动映射支持复杂场景。
  3. 高效执行:通过批处理、缓存机制优化性能。
  4. 强扩展性:插件机制可定制功能(如分页、审计)。

六、适用场景

  • 复杂查询:多表关联、动态条件拼接。
  • 遗留系统:非标准表结构适配。
  • 高性能批处理:大数据量插入/更新(BatchExecutor)。
  • 定制需求:通过插件实现 SQL 日志、分页等功能。