I found really a flexible security framework Apache Shiro. I successfully implemented authentication and authorization using Shiro.
One of appealing features of the framework is instance based security. I just copied example from Shiro website.
The following permissions are stored in the database.
printer:query:lp7200
printer:print:epsoncolor
The following code check if for a given printer instance, the current authenticated user has permission or not.
if ( SecurityUtils.getSubject().isPermitted("printer:query:lp7200") {
// Return the current jobs on printer lp7200
}
My question is that "Is this how permissions are stored in database?" Is there a better way to store instance based permissions?
Please let me know.
Thanks
Apache Shiro Authorization. Authorization, also known as access control, is the process of managing access to resources. In other words, controlling who has access to what in an application.
In Apache Shiro's terminologies, a Subject is any entity interacting with the system. It may either be a human, a script, or a REST Client. Calling SecurityUtils.getSubject () returns an instance of the current Subject, that is, the currentUser.
The SecurityManager is the center piece of Apache Shiro's framework. Applications will usually have a single instance of it running. In this tutorial, we explore the framework in a desktop environment.
One possible way of performing permission checks is to instantiate an instance of Shiro’s org.apache.shiro.authz.Permission interface and pass it to the *isPermitted methods that accept permission instances. For example, consider the following scenario: There is a Printer in an office with a unique identifier laserjet4400n.
How you store this information is entirely up to you. Your Realm
implementation is responsible for querying whatever datasource you're using and extracting permission data in the format you prefer.
Some people store them as strings directly (like those shown in your example), other people store them in a dedicated table (e.g. if using an RDBMS) (e.g. permission_type, target, action columns). You can associate the permission entities to roles or directly to users or to groups which are assigned to users, etc - however it makes sense for your application.
Your storage options are entirely up to you. You materialize the data however you wish to ensure the Realm.isPermitted(...)
operations function as expected.
Instead of implementing the Realm.isPermitted(...)
methods directly, many people find it more convenient to subclass the abstract AuthorizingRealm
class and override the doGetAuthorizationInfo
method and return AuthorizationInfo
instances that support permission representations.
In that method, you could query your datastore, translate the data returned into AuthorizationInfo
instances, and you'll be done (don't forget to enable authorization caching - you'll see a big performance benefit).
Overriding the Realm
isPermitted
methods is only necessary if you want very specific control over queries, etc.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With