I'm trying to validate an OTP that was sent to the user when registering i have a separate model for otp which has an OneToOne relation with the user
Otp Model
class Verify(models.Model):
user = models.ForeignKey(
User, on_delete=models.CASCADE, related_name="userverify", blank=False, null=True)
otp = IntegerRangeField(
min_value=111111, max_value=999999, blank=True, null=True)
created_at = models.DateTimeField(
_("created at"), auto_now=False, auto_now_add=True, blank=False)
expires_at = models.TimeField(null=True)
the VerifySerializer: I don't specify the model because i only need it to check the validity of the input, although i think this might be the problem
class VerifySerializerBase(serializers.Serializer):
email = serializers.EmailField()
otp = serializers.CharField()
the Verify_Email view takes an email and otp value to validate the email
How I'm trying to verify the otp
class Verify_Email(APIView):
def post(self, request):
try:
data = request.data
serializer = VerifySerializerBase(data=data)
if serializer.is_valid():
email = serializer.data['email']
otp = serializer.data['otp']
verify = Verify.objects.filter(email=email, otp=otp)
user = User.objects.filter(email=email)
if not user[0].exists():
return Response({
'message': "A user with this email was not found"
}, status=status.HTTP_400_BAD_REQUEST)
elif user[0].is_active:
return Response({
'message': "This email has already been verified"
}, status=status.HTTP_400_BAD_REQUEST)
elif verify[0].exists():
if verify[0].expires_at >= datetime.now():
return Response({
'message': "This OTP has expired, please request another one"
}, status=status.HTTP_400_BAD_REQUEST)
elif verify[0].otp != otp:
return Response({
'message': "This OTP is invalid"
}, status=status.HTTP_400_BAD_REQUEST)
else:
verify[0].delete()
user[0].is_active = True
user[0].save()
return Response({
'message': "Email has been verified"
}, status=status.HTTP_200_OK)
return Response({
'message': "Something is wrong"
}, status=status.HTTP_400_BAD_REQUEST)
return Response({
'message': "Something is wrong"
}, status=status.HTTP_400_BAD_REQUEST)
except Exception as e:
return Response(str(e), status=status.HTTP_404_NOT_FOUND, template_name=None, content_type=None)
and when testing i get
"Cannot resolve keyword 'email' into field. Choices are: created_at, expires_at, id, otp, user, user_id"
from what I understand i think it's telling me that I'm checking for fields that are not in the OTP model fields but I don't think I'm doing that??
CodePudding user response:
The error relates to the models, not the serializer. This line implies that a Verify
model has a field email
, because you're building a query on that field:
verify = Verify.objects.filter(email=email, otp=otp)
Perhaps you meant to query by user instead, which involves swapping with the following line like so:
user = User.objects.get(email=email)
verify = Verify.objects.filter(user=user, otp=otp)