Hi, Chris. On Tuesday January 6, 2009 20:00:11 Chris McDonough wrote: > That sounds fine, as repoze.who does indeed set REMOTE_USER, and the > relationship between what and who right now is a little weird (what is > essentially a superset of who, which makes me a little nervous). Splitting > them apart seems about right.
Glad to know that. > I'm not sure *just* adding roles really cuts it for maximum generality. > Maximum generality may not be a goal here, however, and that's your call. > But I'll note that roles granted to users or groups seems to be just > another way to spell global assertions. > > A common thing to want to do is be able to make security assertions against > a *particular resource* (which might be represented as PATH_INFO in a URL, > or some object in a graph, or whatever). For example, you'd like to be > able to say that ("joe has permission to edit blog entry 1" and "joe cannot > edit blog entry 2") instead of "joe has permission to edit blog entries" > and then relying on imperative controller logic or decorators in the > downstream app itself to figure out whether joe has permission to edit > *this* blog entry. You can achieve that with repoze.what predicates. You can write your own predicate to check for that condition: # This has not been tested: from paste.request import parse_dict_querystring from repoze.what.predicates import Predicate class can_edit_THIS_post(Predicate): message = 'Only Bob can edit posts 1 and 2' def _eval_with_environ(self, environ): form_vars = parse_dict_querystring(environ) blog_id = form_vars.get('blog_id') user = environ.get('REMOTE_USER') # Ignore this if this post is not #1 or #2! if blog_id not in ('1', '2'): return True return user == 'bob' Then, for example, in a TG2-powered application, you would use it like this: from tg import require from repoze.what.predicates import All, has_permission from my_cool_app.predicates import can_edit_THIS_post class BlogController(BaseController): # ... @require(All(has_permission('edit-post'), can_edit_THIS_post())) @expose('my_cool_app.edit_post') def edit_post(self, blog_id, new_title, new_contents): # process the post edition... > I came up with a pattern for this in repoze.decsec (proposal at > http://www.plope.com/Members/chrism/decsec_proposal and implementation > notes at http://www.plope.com/Members/chrism/decsec_revisited). It's too > frameworky for general purpose use but it is implemented and described. Those documents are rather interesting. ACLs are a good alternative to predicate-based assertions, *and* I think they are not mutually exclusive. In fact, I think they may complement each other under some situations: * For example, repoze.decsec may use repoze.what predicates for conditions in ACEs: [ {'action':'allow', 'principal':'Bob', 'permission':'system.Write' 'condition': has_ip("192.168.1.5")} ] (where has_ip is a repoze.what predicate -- not yet written, AFAIK) * repoze.what may provide a predicate that evaluates an ACL in a given context. For example, if you have the following ACL: [ {'action':'allow', 'principal':'system.Everyone', 'permission':'application.Read'}, {'action':'allow', 'principal':'system.Authenticated', 'permission':'application.Write'} ] with plain repoze.what predicates in TG2 you could use: # ... @require(not_anonymous()) def Read(self): pass @require(Not(not_anonymous())) def Write(self): pass but with ACLs, repoze.what may provide the eval_acl predicate (for example) which will use an ACL loaded in the repoze.what middleware and could be used in the fake TG2 controller in question as: # ... @require(eval_acl()) def Read(self): pass @require(eval_acl()) def Write(self): pass (eval_acl would pass the script path in the environ to evaluate the ACL against the resource in question) To sum up, I think ACL support would be a great addition to repoze.what, instead of plain roles granted to users/groups, as an alternative (not a replacement) to the current groups/permissions-based pattern with individual predicate assertions. But I wonder what would be the best way to support ACLs... * Support ACLs through a plugin that uses repoze.decsec? * Support ACLs in repoze.what itself using repoze.decsec? * Merge both packages? Anyway, did I get it right? Is ACL support what you were proposing specifically? :) > > Anti-spam pattern > > ================= > <<<snip>>> > > I'm not sure what this has to do with authorization. This seems like it > should be a separate system. > > > CAPTCHA pattern > > =============== > <<<snip>>> > > Same observation here: this sounds like it should be a separate system. I think that if a given routine is performed based on whether the current user is a known spammer (or if a submitted content is spam), according to an anti- spam service, then that's an authorization pattern. Likewise, I think that if a given routine is performed based on whether we are certain that the current user is human, then that's another authorization pattern. And because both authorization patterns are widely used, I think they should be supported out-of-the-box, *although* I wouldn't mind to implement such functionalities in two independent packages, as repoze.what plugins that provide the predicates mentioned above. Cheers! -- Gustavo Narea <http://gustavonarea.net/>. Get rid of unethical constraints! Get freedomware: http://www.getgnulinux.org/ _______________________________________________ Repoze-dev mailing list Repoze-dev@lists.repoze.org http://lists.repoze.org/listinfo/repoze-dev