Как я могу использовать GUID роли вместо имен в ASP.NET Core Identity? - PullRequest
0 голосов
/ 15 ноября 2018

Я играл с Identity в ASP.NET Core, используя несколько примеров, и что-то меня расстраивает. Хотя образец для подражания имеет первичный ключ Id и строку Name, это имя передается различными встроенными службами.

Например, когда я звоню _userManager.GetRolesAsync(user), я получаю список имен строк. Что делать, если я хочу идентификаторы? Для этого нет API, поэтому мне пришлось бы использовать менеджер ролей, чтобы получить все роли и отобразить их. По умолчанию имена ролей не ограничены уникальным ключом, поэтому это ненадежно.

Должно быть, я что-то упустил, но что? Сейчас я использую один пример использования: я хочу заполнить заявку JWT ролями пользователя. Насколько мне известно, имена ролей являются внутренними для моего приложения, и я не хочу показывать их клиентам.

1 Ответ

0 голосов
/ 20 ноября 2018

Для _userManager.GetRolesAsync(user), он вызывает userRoleStore.GetRolesAsync

        public virtual async Task<IList<string>> GetRolesAsync(TUser user)
    {
        ThrowIfDisposed();
        var userRoleStore = GetUserRoleStore();
        if (user == null)
        {
            throw new ArgumentNullException(nameof(user));
        }
        return await userRoleStore.GetRolesAsync(user, CancellationToken);
    }

Для возврата идентификатора роли вместо имени роли вы можете настроить userRoleStore.GetRolesAsync, реализовав свой собственный UserStore.

  • UserStore.cs

               public class CustomUserStore : UserStore<IdentityUser>
    {
        public CustomUserStore(DbContext context, IdentityErrorDescriber describer = null) : base(context, describer)
        {
        }
    
        public override async Task<IList<string>> GetRolesAsync(IdentityUser user, CancellationToken cancellationToken = default(CancellationToken))
        {
            var roleNames = await base.GetRolesAsync(user, cancellationToken);
            var roleIds = await Context.Set<IdentityRole>()
                                 .Where(r => roleNames.Contains(r.Name))
                                 .Select(r => r.Id)
                                 .ToListAsync();
    
            return roleIds;
        }
    }
    
  • Регистрация UserStore

        services.AddDefaultIdentity<IdentityUser>()
            .AddRoles<IdentityRole>()
            .AddUserStore<CustomUserStore>()
            .AddEntityFrameworkStores<ApplicationDbContext>()
            ;
        services.AddScoped<DbContext, ApplicationDbContext>();
    
  • Тогда вы будетеполучить коллекцию идентификаторов ролей по

        var user = await _userManager.FindByNameAsync(User.Identity.Name);
        var roles = await _userManager.GetRolesAsync(user);
    
...