На моем предыдущем выступлении мы сохранили пароль как хешированное / зашифрованное / соленое значение (используя MD5 в то время) как VARBINARY(32)
.Чтобы сравнить пароль позже, вместо того, чтобы пытаться расшифровать пароль, мы сравнили бы зашифрованное + соленое значение, которое мы сохранили, с зашифрованным + соленым значением пароля, который пытался.Если они совпадали, они входили, если они не совпадали, они не входили.
Хеширование выполнялось на среднем уровне (как для первоначального сохранения пароля, так и для сравнения позже),но пример на основе SQL Server (, чтобы остановить ворчание @ Yahia, это не означает, что вы можете сказать самый безопасный способ, я просто иллюстрирую методологию на очень легком примере. MD5 недостаточно силен для вас?может использовать другой и более сложный алгоритм наряду с более продвинутыми методами посола, особенно если вы выполняете хеширование на уровне приложения ):
CREATE TABLE dbo.Users
(
UserID INT IDENTITY(1,1) PRIMARY KEY,
Username NVARCHAR(255) NOT NULL UNIQUE,
PasswordHash VARBINARY(32) NOT NULL
);
Процедура создания пользователя (без обработки ошибок илипредотвращение дублирования, просто псевдо).
CREATE PROCEDURE dbo.User_Create
@Username NVARCHAR(255),
@Password NVARCHAR(16)
AS
BEGIN
SET NOCOUNT ON;
DECLARE @salt NVARCHAR(16) = '$w0rdf1$h';
INSERT dbo.Users(Username, Password)
SELECT @Username,
CONVERT(VARBINARY(32), HASHBYTES('MD5', @Password + @Salt));
END
GO
Теперь процедура аутентификации пользователя.
CREATE PROCEDURE dbo.User_Authenticate
@Username NVARCHAR(255),
@Password NVARCHAR(16)
AS
BEGIN
SET NOCOUNT ON;
DECLARE @salt NVARCHAR(16) = '$w0rdf1$h';
IF EXISTS
(
SELECT 1 FROM dbo.Users
WHERE Username = @Username AND
PasswordHash = CONVERT(VARBINARY(32), HASHBYTES('MD5', @Password + @salt))
)
BEGIN
PRINT 'Please, come on in!';
END
ELSE
BEGIN
PRINT 'You can keep knocking but you cannot come in.';
END
END
GO
На самом деле вы, скорее всего, выполняете хеширование в приложении и передаете значения хеш-функции.в качестве VARBINARY (32) - это значительно затрудняет "прослушивание" действительного пароля в открытом виде из любого места.И вы, возможно, не будете хранить соль в виде простого текста с кодом, но получите ее из другого места.
Это определенно более безопасно, чем хранение незашифрованного пароля, но устраняет возможность извлечения пароля.,Беспроигрышный на мой взгляд.