【问题标题】:Using action parameters in custom Authorization Attribute in ASP.NET MVC3在 ASP.NET MVC3 的自定义授权属性中使用操作参数
【发布时间】:2011-07-29 19:03:20
【问题描述】:

我有一个控制器,它应该只在加载特定参数时请求授权。比如参数ID为8的时候。

我想出了使用这样的自定义验证属性:

public class MyAuthorizeAttribute : AuthorizeAttribute
{
    protected override bool AuthorizeCore(HttpContextBase httpContext)
    {
        if (/* Action's inputparameter ID = 8 */)
        {
        return base.AuthorizeCore(httpContext);
        }
        return true;
    }
}

我的动作看起来是这样的(不是很有趣)

[MyAuthorize]
public ActionResult Protected(int id)
{
    /* custom logic for setting the viewmodel from the id parameter */
    return View(viewmodel);
}

问题是如您所见,我不知道如何在授权属性中检查该 ID 参数。 你能帮我解决一下吗?

【问题讨论】:

    标签: asp.net-mvc-3 authorization custom-attributes


    【解决方案1】:

    如果 id 作为请求参数(GET 或 POST)或路由数据参数传递:

    protected override bool AuthorizeCore(HttpContextBase httpContext)
    {
        // first look at routedata then at request parameter:
        var id = (httpContext.Request.RequestContext.RouteData.Values["id"] as string) 
                 ??
                 (httpContext.Request["id"] as string);
        if (id == "8")
        {
            return base.AuthorizeCore(httpContext);
        }
        return true;
    }
    

    【讨论】:

    • 代码是多余的,请看下面我的解决方案。
    • @Darin,你能告诉我动作的输入参数是否是模型,如何检索该模型对象而不是命名参数?
    • 听起来你实际上是在寻找stackoverflow.com/questions/1335315/…
    【解决方案2】:

    只要AuthorizeAttribute被继承,就可以从AuthorizationContext获取你的参数,如下:

    public class MyAuthorizeAttribute : AuthorizeAttribute
    {
        public override void OnAuthorization(AuthorizationContext filterContext)
        {
            string idParam = filterContext.Controller.ValueProvider.GetValue("id").AttemptedValue;
            int id;
    
            if (int.TryParse(idParam, out id))
            {
                if (id == 8) // apply your business logic here
                    return;
            }
    
            filterContext.Result = new HttpUnauthorizedResult();
        }
    }
    
    [MyAuthorize]
    public ActionResult Protected(int id)
    {
        return View();
    }
    

    ValueProvider 将遍历所有已注册的提供程序,默认情况下包括RouteDataValueProviderQueryStringValueProviderFormValueProvider,并为您完成所有工作。

    否则我建议使用ActionFilterAttribute

    【讨论】:

    • 这并不能完全回答我的问题。我想根据id 参数的值启用/禁用授权。有没有办法影响来自OnAuthorization 处理程序的授权?您能否详细说明答案中的... 部分?
    • @SoonDead,我改变了我的例子。如您所见,它仍然非常简单,但功能齐全。
    【解决方案3】:

    你需要这样的东西。

        public override void OnActionExecuting(ActionExecutingContext filterContext)
        {
            int? id = GetId(filterContext);
    
            if (id.HasValue)
            {
              ...
            }
        }
    
        private static int? GetId(ActionExecutingContext filterContext)
        {
            int? Id = null;
    
            if (filterContext.ActionParameters.ContainsKey("Id"))
            {
                Id = (int?)filterContext.ActionParameters["Id"];
            }
        }
    

    【讨论】:

    • 是的,类似的,但我在 AuthorizeCore 方法中有一个 HttpContextBase 参数,而不是 ActionExecutingContext。而且我不知道如何在 OnActionExecuting 方法中编写授权逻辑。
    • 这是一篇很棒的文章,解释了如何访问 ActionParameters 以进行授权:joe-stevens.com/2010/08/19/…
    【解决方案4】:
        protected override bool AuthorizeCore(HttpContextBase httpContext)
        {
            var rd = httpContext.Request.RequestContext.RouteData;
            string currentAction = rd.GetRequiredString("action");
            string actionparam =Convert.ToString(rd.Values["param"]);
    
            if (id == actionparam)
            {
                return base.AuthorizeCore(httpContext);
            }
    return true;
     }
    

    【讨论】:

    • 这与 Darin Dimitrov 的回答有何不同?
    猜你喜欢
    • 1970-01-01
    • 2012-01-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-04-11
    • 2015-08-22
    • 2012-05-09
    相关资源
    最近更新 更多