-
Notifications
You must be signed in to change notification settings - Fork 5
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Modified permissions scheme #353
Conversation
e1339b7
to
460c84a
Compare
…rsion: 2.0.0 → 2.1.0 to test
…ess/scope modifiers + perms doc
460c84a
to
eb62b54
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So far so good. Everything is now in place to implement the effective permission.
Do you plan to make the generic one up front or update the rest api implementation first?
I will implement the generic resolution under |
Please check also for the thredds service as this is another tree based permissions scheme. |
Codecov Report
@@ Coverage Diff @@
## master #353 +/- ##
==========================================
+ Coverage 68.91% 69.67% +0.76%
==========================================
Files 65 65
Lines 7009 7324 +315
Branches 950 992 +42
==========================================
+ Hits 4830 5103 +273
- Misses 1961 1993 +32
- Partials 218 228 +10
Continue to review full report at Codecov.
|
…-type param error
…requirement-dev twitcher to test adapter
@dbyrns |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Review in progress.
@dbyrns adjusted with comment details as per review |
Regarding ea2455d, you were not supposed to start another PR for that? |
# explicit deny overrides allow if any already found | ||
if perm is None or perm_set.access == Access.DENY: | ||
effective_perms[perm_name] = perm_set | ||
if perm is None or (perm.type == PermissionType.INHERITED and perm_set.access == Access.DENY): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for the update, much easier to follow. I think it still miss a point about the perm.type == PermissionType.INHERITED.
If the perm is direct (line 312), an allow permission overrides any access type that has been inherited. It means that a direct "allow" takes precedance over inherited "deny",
Here, to override any inherited permissions the access type must be deny. It means that a "deny" group permission take precedance over other "allow" group permission.
In short, we should better explain the difference between INHERITED or DENY of line 316 vs INHERITED and DENY of line 324
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I feel that is what comments on lines 311 and 318 describe,
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll try to be more explicit. The following 3 rules should be clear while reading the comments:
- direct > inherited (line 311 is fine and line 318 cover the fact that once direct is set we're done, but line 314 put emphasis on DENY override ALLOW while opposite is true too (the reason why we got a type == inherited or access == DENY is not covered)
- direct DENY > direct ALLOW (line 314)
- inherited DENY > inherited ALLOW (line 321 is confusing because it's stating like previously while this time it's between group (the reason why we got a type == inherited and access == DENY is not covered)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe it is because of the way I parse the sequence that doesn't feel ambiguous for me.
- User > Group - so if Group was set (ALLOW or DENY) we don't care, we set whatever User permission says.
For this reason, the opposite use case is never true. - We then enter User branch. We are in the realm of User-only permissions. So DENY > ALLOW is the only thing to evaluate.
- ONLY THEN, once we established we are not evaluating User permissions, we compare only Group with Group.
- Again, the only thing to check is DENY > ALLOW resolution.
It is mostly for this reason I had 2 ifs before. It gave a clean distinction between the 2 phases (eval User > Group) and then, for each (DENY > ALLOW).
If you think about it, the original 2nd if of the Group block is identical to the 2nd one of the User group
if perm is None or perm.type == PermissionType.INHERITED or perm_set.access == Access.DENY:
Only thing is that we have a redundant check for perm.type == PermissionType.INHERITED
since we evaluated that on the 1st if of the Group block, which is why it became if perm is None or perm_set.access == Access.DENY:
Making the if all-in-one for Group portion makes it more complicated to evaluate in my opinion because it introduces the mixing of Type and Access simultaneously.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
- [...] For this reason, the opposite use case is never true.
I meant if group was DENY, but user is ALLOW, allow override deny. Just explaining that would explain perfectly why we have a inherited or deny. For me line 311, 314 and 318 doesn't make that obvious.
- [...] So DENY > ALLOW is the only thing to evaluate.
This statement cover the second part of the if of l316. And the comment just above cover only that part. My point is reallly to cover the inherited part too. Comment should look like that : "permission is set if not already found (first occurence), if inherited regardless of access (direct > inherited) or deny (deny > allow)"
3 [...] we compare only Group with Group
Exact. But comment said "like previously" which compare direct with group and direct with direct.
I would change the comment to put the emphasis on the group with group and deny > allow to reflect the if, something like : "otherwise check for group permission, permission is set if not already found (first occurence) or if inherited (compare group with group only) AND deny (deny > allow)"
Sorry to be bothering, but I'm only looking to have better comments explaining what is going on for non-initiated, not to refactor the whole part.
Yes, look at the branch name permission-extensions This one is permissions-scheme |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good job with all that. The tests are pretty exhaustives!
Here is some issues I got with the UI:
- Cannot collapse tree using the small arrow (the text do the job but it's less obvious)
- The apply button position isn't appropriate for me, it's goal is not clear at first. Renamed to "Apply permissions" and moved to the bottom right under the tree view along with a Cancel button that simply refresh the page could do the trick, don't you think?
- I can leave the page with pending changes without any notice. Using https://stackoverflow.com/questions/7317273/warn-user-before-leaving-web-page-with-unsaved-changes and the dirty flag could solve that and even improve issue PAV-415 Improve Magpie UI #2 solution by enabling the button only when changes are done.
- Why the effective permission test button is only enabled with inherited permission checked? Is it because the effective resolution doesn't exist for the current user only? Maybe we should check the view inherited group permissions checkbox by default so that we can see this nice feature up front?
# explicit deny overrides allow if any already found | ||
if perm is None or perm_set.access == Access.DENY: | ||
effective_perms[perm_name] = perm_set | ||
if perm is None or (perm.type == PermissionType.INHERITED and perm_set.access == Access.DENY): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll try to be more explicit. The following 3 rules should be clear while reading the comments:
- direct > inherited (line 311 is fine and line 318 cover the fact that once direct is set we're done, but line 314 put emphasis on DENY override ALLOW while opposite is true too (the reason why we got a type == inherited or access == DENY is not covered)
- direct DENY > direct ALLOW (line 314)
- inherited DENY > inherited ALLOW (line 321 is confusing because it's stating like previously while this time it's between group (the reason why we got a type == inherited and access == DENY is not covered)
removed_perms, new_perms = \ | ||
self.edit_user_or_group_resource_permissions(user_name, res_id, is_user=True) | ||
elif "edit_permissions" in self.request.POST and not inherit_grp_perms: | ||
# FIXME: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why doing stuff in batch remove the need to add remote ressources?
If I want to add a permission on something that doesn't already exist, it seems like the add_remote fct should be required, no?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I actually never understood that operation... in order to add a new permission on a resource, the resource must exist already (locally), or it wouldn't be listed in the tree to had the permission on it in the first place...
The only use case I can see is to fetch new resources from the remote-service to populate missing ones locally (Magpie's representation of the real resources), which is what the sync-button is for (already available).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is because david c. did that part, but the trick is that the ui shows ressources that doesn't exist in magpie db. It is using the synched remote ressources db (if I remember correctly) and mix it with the magpie ressources.
So the synch doesn't really populate the magpie ressources, but the remote db and the mix occurs in real time for the ui. So checking a ressource doesn't mean that it already exists. If that ressource came from the remote db it must first be added to the magpie db before setting its permission.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We will need to revisit this whole functionality IMHO. It is not very well maintained.
For example, we cannot update the service type at later date using the API, and creating a service via the UI doesn't provide any selector to specify which one we want.
I have also booted a quick demo THREDDS server and it fails to sync files (with force sync button) due to internal parsing.
Yes. The event is only on the line-text. I struggled a bit to make it work because adding the event directly on the list-item was firing when clicking on the selects. I defined a "hover-area" using the text only to avoid it. I can try looking into adding the event only on the
I agree with renaming it to make it more explicit. The reason I put the button on top was purposely to avoid the situation of changing permissions and forgetting to press apply at the bottom without going into the full dirty form handling. Looking at the link, it seems like validating that items were modified is more troublesome than it looks. Quick method doesn't work for selects... need to had many flags to handle edge cases, and then, many different browsers work differently or come keys/mouse-clicks won't work. I feel it is too much effort to be worth it, and we will probably hit edge cases were minor edits spams for "validate to leave page warnings" that I will forcefully disable anyway. Sadly, I think the best will be "make the error once and then you know for the future".
Yes. Effective are by definition user+inherited. When testing, I found that it was really confusing to have only user permissions displayed and have things allowed/denied without the corresponding checkboxes and permissions displayed in the selects. I find I go into that view way more often to set permissions than to test effective ones. I also find viewing user+group permissions by default is not natural since we arrive there from clicking "Users" button. We would be greeted with a page full of inactive options, and it is not intuitive to know we need to click the checkbox to make them active. |
@dbyrns Regarding the permission, is your user an admin? If so, you got full access for effective permissions. |
Haha, that's it! Everything works fine. |
Regarding my 4 issues :
|
I found a way to do it using a fake div area. I couldn't apply the event on the marker directly.
It doesn't align very nicely with
Sounds good. |
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well done! Another great addition to Magpie.
Fixes #235
Fixes #342
Tasks
Summary of things listed in #342 that are being addressed:
update: no extensive UI unittest, done manually while implementing
make UI checkbox display effective permissions (disabled, read-only permissions resolved according to access/scope)update: resolution per-resource computation is heavy with many items. Will require specific function that resolves them all at the same time to speed up. (moved to [Feature] UI rendering of effective permissions against applied permissions #362).
add
BROWSE
permission toTHREDDS
'sDirectory
to allow listing of catalog contents.READ
becomes relative only toFiles
(althoughDirectory
can have it forRECURSIVE
resolution, but does not employ it by itself.update: moved to [Feature] BROWSE permission for ServiceTHREDDS #361, see Modified permissions scheme #353 (comment)