2012-02-20 35 views
11

Tôi đang cố gắng thực hiện một số ủy quyền tùy chỉnh để tôi tạo một bộ điều khiển ghi đè phương thức OnAuthorization. Tôi cũng áp dụng thuộc tính Authorize cho bộ điều khiển này. Câu hỏi đặt ra là tại sao phương pháp OnAuthorization được gọi là TRƯỚC KHI quá trình xác thực biểu mẫu cơ bản?Tại sao thực hiện onAuthorization trước khi xác thực?

Tôi muốn ủy quyền cho người dùng sau khi được xác thực. Tôi có thiếu gì đó không?

Đây là mã:

[Authorize] 
    public class AuthorizationController : Controller 
    { 
     protected override void OnAuthorization(AuthorizationContext filterContext) 
     { 
      base.OnAuthorization(filterContext); 

      if (filterContext == null) 
      { 
       throw new ArgumentNullException("filterContext"); 
      } 

      List<string> allowedControllers = new List<string>() { "SecurityController" }; 
      List<string> allowedActions = new List<string>() { "Index" }; 

      string controllerName = filterContext.Controller.GetType().Name; 
      string actionName = filterContext.ActionDescriptor.ActionName; 

      if (!allowedControllers.Contains(controllerName) 
      || !allowedActions.Contains(actionName)) 
      { 
       filterContext.Result = View("UnauthorizedAccess"); 
      } 
     } 
    } 

Bộ điều khiển mà tôi thử nghiệm với một cái gì đó như:

public class SecurityController : AuthorizationController 
{ 

    public ActionResult Index() 
    { 
     return View(); 
    } 

    public ActionResult AnotherIndex() 
    { 
     return View(); 
    } 
} 

Trả lời

15

Một trong những điều đầu tiên AuthorizeAttribute không được kiểm tra xem nếu người dùng được xác thực . Nếu không thì đó là khi chuyển hướng đến trang đăng nhập sẽ được phát hành.

Các AuthorizeAttribute về cơ bản kết thúc tốt đẹp thẩm định kiểm tra với các mảnh ủy quyền:

protected virtual bool AuthorizeCore(HttpContextBase httpContext) { 
     if (httpContext == null) { 
      throw new ArgumentNullException("httpContext"); 
     } 

     IPrincipal user = httpContext.User; 
     if (!user.Identity.IsAuthenticated) { 
      return false; 
     } 

Khi bạn sử dụng AuthorizeAttribute không có vai trò/người sử dụng như bạn làm trong ví dụ của bạn ([Duyệt]), nó là cơ bản chỉ kiểm tra để đảm bảo người dùng được xác thực trong trường hợp này.

Tôi có thể thay đổi mã của bạn để ghi đè AuthorizeAttribute thay vì thực hiện mã này trong bộ điều khiển của bạn. Bạn có thể làm như sau:

public class CustomAuthorizeAttribute : AuthorizeAttribute 
{ 
    public override void OnAuthorization(AuthorizationContext filterContext) 
    { 
     filterContext.Result = CreateResult(filterContext); 
    } 

    protected ActionResult CreateResult(AuthorizationContext filterContext) 
    { 
     var controllerContext = new ControllerContext(filterContext.RequestContext, filterContext.Controller); 
     var controller = (string)filterContext.RouteData.Values["controller"]; 
     var action = (string)filterContext.RouteData.Values["action"]; 
     // any custom model here 
     var model = new UnauthorizedModel(); 

     // custom logic to determine proper view here - i'm just hardcoding it 
     var viewName = "~/Views/Shared/Unauthorized.cshtml"; 

     return new ViewResult 
     { 
      ViewName = viewName, 
      ViewData = new ViewDataDictionary<UnauthorizedModel>(model) 
     }; 
    } 
} 
+0

Vâng, nó không xảy ra như tôi mong đợi. Đối với ví dụ trên, khi tôi muốn truy cập hành động AnotherIndex, tôi mong đợi để có được trang đăng nhập, nhưng tôi đang nhận được UnauthorizedAccess. – misha

+0

Sau khi chỉnh sửa: Tôi hiểu, nhưng nếu tôi ghi đè lên AuthorizeAttribute, tôi không có quyền truy cập để thực hiện các hành động khác như chuyển hướng người dùng đến trang cho biết anh ta không được ủy quyền thay vì không đăng nhập ... – misha

+0

@misha Chắc chắn rằng bạn làm. Điều gì khiến bạn nghĩ rằng bạn không thể? – Dismissile

-2
public override void OnAuthorization(AuthorizationContext filterContext) 
{ 
    base.OnAuthorization(filterContext); 
    bool flag = false; 
    string UserId; 
    string[] AssignedRights = null; 

    //Check if Http Context Contains User Name 
    if (HttpContext.Current.User.Identity.Name != null && HttpContext.Current.User.Identity.Name != string.Empty) 
    { 
     //Get User Id from HttpContext 
     UserId = HttpContext.Current.User.Identity.Name; 
     RoleRepository roleRepository = new RoleRepository(); 
     AssignedRights = roleRepository.GetRolesByUser(Convert.ToInt32(UserId)); 
     flag = IsUserAuthorized(filterContext, flag, AssignedRights); 

     if (flag == false) 
     { 

      filterContext.Result = new HttpUnauthorizedResult(); 
     } 
    } 

} 
0

Sau đây là một mẫu cho Custom Authorization Thuộc tính.

public class AuthLogAttribute:AuthorizeAttribute 
    { 

     public string View { get; set; } 

     public AuthLogAttribute() 
     { 
      View = "AuthorizeFailed"; 
     } 
     public override void OnAuthorization(AuthorizationContext filterContext) 

     { 
      base.OnAuthorization(filterContext); 
      IsUserAuthorized(filterContext); 
     } 

     private void IsUserAuthorized(AuthorizationContext filterContext) 
     { 
      // If the Result returns null then the user is Authorized 
      if(filterContext.Result ==null) 
       return; 

      //If the user is Un-Authorized then Navigate to Auth Failed View 
      if(filterContext.HttpContext.User.Identity.IsAuthenticated) 

      { 
       var vr = new ViewResult(); 
       vr.ViewName = View; 

       ViewDataDictionary dict = new ViewDataDictionary(); 
       dict.Add("Message", "Sorry you are not Authorized to Perform this Action"); 
       vr.ViewData = dict; 

       var result = vr; 
       filterContext.Result = vr; 
      } 

     } 
    } 

điều khiển của bạn sẽ như thế nào sau đây,

[AuthLog(Roles ="Manager")]  
     public ActionResult Create() 
     { 
      var product = new Product(); 
      return View(product); 
     } 

Cuối cùng tạo mới xem được chia sẻ Call "AuthorizeFailed".

Các vấn đề liên quan