我的 mysql 数据库中有一个包含密码列的用户表。目前,我使用 MD5 算法对用户密码进行哈希处理以存储在数据库中。现在我喜欢认为我是一个有安全意识的人。我在阅读 MySQL 文档时注意到他们不推荐 MD5 或 SHA/SHA1 散列方法,但不提供替代方法。
在 MySQL 中散列密码的最佳方法是什么?在我当前的实现中,PHP 和 MySQL 原生支持的函数将是理想和必要的。
谢谢!
不一定你不应该使用 MD5,而是你不应该只使用MD5,因为这会使你容易受到彩虹表攻击(彩虹表是预先计算的哈希值表 - 如果你的密码是偶数远程常见或简单,攻击者只需要查找哈希值,他就知道你的明文密码。)
至少你应该为每个密码添加一个盐,这样任何现有的彩虹表都是无用的,迫使攻击者为你的密码数据库生成一个全新的彩虹表。
更好的办法是对数据库中的每个密码使用不同的盐,比如与之关联的用户名,这样攻击者甚至无法为您的整个数据库生成彩虹表,而必须分别破解每个条目。
MD5 也是一种非常快速的算法。速度是破解的敌人——生成哈希所需的时间越长,黑客每次尝试所需的时间就越长。对于登录到您的网站的用户来说,像每次使用新的额外盐对纯文本进行 100 次散列处理这样简单的操作几乎无法察觉(如果有的话),但它会增加暴力破解密码所需的时间。 100 次。
这里有更多详细信息:http: //www.codinghorror.com/blog/archives/000953.html
按照今天的标准,MD5 被认为是弱的。破解使用 MD5 生成的哈希仍然需要一些工作,但它比通过暴力猜测密码要容易几倍。理想情况下,破解哈希不应该比蛮力更容易。
SHA1 也被认为比暴力猜测密码更容易破解。
实际上,我为 MySQL 贡献了一个补丁,以显示来自 OpenSSL 的 SHA224、SHA256、SHA384 和 SHA512 函数。NIST 推荐这些用于密码散列(实际上是 SHA256 和更高版本)。
我的补丁是由 MySQL 工程师完成的,如果我记得的话,它包含在 MySQL 6.0.5 及更高版本中。
如果您使用早期版本的 MySQL(而谁不使用),那么您可能可以在您的宿主语言中使用强散列函数的实现。例如, PHP 具有该hash()
功能。您可以在应用程序中进行散列处理并将生成的消息字符串保存到数据库中。
别忘了做盐腌!
这个问题是7岁。在那段时间里,我们在计算方面取得了进步,MD5 和 SHA1 现在很容易被现代计算机破解。现在应该避免这些。
PHP 5.5 引入了password_hash,它使用更安全的 bcrypt 算法。虽然 MySQL 可以加密/解密 bcrypt,但这是一个糟糕的解决方案,因为您不仅会为数据库层添加潜在的大型计算负载,而且未经哈希处理的密码可能会存储在您的日志中
在任何情况下,明文密码都不应该命中 MySQL,即使是在查询级别。否则,您可能会将密码写入日志(查询日志、一般日志、慢查询日志等)。这太可怕了。所以不,甚至不要打扰...
我正在使用组合。例如SHA1(MD5())工作正常。