bubbleking
bubbleking

Reputation: 3601

How to properly customize an Attribute for custom security in MVC 4?

In an intranet web application at my company, numerous operations have a granular, custom security system which is used in each action/http method in our MVC controllers. Basically there are two enums; one is a set of actions that can be performed (this is extremely granular; practically every possible action has a corresponding value in the enum) and one is a set of our subcompanies. For the context of this question, I will call these enums Action and Company.

Each user in our system is associated to one Company and zero or more Actions. Inside each method in our controllers, somewhere along the way there is a check for if the current user has the right Action and Company value to be using that feature. Every controller has a "UserHelper" injected into it which contains the Company and list of Actions the authenticated user is associated with.

Approaching it this way, there is a lot of code duplication in that every method is doing its own check on these enum values and reacting to violations when necessary. I am hoping to reduce this all to a System.Attribute or System.Web.Mvc.AuthorizeAttribute which we can put on controllers or methods to automatically handle violations in a uniform way and not have to check for it within the methods. Something akin to:

public class MyController : Controller
{
    [RequireActionAndCompanyAttribute(Action = Action.MyMethod, Company = Company.AbcInc)]
    MyMethod()
    {
        // do stuff, but don't bother checking for the security values
    }
}

As mentioned, I am assuming I can inherit from System.Attribute or System.Web.Mvc.AuthorizeAttribute for this purpose. However, I'm struggling. I'm not sure how to adapt AuthorizeAttribute to use our own internal security implementation (based on Action and Company) rather than one of the ASP.NET Membership systems. And the plain old System.Attribute seems so vague that I'm thinking it wasn't designed for this kind of use at all. I'm also not sure how I'm supposed to pass anything to the methods in the attribute. When I put the attribute on a method, I just want to specify what Action and Company are required to continue, like in the code snippet above. But then, how do I pass the user's actual values for these into the attribute's validation method?

Upvotes: 1

Views: 343

Answers (1)

Niels V
Niels V

Reputation: 995

Use a custom attribute inherited from ActionFilterAttribute instead of the AuthorizeAttribute. You can inject your UserHelper in this class and override the OnActionExecuting method and set the Result property of the context when your condition isn't met.

Upvotes: 2

Related Questions