options.py 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134
  1. from rest_framework import serializers
  2. from django.contrib.auth import get_user_model, logout
  3. from django.contrib.auth.password_validation import validate_password
  4. from django.utils.translation import gettext as _
  5. from misago.conf import settings
  6. from misago.users.online.tracker import clear_tracking
  7. from misago.users.permissions import allow_delete_own_account
  8. from misago.users.validators import validate_email, validate_username
  9. UserModel = get_user_model()
  10. __all__ = [
  11. 'ForumOptionsSerializer',
  12. 'EditSignatureSerializer',
  13. 'ChangeUsernameSerializer',
  14. 'ChangePasswordSerializer',
  15. 'ChangeEmailSerializer',
  16. 'DeleteOwnAccountSerializer',
  17. ]
  18. class ForumOptionsSerializer(serializers.ModelSerializer):
  19. class Meta:
  20. model = UserModel
  21. fields = [
  22. 'is_hiding_presence', 'limits_private_thread_invites_to',
  23. 'subscribe_to_started_threads', 'subscribe_to_replied_threads'
  24. ]
  25. extra_kwargs = {
  26. 'limits_private_thread_invites_to': {
  27. 'required': True
  28. },
  29. 'subscribe_to_started_threads': {
  30. 'required': True
  31. },
  32. 'subscribe_to_replied_threads': {
  33. 'required': True
  34. },
  35. }
  36. class EditSignatureSerializer(serializers.ModelSerializer):
  37. class Meta:
  38. model = UserModel
  39. fields = ['signature']
  40. def validate(self, data):
  41. if len(data.get('signature', '')) > settings.signature_length_max:
  42. raise serializers.ValidationError(_("Signature is too long."))
  43. return data
  44. class ChangeUsernameSerializer(serializers.Serializer):
  45. username = serializers.CharField(max_length=200, required=False, allow_blank=True)
  46. def validate(self, data):
  47. username = data.get('username')
  48. if not username:
  49. raise serializers.ValidationError(_("Enter new username."))
  50. user = self.context['user']
  51. if username == user.username:
  52. raise serializers.ValidationError(_("New username is same as current one."))
  53. settings = self.context['settings']
  54. validate_username(settings, username)
  55. return data
  56. def change_username(self, changed_by):
  57. user = self.context['user']
  58. user.set_username(self.validated_data['username'], changed_by=changed_by)
  59. user.save(update_fields=['username', 'slug'])
  60. class ChangePasswordSerializer(serializers.Serializer):
  61. password = serializers.CharField(max_length=200, trim_whitespace=False)
  62. new_password = serializers.CharField(max_length=200, trim_whitespace=False)
  63. def validate_password(self, value):
  64. if not self.context['user'].check_password(value):
  65. raise serializers.ValidationError(_("Entered password is invalid."))
  66. return value
  67. def validate_new_password(self, value):
  68. validate_password(value, user=self.context['user'])
  69. return value
  70. class ChangeEmailSerializer(serializers.Serializer):
  71. password = serializers.CharField(max_length=200, trim_whitespace=False)
  72. new_email = serializers.CharField(max_length=200)
  73. def validate_password(self, value):
  74. if not self.context['user'].check_password(value):
  75. raise serializers.ValidationError(_("Entered password is invalid."))
  76. return value
  77. def validate_new_email(self, value):
  78. if not value:
  79. raise serializers.ValidationError(_("You have to enter new e-mail address."))
  80. if value.lower() == self.context['user'].email.lower():
  81. raise serializers.ValidationError(_("New e-mail is same as current one."))
  82. validate_email(value)
  83. return value
  84. class DeleteOwnAccountSerializer(serializers.Serializer):
  85. password = serializers.CharField(max_length=200, trim_whitespace=False)
  86. def validate_password(self, value):
  87. if not self.context['user'].check_password(value):
  88. raise serializers.ValidationError(_("Entered password is invalid."))
  89. return value
  90. def mark_account_for_deletion(self, request):
  91. """
  92. Deleting user account can be costful, so just mark account for deletion, deactivate it
  93. and sign user out.
  94. """
  95. profile = self.context['user']
  96. allow_delete_own_account(request.user, profile)
  97. logout(request)
  98. clear_tracking(request)
  99. profile.mark_for_delete()