MongoDB实际上不是存储明文密码吗?

信息安全 验证 mongodb
2021-09-09 02:26:37

根据 http://docs.mongodb.org/meta-driver/latest/legacy/implement-authentication-in-driver/的文档:

然后驱动程序为要进行身份验证的数据库运行身份验证命令。验证命令具有以下语法:

db.runCommand( { authenticate : 1, user : <username>, nonce : <nonce>, key : <digest> }

<username> 是数据库的 system.users 集合中的用户名。

<nonce> 是从前一个 getnonce 步骤返回的随机数。

<digest>MD5 消息摘要的十六进制编码。

MD5 消息摘要是 , , 的串联<nonce><username>MD5哈希<password_digest>

是与数据库集合中的 相关联字段中<password_digest>的值。是的十六进制编码pwd<username>system.userspwdMD5( <username> + ":mongo:" + <password_text> )

这意味着散列实际上是在客户端完成的,因为驱动程序是用于数据库连接的客户端的一部分。为了进行身份验证,客户端不需要证明对密码的了解,而是对存储的散列的了解。所以,真正的密码是存储的散列,它恰好是通过散列生成的。该真实密码以明文形式存储在pwd.system.users

我读错了吗?有没有办法保护这种身份验证?

2个回答

从某种意义上说,这可以被认为是正确的。

根据我从 MongoDB 文档中了解到的情况,db.addUser()期望传递一个已经散列的密码。从函数的文档中可以清楚地看到这一点,其中pwd字段的预期数据类型是hash.

我将其读作 MongoDB,希望系统在数据库中用户注册或身份验证之前执行散列。当您认为 MongoDB 用户很可能不会手动输入密码哈希时,这是有道理的。这些用户帐户的用例是作为应用程序的身份验证凭据,因此密码肯定会存储在某个配置文件中。

企业MongoDB 支持使用 Kerberos 进行身份验证。设置 Kerberos 的步骤也可以在文档中找到。如果您真的担心这是一个安全因素,您应该考虑设置 Kerberos。

MongoDB 不以明文形式存储密码。从 MongoDB 3.0 开始,Salted Challenge Response Authentication Mechanism (SCRAM) 是 MongoDB 的默认身份验证机制。Scram 支持 SCRAM-SHA-1 和 SCRAM-SHA-256 散列机制。

话虽如此,当通过驱动程序与数据库交互时,它们通常接受散列密码,因此它不会以明文形式传入和传出数据库。这给开发人员带来了额外的责任,因为他/她必须使用与数据库服务器中使用的相同算法在他们的末端执行散列。幸运的是,这些对于几乎任何编程语言都是现成的。

查询 system.users 集合将返回一个类似这样的文档:

{
  "_id": "admin.123",
  "user": "123",
  "db": "admin",
  "credentials": {
    "SCRAM-SHA-1": {
      "iterationCount": 10000,
      "salt": "f9SdPCCcBOwk71/xDkj6Sw==",
      "storedKey": "83mNhTYctOdlYsL1sbnfpiA0uxw=",
      "serverKey": "09H9aEKKufaoCDxqUkHntx6EqrE="
    }
  },
  "roles": []
}

您可以使用好的数据库管理工具(例如Navicat for MongoDB )深入研究用户和其他集合。它允许您以三种格式查看文档:树、JSON 和网格:

Navicat 视图

希望这能回答你的问题。