【问题标题】:Customized authorization attribute in MVC 4 with RolesMVC 4 中的自定义授权属性与角色
【发布时间】:2014-01-23 09:20:22
【问题描述】:

我已经创建了一个自定义的角色基​​础授权属性。我的想法是,当角色名称为“employee”的用户登录时,不应允许通过 URL 访问“admin”页面。但是当我在员工控制器中实现[MyRoleAuthorization] 并登录时,错误显示“此网页有一个重定向循环”。 这是[MyRoleAuthorization] 的代码

public class MyRoleAuthorization : AuthorizeAttribute
{
    string isAuthorized;
    private string AuthorizeUser(AuthorizationContext filterContext)
    {
        if (filterContext.RequestContext.HttpContext != null)
        {
            var context = filterContext.RequestContext.HttpContext;


            if (Convert.ToString(context.Session["RoleName"]) == "Admin")
            {
                isAuthorized = "Admin";

            }
            else if (Convert.ToString(context.Session["RoleName"]) == "Employee")
            {
                isAuthorized = "Employee";

            }
            else if (Convert.ToString((context.Session["RoleName"])) == "Customer")
            {
                isAuthorized = "Customer";
            }
            else
            {
                throw new ArgumentException("filterContext");
            }
        }
        return isAuthorized;
    }

    public override void OnAuthorization(AuthorizationContext filterContext)
    {
        if (filterContext == null)
            throw new ArgumentException("filterContext");

        if (AuthorizeUser(filterContext) == "Admin")
        {
            filterContext.Result = new RedirectToRouteResult
                 (new RouteValueDictionary(new { controller = "Admin" }));
        }

        else if (AuthorizeUser(filterContext) == "Employee")
        {
            filterContext.Result = new RedirectToRouteResult
                 (new RouteValueDictionary(new { controller = "Employee" }));
        }
        else if (AuthorizeUser(filterContext) == "Customer")
        {
            filterContext.Result = new RedirectToRouteResult
                 (new RouteValueDictionary(new { controller = "Customer" }));

        }
    }

}
} 

我的 Employee 控制器看起来像这样

   [MyRoleAuthorization]        
    public ActionResult Index()
    {
        var employee = db.Employee.Include(e => e.User);
        return View(employee.ToList());
    }

你能帮帮我吗?

【问题讨论】:

    标签: c# asp.net asp.net-mvc-4 asp.net-authorization


    【解决方案1】:

    您的重定向代码始终会将用户重定向到员工索引操作,即使您重定向到的操作已针对员工进行了身份验证。您将需要在您的授权中提供另一组规则并更改您的 OnAuthorize 方法。

    public class MyRoleAuthorization : AuthorizeAttribute
    {
    /// <summary>
    /// the allowed types
    /// </summary>
    readonly string[] allowedTypes;
    
    /// <summary>
    /// Default constructor with the allowed user types
    /// </summary>
    /// <param name="allowedTypes"></param>
    public MyRoleAuthorization(params string[] allowedTypes)
    {
        this.allowedTypes = allowedTypes;
    }
    
    /// <summary>
    /// Gets the allowed types
    /// </summary>
    public string[] AllowedTypes
    {
        get { return this.allowedTypes; }
    }
    
    /// <summary>
    /// Gets the authorize user
    /// </summary>
    /// <param name="filterContext">the context</param>
    /// <returns></returns>
    private string AuthorizeUser(AuthorizationContext filterContext)
    {
        if (filterContext.RequestContext.HttpContext != null)
        {
            var context = filterContext.RequestContext.HttpContext;
            string roleName = Convert.ToString(context.Session["RoleName"]);
            switch (roleName)
            {
                case "Admin":
                case "Employee":
                case "Customer":
                    return roleName;
                default:
                    throw new ArgumentException("filterContext");
            }
        }
        throw new ArgumentException("filterContext");
    }
    
    /// <summary>
    /// The authorization override
    /// </summary>
    /// <param name="filterContext"></param>
    public override void OnAuthorization(AuthorizationContext filterContext)
    {
        if (filterContext == null)
            throw new ArgumentException("filterContext");
        string authUser = AuthorizeUser(filterContext);
        if (!this.AllowedTypes.Any(x => x.Equals(authUser, StringComparison.CurrentCultureIgnoreCase)))
        {
            filterContext.Result = new HttpUnauthorizedResult();
            return;
        }
    }
    

    }

    然后可以将其装饰为

    public class EmployeeController : Controller
    {
        [MyRoleAuthorization("Employee")]
        public ActionResult Index()
        {
            return View();
        }
    }
    

    现在应该修改您的登录代码以将用户发送到正确的控制器。

    【讨论】:

      【解决方案2】:

      您最大的问题是当您作为员工访问员工控制器时,您会被重定向到员工控制器,您的属性会将您重定向到员工控制器等等。尽量避免在属性内重定向,因为它会使您的代码变脆,并且当您在几年后回来时,您将不记得为什么您的路线不能按预期工作

      试试这个:

      public class MyRoleAuthorization : AuthorizeAttribute
      {
      
          public string Role{get;set;}
      
          private string AuthorizeUser(AuthorizationContext filterContext)
          {
              if (filterContext.RequestContext.HttpContext != null)
              {
                  var context = filterContext.RequestContext.HttpContext;
      
                  return (string)context.Session["RoleName"];
              }
              throw new ArgumentException("filterContext");
          }
      
          public override void OnAuthorization(AuthorizationContext filterContext)
          {
              if (filterContext == null)
                  throw new ArgumentException("filterContext");
      
              var role = AuthorizeUser(filterContext);
              if (role.Equals(Role))
              {
              // insert positive outcome from role check, ie let the action continue
              }
              else
              {
              // denied! redirect to login page or show denied page (403)
              }
          }
      } 
      
      
      [MyRoleAuthorization("Employee")]        
      public ActionResult Index()
      {
          var employee = db.Employee.Include(e => e.User);
          return View(employee.ToList());
      }
      

      【讨论】:

        【解决方案3】:

        例如,在获得授权后,您似乎会重定向到客户控制器。该控制器可能具有您的属性,因此它授权被视为客户的用户,并重定向到客户控制器...具有您的属性,因此它授权用户...

        无限循环。

        【讨论】:

          猜你喜欢
          • 2012-10-27
          • 1970-01-01
          • 1970-01-01
          • 2012-03-19
          • 2015-03-03
          • 1970-01-01
          • 2011-09-03
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多