Looking for Domain Permission Framework
I am currently building a project that needs a permissions framework. The overall idea is that you have a user, an object and a set of permissions, and I need to verify whatever a user has or hasn't the specified permission on the object.
Problems:
- Permissions may be granted to a group, and a group may aggregate other groups.
- Aggregates always has their own set of permissions, but some permissions are inherited to child objects, some do not.
- Permission may be granted on a group of (unrelated) objects.
- Need for deny permission.
- It has to perform well for large amount of permission queries (I want to call it over set of objects returned from a query).
I considered AzMan, and it would be great, but as far as I know, it handles only roles, not permissions on objects, and while I could handle this using some sort of a naming convention, I would rather avoid it. Creating objects in Active Directory and using Windows Permissons on that is also not a good idea, most probably.
Any suggestions?
Comments
I thought AzMan let you go down to the level of objects? Grant you, you had to define what they were but it was broken down to roles, groups, tasks, and operations. You would have to map that to what object or method you wanted to perform.
Generally I've been using the ASP.NET providers as they give me roles and users for free and I just build an abstraction layer on top of it that I can use for whatever purpose.
AzMan doesn't do object-based permissions, at least as far as I know.
Ayende,
My short answer is to look at Enterprise Library 3.0 and use the Security Block combined with Policy Injection. I think it will provide you all you need. It is very flexible, especially when combined with Active Directory which is where I would personally store the groups / roles if you have that available to you. It works really well.
I would suggest moving the settings out of the .config file into a database so you can be more agile with the permissions. I'm writing a blog post about this now so stay tuned. Check out David Hayden's block, he has a lot of good info on EntLib.
http://www.davidhayden.com/blog/dave/archive/2007/03/03/PolicyInjectionApplicationBlockSample.aspx
Keith, thanks for the suggestion, but I have checked the security block, and I don't see it support per-object permissions, which is what I must use.
Frankly, the policy injection block isn't very interesting to me:
http://www.ayende.com/Blog/archive/2007/03/07/Building-the-Policy-Injection-in-40-Minutes-with-Windsor.aspx
Fair enough. So what is an example use case you want to see with how the permissions would be handled for objects?
Given customer A and customer B, I have permission to view customer A orders, but not customer B.
This is getting into quixotic territory. What you want is a "claims based" system. That is you want each user to have a list of claims (name, organization, role/group membership) and each object to have a list of claims required to gain access to a permission on this object. Rather you probably want that object to require a composite set of claims or what I'd call an expression. Furthermore it should have several discrete expressions that would allow a given permission to that particular object.
I've addressed this several times in several applications with varying degrees of success. It is a very hard problem. I think it's something you almost have to consider from the get-go. In a lot of cases I'd say an Entity Oriented UI is required, almost a quasi-"Naked Objects" approach. That is, something like you described is more easily achieved when you have a UI that says "okay user find this business object you want to deal with and invoke actions or tasks off of that."
You can, then, apply an expression to each user (reversing the model I describe above), so:
User A -> Sees Objects of Type B that Match Filter Expression C
User A -> Sees Objects of Type E that Match Filter Expression F
Assuming you can take the user experience architecture I like the idea of only using the domain layer for "actions" and building a seperate layer(s) for query where you provide an filter/interception point that handles the above. It works well, is easy to build administrative tooling around, user's grok it. All this assumes you can swallow the rather large constraint pills such an approach comes with.
Sorry for the book. This really should have been a post.
I agree with Dave, the claims-based model seems to be the way to go if you're really serious about doing this. Take a look at the System.IdentityModel stuff. You don't have to use it with WCF, but it plugs in nicely. You can create your own custom attributes that map to different claim types so you're not stuck with role-based security. These attributes can be enforced by CAS just like PrincipalPermissionAttribute.
So far I've only used this approach for permissions that are serialized into the attribute. You would probably have to take a non-attribute approach to enforce the matching of arbitrary user claims with the set of claims required by the object, most likely stored in a RequiredClaims collection on the object.
Check out Michele Leroux Bustamante's implementation of claims-based permission demands at http://www.dasblonde.net/downloads/wcf/WCFClaimsBased.zip
More background here which is where I found it: http://forums.microsoft.com/MSDN/ShowPost.aspx?PostID=731596&SiteID=1
Again, you can ignore all the WCF goop since you don't need WCF to make this work. Maybe I'll get around to posting a simplified version of this that demonstrates using different custom attributes for different claim types.
What about combination of AzMan and ADAM (Active Directory Application Mode)?
IIRC, AzMan has a concept of 'Operations' that could be used to implement the functionality you are desiring. The benefits I can see are the existing administration tools as well as the ability to inject VBScript to modify Operation security at run time.
-Bill
Have you looked at the Microsoft SAAS reference implementation? They would have had to address this issue: http://www.codeplex.com/LitwareHR
Hello I've develop a frameword in my app that use System.Security.AccessControl. I serialize acl in database and i can query very fast in my stored procedure. for each domain object i can define read/write/specific right allowed or desallowed with inheritance. Now I extend model to specify read/write/specific right to domain object property. Azman is for me a solution to secure commands and operations but not domain object.
While I'm not aware of a ready to use framework what about good old bitmasks? A single Int32 gives you enough ids to create an awful lot of permissions that can easily be assigned to objects etc.
Comparing and getting relevant permissions for an object is a simple AND operation between required and assigned permissions. Simple approach but worked well for me in previous solutions.
AzMan could be a definite consideration. I've used it extensively on some projects and found it very flexible and useful. It does a great job when tasks/operation level permissions is what you need instead of simple roles. (If you're only using it for roles it's overkill in my experience).
You could easily map task/operation => aggregate.
In my experience it has performed well when making multiple calls in a loop (for instance on one project we used it to toggle state of menu items based on a user's permissions to do the action indicated by the menu) YMMV.
http://www.codeproject.com/dotnet/AzManAccessComponent.asp has some example code (I haven't read in detail) and more importantly links to two great MSDN articles on using AzMan.
Did you find a solution for your problem?
Thanks
Marco
Comment preview