This is my serializers.py (I want to create a serializer for the built-in User model):
from rest_framework import serializers
from django.contrib.auth.models import User
class UserSerializer(serializers.ModelSerializer):
class Meta:
model = User
fields = ('username', 'password', 'email', )
def validate_username(self, username):
if not re.search(r'^\w+$', username): #checks if all the characters in username are in the regex. If they aren't, it returns None
raise serializers.ValidationError('Username can only contain alphanumeric characters and the underscore.')
try:
User.objects.get(username=username)
except ObjectDoesNotExist:
return username
raise serializers.ValidationError('Username is already taken.')
The issue is, when I try to create a user using a username which already exists, it returns the following dictionary:
{'username': [u'This field must be unique.']}
rather than saying
{'username': [u'Username is already taken']}
I recreated the validate_username function to this (for testing purposes):
def validate_username(self, username):
raise serializers.ValidationError('Testing to see if an error is raised.')
and it doesn't raise an error. Any idea why DjangoRestFramework is ignoring the validate_username function?
Edit: Note that I am using a ModelSerializer (in the tutorial here: http://www.django-rest-framework.org/api-guide/serializers/#validation it talks about field-level validation only for a Serializer, not a ModelSerializer). Note sure if it makes a difference or not.
Field-level validation is called before serializer-level validation.
So model User
having username as unique=True
, the field-level validation will raise exception because of username being already present. DRF's UniqueValidator
does this work of raising exception when a field is not unique.
As per DRF source code,
class UniqueValidator:
"""
Validator that corresponds to `unique=True` on a model field.
Should be applied to an individual field on the serializer.
"""
message = _('This field must be unique.')
Since these validators run before serializer-level validation, your validate_username
is never called.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With