"""Serializers for account web""" from django.conf import settings from django.contrib.auth import password_validation as password_validators from django.db.models import Q from django.utils.translation import gettext_lazy as _ from rest_framework import serializers from account import models, tasks from utils import exceptions as utils_exceptions from utils.methods import username_validator class PasswordResetSerializer(serializers.ModelSerializer): """Serializer from model PasswordReset""" username_or_email = serializers.CharField(required=False, write_only=True,) class Meta: """Meta class""" model = models.ResetPasswordToken fields = ( 'username_or_email', ) @property def request(self): """Get request from context""" return self.context.get('request') def validate(self, attrs): """Override validate method""" user = self.request.user if user.is_anonymous: username_or_email = attrs.get('username_or_email') if not username_or_email: raise serializers.ValidationError(_('Username or Email not in request body.')) # Check user in DB filters = {} if username_validator(username_or_email): filters.update({'username': username_or_email}) else: filters.update({'email': username_or_email.lower()}) user_qs = models.User.objects.filter(**filters) if user_qs.exists() and filters: attrs['user'] = user_qs.first() else: attrs['user'] = user return attrs def create(self, validated_data, *args, **kwargs): """Override create method""" user = validated_data.pop('user') ip_address = self.request.META.get('REMOTE_ADDR') obj = models.ResetPasswordToken.objects.create( user=user, ip_address=ip_address, source=models.ResetPasswordToken.WEB) if settings.USE_CELERY: tasks.send_reset_password_email.delay(request_id=obj.id, country_code=self.request.country_code) else: tasks.send_reset_password_email(request_id=obj.id, country_code=self.request.country_code) return obj class PasswordResetConfirmSerializer(serializers.ModelSerializer): """Serializer for model User""" password = serializers.CharField(write_only=True) class Meta: """Meta class""" model = models.ResetPasswordToken fields = ('password', ) def validate(self, attrs): """Override validate method""" user = self.instance.user password = attrs.get('password') try: # Compare new password with the old ones if user.check_password(raw_password=password): raise utils_exceptions.PasswordsAreEqual() # Validate password password_validators.validate_password(password=password) except serializers.ValidationError as e: raise serializers.ValidationError(str(e)) else: return attrs def update(self, instance, validated_data): """Override update method""" # Update user password from instance instance.user.set_password(validated_data.get('password')) instance.user.save() # Overdue instance instance.overdue() return instance