代码之家  ›  专栏  ›  技术社区  ›  user2806570

具有Windows身份验证的ASP.NET Core 2.1自定义RoleProvider

  •  5
  • user2806570  · 技术社区  · 6 年前

    我正在将应用程序从ASP.NETMVC5框架迁移到新的.NETCore2.1。

    ASP.NET MVC How to create a custom role provider

    如何在Core2.1中实现与它似乎不包含RoleProvider功能相同的功能?

    我遇到的每个例子都使用具有IdentityUser和IdentityRole的个人帐户。

    我的用户和角色自定义表:

    public class User
    {
        public User() { UserRoles = new HashSet<UserRole>(); }
    
        [Key]
        public string Id { get; set; }
    
        [StringLength(50)]
        [Required]
        public string Logon { get; set; } //The users Active Directory Username
    
        public bool Active { get; set; }
    
        public ICollection<UserRole> UserRoles { get; set; }
    
    }
    
    
    public class Role
    {
        public Role() { UserRoles = new HashSet<UserRole>(); }
    
        [Key]
        public string Id { get; set; }
    
        public string Name { get; set; }
    
        public ICollection<UserRole> UserRoles { get; set; }
    }
    

    编辑:

    public class CustomClaimsPrincipal : ClaimsPrincipal
    {
        private readonly ApplicationDbContext _context;
    
        public CustomClaimsPrincipal(ApplicationDbContext context)
        {
            _context = context;
        }
    
        public override bool IsInRole(string role)
        {
            var currentUser = ClaimsPrincipal.Current.Identity.Name;
    
            IdentityUser user = _context.Users.FirstOrDefault(u => u.UserName.Equals(currentUser, StringComparison.CurrentCultureIgnoreCase));
                //(ApplicationUser)_context.Users.FirstOrDefault(u => u.UserName.Equals(currentUser, StringComparison.CurrentCultureIgnoreCase));
    
            var roles = from ur in _context.UserRoles.Where(p => p.UserId == user.Id)
                        from r in _context.Roles
                        where ur.RoleId == r.Id
                        select r.Name;
            if (user != null)
                return roles.Any(r => r.Equals(role, StringComparison.CurrentCultureIgnoreCase));
            else
                return false;
        }
    }
    

    并添加到Startup.cs

    services.AddIdentity<ApplicationUser, IdentityRole>().AddEntityFrameworkStores<ApplicationDbContext>();
    
    services.AddScoped<ClaimsPrincipal, CustomClaimsPrincipal>();
    

    但它似乎仍然采用原始的ClaimsPrincipal IsInRole函数,而不是重写,我相信这就是为什么我得到错误消息“主域和受信任域之间的信任关系失败”

    2 回复  |  直到 6 年前
        1
  •  1
  •   Will    6 年前

    在net core中管理自定义权限通常是通过声明来完成的。您可以通过aspnet身份进行此操作( How to add claims in ASP.NET Identity

    一旦有了索赔,就需要创建策略。这是通过 Startup.cs ConfigureServices 方法。

    services.AddAuthorization(options =>
            {
                options.AddPolicy("HR", policy => policy.RequireClaim("HRTeam"));
                options.AddPolicy("Helpdesk", policy => policy.RequireClaim("HelpdeskTeam"));
            });
    

    然后用 Authorize 属性

    [Authorize(Policy="Helpdesk")]
    public class HelpDeskController : Controller
    
        2
  •  4
  •   Aceofspades25    6 年前

    步骤1:创建ClaimsTransformer-替换“Admin”,并为从数据库中获取的每个角色添加单独的声明

    using System.Security.Claims;
    using System.Threading.Tasks;
    using Microsoft.AspNetCore.Authentication;
    
    public class ClaimsTransformer : IClaimsTransformation
    { 
        public Task<ClaimsPrincipal> TransformAsync(ClaimsPrincipal principal)
        {
            var ci = (ClaimsIdentity) principal.Identity;
            var c = new Claim(ci.RoleClaimType, "Admin");
            ci.AddClaim(c);
            return Task.FromResult(principal);
        }
    }
    

    步骤2:将ClaimsTransformer添加到Startup.cs的ConfigureServices方法

    services.AddAuthentication(Microsoft.AspNetCore.Server.IISIntegration.IISDefaults.AuthenticationScheme);
    services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
    services.AddSpaStaticFiles(configuration =>
    {
        configuration.RootPath = "ClientApp/dist";
    });
    
    services.AddSingleton<IClaimsTransformation, ClaimsTransformer>();
    

    [Authorize(Roles = "Admin")]
    [HttpGet("[action]/{id}")]        
    public User GetUser([FromRoute] int id)
    {
        UserLogic ul = new UserLogic();
        return ul.GetUser(id);
    }