🚫 MyBatis-Plus 防止 SQL 注入最佳实践指南
作者:William Dawson
标签:Java、MyBatis-Plus、安全、SQL 注入、防护
💥 什么是 SQL 注入?
SQL 注入是一种常见的安全漏洞,攻击者通过恶意构造 SQL 输入参数,干扰原有查询逻辑,进而非法访问、修改、甚至删除数据库内容。
举个例子:
SELECT * FROM user WHERE name = '' OR '1'='1'
这种语句如果没有做输入过滤,就可能返回整个用户表。
🛡 MyBatis-Plus 如何应对 SQL 注入?
MyBatis-Plus(简称 MP)在设计上遵循 MyBatis 的安全原则,默认会将参数作为预编译处理(使用 ?
占位符绑定参数),对常见的注入场景已经有良好的防护能力。
但!开发者自己拼接 SQL 或处理字段名时,仍然可能埋下安全隐患。
✅ 正确使用 MP 防注入的 5 个实战技巧
1️⃣ 永远使用 #{}
,而不是 ${}
// ❌ 有风险(拼接字符串)
@Select("SELECT * FROM user WHERE name = ${name}")// ✅ 推荐(参数绑定)
@Select("SELECT * FROM user WHERE name = #{name}")
#{}
是预编译参数,自动处理 SQL 注入
${}
是直接拼接字符串,完全不安全!
2️⃣ 优先使用 Wrapper 条件构造器
MyBatis-Plus 提供的 QueryWrapper
和 LambdaQueryWrapper
是构建查询语句的利器,自动处理参数绑定,避免手动拼接 SQL。
QueryWrapper<User> wrapper = new QueryWrapper<>();
wrapper.eq("username", username); // 自动参数绑定userMapper.selectList(wrapper);
3️⃣ 使用 Lambda 表达式防止拼接字段名
// ✅ 推荐
LambdaQueryWrapper<User> wrapper = new LambdaQueryWrapper<>();
wrapper.eq(User::getUsername, username);
Lambda 方式能避免拼接字段名带来的注入风险,也能在字段名变更时自动更新。
4️⃣ 对动态字段 / 排序字段做白名单校验
// 用户传入排序字段
String sortField = "price"; // 比如来自前端参数// ✅ 白名单验证
List<String> allowedFields = Arrays.asList("price", "create_time", "sales");
if (!allowedFields.contains(sortField)) {throw new IllegalArgumentException("非法字段!");
}queryWrapper.orderByAsc(sortField);
任何“用户可控的 SQL 结构部分”(如字段名、表名)都需要你手动过滤!
5️⃣ 避免拼接完整 SQL
// ❌ 高危操作
String sql = "SELECT * FROM user WHERE " + userInput;
可以考虑使用 XML 配置 + #{} 参数绑定
或 Wrapper 来组合条件。
🚨 特殊场景警告
- ⚠ 动态 SQL、批量查询
IN (${ids})
中使用${}
特别容易出问题 - ⚠ 条件字段、排序字段、表名、列名:不要从用户输入直接拼接
- ⚠ 不要相信前端传来的所有参数
🔒 额外建议
- ✅ 使用 ORM 框架本身的构建器(Wrapper / Lambda)
- ✅ 所有用户输入参数都进行正则或白名单校验
- ✅ 使用数据库账户权限控制,限制写/删权限
- ✅ 配合使用代码审查工具(如 SonarQube)检查 SQL 风险
📌 总结
防护点 | 是否安全 | 建议做法 |
---|---|---|
使用 #{} | ✅ | 安全,使用参数绑定 |
使用 ${} | ❌ | 高风险,避免使用 |
条件构造器 Wrapper | ✅ | 推荐使用,自动处理绑定 |
拼接字段名 / 排序字段 | ⚠ | 使用白名单验证 |
拼接完整 SQL 语句 | ❌ | 尽量避免,转为 XML 或 Wrapper 构建 |
📚 推荐阅读
- MyBatis-Plus 官方文档
- OWASP SQL Injection 指南
- Java Web 安全编码规范
想要构建高质量、安全的 Java 后台系统,安全从参数开始,MyBatis-Plus 是你的好帮手,但“防注入”的责任仍然在开发者手中。
如果你喜欢这篇文章,欢迎点赞、收藏或关注我持续更新更多 Java / 后端 / 安全开发干货 👇
📬 有问题也可以评论区一起交流~