Django Rest Framework:访问serializer.is_valid中的字段主键 - > serializer.errors

时间:2018-04-23 10:19:14

标签: python django django-rest-framework serializer

当我在django REST Framework中验证数据时出现错误时,如何获取失败的数据的id值?

这是我的问题的一个简单用例。 我有一个简单的模型:

class User(models.Model):
    id = models.IntegerField(primary_key=True)
    name = models.CharField(max_length=255)

一个基本的序列化器:

class UserSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = ('__all__')

现在,有时候,当添加具有以下功能的用户列表时,我会收到错误:

def add_users(data):
    serializer = UserSerializer(
        data=data, many=True)
    if serializer.is_valid():
        serializer.save()
     else:
        for index in range(0, len(serializer.errors)):
           logger.error("Validation failed: {0}".format(serializer.errors[index]))

错误看起来像:

  

验证失败:{'name':['此字段可能不为空。']}

     

验证失败:{'name':['此字段可能不为空。']}

但我的列表中有100个不同的用户。

我想知道没有“name”属性的人的PK / id值。我怎么能这样做?

2 个答案:

答案 0 :(得分:1)

serializer.save()方法保存单个对象。并且序列化器中的many=True与写操作无关。如果您的数据包含多个用户数据,请尝试使用此类

def add_users(data):
    users = []
    for user_data in data:
        serializer = UserSerializer(data=data)
        serializer.is_valid(raise_exception=True)
        user = serializer.save()
        users.append(user)
    return Response(data=UserSerializer(users, many=True).data)

答案 1 :(得分:0)

我找到了一个非常优雅的解决方案。

我创建了一个GenericModelSerializer,它继承自“ rest_framework.serializers.ModelSerializer”,而我已经覆盖了“ run_validation”方法。

我捕获到异常并记录了更多信息。我使用“元”来获取primary_key字段名称和值。

然后,我所有的序列化程序都继承于此。

当使用“ many = True”对序列化程序进行初始化时,Django Rest Framework在每个元素上都会调用“ run_validaiton()”。

当只处理一个元素时,它也可以工作。

这是一段代码:

from rest_framework.exceptions import ValidationError
from rest_framework import serializers


class GenericModelSerializer(serializers.ModelSerializer):

    def run_validation(self, data):
        try:
            valid = super().run_validation(data)
            return valid
        except ValidationError as e:
            #check if it is a list. It is a specific error.
            if data.__class__ is [].__class__:
                raise e
            primary_key_field_name = self.Meta.model._meta.pk.name
            raise ValidationError("Entity {0} : {1}. Caused by : {2}".format(primary_key_field_name, data[primary_key_field_name], e.detail)) 

现在,显示的错误看起来像这样,带有实体主键值:

rest_framework.exceptions.ValidationError: [["Entity id : 1. Caused by : {'name': ['This field may not be null.']}"], ["
Entity id : 2. Caused by : {'name': ['This field may not be null.']}"], {}]