65.9K
CodeProject 正在变化。 阅读更多。
Home

ASP.NET MVC - AuthorizeWithExemptionsAttribute

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.57/5 (5投票s)

2010年8月23日

CPOL

2分钟阅读

viewsIcon

34514

downloadIcon

492

这个基础控制器将保护您的所有操作,除了那些被标记为“UnsecuredAction”的操作。

引言

在本文中,我将向您提供一种解决方案,以保护 ASP.NET MVC 应用程序的控制器,使其所有操作都受到保护,除了您定义为不安全的操作(默认情况下,除非您将操作定义为安全,否则所有操作都是不安全的)。

我在 ASP.NET MVC 授权模型中遇到一个问题,该模型是基于选择加入的。您可以使用 [Authorize] 属性来保护一个操作或控制器。问题是,如果您想保护整个控制器,并使控制器中的某些操作不受到保护,您就无法做到。

本文将向您解释如何保护整个控制器,并在其中使某些操作不受到保护。

该项目是在 Visual Studio 2010 中作为 ASP.NET MVC 2 项目编写的。

背景

我一直在寻找解决该问题的方法,但没有找到合理的解决方案。其他解决方案建议

  • 将不安全的操作移动到另一个控制器(未受保护)
  • 编写 AuthorizeCore 方法,使其依赖于操作的名称
  • [Authorize] 属性放在所有操作上,除了不安全的操作

在本文中,我将向您提供我对这个问题的解决方案。

Using the Code

要使用此代码,您需要让您的控制器放置任何继承自 AuthorizeWithExemptionsAttribute[CustomAuthorize] 属性在您的控制器上。调用此控制器的任何操作都将包含授权检查。如果您想将一个操作标记为不安全,只需将 [UnsecuredAction] 属性放在它上面即可。

解释

此解决方案的核心在于 OnAuthorization 方法中的 [AuthorizeWithExemptions] 属性。此方法检查被调用的操作是否具有 UnsecuredActionAttribute,如果有,则将 filterContext.HttpContext.SkipAuthorization 标记为 true

public override void OnAuthorization(AuthorizationContext filterContext)
{
    ActionDescriptor action = filterContext.ActionDescriptor;
    bool IsUnsecured = action.GetCustomAttributes(
                         typeof(UnsecuredActionAttribute), true).Count() > 0;

    //If doesn't have UnsecuredActionAttribute - then do the authorization
    filterContext.HttpContext.SkipAuthorization = IsUnsecured;

    base.OnAuthorization(filterContext);
}

然后,CustomAuthorizeAttribute 仅在 SkipAuthorizationfalse 时才执行授权检查。

protected override bool AuthorizeCore(HttpContextBase httpContext)
{
  if (httpContext.SkipAuthorization)
  {
      return true;
  }

  // Do any authorization logic here
  return httpContext.Request.QueryString["password"] == "password";
}

* 当然,永远不要在 QueryString 中提供密码,这样做只是为了示例的方便性。

因此,现在,当您尝试调用受保护的控制器时,您将收到 HTTP 错误代码 401:未授权。

而不安全的控制器无需任何授权即可工作。

历史

  • 2010 年 8 月 23 日:初始发布
  • 2010 年 8 月 24 日:更新了文章和源代码
© . All rights reserved.