werkzeug generate_password_hash,有什么意义吗?

7

我正在编写一个使用 Werkzeug 哈希函数 的 Python 应用程序。下面是一个示例User 模型:

class User(db.Model):
    __tablename__ = 'users'
    id = db.Column(db.Integer, primary_key=True)
    username = db.Column(db.String(64), unique=True, index=True)
    role_id = db.Column(db.Integer, db.ForeignKey('roles.id'))
    password_hash = db.Column(db.String(128))

    # Custom property getter
    @property
    def password(self):
        raise AttributeError('password is not a readable attribute')

    # Custom property setter
    @password.setter
    def password(self, password):
        self.password_hash = generate_password_hash(password)

    def verify_password(self, password):
        return check_password_hash(self.password_hash, password)

    def __repr__(self):
        return '<User %r>' % self.username

我发现现在数据库中存储的密码已经以哈希方式存储,任何看到哈希值的攻击者都不能在解密之前知道密码。但是,werkzeug哈希函数对于许多应用程序来说是否是一个相当明显的选择呢?攻击者能否使用check_password_hash函数并解密密码呢?

4
我认为您会发现check_password_hash并不是解密密码的功能;我想它是将提供的密码进行哈希处理,并将其与存储的哈希值进行比较(即大致相当于return self.password_hash == generate_password_hash(password))。哈希加盐的目的在于,它是不可逆的;这是哈希,而不是加密。 - jonrsharpe
2
实际上,您可以在文档中查看描述,并在GitHub上的代码中查看。 - jonrsharpe
1
它的工作方式完全相同。这就是为什么在哈希之前加盐,否则某人可以对所有可能的密码运行哈希算法并进行反向查找。该算法是单向的,无法反向运行,这就是重点。请阅读基础知识,那将回答大部分您的问题。 - jonrsharpe
1
@KexAri...你并不愚蠢,但你更像是无法哈希的:D :D :D - Iron Fist
1
不用担心,这并不傻;你只是缺乏所有信息而已。攻击者可以使用该函数来针对哈希测试密码,但这就是为什么我们建议人们使用长而不常见的密码的原因;以增加成功攻击所需的时间,并阻止大多数攻击者。 - jonrsharpe
显示剩余6条评论
1个回答

10

实际上,password_hash 使用单向函数创建不可逆的哈希值。此外,它还添加了一些信息到哈希值中,如哈希算法、盐值、迭代次数和哈希值本身,这就是所存储的内容。password_verify 会使用密码和 password_hash 结果中包含的额外信息重新创建哈希值,并进行比较。

此外,非常重要的一点是,password_hash 对哈希函数进行多次迭代,以使处理时间更长。一个好的值是100毫秒。因此,攻击者能做的最好的事情就是尝试密码以找到匹配的密码,每个尝试都需要花费大量时间。当然,更快的计算系统可以缩短 ~100 毫秒的时间,但成本仍然很高。


为什么这不能在别人的系统上反转?哈希函数是否使用系统特定的秘密密钥? - KexAri
3
密码哈希是不可逆的,这是设计上的要求。在处理过程中,数据会有意地丢失,就像汉堡一样,无法从汉堡中重新创造出原本的牛。 - zaph
2
@KexAri 你无法对土豆进行反哈希操作! - jonrsharpe

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