亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

Bcrypt 加密每次使用相同的輸入都不同

Bcrypt 加密每次使用相同的輸入都不同

Go
FFIVE 2023-03-29 15:27:42
使用golang.org/x/crypto/bcrypt和 GORM ( http://gorm.io/docs/ ) 我正在嘗試加密密碼。問題是它的每次加密每次都不一樣,所以它永遠無法與數據庫中的相匹配。var result []stringpassword := []byte(data.Password)encryptedPassword, err := bcrypt.GenerateFromPassword(password, bcrypt.DefaultCost) // different every timedb.Where(&User{Username: strings.ToLower(data.Username)}).First(&user).Pluck("password", &result)encryptionErr := bcrypt.CompareHashAndPassword(encryptedPassword, []byte(result[0]))if encryptionErr == nil { // passwords match! }我已經確認每次輸入的內容都是一樣的,并且數據庫中給出的密碼是正確的。我在這里做錯了什么?
查看完整描述

2 回答

?
白板的微信

TA貢獻1883條經驗 獲得超3個贊

問題是它的每次加密每次都不一樣,所以它永遠無法與數據庫中的相匹配。

這是正常的 bcrypt 行為。

bcrypt 每次都返回不同的散列,因為它將不同的隨機值合并到散列中。這被稱為“鹽”。它可以防止人們使用“彩虹表”攻擊您的散列密碼,這是一個預先生成的表,將密碼散列映射回他們的密碼。salt 意味著密碼不是一個散列,而是 2^16 個。太多無法存儲。

鹽作為散列密碼的一部分存儲。因此bcrypt.CompareHashAndPassword(encryptedPassword, plainPassword)可以plainPassword使用相同的鹽進行加密encryptedPassword并進行比較。

我在這里做錯了什么?

您正在嘗試將生成的散列密碼與存儲的散列密碼進行比較。至少我當然希望它是存儲在數據庫中的散列密碼。

相反,您想要的是將存儲的散列密碼與用戶輸入的普通密碼進行比較。

// Normally this comes from user input and is *never* stored

plainPassword := "supersekret"


// The encrypted password is stored in the database

db.Where(&User{Username: strings.ToLower(data.Username)}).First(&user).Pluck("password", &result)

encryptedPassword := []byte(result[0])


// Check if the stored encrypted password matches "supersekret"

encryptionErr := bcrypt.CompareHashAndPassword(encryptedPassword, plainPassword)

if encryptionErr == nil {

? ? fmt.Println("Greetings Professor Falken")

} else {

? ? fmt.Println(encryptionErr)

}


查看完整回答
反對 回復 2023-03-29
?
德瑪西亞99

TA貢獻1770條經驗 獲得超3個贊

bcrypt散列算法在設計上會在您每次調用它時生成一個不同的加密字符串(它是加鹽的)。如果您有要檢查的明文密碼和數據庫中的密文,您應該能夠將這兩件事傳遞給bcrypt.CompareHashAndPassword.?調整您的代碼:


var result []string

db.Where(&User{Username: strings.ToLower(data.Username)})

? ? ? ? .First(&user)

? ? ? ? .Pluck("password", &result)


encryptionErr := bcrypt.CompareHashAndPassword([]byte(result[0]), []byte(data.Password))

您不需要bcrypt.GenerateFromPassword再打電話;正如您所注意到的,它將生成一個不同的加密密碼,并且幾乎不可能比較兩者是否相等。


查看完整回答
反對 回復 2023-03-29
  • 2 回答
  • 0 關注
  • 908 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號