Function-based view
You can construct a decorator that will pass the usertype_var to the view function:
from functools import wraps
def with_usertype(f):
@wraps(f)
def wrapped(request, *args, **kwargs):
return f(request, *args, **kwargs, usertype=request.session.get('type_user'))
return wrapped
You can then use the decorator as:
@with_usertype
def dashboard(request, usertype):
return render(request,'dashboard.html', {'usertype_var': usertype})
@with_usertype
def anotherview(request, usertype):
return render(request,'dashboard.html', , {'usertype_var': usertype})
You can also restrict it with:
from functools import wraps
from django.core.exceptions import PermissionDenied
def restrict_usertype(*restrictions):
def mydecorator(f):
@wraps(f)
def wrapped(request, *args, **kwargs):
usertype = request.session.get('type_user')
if usertyp in restrictions:
return f(request, *args, **kwargs, usertype=usertype)
else:
raise PermissionDenied
return wrapped
return mydecorator
then you can restrict this with:
@restrict_usertype('Admin')
def dashboard(request, usertype):
return render(request,'dashboard.html', {'usertype_var': usertype})
@restrict_usertype('Admin', 'Other')
def anotherview(request, usertype):
return render(request,'dashboard.html', , {'usertype_var': usertype})
Class-based views
For class-based views, since django-2.2 you can make use of the setup(…) method [Django-doc]. This method normally sets the request, args and kwargs to the view object:
# since Django-2.2
class UsertypeMixin:
def setup(self, request, *args, **kwargs):
self.usertype = request.session.get('type_user')
return super().setup(*args, **kwargs)
def get_context_data(self, *args, **kwargs):
return super().get_context_data(
*args,
**kwargs,
usertype=self.usertype
)
Then the mixin can be used, for example in a ListView with:
class MyListView(UserTypeMixin, ListView):
def get_queryset(self, *args, **kwargs):
# use self.usertype
# …
return super().get_queryset(*args, **kwargs)
we can restrict this as well with:
# since Django-2.2
from django.core.exceptions import PermissionDenied
class UsertypeRestrictMixin(UsertypeMixin):
required_usertype = ()
def setup(self, request, *args, **kwargs):
result = super().setup(*args, **kwargs)
if self.usertype not in self.required_usertype:
raise PermissionDenied
return result
and then use this as:
class MyListView(UsertypeRestrictMixin, ListView):
required_usertype = ('Admin',)
Django's groups and permissions
However often a better modeling is using groups, since a user can often have multiple roles. It can be a commentator, administrator, author, etc. and often after a while users can have multiple roles. Django has a system of groups and permissions [Django-doc] for this in place.
The advantage of using permissions is that this is more fine-grained, so one can make permissions for each (type of) view, and furthermore it allows a person to be a member of multiple groups, and also thus obtain the permissions of all these groups. This makes it more flexible since sometimes you want to give a small set of users an extra permission.