werkzeug:generate_password_hash()函數如何破解相同密碼設置,驗證用戶對應的“密碼散列值”

接上章節:https://blog.csdn.net/Miao_Hen/article/details/105157765

講述:爲什麼generate_password_hash()函數針對同一密碼,生成不同的“密碼散列值”,而用戶登錄時可以判斷密碼是否正確

清晰的描述:A/B兩個用戶,都設置密碼爲“cat”,但是A/B兩個用戶生成的“password_hash”不一致;當A用戶登錄時,怎麼確定自己再次輸入“cat”,會匹配到正確的“password_hash”?

解答:因爲當用戶調用下方的方法時,並不是將“cat”重新進行加密爲新的“密碼散列值”,而是將數據庫保存的“password_hash”進行反向解碼,確認解碼結果是否和“cat"一致,是:返回True,不是:返回False

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

舉例:

# 模板
class User(UserMixin, db.Model):

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

    def __init__(self, email=None, username=None, password=None):
        self.email = email
        self.username = username
        self.password = password

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

    @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 f'<User {self.username}>'


if __name__ == '__main__':
    u = User(email='[email protected]', username='ddd', password='cat')
    u2 = User(email='[email protected]', username='ddd', password='cat')
    print(u.password_hash)
    print(u2.password_hash)



>>>pbkdf2:sha256:150000$WlU6hKVc$b85531b52dafbead09b983cd6942840ded3fd897bde528531c677cc95046c52e
>>>pbkdf2:sha256:150000$BXGUQbSK$7a8a1e95707688d4f46e4b586ff718e9ead8a3b55a3b60fe8a15cda8ec0cede4

可以看出相同的密碼兩次生成的密碼散列值不一致

此時我們將上述生成的兩個密碼散列值進行驗證,看是否解碼爲“cat”

# 修改上述的verify_password(self, password)函數:

def verify_password(self, password):
    return check_password_hash('pbkdf2:sha256:150000$WlU6hKVc$b85531b52dafbead09b983cd6942840ded3fd897bde528531c677cc95046c52e', password)


def verify_password2(self, password):
    return check_password_hash('pbkdf2:sha256:150000$BXGUQbSK$7a8a1e95707688d4f46e4b586ff718e9ead8a3b55a3b60fe8a15cda8ec0cede4', password)


# 將上次輸出的兩個密碼散列值當做匹配對象

if __name__ == '__main__':
    print(verify_password('cat'))
    print(verify_password2('cat'))


>>>True
>>>True

輸出結果全部爲True,由此可見,進行密碼驗證時,並非將‘輸入密碼’進行加密處理,而是將已經保存的密碼散列值進行反向解密,然後與輸入密碼進行匹配。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章