Python - 使用 scrypt 存储密码的正确方法?
Python - Proper way to store passwords with scrypt?
我不明白我应该如何使用 scrypt 存储散列密码。
示例如下:
import pyscrypt
hashed = pyscrypt.hash(password = b"password",
salt = b"seasalt",
N = 1024,
r = 1,
p = 1,
dkLen = 16)
print(hashed.hex()) #70ac953b777e24c4f41c4657eb9f03c2
hashed = pyscrypt.hash(password = b"password",
salt = b"seasalt",
N = 1024,
r = 2,
p = 1,
dkLen = 16)
print(hashed.hex()) #b00b951cd50675806c55d903dba9cbca
hashed = pyscrypt.hash(password = b"password",
salt = b"seasalt",
N = 1024,
r = 1,
p = 2,
dkLen = 16)
print(hashed.hex()) #7c3fa22552c8a9071da0e8c80a0a2767
在上面的示例中,我们可以看到散列根据参数 N, r, p
值发生变化。
这是否意味着我也应该在数据库中保存 N, r, p
个值?
将来市场上会出现更强大的硬件,我该怎么办?例如,要求用户更改密码以便应用新的哈希函数或其他什么?
最重要的是,您必须为每个用户存储 salt
。
因此,您的记录通常如下所示:
username: scrypt,params,seasalt,89435389985698348998364
(您希望显式存储记录的类型,以防使用其他机制,更早进行迁移,或者通常更晚)
是的,您需要将用于生成哈希的参数与哈希一起存储。通常最容易将它们唯一地连接成一个字符串,例如N|r|p|len|salt|hash
,或者 JSON 编码字典。您还必须为每个密码生成一个唯一的随机盐。
未来的升级可以在用户登录时处理。伪代码:
if login_successful:
if not params_up_to_date(hashed_password):
hashed_password = hash(entered_password)
# update database record
您检查散列密码的参数是否与您当前使用的相同,如果不相同,则重新散列您刚刚在登录过程中使用的密码。用户可以通过这种方式逐步、透明地升级。
我不明白我应该如何使用 scrypt 存储散列密码。
示例如下:
import pyscrypt
hashed = pyscrypt.hash(password = b"password",
salt = b"seasalt",
N = 1024,
r = 1,
p = 1,
dkLen = 16)
print(hashed.hex()) #70ac953b777e24c4f41c4657eb9f03c2
hashed = pyscrypt.hash(password = b"password",
salt = b"seasalt",
N = 1024,
r = 2,
p = 1,
dkLen = 16)
print(hashed.hex()) #b00b951cd50675806c55d903dba9cbca
hashed = pyscrypt.hash(password = b"password",
salt = b"seasalt",
N = 1024,
r = 1,
p = 2,
dkLen = 16)
print(hashed.hex()) #7c3fa22552c8a9071da0e8c80a0a2767
在上面的示例中,我们可以看到散列根据参数 N, r, p
值发生变化。
这是否意味着我也应该在数据库中保存 N, r, p
个值?
将来市场上会出现更强大的硬件,我该怎么办?例如,要求用户更改密码以便应用新的哈希函数或其他什么?
最重要的是,您必须为每个用户存储 salt
。
因此,您的记录通常如下所示:
username: scrypt,params,seasalt,89435389985698348998364
(您希望显式存储记录的类型,以防使用其他机制,更早进行迁移,或者通常更晚)
是的,您需要将用于生成哈希的参数与哈希一起存储。通常最容易将它们唯一地连接成一个字符串,例如N|r|p|len|salt|hash
,或者 JSON 编码字典。您还必须为每个密码生成一个唯一的随机盐。
未来的升级可以在用户登录时处理。伪代码:
if login_successful:
if not params_up_to_date(hashed_password):
hashed_password = hash(entered_password)
# update database record
您检查散列密码的参数是否与您当前使用的相同,如果不相同,则重新散列您刚刚在登录过程中使用的密码。用户可以通过这种方式逐步、透明地升级。