如何修改Authorize属性以允许MVC 3中的一组用户角色

时间:2012-11-30 17:27:21

标签: asp.net-mvc-3 authorize-attribute

在我的MVC3 wep应用程序中,我扩展了Authorize属性,如下所示

public class MyAuthorizeAttribute : AuthorizeAttribute
{
    protected override bool AuthorizeCore(HttpContextBase httpContext)
    {
        if (Authenticate.IsAuthenticated() && httpContext.User.Identity.IsAuthenticated)
        {
            var authCookie = httpContext.Request.Cookies[FormsAuthentication.FormsCookieName];
            if (authCookie != null)
            {
                var ticket = FormsAuthentication.Decrypt(authCookie.Value);
                var roles = ticket.UserData.Split('|');
                var identity = new GenericIdentity(ticket.Name);
                httpContext.User = new GenericPrincipal(identity, roles);
            }
        }
        return base.AuthorizeCore(httpContext);
    }

    public override void OnAuthorization(AuthorizationContext filterContext)
    {

        if (!Authenticate.IsAuthenticated())
            HandleUnauthorizedRequest(filterContext);


        base.OnAuthorization(filterContext);

    }

在我的动作中,我使用它像

    [MyAuthorize(Roles = "Member,Inspector,SalesRep,Admin,SuperAdmin")]
    public ActionResult OrderUpload()

现在,我必须在每个操作中指定每个用户角色。我想做的是 指定类似下面的内容

    [MyAuthorize(Roles = "Member")]
    public ActionResult OrderUpload()

这应该允许任何等于或高于“Member”的用户角色。因此,应该允许“SalesRep”,而不应允许“会员”之下的“访客”。

所有用户角色都是枚举,数字越来越多

public enum UserAccountType
{
    Visitor = 5,
    Member = 10,
    Inspector = 15,
    SalesRep = 20,
    Admin = 25,
    SuperAdmin = 30
}

如何修改MyAuthorizeAttribute以使其工作?

由于

2 个答案:

答案 0 :(得分:2)

这是我的工作代码

public class MyAuthorizeAttribute : AuthorizeAttribute
{
    protected override bool AuthorizeCore(HttpContextBase httpContext)
    {
        if (Authenticate.IsAuthenticated() && httpContext.User.Identity.IsAuthenticated)
        {
            var authCookie = httpContext.Request.Cookies[FormsAuthentication.FormsCookieName];
            string[] roles = null;

            if (authCookie != null)
            {
                var ticket = FormsAuthentication.Decrypt(authCookie.Value);
                roles = ticket.UserData.Split('|');
                var identity = new GenericIdentity(ticket.Name);
                httpContext.User = new GenericPrincipal(identity, roles);
            }

            if (Roles == string.Empty)
                return true;

            //Assuming Roles given in the MyAuthorize attribute will only have 1 UserAccountType - if more than one, no errors thrown but will always return false
            else if ((UserAccountType)Enum.Parse(typeof(UserAccountType), roles[0]) >= (UserAccountType)Enum.Parse(typeof(UserAccountType), Roles))
                return true;
            else
                return false;
        }
        else
            return false;

        //return base.AuthorizeCore(httpContext);
    }

    public override void OnAuthorization(AuthorizationContext filterContext)
    {
        if (!Authenticate.IsAuthenticated())
            HandleUnauthorizedRequest(filterContext);

        base.OnAuthorization(filterContext);
    }
}

答案 1 :(得分:1)

我不使用AuthorizeAttribute而是使用ActionFilter(它只是我,这就是我学习它的方式)但我要做的是在AuthorizeAttribute上添加一个属性,当属性在Action之前被触发时会更新。

public class MyAuthorizeAttribute : AuthorizeAttribute
{
    private string Role = "";

    public MyAuthorizeAttribute(string role){
        this.Role = role;
    }

    protected override bool AuthorizeCore(HttpContextBase httpContext)
    {
          :
          :
          :
          // now do a check if the Role is authorized or not using your enum. 
          // return error page if not
          if(RoleisAuthorized)
            return; 
          else
            // error page

    }

    public override void OnAuthorization(AuthorizationContext filterContext)
    {
          :
          :
          :
    }
}

现在获得角色之后,从枚举中获取它并比较是否允许角色访问页面,如果没有返回错误页面。因为我不熟悉OnAuthorization,所以我将把进程放在AuthorizeCore中。