最佳实践:在表中存储密码的最安全方法?
我正在使用 PHP。我曾经使用本机mysql函数password()来存储密码。有人告诉我,password() 不再安全了。在 PHP 中存储密码的最佳方法是什么?是MD5吗?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
我正在使用 PHP。我曾经使用本机mysql函数password()来存储密码。有人告诉我,password() 不再安全了。在 PHP 中存储密码的最佳方法是什么?是MD5吗?
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
接受
或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
发布评论
评论(6)
2016 年更新答案:
PHC(密码哈希竞赛)的获胜者是 Argon2。截至 2016 年,使用 Argon2 对密码进行哈希处理是最佳实践。
参考实现可在 GitHub 上找到。
2012 年更新答案:
我在下面给出的原始答案曾经被认为是最佳实践。然而,哈希计算技术的进步使得这些方案变得脆弱。展望未来,唯一安全的密码哈希方案是迭代哈希,例如 bcrypt 和 PBKDF2。有关完整讨论,请参阅Jeff Atwood 的分析。
2009 年原始答案:
我建议首先在密码前添加 salt 值,然后是使用相当强大的哈希函数(例如 SHA256。这可以防止明显的(纯文本密码)和不那么明显的(使用 Rainbow 表的攻击 )。
请记住,如果您以这种方式存储密码,您将无法找回用户丢失的密码。他们只能重置密码。这是因为您将使用单向哈希。但为了更安全的密码存储系统,这种限制通常值得权衡。即使您的数据库遭到破坏,攻击者想要恢复您的用户密码仍然非常困难,而且可能不切实际。
Updated Answer 2016:
The winner of the PHC (Password Hashing Competion) was Argon2. Hashing passwords with Argon2 is the best practice as of 2016.
The reference implementation is available on GitHub.
Updated Answer 2012:
The original answer I gave below was once considered to be a best practice. However, advances in hash-computing technology have rendered these schemes vulnerable. Going forward, the only secure password hashing schemes are iterative hashes such as bcrypt and PBKDF2. For a full discussion, see Jeff Atwood's analysis.
Original Answer 2009:
I recommend first prepending a salt value to your password, followed by hashing the resultant string with a reasonably strong hashing function like SHA256. This secures against the obvious (plain text passwords) and the not so obvious (attack using Rainbow tables).
Keep in mind that if you store passwords in this way, you will not be able to retrieve a user's lost password. They'll only be able to reset passwords. This is because you'll be using a one way hash. But this limitation is generally worth the tradeoff for a more secure password storage system. Even if your database is compromised, your user's passwords will still be exceedingly difficult and probably unpractical to recover by a would be attacker.
bcrypt 实际上更安全。请参阅:彩虹表已经足够了:关于安全密码方案您需要了解的内容
bcrypt is actually more secure. See: Enough With The Rainbow Tables: What You Need To Know About Secure Password Schemes
您需要对密码加盐。
vBulletin 在存储密码方面做得非常好。 md5(md5(密码) + 盐);
You need to salt the password.
vBulletin does a pretty good job at storing passwords. md5(md5(password) + salt);
为了与另一个答案争论,VBulletin 在散列密码方面做了一项可怕的工作。它们的盐只有 3 个字符长,只能部分提高应用程序的安全性。
请查看 http://www.openwall.com/phpass/ 。他们在使用每个密码唯一的长哈希以及通过 md5 运行密码数千次方面做得非常出色。它是目前最好的 php 哈希系统之一。
To argue with the the other answer, VBulletin does a horrid job of hashing passwords. Their salt is only 3 characters long, only fractionally increasing the security of your application.
Check out http://www.openwall.com/phpass/ . They do an excellent job of using a long hash, unique to each password, and running the password through md5 thousands of times. It is one of the best hashing systems for php out there.
在我看来,如果您可以避免存储用户密码,那么这是您的最佳选择。使用 OpenId(如 Stackoverflow)对用户进行身份验证。或实时身份验证 (http://dev.live.com/liveid/)。如果您确实非常需要自己对用户进行身份验证;按照亚萨在回答中所说的去做。 :)
If you can avoid storing the user password that's your best option, imo. Use OpenId (like Stackoverflow) to authenticate the user. Or Live Authentication (http://dev.live.com/liveid/). If you really, really need to authenticate the users yourself; do what Asaph says in his answer. :)
盐和哈希。
我们通常使用随机 guid 作为盐,然后使用 SHA512 进行哈希处理。
Salt and hash.
We typically use a random guid as the salt and then SHA512 to hash.