permsadmin.py 7.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219
  1. from django.contrib import messages
  2. from django.shortcuts import redirect
  3. from django.utils.translation import ugettext_lazy as _
  4. from misago.acl import version as acl_version
  5. from misago.acl.forms import get_permissions_forms
  6. from misago.acl.models import Role
  7. from misago.acl.views import RoleAdmin, RolesList
  8. from misago.admin.views import generic
  9. from misago.categories.forms import (
  10. CategoryRoleForm, CategoryRolesACLFormFactory, RoleCategoryACLFormFactory)
  11. from misago.categories.models import Category, CategoryRole, RoleCategoryACL
  12. from .categoriesadmin import CategoriesList, CategoryAdmin
  13. class CategoryRoleAdmin(generic.AdminBaseMixin):
  14. root_link = 'misago:admin:permissions:categories:index'
  15. model = CategoryRole
  16. templates_dir = 'misago/admin/categoryroles'
  17. message_404 = _("Requested role does not exist.")
  18. class CategoryRolesList(CategoryRoleAdmin, generic.ListView):
  19. ordering = (('name', None), )
  20. class RoleFormMixin(object):
  21. def real_dispatch(self, request, target):
  22. form = CategoryRoleForm(instance=target)
  23. perms_forms = get_permissions_forms(target)
  24. if request.method == 'POST':
  25. perms_forms = get_permissions_forms(target, request.POST)
  26. valid_forms = 0
  27. for permissions_form in perms_forms:
  28. if permissions_form.is_valid():
  29. valid_forms += 1
  30. form = CategoryRoleForm(request.POST, instance=target)
  31. if form.is_valid() and len(perms_forms) == valid_forms:
  32. new_permissions = {}
  33. for permissions_form in perms_forms:
  34. cleaned_data = permissions_form.cleaned_data
  35. new_permissions[permissions_form.prefix] = cleaned_data
  36. form.instance.permissions = new_permissions
  37. form.instance.save()
  38. messages.success(request, self.message_submit % {'name': target.name})
  39. if 'stay' in request.POST:
  40. return redirect(request.path)
  41. else:
  42. return redirect(self.root_link)
  43. elif form.is_valid() and len(perms_forms) != valid_forms:
  44. form.add_error(None, _("Form contains errors."))
  45. return self.render(
  46. request,
  47. {
  48. 'form': form,
  49. 'target': target,
  50. 'perms_forms': perms_forms,
  51. },
  52. )
  53. class NewCategoryRole(RoleFormMixin, CategoryRoleAdmin, generic.ModelFormView):
  54. message_submit = _('New role "%(name)s" has been saved.')
  55. class EditCategoryRole(RoleFormMixin, CategoryRoleAdmin, generic.ModelFormView):
  56. message_submit = _('Role "%(name)s" has been changed.')
  57. class DeleteCategoryRole(CategoryRoleAdmin, generic.ButtonView):
  58. def check_permissions(self, request, target):
  59. if target.special_role:
  60. message = _('Role "%(name)s" is special role and can\'t be deleted.')
  61. return message % {'name': target.name}
  62. def button_action(self, request, target):
  63. target.delete()
  64. message = _('Role "%(name)s" has been deleted.')
  65. messages.success(request, message % {'name': target.name})
  66. class CategoryPermissions(CategoryAdmin, generic.ModelFormView):
  67. """category roles view for assinging roles to category, add link to it in categories list"""
  68. templates_dir = 'misago/admin/categoryroles'
  69. template = 'categoryroles.html'
  70. def real_dispatch(self, request, target):
  71. category_roles = CategoryRole.objects.order_by('name')
  72. assigned_roles = {}
  73. for acl in target.category_role_set.select_related('category_role'):
  74. assigned_roles[acl.role_id] = acl.category_role
  75. forms = []
  76. forms_are_valid = True
  77. for role in Role.objects.order_by('name'):
  78. FormType = CategoryRolesACLFormFactory(
  79. role, category_roles, assigned_roles.get(role.pk)
  80. )
  81. if request.method == 'POST':
  82. forms.append(FormType(request.POST, prefix=role.pk))
  83. if not forms[-1].is_valid():
  84. forms_are_valid = False
  85. else:
  86. forms.append(FormType(prefix=role.pk))
  87. if request.method == 'POST' and forms_are_valid:
  88. target.category_role_set.all().delete()
  89. new_permissions = []
  90. for form in forms:
  91. if form.cleaned_data['category_role']:
  92. new_permissions.append(
  93. RoleCategoryACL(
  94. role=form.role,
  95. category=target,
  96. category_role=form.cleaned_data['category_role'],
  97. )
  98. )
  99. if new_permissions:
  100. RoleCategoryACL.objects.bulk_create(new_permissions)
  101. acl_version.invalidate()
  102. message = _("Category %(name)s permissions have been changed.")
  103. messages.success(request, message % {'name': target.name})
  104. if 'stay' in request.POST:
  105. return redirect(request.path)
  106. else:
  107. return redirect(self.root_link)
  108. return self.render(request, {
  109. 'forms': forms,
  110. 'target': target,
  111. })
  112. CategoriesList.add_item_action(
  113. name=_("Category permissions"),
  114. icon='fa fa-adjust',
  115. link='misago:admin:categories:nodes:permissions',
  116. style='success',
  117. )
  118. class RoleCategoriesACL(RoleAdmin, generic.ModelFormView):
  119. """role categories view for assinging categories to role, add link to it in user roles list"""
  120. templates_dir = 'misago/admin/categoryroles'
  121. template = 'rolecategories.html'
  122. def real_dispatch(self, request, target):
  123. categories = Category.objects.all_categories()
  124. roles = CategoryRole.objects.order_by('name')
  125. if not categories:
  126. messages.info(request, _("No categories exist."))
  127. return redirect(self.root_link)
  128. choices = {}
  129. for choice in target.categories_acls.select_related('category_role'):
  130. choices[choice.category_id] = choice.category_role
  131. forms = []
  132. forms_are_valid = True
  133. for category in categories:
  134. category.level_range = range(category.level - 1)
  135. FormType = RoleCategoryACLFormFactory(category, roles, choices.get(category.pk))
  136. if request.method == 'POST':
  137. forms.append(FormType(request.POST, prefix=category.pk))
  138. if not forms[-1].is_valid():
  139. forms_are_valid = False
  140. else:
  141. forms.append(FormType(prefix=category.pk))
  142. if request.method == 'POST' and forms_are_valid:
  143. target.categories_acls.all().delete()
  144. new_permissions = []
  145. for form in forms:
  146. if form.cleaned_data['role']:
  147. new_permissions.append(
  148. RoleCategoryACL(
  149. role=target,
  150. category=form.category,
  151. category_role=form.cleaned_data['role'],
  152. )
  153. )
  154. if new_permissions:
  155. RoleCategoryACL.objects.bulk_create(new_permissions)
  156. acl_version.invalidate()
  157. message = _("Category permissions for role %(name)s have been changed.")
  158. messages.success(request, message % {'name': target.name})
  159. if 'stay' in request.POST:
  160. return redirect(request.path)
  161. else:
  162. return redirect(self.root_link)
  163. return self.render(request, {
  164. 'forms': forms,
  165. 'target': target,
  166. })
  167. RolesList.add_item_action(
  168. name=_("Categories permissions"),
  169. icon='fa fa-comments-o',
  170. link='misago:admin:permissions:users:categories',
  171. style='success',
  172. )