| 1 | import logging |
|---|
| 2 | |
|---|
| 3 | from pylons import config, tmpl_context as c |
|---|
| 4 | from pylons import request |
|---|
| 5 | from pylons.controllers.util import abort |
|---|
| 6 | from pylons.i18n import _ |
|---|
| 7 | |
|---|
| 8 | from sqlalchemy import and_, or_ |
|---|
| 9 | from sqlalchemy.orm import eagerload |
|---|
| 10 | |
|---|
| 11 | from repoze.what.predicates import has_permission as what_has_permission |
|---|
| 12 | from repoze.what.adapters import BaseSourceAdapter, SourceError |
|---|
| 13 | from repoze.what.plugins.sql.adapters import SqlGroupsAdapter |
|---|
| 14 | |
|---|
| 15 | import adhocracy.model as model |
|---|
| 16 | |
|---|
| 17 | |
|---|
| 18 | log = logging.getLogger(__name__) |
|---|
| 19 | |
|---|
| 20 | |
|---|
| 21 | class InstanceGroupSourceAdapter(SqlGroupsAdapter): |
|---|
| 22 | |
|---|
| 23 | def __init__(self, *args, **kwargs): |
|---|
| 24 | super(InstanceGroupSourceAdapter, self).__init__(model.Group, model.User, model.meta.Session) |
|---|
| 25 | self.is_writable = False |
|---|
| 26 | |
|---|
| 27 | |
|---|
| 28 | def _get_section_items(self, section): |
|---|
| 29 | q = model.meta.Session.query(model.User.user_name) |
|---|
| 30 | q = q.join(model.Membership) |
|---|
| 31 | q = q.join(model.Group) |
|---|
| 32 | q = q.filter(model.Group.code==section) |
|---|
| 33 | q = q.filter(or_(model.Membership.instance==None, |
|---|
| 34 | model.Membership.instance==model.filter.get_instance())) |
|---|
| 35 | return q.all() |
|---|
| 36 | |
|---|
| 37 | |
|---|
| 38 | def _find_sections(self, credentials): |
|---|
| 39 | sections = list(super(InstanceGroupSourceAdapter, self)._find_sections(credentials)) |
|---|
| 40 | sections.append(u"Anonymous") |
|---|
| 41 | return set(sections) |
|---|
| 42 | |
|---|
| 43 | |
|---|
| 44 | def _get_item_as_row(self, item_name): |
|---|
| 45 | q = model.meta.Session.query(model.User) |
|---|
| 46 | q = q.filter(model.User.user_name==unicode(item_name)) |
|---|
| 47 | q = q.options(eagerload(model.User.memberships)) |
|---|
| 48 | try: |
|---|
| 49 | return q.limit(1).first() |
|---|
| 50 | except Exception, e: |
|---|
| 51 | log.exception(e) |
|---|
| 52 | raise SourceError("No such user: %s" % item_name) |
|---|
| 53 | |
|---|
| 54 | |
|---|
| 55 | class has_permission(what_has_permission): |
|---|
| 56 | """ |
|---|
| 57 | This modified version of ``repoze.what``'s ``has_permission`` will apply ``Anonymous`` |
|---|
| 58 | rights to any user making requests. This allows to call ``has_permission`` on methods |
|---|
| 59 | even when they are not protected, thus making the authorization system more |
|---|
| 60 | configurable. |
|---|
| 61 | """ |
|---|
| 62 | |
|---|
| 63 | def evaluate(self, environ, credentials): |
|---|
| 64 | if c.user: |
|---|
| 65 | super(has_permission, self).evaluate(environ, credentials) |
|---|
| 66 | else: |
|---|
| 67 | if environ.get('anonymous_permissions') is None: |
|---|
| 68 | anon_group = model.Group.by_code(model.Group.CODE_ANONYMOUS) |
|---|
| 69 | environ['anonymous_permissions'] = [p.permission_name for p in anon_group.permissions] |
|---|
| 70 | if not self.permission_name in environ['anonymous_permissions']: |
|---|
| 71 | self.unmet() |
|---|
| 72 | |
|---|
| 73 | |
|---|
| 74 | def has(permission): |
|---|
| 75 | #return permission in request.environ.get('repoze.what.credentials', {}).get('permissions', []) |
|---|
| 76 | p = has_permission(permission) |
|---|
| 77 | return p.is_met(request.environ) |
|---|
| 78 | |
|---|
| 79 | |
|---|
| 80 | |
|---|