我正在和MySQL一起建立一个姜戈网站。我已经决定使用Django内置的pbkdf2-sha256和随机生成的salt散列来存储用户的密码。
然而,这个网站还需要存储许多其他网站(不使用oauth)的第三方登录凭据。所以我正在研究AES-256加密,当然问题是在哪里安全地存储加密密钥。
现在我的解决方案是:让每个加密密钥=用户实际密码的散列和一个随机生成的盐(不同于已经用于密码存储散列的盐)。盐将存储在表中,而实际的密码和散列显然不是。因此,加密密钥将在登录时生成并临时存储,但在注销时过期。此外,如果不破解原始的pbkdf2-sha256散列,就无法生成加密密钥,即使这样,也只能为该用户生成加密密钥,而不是通用密钥。
缺点是,如果他们更改/重置密码,他们将不得不重新输入每个站点的凭据。但这并不是什么大问题,而且似乎比将密钥存储在服务器上的某个地方甚至是另一个服务器更安全。
但是我24小时前才知道哈希是什么,所以我知道什么呢?我是否忽略了什么,或者这是合理的安全吗?还是有更好的方法?
发布于 2013-06-22 02:18:52
您提到的算法PBKDF2实际上就是为这个明确的目的而设计的。
因此,工作流程将是生成一个随机的盐。然后将其存储在数据库中供用户使用。
使用具有高迭代计数的PBKDF2和salt,生成640位密钥材料(80字节)。
前128位成为密码的IV
接下来的256位成为加密密钥(AES-256使用的密钥)
最后256位成为MAC密钥(用于验证加密的密钥)。
key = PBKDF2-SHA256(password, salt, 50000, 80)
iv = key[0:128]
cipherKey = key[128:384]
macKey = key[384:640]然后,使用这些密钥(伪代码)加密数据:
ciphertext = AES-256-CBC(data, cipherKey, iv)
authtext = SHA256-HMAC(ciphertext, macKey)
result = '{}{}'.format(authtext, ciphertext)现在,在解密时,只需反向走回...
key = PBKDF2-SHA256(password, salt, 50000, 80)
iv = key[0:128]
cipherKey = key[128:384]
macKey = key[384:640]
authtext = result[0:32]
ciphertext = result[32:]
if !timingSafeComparison(authtext, SHA256-HMAC(ciphertext, macKey)):
return false
return AES-256-CBC-DECRYPT(ciphertext, cipherKey, iv)是的,如果你的用户忘记了密码,所有加密的数据都会消失。但这就是你想要的,对吧?
https://stackoverflow.com/questions/12935409
复制相似问题