participants.py 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778
  1. from django.contrib.auth import get_user_model
  2. from django.core.exceptions import PermissionDenied
  3. from django.utils import six
  4. from django.utils.translation import ugettext as _, ungettext
  5. from rest_framework import serializers
  6. from misago.categories.models import PRIVATE_THREADS_ROOT_NAME
  7. from . import PostingEndpoint, PostingMiddleware
  8. from ...participants import add_owner, add_participant
  9. from ...permissions import allow_message_user
  10. class ParticipantsMiddleware(PostingMiddleware):
  11. def use_this_middleware(self):
  12. if self.mode == PostingEndpoint.START:
  13. return self.tree_name == PRIVATE_THREADS_ROOT_NAME
  14. return False
  15. def get_serializer(self):
  16. return ParticipantsSerializer(data=self.request.data, context={
  17. 'user': self.user
  18. })
  19. def save(self, serializer):
  20. add_owner(self.thread, self.user)
  21. for user in serializer.users_cache:
  22. add_participant(self.request, self.thread, user)
  23. class ParticipantsSerializer(serializers.Serializer):
  24. to = serializers.ListField(
  25. child=serializers.CharField()
  26. )
  27. def validate_to(self, usernames):
  28. clean_usernames = self.clean_usernames(usernames)
  29. self.users_cache = self.get_users(usernames)
  30. def clean_usernames(self, usernames):
  31. clean_usernames = []
  32. for name in usernames:
  33. clean_name = name.strip().lower()
  34. if clean_name == self.context['user'].slug:
  35. raise serializers.ValidationError(
  36. _("You can't include yourself on the list of users to invite to new thread."))
  37. if clean_name and clean_name not in clean_usernames:
  38. clean_usernames.append(clean_name)
  39. max_participants = self.context['user'].acl['max_private_thread_participants']
  40. if max_participants and len(clean_usernames) > max_participants:
  41. message = ungettext(
  42. "You can't start private thread with more than %(users)s participant.",
  43. "You can't start private thread with more than %(users)s participants.",
  44. max_participants)
  45. raise forms.ValidationError(message % {'users': max_participants})
  46. return list(set(clean_usernames))
  47. def get_users(self, usernames):
  48. users = []
  49. for user in get_user_model().objects.filter(slug__in=usernames):
  50. try:
  51. allow_message_user(self.context['user'], user)
  52. except PermissionDenied as e:
  53. raise serializer.ValidationError(six.text_type(e))
  54. users.append(user)
  55. if len(usernames) != len(users):
  56. invalid_usernames = set(usernames) - set([u.slug for u in users])
  57. message = _("One or more users could not be found: %(usernames)s")
  58. raise serializers.ValidationError(
  59. message % {'usernames': ', '.join(invalid_usernames)})
  60. return users