I'm implementing a web based document management system and I'd like to implement ACLs in my system.
My formal requirements are hierarchal permissions (documents inherit permissions from their folders) user groups (users can dynamically create groups and associate users with groups). Such groups can have permissions on objects in the system.
My code will query permission on objects in two cases:
1. Manipulating a single document
2. Listing all documents where a manipulation is possible
The latter requirement seems the achilles heel for Spring Security ACLs (their method seems likely to incur multiple DB hits for each document I manage)
Anyone know of another ACL implementation?
Thanks!
I'm not familiar with Spring Security's ACLs, but I believe that typical ACL's do you require you to hit each node to discover whether a given principal has permissions on that node. I don't know if you are going to find a way around that problem without making a canRead() or canAccess() call (or something similar) each time on each the nodes you are presenting.
As an aside:
Have you evaluated using something that's JSR-170 compliant (Java Content Repository or 'JCR') instead of rolling your own full document management system implementation? Potentially, you could use the things in JCR for the backend and simply write a web interface on top of it. Jackrabbit has a default ACL implementation that should suffice.
Related
So my company decided that it needs some kind of system / service that has the following properties:
Uses Java and Spring-Boot as a Back-End
Has an Angular Front-End for and Admin UI
Uses mongoDB for persistence
The system should include following functionality:
Users (Experts, Data-Engineers, Developers) should be able to define the data model including dynamic types having a set of properties and relationships via an Admin UI.
The system should support multi-tenancy, meaning that it should integrate multiple clients from different tenants.
It is important, that different clients have different projections of the data when reading, meaning that not all clients are allowed to read all the properties of an entity, but are restricted to what has been configured for them.
There must be some kind of validation for the properties (e.g. if it is of type string it must follow a common pattern, if it is of type enum only certain values are accepted)
I did some research and came to the conclusion that there are certain drawbacks with this proposed solution being:
using java for handling dynamic types
favoring abstract code instead of an explicit data model violating the "use before re-use principle"
I also fear, that we are re-inventing the wheel - meaning that there might be existing solutions for dynamically defining a data model.
I have to take these decisions as a given and try to find a way to still use existing implementations as far as possible.
In the end it will adapt a pattern similar to the EAV model. In my opinion there will be almost no possibility to adapt domain specific language and rules, since it aims to be as abstract as possible. It seems to me that it is a clear case of the inner-platform-effect, meaning that it will be result in a system that is
"so customizable as to become a replica, and often a poor replica, of
the software development platform they are using"
Nonetheless I have to deliver some kind of implementation which has to move within this frame.
I don't want to re-invent the wheel and create a proprietary solution - so I am thinking about using at least some standard for solving this issue, as for example generating json-schema from the user configuration instead of inventing my own data structures and validation logic.
Has anyone experience with json-schema and dialects or can point me to any other solution that I can adapt to make my life easier without having to come up with a home-made solution?
PS: I am not sure if these design questions belong to SO or any other place, so please let me know if you think I misused SO
I'm looking at using Apache Jackrabbit for a personal project but would like to know what are the advantageous/disadvantageous to using it versus a custom content repository or traditional database with content stored in the file system.
I'm not sure that I like the tree structure of the JCR so if you can explain the design decisions (adv/dis) behind that it would also help.
There are several benefits to using an existing JCR implementation, such as Jackrabbit or ModeShape. First and foremost, you immediately get lot of functionality for free:
Hierarchical data storage - Lots of data is naturally hierarchical, and a JCR repository allows you to organize your data in the way that your applications will access it. Anything keyed by a URI, date/time, categories, or folder structures are natural fits for storing in a repository.
Use a standard Java API - The JCR API is standard Java API with a TCK, meaning your applications can rely upon standard behavior and not be tied to a particular JCR implementation.
Flexible schema enforcement - You can choose whether and where the node structure and property values are enforced by how you define and use node types.
Data evolution - Your data structure will likely evolve over time, and JCR makes this very easy to do.
Query and full-text search - Your applications can navigate through the data, or they can query for content independently of location. The JCR query languages are very rich, and they support full-text search.
Transactions - You can control the transaction boundaries, which means that JCR Sessions can participate in JTA transactions controlled by your application or its container.
Events - Your applications can be notified when nodes and/or properties are added, changed, or removed.
Clustering - Scale your application by clustering the JCR Repository across multiple processes. Each implementation configure clustering differently, but they behave the same to client applications.
Versioning - JCR includes a standard mechanism for versioning content. It might not be suitable to all use cases, but it is extremely handy when it is a fit.
Locking - JCR includes a standard mechanism for short-term locks, which are useful when your applications need to ensure parts of the repository are updated by only one process.
If some of these features are important to you, then you should definitely consider reusing an existing implementation rather than rolling your own - otherwise you'll be spending all your time implementing these kinds of features.
However, if none of these features fits your use case, then you should consider other data storage technologies:
Relational databases work great when your data is very constrained, when your schema is not likely to change too often, or when your data is flat (lots of values of a few key types). (Note that many JCR implementations can store the content inside relational databases, so "I have to store my data in a relational database" is not really a good reason for your application to directly use a relational database.)
Key-value stores work great when you need to store arbitrary values by unique keys, and all access is via gets and puts. The values are usually opaque to the store.
Document stores are similar to key-value stores, except that the store is aware of the structure of the values. Some document stores support queries.
Other storage technologies have their own sweet spot.
Other things to consider are whether you need or want an eventually-consistent database or a strongly-consistent database. It's far easier to write many "conventional" applications against strongly-consistent databases, and in fact most JCR repositories (including Jackrabbit and ModeShape) are strongly-consistent.
I asked a similar question earlier, and this is an extension to it. Basically, we need to have auditable logs for legal reasons of permission/user management and authentication attempts. Our permissions and users are stored in an LDAP service, and I was wondering what auditing libraries were available for usage? Are there any? Is it better to use an auditing library that is a little higher level? Are there any good resources on what auditing should be and how it is traditionally done?
For me, what you are looking for, is particular for each Directory server. Because 'Authentication' is more defined as an interface than a feature, and 'Permissions' are just non standard.
Authentication is normalized via "simple bind" or "SASL", but the behaviour of the server (log) are not a standard as far as I know.
Permissions, I mean Access Control List (ACLs) are a non standard feature. The way permissions are implemented in Active directory, is different from the way they are implemented in Sun e-Directory (special attributes). For example in OpenLDAP permissions are implented in a kind of access filter.
So my advice is to start from you Directory Server and have a look on what exists.
LDAP keeps its own audit logs, at least OpenLDAP does, or can be made to.
I'm designing the security subsystem for a new product. The system requires the following:
Complex user/group/permission model, both service-level and domain-level (ACL)
Administration UI for the above
Rules performed upon user actions (account disable on failed login, password complexity requirements, etc).
Before going ahead and implementing most of the features that Spring Security (2.x) lacks, I was wondering if anyone is familiar with and can recommend a package that may already implement / support these requirements? ideally JAR + WAR that can be dropped into the project and support everything off-the-shelf.
Thanks
Not exactly what you are looking for, but you might be interested in checking out jSecurity. It is a well thought out security framework that handles authentication, authorization, and fine-grained permissions. But from what I can gather, much like Spring Security, they try not to make assumptions about how this data is stored and organized. (I haven't found, for example, a reference implementation for User, Roles, Permissions, etc. in a database.)
Note that the JSecurity project has permanently moved to the Apache Software Foundation and is now known as the Apache Shiro project.
Interesting you asked, I also have a very similar requirement and have been searching this for a while. I gave up and started doing it myself and have some decent progress in the last 2 weeks. Currently I have support for domain ids that are not necessarily Long, it could be anything such as a wild-card string to denote a group of things that could be granted to an authority (ROLE, GROUP, USER) or a String id or even a long. Multiple permission types each with their or sets of permissions can be defined and these permission types could be assigned as supported to a secured entity and the instances be protected by them, so you don't have the limitation of a maximum of 32 possible permissions across the system. Also you could use any actual or virtual entities in the ACL configuration. All this is based on the new (3.0.0.R1) of Spring security with method expression support and it works fairly well. The whole thing uses hibernate so you can take advantage of the transparent persistence and distributed caching. There are lots of rough edges, but being a proof of concept its expected. Anyways let me know if you are interested and we could collaborate to make this useful to us and probably others too.
I'm looking at creating a decentralized role-management system which integrates with Java EE roles. Does anything like this exist?
Example use cases:
System A is a limited-access system which uses corporate roles. John joins a team, and requires SYSTEM_A_READONLY to perform his function. He logs on to the decentralised role-management system, and puts in a request for SYSTEM_A_READONLY. Bill is the administrator for System A, and receives a notification that John has applied for this access. He can then log on to the same system and approve the request. John now has access to System A.
System B is a sensitive customer management system. It has 1 role for each company that it serves. Currently it has SYSTEM_B_CLIENT_FOO, SYSTEM_B_CLIENT_BAR, etc. Greg is the administrator for this system, and he is notified by the sales team that TNT have signed on as a customer. He logs on to the role management system, and adds the new client. Web Application C (hosted remotely, but still using corporate roles) detects the new role, and adds it as an option for it's users.
Hope that makes sense. I've looked into making it myself, but it seems like a requirement that must be quite common.
I don't think anything like this exists. The requirement indeed seems quite common, but I think appearances are deceiving. Every company, for ever (range of) application(s), will have very specific requirements concerning the interface to administer users and roles.
Depending on the requirements, it may also be reasonably simple to set up. If 'putting in a request' simply means 'an email is sent to the admin' and 'adding the client' means logging in using a simple, CRUD-framework generated, admin and filling out a form, then you are already done.
You could look at Apache Shiro http://incubator.apache.org/shiro/ although I'm not sure it's either ready for prime time or completely does what you're looking for out of the box.
You could develop the authorization components using Spring Security, specifically by implementing your own AccessDecisionVoter and UserDetailsService. The entities, persistence and web ui components are pretty straightforward, you could do those in whatever framework you're comfortable with.
There are some products out there to help you - things like crosslogix from bea.
These are generally logic decision engines that let you craft complex rules that allow for things like roles and permissions to be nested and hierarchal. they also (generally) allow for parameterized permission checks like user is in role ACCOUNT_APPROVER if it's the last week of the month.
"Detecting new roles" generally comes as a by-product of having the centralized system - i.e everything just queries it, and the API is very fast specifically to make querying a 'cheap' operation.
What they are generally not so good at (I guess as they perceive it's not in their space) is the workflow around approving access to these roles. They'll generally give you a console ( & an API ) to modify them, but leave the approval workflow up to you.
As the previous poster said - the problem with the approval bit is that it tends to be very company specific - so it's often left as an API.
In short - something like crosslogix would do half of what you need - the decision logic, and this, and most products give you a simple uber-console to manage the permission logic, but if you wanted company specific logic for approvals - you'd probably have to skin a website on top.
-ace
Well, to me, such a system exists and is called LDAP (LDAP groups are typically mapped to J2EE roles). But I admit that LDAP engine doesn't provide all the facilities and workflows that you mentioned. Actually, my experience is that these are specific to each company (maybe because of the lack of "universal" tool) and, most of time, companies I've worked for had custom admin applications and custom APIs to interact with it from applications.
We have used something very similay to what you are asking . Icefaces has renderonUserRole propery for their components , this can be combined with Spring Security to achive part of what you need. See this