MyBatis 知识体系概览
什么是 MyBatis?
MyBatis 是 Java 世界中最流行的半自动 ORM(对象关系映射)框架——它不像 Hibernate 那样完全自动生成 SQL,而是让开发者手写 SQL 并与 Java 对象映射,兼顾了灵活性和效率。
ORM(Object-Relational Mapping,对象关系映射)是将数据库的表和行映射为 Java 的类和对象。没有 ORM 时,你需要手动写 JDBC 代码:获取连接 → 创建 Statement → 执行 SQL → 遍历 ResultSet → 封装为对象 → 关闭连接。ORM 框架帮你自动完成这些"苦力活"。
MyBatis 在国内的使用率远超 Hibernate / JPA——因为国内业务系统 SQL 往往很复杂(多表 JOIN、动态条件、分库分表),手写 SQL 比自动生成更可控。
MyBatis 的执行流程
- 调用 Mapper 接口方法(如
userMapper.findById(1)) - MyBatis 通过 JDK 动态代理生成 Mapper 接口的实现类
- 根据方法名找到对应的 SQL 语句(XML 或注解中定义)
- Executor 执行 SQL,经过 StatementHandler → ParameterHandler → ResultSetHandler
- 将
ResultSet映射为 Java 对象返回
核心知识点
#{} 与 ${} ——最常考的基础问题
| 语法 | 原理 | 安全性 |
|---|---|---|
#{} | 预编译,使用 ? 占位符,通过 PreparedStatement 设值 | ✅ 防 SQL 注入 |
${} | 字符串拼接,直接替换进 SQL | ❌ 有 SQL 注入风险 |
绝大多数情况下使用 #{}。${} 仅在需要动态表名、列名等不能用占位符的场景使用。
动态 SQL——灵活的条件查询
MyBatis 提供了一套 XML 标签来构建动态 SQL,避免手动拼接字符串:
<select id="findUsers" resultType="User">
SELECT * FROM user
<where>
<if test="name != null">AND name = #{name}</if>
<if test="age != null">AND age = #{age}</if>
<if test="status != null">AND status IN
<foreach collection="status" item="s" open="(" separator="," close=")">
#{s}
</foreach>
</if>
</where>
</select>
<where> 标签会自动处理多余的 AND/OR,<foreach> 用于 IN 条件和批量操作。
缓存机制——一级缓存与二级缓存
| 缓存 | 作用域 | 默认状态 | 说明 |
|---|---|---|---|
| 一级缓存 | SqlSession 级别 | 默认开启 | 同一个 SqlSession 内相同查询直接返回缓存 |
| 二级缓存 | Mapper(namespace)级别 | 默认关闭 | 跨 SqlSession 共享,需手动开启 |
一级缓存在 Spring 中每个请求对应不同的 SqlSession,基本不生效。二级缓存在多表关联查询时容易出现脏读(A 表的 Mapper 缓存了结果,B 表更新后 A 的缓存没失效)。生产环境通常不使用 MyBatis 二级缓存,而是用 Redis 做应用层缓存。
插件机制——拦截器扩展
MyBatis 允许通过拦截器(Interceptor) 对 SQL 执行过程进行拦截和增强,最典型的应用是 PageHelper 分页插件——拦截查询语句,自动改写为分页 SQL(添加 LIMIT)。
MyBatis-Plus——"增强版"MyBatis
MyBatis-Plus 在 MyBatis 基础上提供了通用 CRUD、条件构造器、代码生成器等功能,减少了样板代码。简单的单表 CRUD 不再需要写 XML:
// 条件查询,无需写 SQL
List<User> users = userMapper.selectList(
new LambdaQueryWrapper<User>()
.eq(User::getStatus, 1)
.ge(User::getAge, 18)
.orderByDesc(User::getCreateTime)
);
学习建议
- 基础使用 → Mapper 接口 + XML 映射
- 执行流程 → 从接口调用到 SQL 执行的全链路
- 动态 SQL → if/where/foreach 等标签
- 缓存机制 → 一级缓存/二级缓存的原理与陷阱
- 插件机制 → PageHelper 原理、自定义拦截器
- MyBatis-Plus → 提效工具