Jim*_*opp 4 c# asp.net-mvc authorization authorize-attribute asp.net-core-2.1
我正在使用Asp.Net Core 2.1和Windows身份验证的Intranet应用程序上工作。我可以很好地从IIS获得通过,但我想使用存储在数据库中的角色进行授权。
我有一个IClaimsTransformeration类,该类基于LAN Id从数据库中获取角色,并将它们添加到带有角色密钥的声明列表中。
public class MyClaimsTransformer : IClaimsTransformation
{
private readonly IUnitOfWorkMtuSecurity _unitOfWork;
public MyClaimsTransformer(IUnitOfWorkMtuSecurity unitOfWork)
{
_unitOfWork = unitOfWork;
}
// Each time HttpContext.AuthenticateAsync() or HttpContext.SignInAsync(...) is called the claims transformer is invoked. So this might be invoked multiple times.
public async Task<ClaimsPrincipal> TransformAsync(ClaimsPrincipal principal)
{
var identity = principal.Identities.FirstOrDefault(x => x.IsAuthenticated);
if (identity == null) return principal;
//var user = await _userManager.GetUserAsync(principal);
var user = identity.Name;
if (user == null) return principal;
//Get user with roles from repository.
var dbUser = _unitOfWork.UserInformations.GetUserWithRoles(user);
// Inject DbRoles into Claims list
foreach (var role in dbUser.UserInformationUserRoles.Select((r=>r.UserRole)))
{
var claim = new Claim(ClaimTypes.Role, role.Name);
identity.AddClaim(claim);
}
return new ClaimsPrincipal(identity);
}
}
Run Code Online (Sandbox Code Playgroud)
我在startup.cs中将IClaimsTransformation添加到了我的服务中
services.AddScoped<IClaimsTransformation, MyClaimsTransformer>();
Run Code Online (Sandbox Code Playgroud)
然后我将属性添加到我的控制器
[Authorize(Roles = "Administrator")]
Run Code Online (Sandbox Code Playgroud)
当我运行我的应用程序时,出现以下错误:
处理请求时发生未处理的异常。InvalidOperationException:未指定authenticationScheme,也未找到DefaultForbidScheme。Microsoft.AspNetCore.Authentication.AuthenticationService.ForbidAsync(HttpContext上下文,字符串方案,AuthenticationProperties属性)
在startup.cs中,我将以下内容添加到服务中
services.AddAuthentication(IISDefaults.AuthenticationScheme);
Run Code Online (Sandbox Code Playgroud)
这摆脱了错误,但是无论我得到什么403错误。
您无权查看此页面。HTTP错误403
当我查看MyClaimsTransformer的返回值时,可以看到管理员的角色已添加到索赔列表中,但是无论如何我都会收到403错误。
有人对我的失踪有任何建议吗?
如果我在视图中使用以下语法,那么它将在视图级别起作用:
@if (User.HasClaim("http://schemas.microsoft.com/ws/2008/06/identity/claims/role", "Administrator"))
{
<li><a asp-area="" asp-controller="UserInformationAdmin" asp-action="Index">Admin</a></li>
}
Run Code Online (Sandbox Code Playgroud)
我必须指定整个架构网址。
ClaimIdentity的RoleClaimType为“ http://schemas.microsoft.com/ws/2008/06/identity/claims/groupsid ”
并且它必须是“ http://schemas.microsoft.com/ws/2008/06/identity/claims/role ” 的RoleClaimType
由于这是一个只读属性,因此我更改了TransformAsync方法以创建新的ClaimsPrincipal,而不是尝试将数据库角色添加到现有声明中。我的应用程序不需要任何AD组,因此仅使用Windows进行身份验证。下面的代码似乎有效。
public class MyClaimsTransformer : IClaimsTransformation
{
private readonly IUnitOfWorkSecurity _unitOfWork;
public MyClaimsTransformer(IUnitOfWorkSecurity unitOfWork)
{
_unitOfWork = unitOfWork;
}
// Each time HttpContext.AuthenticateAsync() or HttpContext.SignInAsync(...) is called the claims transformer is invoked. So this might be invoked multiple times.
public async Task<ClaimsPrincipal> TransformAsync(ClaimsPrincipal principal)
{
var identity = principal.Identities.FirstOrDefault(x => x.IsAuthenticated);
if (identity == null) return principal;
var user = identity.Name;
if (user == null) return principal;
//Get user with roles from repository.
var dbUser = _unitOfWork.UserInformations.GetUserWithRoles(user);
var claims = new List<Claim>();
//The claim identity uses a claim with the claim type below to determine the name property.
claims.Add(new Claim(@"http://schemas.xmlsoap.org/ws/2005/05/identity/claims/name", user, "Name"));
//todo: We should probably create a cache for this
// Get User Roles from database and add to list of claims.
foreach (var role in dbUser.UserInformationUserRoles.Select((r=>r.UserRole)))
{
claims.Add(new Claim(ClaimTypes.Role, role.Name));
}
var newClaimsIdentity = new ClaimsIdentity(claims,"Kerberos","", "http://schemas.microsoft.com/ws/2008/06/identity/claims/role");
var newClaimsPrincipal = new ClaimsPrincipal(newClaimsIdentity);
return new ClaimsPrincipal(newClaimsPrincipal);
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1974 次 |
| 最近记录: |