网站用户重置密码的安全高效方法是什么?

5
许多网站实现了不同的方法,我很难决定哪种方法适用于我的网站。
我的用户资料包含以下数据:
username
password (in hash/digest form)
email

我希望密码重置方法既安全,又用户友好且高效。
3个回答

8
您应该添加两个字段,reset_code和reset_expiry。
这是一个安全的密码重置功能流程:
1. 用户选择“忘记密码”。 2. 用户被要求输入电子邮件/用户名。 3. 如果有效,则生成GUID,并将其存储在reset_code中,并将Now()+24小时存储在数据库中的reset_expiry中,针对特定的用户。 4. 然后,它会向电子邮件地址发送一封电子邮件,其中包含确认密码重置的链接。此电子邮件将包含一个带有用户的用户名和reset_code嵌入的指向您网站的链接。(这可以防止恶意用户仅凭知道其电子邮件即可重置第三方的密码) 5. 一旦用户点击电子邮件中的链接,他们将被引导到您的网站。 6. 您的网站将验证:用户名和reset_code是否匹配,并且当前时间是否超过了reset_expiry时间。 7. 如果一切正常,我们可以完成密码重置。这可以通过以下任何一种方式完成: a) 在屏幕上显示新生成的随机密码 b) 通过电子邮件发送新生成的随机密码 c) 允许用户输入自己选择的密码

4
如果使用随机生成的密码,请确保调整复杂度以匹配您用户的能力水平,即如果你的用户不是非常擅长电脑操作,不要使用太多的非字母数字字符。此外,请确保从输入的密码中删除空格,因为它们很可能会从电子邮件中被复制粘贴,并且通常会带有额外的空格。 - Matt Lacey
1
一些字符限制和替换也是很好的主意:从字符列表中删除 {0,1,2,3,5,l},将所有内容改为小写并应用映射像 [0,1,2,3,5,l] -> [o,i,z,b,s,i] 到从用户回传的密码上。 "3" 在那里是因为在没有熟悉的上下文情况下,"B" 经常被误认为是 "3",其他字符应该是清晰明了的。 - mu is too short

7
您不应该存储用户的密码,即使是加密形式。您只需存储用于身份验证的哈希/摘要。然后,您无法“恢复”密码(因为您不知道它),您只能重置密码,并/或者给用户一个临时的一次性密码,以便他设置新密码。
更新:如果您正在执行上述操作,则标准程序是拥有一个“要求密码重置”的表单。用户输入其ID(通常是电子邮件),生成一个“令牌”(例如,随机字符串),存储在某个表格中,并发送到他的电子邮件中,同时附带一个链接到“密码重置”表单。在此表单中,检查令牌,允许用户输入新密码,并指示尝试新登录。
更新2:可能会出现小的隐私问题:如果请求表单中输入的用户ID(电子邮件、用户名或其他)在我们的数据库中不存在怎么办?输出消息“用户不存在。检查ID并重试。”可能没问题,但在某些情况下,这可能会导致隐私问题:任何人都可以检查其他人是否在您的数据库中注册!如果您想避免这种情况,请输出相同的消息(“已发送一封电子邮件,其中包含说明...”),即使未找到用户(因此实际上没有发送邮件)。
类似的隐私问题建议在用户尝试登录失败时只输出消息“登录不正确:用户或密码错误”,而不要透露是错误的用户还是密码。

抱歉,实际上我确实存储了哈希/摘要,所谓的恢复是指重置 :) - TheOne
+1. @Absolute0:想一想如果有人盗取了你的密码数据库会发生什么。如果密码已经被哈希,那么损失不大(你已经被攻击者控制了,但至少攻击者不能使用密码数据库做任何事情)。然而,如果你存储了密码,并且如果你的用户在你的网站和他们的电子邮件中使用相同的密码(他们会这样做),那么当他们的电子邮件也被黑客攻击时,他们会责怪你... - psmears
@Absolute0: 不好意思,碰巧跟你的评论重复了 - 很高兴听到你正在做正确的事情 :) - psmears

0

我同意Leonbloy的观点。存储密码会导致麻烦,就像几周前的Gawker事件一样(1.5百万个用户ID/密码组合被发现并公开)。

然而,您应该有一个“重置密码”功能,该功能会将新密码发送到用于打开帐户的原始电子邮件地址。

在密码重置期间不应提供更改电子邮件地址的选项。如果用户不再能够访问旧电子邮件帐户,那就太糟糕了。放弃该帐户并重新开始。

并且在重置屏幕上使用良好的验证码。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接