Skip to content

Instantly share code, notes, and snippets.

@justanr
Last active September 14, 2015 12:39
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save justanr/b8fc4aeb5093d172af10 to your computer and use it in GitHub Desktop.
Save justanr/b8fc4aeb5093d172af10 to your computer and use it in GitHub Desktop.
Simple Criteria Filtering
from functools import singledispatch
from abc import ABCMeta, abstractmethod
class CriterionMeta(ABCMeta):
def __new__(mcls, name, bases, attrs):
dispatcher = singledispatch(attrs['_default'])
attrs.update({'_dispatcher': dispatcher, 'register': dispatcher.register})
return super(CriterionMeta, mcls).__new__(mcls, name, bases, attrs)
class Criterion(metaclass=CriterionMeta):
@abstractmethod
def _default(self, current_query):
return current_query
def __call__(self, repository, current_query):
matcher = self._dispatcher.dispatch(repository)
return matcher(self, current_query)
from collections import namedtuple
import operator
from criteria import Criterion
User = namedtuple('User', ['username', 'permission_level'])
Group = namedtuple('Group', ['name', 'perm_level'])
class PermissionLevel(Criterion):
def __init__(self, permission_level, op=operator.eq):
self.op = op
self.permission_level = permission_level
def _default(self, current_query):
return filter(lambda obj: self.op(obj.permission_level, self.permission_level), current_query)
@PermissionLevel.register(Group)
def group_perm_filter(self, cq):
return filter(lambda g: self.op(g.perm_level, self.permission_level), current_query)
IsAdmin = PermissionLevel(permission_level=1)
users = [User('fred', 0), User('hannah', 1)]
groups = [Group('Admins', 1), Group('Members', 0)]
list(IsAdmin(User, users)) # [User('hannah', 1)]
list(IsAdmin(Group, group)) # [Group('Admins', 1)]
from example import PermissionLevel
from fsqla import db
class UserModel(Model):
id = db.Column(db.Integer, primary_key=True)
username = db.Column(db.Unicode(32), unique=True)
permission = db.Column(db.Integer)
@PermissionLevel.register(UserModel)
def user_model_permission_filter(self, current_query):
return current_query.filter(self.op(UserModel.permission, self.permission_level))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment