【问题标题】:Django REST Framework: Integrity error on not null column when posting dataDjango REST Framework:发布数据时非空列的完整性错误
【发布时间】:2017-08-14 12:07:02
【问题描述】:

我有这两个相关的模型:

class EndPoint(TimeStampedModel):
    name = models.CharField(max_length=100)
    url = models.CharField(max_length=100)
    description = models.CharField(max_length=100)   

class Parameter(TimeStampedModel):
    name = models.CharField(max_length=100)
    label = models.CharField(max_length=100)
    required = models.BooleanField()
    type = models.CharField(max_length=100)
    format = models.CharField(max_length=100, null = True)
    endpoint = models.ForeignKey(EndPoint, related_name="parameters",null = True, on_delete=models.CASCADE) 

映射到这些序列化程序:

class ParameterRelationSerializer(serializers.ModelSerializer):
    class Meta:
        model = Parameter
        fields = ('id', 'name', 'label', 'required','type','format')
    
class EndPointSerializer(serializers.ModelSerializer):
    parameters = ParameterRelationSerializer(many = True, read_only=False)

    class Meta:
        model = EndPoint
        fields = ('id', 'name', 'url', 'description', 'parameters')

    def create(self, validated_data):
        parameters = validated_data.pop('parameters')
        endPoint = EndPoint.objects.create(**validated_data)
        for parameter_relation in parameters:
            Parameter.objects.create(endpoint=endPoint, **parameter_relation)
        return endPoint

现在,当我尝试使用此数据发布一个新端点时:

{
   "url":"http://the.url.com",
   "name":"Dummy url",
   "description":"This is a dummy url",
   "parameters":[
      {
         "name":"dummyparam",
         "type":"dummy",
         "label":"dummy_parameter"
      }
   ]
}

我收到一个 500 错误:

/catalogs/endpoints/ 处的 IntegrityError

“必需”列中的空值违反非空约束

详细信息:失败行包含 (6, 2017-08-14 12:01:52.857902+00, 2017-08-14 12:01:52.857984+00, dummyparam, dummy_parameter, null, dummy, null, 6)。

基本上,它抱怨缺少非空“必需”属性(在参数模型中),从而导致数据库错误。

我的问题是,这不应该由序列化程序验证器处理而不是引发 DB 异常吗?事实上,我还有另外一堆非空属性,当 json 数据丢失时会触发验证错误。

【问题讨论】:

    标签: django rest serialization django-rest-framework


    【解决方案1】:

    回答您的具体问题 -

    我的问题是,这不应该由序列化验证器处理吗 而不是抛出数据库异常?其实我还有一堆 缺少时触发验证错误的非空属性 json数据。

    仅当请求数据中存在该键时,才会执行序列化程序末端的验证器。由于您根本没有传递“必需”属性,因此在序列化程序结束时不会调用验证器。

    您还应该在 extra_kwargs 的帮助下告诉您的序列化程序这些字段,如下所示 -

     extra_kwargs = {
         'required': {'required': True},
     }
    

    【讨论】:

    • 谢谢,我设法使用 extra_kwargs 解决了这个问题。尽管如此,仍然缺少一些东西来使 100% 有意义。您说验证器“仅在请求数据中存在该密钥时”运行,但这是奇怪的原因,就像我说的其他字段(例如,'label')不可为空并且即使不存在于要求。我想这与 BooleanFields 具体有关。
    • 也许你是对的。我将不得不再看看这个。完成后会更新您。
    • 我现在也有类似的问题。你能帮我看看吗?stackoverflow.com/questions/62655168/…
    【解决方案2】:

    你可以尝试添加 is_valid()

    ParameterRelationSerializer
    for parameter_relation in parameters:
            parameter_relation.update({"endpoint":endPoint})
            serializer = ParameterRelationSerializer(data=parameter_relation)
            if serializer.is_valid():
                serializer.save()
    

    如果需要,可以添加 raise 验证 exeption:

            serializer.is_valid(raise_exception=True)
            serializer.save()
    

    【讨论】:

      猜你喜欢
      • 2017-04-04
      • 2019-10-12
      • 2021-06-10
      • 1970-01-01
      • 2015-09-28
      • 2018-09-20
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多