- Add view mixins (RoleRequiredMixin, OwnerRequiredMixin, ManagerOwnerRequiredMixin) to user_roles/mixins.py - Replace PermissionRequiredMixin with ManagerOwnerRequiredMixin in all product views - Remove permission_required attributes from view classes - Owner and Manager roles now grant access without Django model permissions This allows owners to access all product functionality through their custom role, without needing to be superusers or have explicit Django permissions. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
137 lines
4.8 KiB
Python
137 lines
4.8 KiB
Python
from django.contrib import admin
|
||
from django.contrib.auth.mixins import AccessMixin
|
||
from django.core.exceptions import PermissionDenied
|
||
from user_roles.services import RoleService
|
||
|
||
|
||
class RoleBasedAdminMixin:
|
||
"""
|
||
Миксин для ModelAdmin с проверкой ролей.
|
||
|
||
Использование:
|
||
class MyAdmin(RoleBasedAdminMixin, admin.ModelAdmin):
|
||
required_roles = ['owner', 'manager']
|
||
"""
|
||
required_roles = [] # Роли, которые имеют доступ
|
||
|
||
def has_module_permission(self, request):
|
||
"""Проверка доступа к модулю"""
|
||
if not super().has_module_permission(request):
|
||
return False
|
||
|
||
# Superuser имеет полный доступ
|
||
if request.user.is_superuser:
|
||
return True
|
||
|
||
if not self.required_roles:
|
||
return True # Нет ограничений
|
||
|
||
return RoleService.user_has_role(request.user, *self.required_roles)
|
||
|
||
def has_view_permission(self, request, obj=None):
|
||
"""Проверка доступа на просмотр"""
|
||
if not super().has_view_permission(request, obj):
|
||
return False
|
||
|
||
# Superuser имеет полный доступ
|
||
if request.user.is_superuser:
|
||
return True
|
||
|
||
if not self.required_roles:
|
||
return True
|
||
|
||
return RoleService.user_has_role(request.user, *self.required_roles)
|
||
|
||
def has_add_permission(self, request):
|
||
"""Проверка доступа на добавление"""
|
||
if not super().has_add_permission(request):
|
||
return False
|
||
|
||
# Superuser имеет полный доступ
|
||
if request.user.is_superuser:
|
||
return True
|
||
|
||
if not self.required_roles:
|
||
return True
|
||
|
||
return RoleService.user_has_role(request.user, *self.required_roles)
|
||
|
||
def has_change_permission(self, request, obj=None):
|
||
"""Проверка доступа на изменение"""
|
||
if not super().has_change_permission(request, obj):
|
||
return False
|
||
|
||
# Superuser имеет полный доступ
|
||
if request.user.is_superuser:
|
||
return True
|
||
|
||
if not self.required_roles:
|
||
return True
|
||
|
||
return RoleService.user_has_role(request.user, *self.required_roles)
|
||
|
||
def has_delete_permission(self, request, obj=None):
|
||
"""Проверка доступа на удаление"""
|
||
if not super().has_delete_permission(request, obj):
|
||
return False
|
||
|
||
# Superuser имеет полный доступ
|
||
if request.user.is_superuser:
|
||
return True
|
||
|
||
if not self.required_roles:
|
||
return True
|
||
|
||
return RoleService.user_has_role(request.user, *self.required_roles)
|
||
|
||
|
||
class OwnerOnlyAdminMixin(RoleBasedAdminMixin):
|
||
"""Миксин для админки, доступной только владельцу"""
|
||
required_roles = ['owner']
|
||
|
||
|
||
class ManagerOwnerAdminMixin(RoleBasedAdminMixin):
|
||
"""Миксин для админки, доступной менеджеру и владельцу"""
|
||
required_roles = ['owner', 'manager']
|
||
|
||
|
||
# Миксины для обычных views (не админки)
|
||
|
||
class RoleRequiredMixin(AccessMixin):
|
||
"""
|
||
Миксин для проверки ролей в обычных CBV.
|
||
|
||
Использование:
|
||
class MyView(RoleRequiredMixin, ListView):
|
||
required_roles = ['owner', 'manager']
|
||
"""
|
||
required_roles = [] # Список ролей, которым разрешен доступ
|
||
|
||
def dispatch(self, request, *args, **kwargs):
|
||
if not request.user.is_authenticated:
|
||
return self.handle_no_permission()
|
||
|
||
# Superuser имеет полный доступ
|
||
if request.user.is_superuser:
|
||
return super().dispatch(request, *args, **kwargs)
|
||
|
||
# Если роли не указаны, доступ разрешен всем аутентифицированным
|
||
if not self.required_roles:
|
||
return super().dispatch(request, *args, **kwargs)
|
||
|
||
# Проверяем роль пользователя
|
||
if not RoleService.user_has_role(request.user, *self.required_roles):
|
||
raise PermissionDenied("У вас нет прав для доступа к этой странице")
|
||
|
||
return super().dispatch(request, *args, **kwargs)
|
||
|
||
|
||
class OwnerRequiredMixin(RoleRequiredMixin):
|
||
"""Миксин для view, доступного только владельцу"""
|
||
required_roles = ['owner']
|
||
|
||
|
||
class ManagerOwnerRequiredMixin(RoleRequiredMixin):
|
||
"""Миксин для view, доступного менеджеру и владельцу"""
|
||
required_roles = ['owner', 'manager']
|