Вот как я создаю пользователя для загрузки моей базы данных
if (!context.Users.Any())
{
var userStore = new UserStore<ApplicationUser>(context);
var userManager = new UserManager<ApplicationUser>(userStore);
userManager.Create(user, "P@ssw0rd");
context.AspNetUsersExtendedDetails.AddOrUpdate(userExtended);
context.SaveChanges();
}
Проблема возникает, когда я пытаюсь обновить свой пароль следующим образом:
var userStore = new UserStore<ApplicationUser>(dbContext);
var userManager = new UserManager<ApplicationUser>(userStore);
var currentPasswordHash = userManager.PasswordHasher.HashPassword(Input.CurrentPassword);
if(user.PasswordHash == currentPasswordHash)
{
var passwordHash = userManager.PasswordHasher.HashPassword(Input.NewPassword);
user.PasswordHash = passwordHash;
dbContext.SaveChanges();
logger.Info(AspNetEventLogs.Update + " Password updated for User: " + user.UserName);
}
else
{
logger.Error(AspNetEventLogs.Error + " Current password incorrect");
}
Я не могу получить хэши, чтобы соответствовать вообще. Метод, который я использовал для создания пользователя и хеш-пароль, аналогичен. Не знаю, что еще я могу сделать.
Если вы посмотрите на исходный код PasswordHasher.HashPassword, вы увидите следующее:
using (var deriveBytes = new Rfc2898DeriveBytes(password, SaltSize, PBKDF2IterCount))
{
salt = deriveBytes.Salt;
subkey = deriveBytes.GetBytes(PBKDF2SubkeyLength);
}
Таким образом, новая соль и подразделение генерируются, когда вы его вызываете. Вот почему ваш чек будет никогда (насколько то, что было доказано, что) возвращают true
.
Для этой конкретной цели PasswordHasher
имеет метод VerifyHashedPassword
который может воссоздать хеш с помощью сохраненной соли и подраздела - это то, что вызывается при входе в систему с Identity.
Обратите внимание, однако, что вашему методу не хватает обновления пользовательского SecurityStamp, который необходимо обновить при изменении пароля для целей безопасности.
Кроме того, обратите внимание, что все эти ручные работы, которые вы делаете, уже были UserManager.UpdatePasswordAsync
в основных библиотеках Identity, и все, что вам нужно сделать, это вызвать UserManager.UpdatePasswordAsync
который будет проверять пароль перед использованием нового.