温馨提示×

温馨提示×

您好,登录后才能下订单哦!

密码登录×
登录注册×
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》

如何防范动态SQL注入

发布时间:2026-07-14 08:31:11 来源:亿速云 阅读:95 作者:小樊 栏目:数据库

防范动态 SQL 注入的核心原则是:永远不要相信用户输入,永远不要把用户输入直接拼进 SQL。下面从原理、常见场景和防护措施三个层面系统说明。


一、什么是动态 SQL 注入

动态 SQL 指的是在代码中拼接字符串生成 SQL 语句,例如:

"SELECT * FROM user WHERE name = '" + userName + "'"

如果 userName 来自用户输入,攻击者可以输入:

' OR '1'='1

最终 SQL 变成:

SELECT * FROM user WHERE name = '' OR '1'='1'

导致绕过认证、越权查询、数据泄露甚至删库


二、最常见的错误写法(高危)

❌ 字符串拼接(任何语言都一样危险)

String sql = "SELECT * FROM user WHERE id = " + id;
$sql = "SELECT * FROM user WHERE name = '$name'";
sql = f"SELECT * FROM user WHERE id = {uid}"

三、正确防范方式(按优先级)

✅ 1. 使用 参数化查询 / 预编译语句(首选)

这是最有效、最通用的防护手段。

Java(JDBC / MyBatis)

PreparedStatement ps =
    conn.prepareStatement("SELECT * FROM user WHERE id = ?");
ps.setInt(1, id);

MyBatis(正确写法)

<select id="getUser">
  SELECT * FROM user WHERE id = #{id}
</select>

#{} 是参数化
${} 是字符串替换(容易注入)


PHP(PDO)

$stmt = $pdo->prepare("SELECT * FROM user WHERE id = ?");
$stmt->execute([$id]);

Python

cursor.execute("SELECT * FROM user WHERE id = %s", (user_id,))

✅ 2. 使用 ORM 框架(天然防注入)

ORM 会自动参数化 SQL:

  • Java:Hibernate、JPA
  • Python:SQLAlchemy、Django ORM
  • JS:Sequelize、Prisma
  • PHP:Eloquent
User.objects.get(id=user_id)

只要不手写 SQL,基本安全


✅ 3. 输入校验 + 白名单(辅助手段)

适用于:

  • 排序字段
  • 表名
  • 字段名(不能参数化)
Set<String> allowSort = Set.of("id", "create_time");
if (!allowSort.contains(sortField)) {
    throw new IllegalArgumentException();
}

只允许“确定安全的值”


✅ 4. 最小权限原则

数据库账号权限最小化:

  • 查询接口 → 只读账号
  • 后台系统 → 限制 DROP / DELETE
  • 禁止应用账号执行:
    DROP TABLE
    xp_cmdshell
    

✅ 5. 关闭错误信息回显

  • 不把 SQL 异常直接返回给前端
  • 防止攻击者通过报错推断表结构

四、MyBatis / 动态 SQL 特别注意事项

❌ 错误(高危)

<if test="name != null">
  AND name = '${name}'
</if>

✅ 正确

<if test="name != null">
  AND name = #{name}
</if>

五、常见误区

误区 说明
用正则过滤单引号 ❌ 可被绕过
前端校验 ❌ 不可信
转义字符 ❌ 不可靠
参数化 + 拼接 ❌ 仍可能注入

六、总结一句话

防动态 SQL 注入 = 参数化查询 + 不拼接 SQL + 白名单校验 + 最小权限

如果你愿意,我可以:

  • 帮你 审计一段具体代码
  • 针对 Java / MyBatis / Spring Boot / PHP / Python 给更细化的方案
  • 模拟一次 SQL 注入攻击过程,让你更直观理解

只要把场景发我即可。

向AI问一下细节

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

AI