Если вы используете VARCHAR, либо убедитесь, что байты являются допустимыми символами, либо принудительно передайте байты в ASCII, прежде чем сохранять хеш и соль.Чтобы защитить данные от повреждения, вы можете захотеть либо кодировать байты в Base64, либо в шестнадцатеричном формате, прежде чем сохранять их в поле VARCHAR.
Например, если вы сохраняете вывод byte[]
из MD5 или SHA1 некоторые байтовые значения могут быть удалены или заменены, когда byte[]
преобразуется в текст, если они недопустимы в кодировке 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;
}