web-dev-qa-db-ja.com

ASP.NET Core 2.1カスタムRoleProviderとWindows認証

アプリケーションをASP.Net MVC 5フレームワークから新しい.Net Core 2.1に移行しています。

以下のリンクに示すように、MVC 5プロジェクトでカスタムRoleProviderを使用してWindows認証を使用しました。

ASP.NET MVCカスタムロールプロバイダーの作成方法

RoleProvider機能が含まれていないように見えるので、Core 2.1で同じようにするにはどうすればよいですか?

私が遭遇するすべての例では、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; }
}

編集:

次のようなCustomClaimsPrincipalを追加しました。

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関数を使用しているようです。そのため、「プライマリドメインと信頼されたドメイン間の信頼関係に失敗しました」というエラーメッセージが表示されます。

7
user2806570

ネットコアでのカスタム権限の管理は通常、クレームを介して行われます。これは、aspnet identity( 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
1
ste-fu

私は同じ問題を抱えていました-投稿で与えられた解決策は役に立たなかったが、コメントは正しい方向に私を指摘しました。 ClaimsPrincipalにクレームを追加する必要があります。

ステップ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>();

ステップ3:コントローラ内にロールベースの承認属性を追加できるようになりました

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