-
Notifications
You must be signed in to change notification settings - Fork 597
Add IAuthorizationHandlerProvider interface #1176
Comments
Looks like I can just implement my own IAuthorizationPolicyProvider and register it. Will give this a shot. Would be good to see this updated on docs.microsoft.com |
For your example you wouldn't need to head down that route, you'd just go off to your database during the evaluation of the policy, and pull down the group members, and the job manager during HandleRequirementAsync(). |
Not sure I follow - how do I allow an admin user change what the requirements are to meet a certain policy? E.g. I secure an area of the app to "Job Maintenance" policy. But don't want to hard code that it's always the "Manager of the Job" or the "Partners in the Group". I want the Administrative User of my app to make those decisions for their company. |
So you still apply the Job maintenance policy to the area. Then have a single requirement for that policy. In that requirement go off to the database, figure out what the actual requirements are, and evaluate them. |
If I'm following - why use the AuthorizationService at all? What's the point if I'm create my own policy, requirement, and mapping them together myself. Guess I'm missing the point here. The IAuthorizationPolicyProvider is registered to the services with TryAdd for a reason is it not? Seems that what you are suggesting violates SRP - a requirement that then has to act as a policy and map which requirements must be met and then also evaluate all those requirements? Requirements should be re-usable, and making a huge requirement to evaluate what requirements really diminishes reuse. |
You could go either way. The Provider was there because people weren't happy with just have policies. It gives the somewhat limited ability to, for example, build policies based on policy name, replacing the parameters in custom attributes folks used before. As for SRP, well that's a choice :) But unless you're restricting to a preset list of requirements in your database you're going to have to build them on the fly anyway, from whatever your ruleset requests, which makes them not reusable. Depends on the complexity of the rules. |
Ok - so I could implement multiple handlers - each needing to check the database to see if it's an enabled handler for the policy. Sees a bit useless to have them check if they are even needed though. I guess I'm expecting that to be able to be configured in the overall security configuration. Just thinking about this... Option 1... I see: IAuthorizationHandlerContextFactory which gets close, but does not have a means to get at the policy, so even using that cannot do this. Option 2... That sounds like an awful lot of duplicative framework code across the handlers. Sure seems like a really valuable mapping is missing from this framework. I think where this missing mapping lies is a means to filter the handlers within the AuthorizeAsync method of the DefaultAuthorizationService. Perhaps that's the custom bit I need to implement, not injecting a IEnumerable into the constructor, but something like a IAuthorizationHandlerProvider that has a method to return Handlers specific to a set of requirements and optionally Policy, instead of just all handlers for the requirement. |
I would recommend the IAuthorizationPolicyProvider, while it was added for the specific scenario @blowdart refers to, its intent is to do exactly what you describe (dynamically map a policy name to requirements at runtime) |
So, what I think I will try is the following:
That way I can map which handlers are available to check for access to a specific area (secured by a specific policy) in my application, with each handler gaining full re-use (e.g. the check for is the user in this role, or is the user the manager of this resource). Any downside to that approach? |
@HaoK the difference from IAuthorizationPolicyProvider and creating a IAuthorizationHandlerProvider going to be that I will end up having to meet all requirements (AND) instead of giving my user many ways to meet the requirement (OR). Per my requirement, I'm looking for the OR (Job Manager) or (Partner Role) can satisfy the policy. |
Ah yes, if you want OR behavior, that's a concern for how a particular requirement is handled. Implementing your own custom service implementation seems fine for filtering which handlers get executed to prevent hitting the db. This doesn't seem like an unreasonable abstraction for us to add in 2.0 actually, we should consider adding that ourselves @blowdart |
Fair enough, make it so Mr @HaoK :) |
@rposener there's also another option you can consider. You can have each requirement also be a handler, and if they are all really HasAccess where if any of them ever succeed you want to pass, then you can have that implementation succeed EVERY requirement in the the request, then you would just need to implement Success short circuiting in your custom authorization service. Basically execute every handler, but check if you can shortcircuit returning true if all the requirements have been met after running each handler. Not sure I like this route better, but it should also work. |
@HaoK I see what you mean - just have the handler go ahead and mark the other requirements as succeeded. Effectively turning the AND to an OR. Only down side is that it will break in the event I did need to add a AND to the policy. Not sure I like that either. |
Is it possible to Map Policies to Requirements at Runtime? E.g. I would like to secure parts of an app using policies ("Job Maintenance") but allow administrative user in my app to map them to certain requirements (stored in DB) and updated during runtime. For example ("In Partners Group" or "Is Manager of Job") might be mapped to the "Job Maintenance" policy.
Is there a way to provide this kind of mapping during runtime? Or change the ones that are currently loaded except to restart the app?
The text was updated successfully, but these errors were encountered: