2011-01-07 141 views
3

我正在使用自定義成員資格提供程序。一切都很好。但是,在我的web.config文件中,我已經「拒絕用戶」啓用,所以整個網站被鎖定。ASP.NET MVC 2授權問題

This works great。用戶被重定向到登錄頁面。

現在,我有幾個控制器/操作,我想允許匿名訪問。關於頁面,密碼重置等。

我可以想出如何做到這一點的唯一方法是解鎖整個站點,將[授權]屬性放在每個控制器上,並將它們移出控制器/我想要匿名的操作。

這似乎倒退給我。我更傾向於默認鎖定所有內容並解鎖匿名內容。

有沒有辦法解決這個問題?

謝謝!

回答

3

我可以考慮實現這一點的替代方法,但它們都涉及使用自定義的AuthorizeAttribute。做到這一點的一種方法是讓基礎控制器使用所有控制器派生自定義的AuthorizeAttribute。該屬性將被自定義以防止匿名(和未授權)訪問動作,除非它是控制器或動作本身已用另一個屬性修飾 - 例如AnonymousEnabledAttribute。所有的控制器都會從這個控制器派生出來,並繼承它的標準的「默認情況下無匿名」行爲。然後,您只需用AnonymousEnabledAttribute修飾想要匿名的控制器/操作 - 爲該控制器或操作提供覆蓋。或者,對於控制器,只是不從受保護的控制器繼承,並且它的所有操作都是公開的。

哦,你的整個網站將不得不保持開放。

[OverridableAuthorize] 
public abstract class ProtectedController : Controller 
{ 
} 

public class MostlyProtectedController : ProtectedController 
{ 
    public ActionResult ProtectedAction() 
    { 
    } 

    [AnonymousEnabled] 
    public ActionResult PublicAction() 
    { 
    } 
} 

[AnonymousEnabled] 
public class ExplicitlyPublicController : ProtectedController 
{ 
    // inherits additional behaviors, but anonymous is enabled by attribute 
} 

public class PublicByOmissionController : Controller 
{ 
    // doesn't inherit and is thus public -- assuming whole site is open 
} 

public class AnonymousEnabledAttribute : Attribute 
{ 
} 

public class OverridableAuthorizeAttribute : AuthorizeAttribute 
{ 
    public override void OnAuthorization(AuthorizationContext context) 
    { 
      context.HttpContext.Items["ActionDescriptor"] = context.ActionDescriptor; 
      base.OnAuthorize(context); 
    } 

    public override bool AuthorizeCore(HttpContextBase context) 
    { 
     var actionDescriptor = context.Items["ActionDescriptor"] as ActionDescriptor; 
     if (actionDescriptor == null) 
     { 
      throw InvalidOperationException("ActionDescriptor missing from context"); 
     } 
     var attribute = actionDescriptor 
          .GetCustomAttributes(typeof(AnonymousEnabledAttribute,true) 
          .FirstOrDefault(); 
     if (attribute == null) 
     { 
      return base.AuthorizeCore(context); 
     } 
     return true; 
    } 
} 
+0

感謝這個建議。所以,這意味着該網站(按照web.config)將完全打開,但所有控制器都會被默認鎖定,只要它們從ProtectedController繼承? – cbmeeks 2011-01-07 20:44:39

+0

@cbmeeks - 正確。另外,我認爲使用AuthorizeAttribute(或從中派生出來的東西),即MVC安全性,絕對比嘗試混合基於WebForms的安全性和MVC安全性更可取。 – tvanfosson 2011-01-07 21:09:38

1

您可以在您要始終允許控制器web.config文件中創建一個位置:

<configuration> 
    <system.web> 
     ... 
     <authorization> 
      <deny users="?" /> 
     </authorization> 
    </system.web> 
    ... 
    <location path="MyArea/MyController"> 
     <system.web> 
      <authorization> 
       <allow users="*" /> 
      </authorization> 
     </system.web> 
    </location> 
    ... 
</configuration>