Django REST框架:OneToOne字段的Serializer字段级验证

时间:2015-08-18 04:14:16

标签: python django django-models django-rest-framework tastypie

我正在创建一个处理新Customer注册的视图。我的Customer模型OneToOne链接到PersonOneToOne再次链接到User,其中UserAUTH_USER_MODEL。当我通过register_customer视图发送客户注册的POST请求时,person_serialized.is_valid()会返回{"user":["This field is required."]},因为user对象不可用并在PersonSerializer上传递。我认为应该有一个更好,更干净的做我在这里做的事情。任何解决方案?

models.py

class User(AbstractBaseUser, PermissionsMixin):
    USERNAME_FIELD = 'mobile_number'

    # Form validation errors
    mobile_number_errors = {'required': 'Mobile number is required',
                            'invalid': 'Enter a valid 10 digit mobile number' +
                            'without spaces, + or isd code.'}

    _mobile_regex_validator = RegexValidator(regex=r"^\d{10}$",
                                             message="Phone number must be 10 digits without + or spaces.")
    mobile_number = models.CharField("Mobile Number", max_length=10,
                                     validators=[_mobile_regex_validator],
                                     blank=False, null=False, unique=True,
                                     error_messages=mobile_number_errors)

    is_active = models.BooleanField("Is Active?", default=True)
    is_staff = models.BooleanField("Is Staff?", default=False)

    created = models.DateTimeField("Account created on", auto_now_add=True, blank=True, null=True)
    modified = models.DateTimeField("Last Modified on", auto_now=True, blank=True, null=True)

    objects = UserManager()

    def __unicode__(self):
        return self.mobile_number

    def get_full_name(self):
        return self.mobile_number

    def get_short_name(self):
        return self.mobile_number


class Person(models.Model):
    user = models.OneToOneField('users.User')

    GENDER_CHOICES = (('M', 'Male'),
                      ('F', 'Female'),
                      ('N', 'Not Specified'))

    first_name = models.CharField("First Name", max_length=32, blank=False, null=False)
    last_name = models.CharField("Last Name", max_length=32, blank=False, null=False)
    gender = models.CharField("Gender", max_length=1, choices=GENDER_CHOICES, blank=False, default='N')



class Customer(models.Model):
    person = models.OneToOneField('users.Person')

    email_errors = {'required': 'Email field is required.',
                    'invalid': 'Enter a valid email id.'}


    email = models.EmailField("Email", blank=False, null=False, unique=True,
                              error_messages=email_error

serializers.py

class UserSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = ('id', 'mobile_number',)


class PersonSerializer(serializers.ModelSerializer):
    user = UserSerializer()
    class Meta:
        model = Person
        fields = ('id', 'user', 'first_name', 'last_name', 'gender',)


class CustomerSerializer(serializers.ModelSerializer):
    person = PersonSerializer()
    class Meta:
        model = Customer
        fields = ('id', 'person', 'email',)

views.py

from django.shortcuts import render

from .serializers import UserSerializer, PersonSerializer, CustomerSerializer
from .models import User, Person, Customer

from rest_framework.decorators import api_view
from rest_framework.response import Response
from rest_framework import status

# Create your views here.
@api_view(['POST'])
def register_customer(request):
    user_serialized = UserSerializer(data=request.data)
    person_serialized = PersonSerializer(data=request.data)
    customer_serialized = CustomerSerializer(data=request.data)

    if user_serialized.is_valid() and person_serialized.is_valid() and customer_serialized.is_valid():
        user = User.objects.create_user(mobile_number=user_serialized.data['mobile_number'],
                                        password=user_serialized.init_data['password'])

        person = Person(user=user, first_name=person_serialized.data['first_name'],
                        last_name=person_serialized.data['last_name'],
                        gender=person_serialized.data['gender'])
        person.save()

        customer = Customer(person=person, email=customer_serialized.data['email'])
        customer.save()

        return Response(request.data, status=status.HTTP_201_CREATED)
    else:
        return Response(person_serialized._errors, status=status.HTTP_400_BAD_REQUEST)

0 个答案:

没有答案