自定义授权(权限)ASP.NET MVC

3
在我的应用程序中,一个角色拥有多个权限。我希望用户能够访问与权限相关的操作,而不是角色。
假设:
- 管理员有perm1、perm2、perm3 - 超级管理员具有管理员拥有的所有权限+perm4和perm5。 - 还有一些小伙子也有perm1、perm3、perm6、perm7。
我想做以下事情:我希望那些拥有perm3或perm4权限的人可以访问操作,这两个权限来自不同的角色。但是除了Admin有perm1和perm2之外,对于拥有perm3的小伙子也可以访问此操作(不一定是管理员或超级管理员)。
所以你明白我的意思了吧?我想在ASP.NET MVC 4中实现这一点。所以我需要制作自己的AuthorizeAttribute,我的自己的IIdentity并编写一些方法在global.asax中。 ASP.NET中还有一个Membership,我需要接触它吗?我不知道如何将所有东西放在一起。有谁能帮我一下?

您可能想使用内置的ASP.NET功能,即基于声明的身份验证。请访问以下链接以获取更多详细信息:http://visualstudiomagazine.com/articles/2013/08/01/leveraging-claims-based-security-in-aspnet-45.aspx - hungrycoder
3个回答

1
public class PermissionAttribute : AuthorizeAttribute
    {
        private readonly IAccountService _accountService;
        private readonly IEnumerable<PermissionEnum> _permissions;

        public PermissionAttribute(params PermissionEnum[] permissions):
            this(DependencyResolver.Current.GetService<IAccountService>())
        {
            _permissions = permissions;
        }

        protected PermissionAttribute(IAccountService accountService)
        {
            _accountService = accountService;
        }

        public override void OnAuthorization(AuthorizationContext filterContext)
        {
            if(!_permissions.Any(x=>_accountService.HasPermission(filterContext.HttpContext.User.Identity.Name,(int)x)))
                filterContext.Result = new HttpStatusCodeResult(HttpStatusCode.Forbidden);
            base.OnAuthorization(filterContext);
        }

    }

1
基本上,您需要创建自己的AuthorizeAttribute,但使用.NET中的IIdentity。您在此处描述的是基于声明的身份验证和授权系统。
最有可能您需要放弃ASP.NET的Membership或仅使用部分。据我所知,它不是为声明而构建的。
在.NET 4.5中,开发人员添加了ClaimsPrincipal类,该类实现了IPrincipal接口。可以使用此类来实现基于声明的自定义身份验证和授权。
因此,当用户通过身份验证时,可以将声明添加到线程上:
var id = new ClaimsIdentity(claims, "Dummy");
var principal = new ClaimsPrincipal(new[] { id });
Thread.CurrentPrincipal = principal;

然后稍后只需使用在Thread.CurrentPrincipal中找到的声明。

在ASP.NET MVC中,您可以执行以下步骤:

  1. 创建一个委托处理程序来验证用户。如果用户已通过身份验证,则向线程主体添加声明。理想情况下,此委托处理程序应尽可能高地位于链中,以便您可以在执行链的任何位置使用声明。还要记得使用相同的主体设置HttpContext.Current.User。

    public class AuthHandler : DelegatingHandler{

    protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
    {
    //验证用户
    //获取声明
    //创建主体
    var newPrincipal = CreatePrincipal(claims);
    Thread.CurrentPrincipal = newPrincipal;
    if (HttpContext.Current != null)
         HttpContext.Current.User = newPrincipal;
    return await base.SendAsync(request, cancellationToken);
    }
    

    }

  2. 创建一个过滤器,根据添加到线程主体的声明进行授权。在这里,您可以像将当前路由与声明中找到的信息进行比较一样做些事情。


0

所以我认为你的意思是:只有当用户拥有perm1、perm2时才能访问ActionA,同样地,只有当用户拥有perm1和perm3时才能访问ActionB。

我提供的代码仅用于说明,我没有编译它。但是可以给您展示我所说的方法的大致思路

步骤1:您可以创建一个带有Flags属性的权限枚举。

步骤2:根据存储在数据存储中的用户权限向当前主体添加声明。

步骤3:当调用Action时,根据声明授权访问。

[Flags]
    enum PermType
    {
        None = 0x0,
        Perm1 = 0x1,
        perm2 = 0x2,
        perm3 = 0x4,
        perm4 = 0x8,
        perm5 = 0x10 
    }

向CurrentPrincipal添加声明

var currentPrincipal = ClaimsPrincipal.Current;
var cms = currentPrincipal.Claims;
var permissions = PermType.Perm1 | PermType.perm2;
var claims = cms.ToList();
claims.Add(new Claim("Action1", permissions.ToString()));
claims.Add(new Claim("Action2", permissions.ToString()));
claims.Add(new Claim("Action3", permissions.ToString()));
System.Threading.Thread.CurrentPrincipal = new ClaimsPrincipal(new ClaimsIdentity(claims));

检查用户是否可以访问特定操作

public bool CanAccessThisAction(string acionName,PermType requiredPerms)
{
    var claim = principal.Claims.FirstOrDefault(c => c.Type == acionName);
    if (customPermissionClaim != null)
    {
        //check if required permission is present in claims for this user
        //return true/false
    }
    return false;
}

关于操作

public ActionResult TestAction(string id)
{
    if(CanAccessThisAction("TestAction",PermType.Perm1|PermType.perm3|PermType.perm5))
    {
        //do your work here
    }
    else
    {
        //redirect user to some other page which says user is not authorized
    }
}

你也可以尝试使用 "ClaimsAuthorizationManager" http://msdn.microsoft.com/en-us/library/system.security.claims.claimsauthorizationmanager.aspx - Prerak K

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接