[英]Best way to store hashed passwords and salt values in the database - varchar or binary?
一旦我生成了一個鹽並散列密碼(使用bcrypt等),最好將結果存儲為數據庫中的字符串或字節數組? 這兩種方式都有什么好處嗎? 或者這是一個更主觀的決定?
VARCHAR應該足夠了。 在我看來,VARCHAR數據將更容易消費並與二進制文件一起使用。
內置的ASP.NET成員資格提供程序還將散列密碼存儲為VARCHAR字段。
如果使用VARCHAR,請確保字節是有效字符,或者在保存哈希值和salt之前將字節強制為ASCII。 為了使數據損壞更安全,您可能希望在將它們存儲在VARCHAR字段中之前對Base64或Hexadecimal中的字節進行編碼。
例如,如果存儲MD5或SHA1的byte[]
輸出,則當byte[]
轉換為text時,某些字節值可能會被刪除或替換,因此它們不是UTF-8 / Unicode。 如果您使用ASCII,這不應該是一個問題,但它仍然可能導致數據損壞。
如果您不想處理Hex,可以使用構建在框架中的這個base64方法Convert.ToBase64String 。
如果您使用VARBINARY並且不嘗試使用和文本編碼方法,則此問題不應存在,但可能會使哈希比較困難。
...請注意,如果您使用NVARCHAR
,則仍可能發生此數據損壞...
static void Main(string[] args)
{
var salt = "MySalt";
var password = "MyPassword";
var saltedKey = CalculateHash(salt, password);
Console.WriteLine(saltedKey);
// MySalt$teGOpFi57nENIRifSW3m1RQndiU=
var checkHash = CheckHash(saltedKey, password);
Console.WriteLine(checkHash);
// True
}
private static string CalculateHash(string saltOrSaltedKey, string password)
{
var salt =
saltOrSaltedKey.Contains('$')
? saltOrSaltedKey.Substring(0, saltOrSaltedKey.IndexOf('$') + 1)
: saltOrSaltedKey + '$';
var newKey = Encoding.UTF8.GetBytes(salt + password);
var sha1 = SHA1.Create();
sha1.Initialize();
var result = sha1.ComputeHash(newKey);
// if you replace this base64 version with one of the encoding
// classes this will become corrupt due to nulls and other
// control character values in the byte[]
var outval = salt + Convert.ToBase64String(result);
return outval;
}
private static bool CheckHash(string saltedKey, string password)
{
var outval = CalculateHash(saltedKey, password);
return outval == saltedKey;
}
大多數md5 / sha1庫返回哈希base64編碼,在這種情況下varchar就足夠了
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.