#models.py
# -*- coding: utf-8
from django.db import models
from django.contrib.auth.models import User
from django.contrib.contenttypes.models import ContentType
from permissions import variables
from permissions.fields import AutoOneToOneField
usermodel = getattr(variables, "UserModel", User)
class Moderator(models.Model):
user = AutoOneToOneField(usermodel, primary_key=True)
sections = models.ManyToManyField(ContentType, blank=True)
def __unicode__(self):
return "%s -> %s" % (self.user.username, ", ".join(self.sections.all()))
class Ban(models.Model):
user = AutoOneToOneField(usermodel, primary_key=True)
sections = models.ManyToManyField(ContentType, blank=True)
def __unicode__(self):
return "%s -> %s" % (self.user.username, ", ".join(self.sections.all()))
#decorators.py
# -*- coding: utf-8
from django.contrib.contenttypes.models import ContentType
from django.core.urlresolvers import reverse
from django.http import HttpResponseRedirect
from django.shortcuts import get_object_or_404
import flash
import variables
class PermissionsError(Exception): pass
class Permissions(object):
"""
Examples:
@Permissions(model=Post, field="pk", delete=True)
def delete_post(request, post_id):
post = get_object_or_404(Post, pk=post_id)
post.delete()
return HttpResponseRedirect(request.user.show_url())
"""
def __init__(self, model, field=None, delete=None, edit=None, create=None, custom=None, owner_field='user', self_protect=None):
self.model = model
self.field = field
self.delete = delete
self.edit = edit
self.create = create
self.custom = custom
self.owner_field = owner_field
self.self_protect = self_protect
self.content_type = ContentType.objects.get_for_model(self.model)
self.activation = getattr(variables, "ACTIVATION", None)
self.notice_handler = getattr(variables, "NOTICE_HANDLER")
self.error_handler = getattr(variables, "ERROR_HANDLER")
def __call__(self, func):
self.func = func
return self.decorate
def decorate(self, request, *args, **kwargs):
self.request = request
self.args = args
self.kwargs = kwargs
try:
if self.is_authorized():
return self.func(self.request, *self.args, **self.kwargs)
except PermissionsError, e:
self.error_handler(e)
return HttpResponseRedirect(self._redirect_url())
else:
return self.func(self.request, *self.args, **self.kwargs)
def _redirect_url(self):
referer = self.request.META.get('HTTP_REFERER')
if referer and referer == self.request.path:
referer = "/"
if not referer:
referer = "/"
return referer
def is_authorized(self):
if self.activation and not self.request.user.is_active:
raise PermissionsError(u"Please activate your account")
if not self.request.user.is_authenticated():
raise PermissionsError(u"Please authorize")
return self.is_banned()
def is_banned(self):
if self.content_type in self.request.user.ban.sections.all():
raise PermissionsError(u"You are banned from this section")
return self.is_moderator()
def is_moderator(self):
if self.content_type in self.request.user.moderator.sections.all() or self.request.user.is_staff:
return True
if self.create:
self._create()
elif self.custom:
self._custom()
elif self.edit:
self._edit()
elif self.delete:
self._delete()
def _create(self):
if self.self_protect and int(self.args[0]) == self.request.user.id:
raise PermissionsError(u"You can't do it for yourself")
def _delete(self):
self.obj = get_object_or_404(self.model, **{self.field: self.args[0]})
if getattr(self.obj, self.owner_field) != self.request.user:
raise PermissionsError(u"You can't delete others records")
def _edit(self):
self.obj = get_object_or_404(self.model, **{self.field: self.args[0]})
if getattr(self.obj, self.owner_field) != self.request.user:
raise PermissionsError(u"You can't edit others records")
def _custom(self):
self.obj = get_object_or_404(self.model, **{self.field: self.args[0]})
if self.self_protect and getattr(self.obj, self.owner_field).id == self.request.user.id:
raise PermissionsError(u"You can't do it for yourself")