Thanks, Brian!

There you go, Richard, you can comment / upvote that one.

> On Jul 7, 2016, at 8:18 AM, Brian Demers <[email protected]> wrote:
> 
> Take a look at this one: https://issues.apache.org/jira/browse/SHIRO-314 
> <https://issues.apache.org/jira/browse/SHIRO-314>
> 
> 
> On Thu, Jul 7, 2016 at 4:46 AM, Lenny Primak <[email protected] 
> <mailto:[email protected]>> wrote:
> Ok, you can open an enhancement JIRA with that.
> 
> > On Jul 7, 2016, at 3:43 AM, Richard Adams <[email protected] 
> > <mailto:[email protected]>> wrote:
> >
> > Well, Spring Security implements ACL;
> > http://docs.spring.io/spring-security/site/docs/3.0.x/reference/domain-acls.html
> >  
> > <http://docs.spring.io/spring-security/site/docs/3.0.x/reference/domain-acls.html>
> >> On 7 Jul 2016, at 09:42, Lenny Primak <[email protected] 
> >> <mailto:[email protected]>> wrote:
> >>
> >> The tricky thing is to figure out what the common feature set actually is 
> >> (i.e. to design it or take already existing design)
> >> Is there another framework that you know of or any existing project that 
> >> implements this already?
> >> If this was such a desirable feature for lots of people, it would be hard 
> >> to believe that this wasn’t already implemented somewhere.
> >>
> >>> On Jul 7, 2016, at 3:39 AM, Richard Adams <[email protected] 
> >>> <mailto:[email protected]>> wrote:
> >>>
> >>> Yes, I take your point - Shiro has all the Core features you need to get 
> >>> started, it’s conciseness is one of its main attractions, and there’s 
> >>> certainly a strong argument to avoid feature bloat and unnecessary 
> >>> complexity.
> >>> But, perhaps it is the case, that if many Shiro users are independently 
> >>> having to extend Shiro to obtain additional similar functionality, then 
> >>> there is a case for considering adding to Shiro.
> >>> Richard
> >>>> On 7 Jul 2016, at 09:26, Lenny Primak <[email protected] 
> >>>> <mailto:[email protected]>> wrote:
> >>>>
> >>>> My sentiments exactly.
> >>>>
> >>>> There are a lot of SNACs (shiny new ACronyms) popping up every few 
> >>>> months that “some other framework” may have that are “missing” from 
> >>>> Shiro,
> >>>> like many variants of **BAC (which are very much too vaguely defined, 
> >>>> and not in any way standard)
> >>>> All of this can easily be solved by a few lines of custom code (in 
> >>>> custom realm etc.)
> >>>> You can’t possibly chase all those vague acronyms and succeed.
> >>>>
> >>>> Saying that, I am not opposed to adding some sort of additional 
> >>>> abstraction layer for **BAC, but it has to be well defined.
> >>>>
> >>>> Here is what I see as viable options:
> >>>> - Write an implementation yourself on top of Shiro, get traction in the 
> >>>> wild, and then contribute it to Shiro, if still makes sense.
> >>>> - Point out specific code / features / documentation in another 
> >>>> framework that implements your feature that has traction in the industry,
> >>>> i.e. has proven useful in the wild, and propose inclusion of such 
> >>>> specific functionality in Shiro.
> >>>>
> >>>>> On Jul 7, 2016, at 3:02 AM, Richard Bradley 
> >>>>> <[email protected] <mailto:[email protected]>> 
> >>>>> wrote:
> >>>>>
> >>>>> Could you explain what the benefit of this is over just implementing 
> >>>>> those restrictions in plain old Java code directly?
> >>>>>
> >>>>> Each of the use cases you have given could be translated into plain old 
> >>>>> Java code more or less 1-1 and the resulting code would be:
> >>>>> 1. simpler
> >>>>> 2. more maintainable
> >>>>> 3. more accessible to newcomers (no new language needs to be learnt)
> >>>>> 4. benefit from IDE support and static analysis support
> >>>>> 5. likely more reliable (there are fewer moving parts; no AOP framework 
> >>>>> is needed etc.; no chance of bugs in the implementation of 
> >>>>> @RequiresAttributes or misunderstandings in its usage)
> >>>>> 6. easier to test
> >>>>>
> >>>>> The only downside I can see is that it might be slightly harder to 
> >>>>> statically verify that a developer has remembered to address security 
> >>>>> (in the proposed version you might be able to write a unit tests that 
> >>>>> asserts that all relevant methods have a non-empty 
> >>>>> "@RequiresAttributes" annotation).
> >>>>>
> >>>>> Here are the examples from below rewritten in POJ:
> >>>>>
> >>>>> Assume the following helper code is imported in each case:
> >>>>>
> >>>>> public class AuthenticationHelper {
> >>>>> public static void assertAuth(bool ok) {
> >>>>> if (!ok) {
> >>>>>  throw new AuthenticationException("Insufficient permissions");
> >>>>> }
> >>>>> }
> >>>>>
> >>>>> public static User currentUser() {
> >>>>> // create a domain-specific User class from Shiro's 
> >>>>> SecurityUtils.getSubject()
> >>>>> }
> >>>>> }
> >>>>>
> >>>>> Example of use case #1:
> >>>>>
> >>>>> public class ProfileEditor {
> >>>>>
> >>>>> // all users implicitly have permission to edit their own profile,
> >>>>> // so don't need RequiresPermissions, but we do need to check
> >>>>> // that the profile belongs to this user
> >>>>> public void store(Profile userProfile) {
> >>>>>  assertAuth(currentUser().id == userProfile.userId);
> >>>>>
> >>>>>    // TODO: store the changes
> >>>>> }
> >>>>>
> >>>>> }
> >>>>>
> >>>>> Example of use case #2:
> >>>>>
> >>>>> public class Project {
> >>>>> List<String> getMemberIds() {
> >>>>>    // TODO: return list of member ids in this project
> >>>>> }
> >>>>>
> >>>>> // the user has role "project manager" with a "settings:edit" permission
> >>>>> // BUT... it's only for this project, not for all projects!
> >>>>> @RequiresPermissions("settings:edit")
> >>>>> public void editSettings(String key, String newValue) {
> >>>>>   assertAuth(getMemberIds().contains(currentUser().id));
> >>>>>
> >>>>>    // TODO: change the setting
> >>>>> }
> >>>>>
> >>>>> }
> >>>>>
> >>>>> Example of use case #3:
> >>>>>
> >>>>> public class ClassifiedDocumentRepository {
> >>>>>
> >>>>> @RequiresPermissions("documents:store")
> >>>>> public void storeDocument(@Map("document") Document doc) {
> >>>>>    assertAuth(currentUser().clearanceLevel >= document.clearanceLevel);
> >>>>>    // TODO: store the document
> >>>>> }
> >>>>>
> >>>>> // applying access control on return value here with special variable 
> >>>>> $return
> >>>>> @RequiresPermissions("documents:retrieve")
> >>>>> public Document retrieveDocument(String documentId) {
> >>>>>    // TODO: find the document and its metadata
> >>>>>
> >>>>>    Document document = ...
> >>>>>
> >>>>>    assertAuth(currentUser().clearanceLevel >= document.clearanceLevel);
> >>>>>    return document;
> >>>>> }
> >>>>>
> >>>>>
> >>>>> }
> >>>>>
> >>>>> Best,
> >>>>>
> >>>>>
> >>>>> Rich
> >>>>>
> >>>>>
> >>>>>
> >>>>> -----Original Message-----
> >>>>> From: jbuhacoff [mailto:[email protected] 
> >>>>> <mailto:[email protected]>]
> >>>>> Sent: 07 July 2016 05:19
> >>>>> To: [email protected] <mailto:[email protected]>
> >>>>> Subject: Attribute-based access control
> >>>>>
> >>>>> Hi, I've been using Shiro for a couple of years now in various projects 
> >>>>> with annotations and the wildcard permission syntax. Now I have a new 
> >>>>> requirement for ABAC, and I think it should be possible to add this 
> >>>>> capability to Shiro.
> >>>>> I have a proposal below, and wanted to get some comments.  If there's 
> >>>>> interest,  I would develop it myself and contribute the code & 
> >>>>> documentation.
> >>>>>
> >>>>> Here are some use cases:
> >>>>>
> >>>>> 1. a "my profile" or "my settings" feature:  user should be able to 
> >>>>> edit own things but not everything in the table.
> >>>>>
> >>>>> 2. project or organization based permissions:  user should be able to 
> >>>>> read documents in a project while user is associated with the project 
> >>>>> or team, possibly combined with a general "can read documents" 
> >>>>> permission.
> >>>>>
> >>>>> 3. clearance level:  user has a "can read documents" permission but 
> >>>>> this needs to be matched with the user's clearance level and the 
> >>>>> document's clearance level.
> >>>>>
> >>>>> I see attribute-based access control as being a nice complement and 
> >>>>> orthogonal to the permission-based access control.  A given method 
> >>>>> could be annotated with either one or both together to achieve the 
> >>>>> right level of control.
> >>>>>
> >>>>> My proposal is to add a new annotation  @RequiresAttributes   and to 
> >>>>> let its
> >>>>> value be a boolean expression to be evaluated.  Of course the 
> >>>>> expression will need to be able to refer to the current user, the 
> >>>>> object in question, and maybe even other things like the time of day, 
> >>>>> the https client certificate, or whatever. Getting these bits of info 
> >>>>> into the context of the expression language would be a combination of 
> >>>>> three things:  1) the realm can set some context when the user is 
> >>>>> authenticated based on information available at that time (user 
> >>>>> attributes, connection attributes, etc.) , 2) there could be generic 
> >>>>> "attribute injectors" like for calendar/time, system properties, or 
> >>>>> other things that are neither user nor object in question;
> >>>>> 3)  a new @Map annotation that can be applied to method parameters in 
> >>>>> order to give them a specific name in the expression.
> >>>>>
> >>>>> Also there is a special case when we might want to apply 
> >>>>> attribute-based permissions on the return value of a method. For this 
> >>>>> we have another annotation @RequiresAttributesOnReturn which would be 
> >>>>> applied with around advice, calling proceed() and then checking 
> >>>>> permissions using the return value of the original method bound to a 
> >>>>> special variable $return.
> >>>>>
> >>>>> Both @RequiresAttributes and @RequiresAttributesOnReturn would have 
> >>>>> corresponding methods that could be called directly from anywhere in 
> >>>>> the code in order to perform the same evaluation without annotations.
> >>>>>
> >>>>> Special variable $this would be available to expressions annotated on 
> >>>>> instance methods.
> >>>>>
> >>>>> Variables and methods of objects would be accessible via dot notation, 
> >>>>> with automatic use of bean-style "getter" methods when they exist.
> >>>>>
> >>>>> In all the following examples, $user is a variable bound by the 
> >>>>> authentication realm to a User object with methods String getId() and 
> >>>>> Integer getClearanceLevel().
> >>>>>
> >>>>> Example of use case #1:
> >>>>>
> >>>>> public class ProfileEditor {
> >>>>>
> >>>>> // all users implicitly have permission to edit their own profile,
> >>>>> // so don't need RequiresPermissions, but we do need to check
> >>>>> // that the profile belongs to this user
> >>>>> @RequiresAttributes("$user.id <http://user.id/> = $profile.userId")
> >>>>> public void store(@Map("profile") Profile userProfile) {
> >>>>>    // TODO: store the changes
> >>>>> }
> >>>>>
> >>>>> }
> >>>>>
> >>>>> Example of use case #2:
> >>>>>
> >>>>> public class Project {
> >>>>> List<String> getMemberIds() {
> >>>>>    // TODO: return list of member ids in this project
> >>>>> }
> >>>>>
> >>>>> // the user has role "project manager" with a "settings:edit" permission
> >>>>> // BUT... it's only for this project, not for all projects!
> >>>>> // also special variable $this refers to enclosing class instance
> >>>>> @RequiresPermissions("settings:edit")
> >>>>> @RequiresAttributes("$this.memberIds.contains($user.id 
> >>>>> <http://user.id/>)")
> >>>>> public void editSettings(String key, String newValue) {
> >>>>>    // TODO: change the setting
> >>>>> }
> >>>>>
> >>>>> }
> >>>>>
> >>>>> Example of use case #3:
> >>>>>
> >>>>> public class ClassifiedDocumentRepository {
> >>>>>
> >>>>> @RequiresPermissions("documents:store")
> >>>>> @RequiresAttributes("$user.clearanceLevel >= $document.clearanceLevel")
> >>>>> public void storeDocument(@Map("document") Document doc) {
> >>>>>    // TODO: store the document
> >>>>> }
> >>>>>
> >>>>> // applying access control on return value here with special variable 
> >>>>> $return
> >>>>> @RequiresPermissions("documents:retrieve")
> >>>>> @RequiresAttributesOnReturn("$user.clearanceLevel >=
> >>>>> $return.clearanceLevel")
> >>>>> public Document retrieveDocument(String documentId) {
> >>>>>    // TODO: find the document and its metadata
> >>>>>    return document;
> >>>>> }
> >>>>>
> >>>>>
> >>>>> }
> >>>>>
> >>>>>
> >>>>>
> >>>>>
> >>>>>
> >>>>>
> >>>>>
> >>>>> --
> >>>>> View this message in context: 
> >>>>> http://shiro-user.582556.n2.nabble.com/Attribute-based-access-control-tp7581093.html
> >>>>>  
> >>>>> <http://shiro-user.582556.n2.nabble.com/Attribute-based-access-control-tp7581093.html>
> >>>>> Sent from the Shiro User mailing list archive at Nabble.com.
> >>>>>
> >>>>> Richard Bradley
> >>>>> Tel : 020 7485 7500 ext 3230 | Fax : 020 7485 7575
> >>>>>
> >>>>> softwire
> >>>>> Sunday Times Best Small Companies - UK top 25 six years running
> >>>>> Web : www.softwire.com 
> >>>>> <http://www.softwire.com/><http://www.softwire.com/ 
> >>>>> <http://www.softwire.com/>> | Follow us on Twitter : 
> >>>>> @SoftwireUK<https://twitter.com/SoftwireUK 
> >>>>> <https://twitter.com/SoftwireUK>>
> >>>>> Addr : 110 Highgate Studios, 53-79 Highgate Road, London NW5 1TL
> >>>>> Softwire Technology Limited. Registered in England no. 3824658. 
> >>>>> Registered Office : Gallery Court, 28 Arcadia Avenue, Finchley, London. 
> >>>>> N3 2FG
> >>>>>
> >>>>
> >>>
> >>
> >
> 
> 

Reply via email to