Как создать SecurityStamp для AspNetUser в ASP .NET MVC 5

Когда я создаю пользователя с помощью регистра, при запуске приложения пользователь получает SecurityStamp. Когда я добавляю пользователя по:

if (!context.Users.Any()) {
                System.Diagnostics.Debug.WriteLine("INSIDE");
                var hasher = new PasswordHasher();
                try {
                    var users = new List<ApplicationUser> { 
                        new ApplicationUser{PasswordHash = hasher.HashPassword("TestPass44!"), Email = "informatyka4444@wp.pl", UserName = "informatyka4444@wp.pl"},
                        new ApplicationUser{PasswordHash = hasher.HashPassword("TestPass44!"), Email = "informatyka4445@wp.pl", UserName = "informatyka4445@wp.pl"}
                        };

                    users.ForEach(user => context.Users.AddOrUpdate(user));

                    context.SaveChanges();
                } catch (DbEntityValidationException e) {
                    System.Diagnostics.Debug.WriteLine("EXC: ");
                    foreach (DbEntityValidationResult result in e.EntityValidationErrors) {
                        foreach (DbValidationError error in result.ValidationErrors) {
                            System.Diagnostics.Debug.WriteLine(error.ErrorMessage);
                        }
                    }

                }
            }

пользователь не получает штамп безопасности:

и тогда, когда я хочу войти, я получаю:

Вопрос: как сгенерировать SecurityStamp для пользователя?

1 ответ

Решение

Печать безопасности может быть чем угодно. Это часто ошибочно быть меткой времени, но это не так. Он будет переопределен ASP.NET Identity, если что-то изменится в пользовательской сущности. Если вы работаете непосредственно с контекстом, лучше всего создать новый Guid и использовать его в качестве штампа. Вот простой пример:

var users = new List<ApplicationUser> 
                { 
                    new ApplicationUser
                        {
                            PasswordHash = hasher.HashPassword("TestPass44!"), 
                            Email = "informatyka4444@wp.pl", 
                            UserName = "informatyka4444@wp.pl", 
                            SecurityStamp = Guid.NewGuid().ToString()
                        },
                    new ApplicationUser
                        {
                            PasswordHash = hasher.HashPassword("TestPass44!"),
                            Email = "informatyka4445@wp.pl", 
                            UserName = "informatyka4445@wp.pl", 
                            SecurityStamp = Guid.NewGuid().ToString()
                         }
                };

Если мы заглянем внутрь IdentityUser Таблица AspNetUsers данные, мы увидим, что SecurityStamp имеет иную форму, чем нормальный GUID:

Это потому, что GUID преобразуется в строку карты HEX.

Мы можем создать функцию для генерации новых штампов безопасности, которая будет генерировать новые GUID и преобразовать его в строку карты HEX:

Func<string> GenerateSecurityStamp = delegate()
{
    var guid = Guid.NewGuid();
    return String.Concat(Array.ConvertAll(guid.ToByteArray(), b => b.ToString("X2")));
};

Вы можете проверить, что он работает с этой .NET Fiddle.

Итак, если мы хотим заполнить Identity Users, мы можем использовать его для генерации SecurityStamp:

modelBuilder.Entity<IdentityUser>().HasData(new ApplicationUser
{
    ...

    // Security stamp is a GUID bytes to HEX string
    SecurityStamp = GenerateSecurityStamp(),
});

Предупреждение: будьте очень осторожны и не используйте приведенный выше пример для заполнения, потому что он будет изменять данные каждый раз, когда мы создаем новую миграцию. Данные для заполнения всегда должны создаваться заранее при использованииHasData а не динамический встроенный.

Другие вопросы по тегам