2009-08-22 29 views
9

Tôi tự hỏi liệu tôi có thể ghi đè hành vi [Ủy quyền] mặc định trong ASP.NET MVC hay không. Tôi biết rằng tôi có thể tạo Bộ lọc hành động mới, tạo thuộc tính của riêng tôi và v.v. Tôi chỉ quan tâm nếu tôi chỉ có thể thay đổi hành vi [Ủy quyền] và thay thế hoạt động của nó bằng mã của riêng tôi?Có thể ghi đè lên hành vi mặc định của [Ủy quyền] trong ASP.NET MVC không?

Chỉnh sửa: Guys and Girls. Tôi đánh giá cao ý kiến ​​của bạn nhưng như tôi đã viết, tôi là không tìm cách giới thiệu thuộc tính [XYZAuthorize] mới. Tôi biết cách làm điều này. Tôi muốn giữ ký hiệu [Authorize] nhưng chỉ thay đổi cách nó hoạt động.

+7

Tại sao bạn muốn giữ tên "ủy quyền" thuộc tính và thay đổi hành vi của thuộc tính? Đó là một điều xấu để làm. Mọi người, khi họ thấy [Ủy quyền] họ mong đợi những gì nó sẽ làm. Nếu bạn thay đổi nó, đọc mã của bạn sẽ khó hơn nhiều. Ngay cả đối với bạn trong tương lai. –

+3

Tôi không đồng ý; nếu bạn tranh cãi điều này, bất kỳ điều hành hoặc phương thức nào quá tải/ghi đè sẽ sai. – Alex

+5

@ Alex: Tôi không đồng ý. Vận hành quá tải là một điều tốt. Đó là một điều xấu để lạm dụng nó. Ví dụ thông thường: bạn có một lớp Vector, bạn tạo toán tử "+". Nó rõ ràng những gì nó sẽ làm. Nhưng còn về toán tử "*" thì sao? Đó là một điều xấu để làm, nó là một sản phẩm chéo hoặc một sản phẩm chấm? Hoặc một loại sản phẩm tùy chỉnh khác? Vì vậy: quá tải là tốt, nhưng nó rất xấu khi bạn che giấu các quy ước. –

Trả lời

6

Vâng, hãy nhìn vào các tài liệu MSDN cho AuthorizeAttribute: http://msdn.microsoft.com/en-us/library/system.web.mvc.authorizeattribute.aspx.

Về cơ bản, bạn có thể ghi đè phương thức OnAuthorization() và tùy chỉnh hành vi. Còn có các phương thức ảo khác trên thuộc tính.

EDIT: Như Bruno đã chỉ ra, bạn có thể ghi đè phương thức AuthorizeCore(). Sự khác biệt chính là AuthorizeCore() lấy một HttpContextBase, trong khi OnAuthorization() lấy một AuthorizationContext. Một thể hiện của AuthorizationContext cung cấp cho bạn nhiều thông tin hơn, chẳng hạn như Controller, RequestContext và RouteData. Nó cũng cho phép bạn chỉ định một ActionResult.

AuthorizeCore() bị hạn chế hơn trong thông tin bạn có thể truy cập cũng như kết quả bạn có thể trả lại, nhưng nếu bạn cần ủy quyền dữ liệu được lưu trong bộ nhớ cache, thì logic của bạn cần xử lý trường hợp bạn không có bất kỳ dữ liệu bổ sung đó (vì dữ liệu được phân phát từ bộ nhớ cache trước khi yêu cầu được định tuyến thông qua đường dẫn MVC).

Như mọi khi, bạn cần phải hiểu kịch bản của bạn và các công cụ có sẵn và sự cân bằng giữa chúng.

+1

AuthorizeAttribute không chứa phương thức OnAuthorize. Bạn có nghĩa là OnAuthorization()? Dù sao, bạn không nên thay đổi nó, trừ khi bạn muốn một số nhức đầu khi thực hiện bộ nhớ đệm, vì nó là một phương pháp (OnAuthorization) mà đề với nó. –

9

Bạn có thể phân lớp bộ lọc AuthorizeAttribute và đặt logic của riêng bạn bên trong nó.

Hãy xem ví dụ. Giả sử bạn muốn luôn cho phép các kết nối cục bộ. Tuy nhiên, nếu nó là một kết nối từ xa, bạn muốn giữ logic ủy quyền thông thường.

Bạn có thể làm một cái gì đó như:

public class LocalPermittedAuthorizeAttribute : AuthorizeAttribute 
{ 
    protected override bool AuthorizeCore(HttpContextBase httpContext) 
     { 
      return (httpContext.Request.IsLocal || base.AuthorizeCore(httpContext))); 
     } 
} 

Hoặc bạn luôn có thể ủy quyền cho một địa chỉ từ xa nào đó (máy tính của bạn, ví dụ).

Vậy đó!

Edit: quên đề cập đến, bạn sẽ sử dụng nó giống như bạn sẽ sử dụng bộ lọc AuthorizeAttribute:

class MyController : Controller 
{ 
    [LocalPermittedAuthorize] 
    public ActionResult Fire() 
    { 
     Missile.Fire(Datetime.Now); 
    } 
} 
2

tôi thấy chỉ có 2 cách: trọng AuthorizeAttribute.OnAuthorization phương pháp hoặc tạo thuộc tính ủy quyền của riêng bạn từ đầu.

1) rất dễ dàng:

public class CustomAuthorizeAttribute : AuthorizeAttribute 
{ 
    public override void OnAuthorization(AuthorizationContext filterContext) 
    { 
     base.OnAuthorization(filterContext); 

     /// your behavior here 
    } 
} 

2) quá dễ dàng - chỉ cần nhìn vào ASP.NET MVC nguồn, AuthorizeAttribute.cs tập tin

+1

Bạn nên tránh tạo một thuộc tính ủy quyền từ đầu nếu bạn không muốn đau đầu khi bạn sẽ thực hiện bộ nhớ đệm ... thuộc tính Authorize từ ASP.NET MVC giao dịch với khía cạnh này rồi. –

1

Dường như bạn có thể triển khai bộ lọc tùy chỉnh như bình thường (và kế thừa AuthorizeAttribute nếu bạn muốn), rồi tạo ActionInvoker mới kế thừa ControllerActionInvoker và ghi đè GetFilters.Trong GetFilters, bạn gọi base.GetFilters() để lấy danh sách các bộ lọc, lặp qua AuthorizationFilters và thay thế các cuộc gọi tới AuthorizeFilter bằng các cuộc gọi tới bộ lọc tùy chỉnh của bạn.

Một cách khác là triển khai tư cách thành viên tùy chỉnh và nhà cung cấp vai trò, tùy thuộc vào những gì bạn đang cố gắng làm.

+0

Tại sao một người cần một ActionInvoker tùy chỉnh chỉ cho một bộ lọc ủy quyền đơn giản? –

+0

@Bruno: Bởi vì dường như không có cách nào khác để thay thế một bộ lọc khung với riêng của mình, chỉ để tạo ra những cái mới. – svinto

+0

Nhưng ... tại sao một người muốn * thay thế * bộ lọc khung? Nhìn nhận xét của tôi cho câu hỏi. Đó là một điều ngu ngốc để làm. –

4

Triển khai Nhà cung cấp vai trò của riêng bạn và đặt ứng dụng của bạn để sử dụng. Sau đó, thuộc tính Authorize sẽ tôn trọng mã athorization của bạn.

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