You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Django DRF序列化器传入数据存入数据库为null问题求助

Django DRF序列化器数据未写入数据库问题排查

问题描述

开发Django项目时,使用REST Framework序列化器接收前端表单框选区域生成的数据并存入数据库,但数据始终未被正确写入,数据库字段显示Null或缺失值,无报错信息。

request.data示例:

{'TextField': [], 'DateField': [], 'SignatureField': [['FieldName', [129, 79], [138, 35], 'Form.jpg']]}

代码片段

序列化器代码

class DataSerializer(serializers.ModelSerializer):
    class Meta:
        model = FormData
        fields = ["FieldName", "StartX", "StartY", "width", "height", "JSONData", "FormType"]
    
    def create(self, **validated_data):
        print(**validated_data)
        return FormData.objects.create(**validated_data)

POST视图代码

@api_view(['POST'])
def create_list(request):
    
    if request.method == 'POST':
        dataDict = request.data
        
        for info in dataDict:
            Field = dataDict[info]
            stringDict = str(dataDict) 


            for object in Field:
                
                datadict = {
                    "FieldName": object[0],
                    "StartX": object[1][0],
                    "StartY": object[1][1],
                    "width": object[2][0],
                    "height": object[2][1],
                    "JSONData": stringDict,  
                    "FormType": object[3]
                }
                  
        serializer = DataSerializer(data=datadict)
        
        if serializer.is_valid():
            serializer.create()  
            return JSONResponse(serializer.data, status=201)
        print(serializer.errors)
            
    return Response("Not Valid")

模型代码

class FormData(models.Model):
    FieldName = models.CharField(max_length=100)
    StartX = models.IntegerField(null=True)
    StartY = models.IntegerField(null=True)
    width = models.IntegerField(null=True)
    height = models.IntegerField(null=True)
    JSONData = models.CharField(max_length=500)
    FormType = models.CharField(max_length=100)

调试尝试

  • 怀疑for循环逻辑导致数据为空,但在serializer.is_valid()后打印serializer.data得到了预期结果,排除该可能:
    {'FieldName': 'FieldNamedefinedbyuser', 'StartX': 246, 'StartY': 108, 'width': 345, 'height': 80, 'JSONData': "{'TextField': [], 'DateField': [], 'SignatureField': [['asdfasdfsadf', [246, 108], [345, 80], 'Darthvad.jpg']]}", 'FormType': 'Form.jpg'}
    
  • 尝试将数据字典转为JSON后传入序列化器,报错:
    代码:
    Json_object = json.dumps(data, indent=4)
    serializer = DataSerializer(data=Json_object)
    
    错误:
    {'non_field_errors': [ErrorDetail(string='Invalid data. Expected a dictionary, but got str.', code='invalid')]}
    
  • 打印**validated_data发现完全为null,推测问题出在序列化器数据处理环节。

问题分析与解决方向

  1. 序列化器create方法参数错误
    序列化器的create方法标准签名是def create(self, validated_data):,不是**validated_data。当前写法会导致无法正确接收验证后的数据,修改为:

    def create(self, validated_data):
        print(validated_data)  # 直接打印validated_data,而非**validated_data
        return FormData.objects.create(**validated_data)
    
  2. 视图中调用create方法的方式错误
    DRF序列化器验证通过后,应调用serializer.save()而非直接调用serializer.create()。save()方法会自动调用create或update方法,并正确传递验证后的数据:

    if serializer.is_valid():
        serializer.save()  
        return JSONResponse(serializer.data, status=201)
    
  3. for循环逻辑导致数据覆盖
    视图中datadict在循环内部被多次赋值,最终仅保留最后一次循环的结果。若要处理多个框选数据,需在每次循环内创建序列化器并保存:

    import json
    @api_view(['POST'])
    def create_list(request):
        if request.method == 'POST':
            dataDict = request.data
            stringDict = json.dumps(dataDict)
            for field_type in dataDict:
                fields = dataDict[field_type]
                for obj in fields:
                    datadict = {
                        "FieldName": obj[0],
                        "StartX": obj[1][0],
                        "StartY": obj[1][1],
                        "width": obj[2][0],
                        "height": obj[2][1],
                        "JSONData": stringDict,  
                        "FormType": obj[3]
                    }
                    serializer = DataSerializer(data=datadict)
                    if serializer.is_valid():
                        serializer.save()
            return JSONResponse({"status": "success"}, status=201)
        return Response("Not Valid")
    
  4. JSONData字段处理优化
    当前用str(dataDict)转换的字符串非标准JSON格式,建议用json.dumps()生成标准JSON字符串存入数据库,避免后续解析问题。

内容的提问来源于stack exchange,提问作者Groggyboi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.12 14:20:35