首页 > 解决方案 > 如何使用一个请求 DRF 创建多个对象

问题描述

我有以下型号

class Product(models.Model):
    name = models.CharField(null=True, blank=True, max_length=500)
    category = models.CharField(null=True, blank=True, max_length=120)


class SpecificationName(models.Model):
    product = models.ForeignKey(Product, on_delete=models.CASCADE, null=True, related_name='specifications')
    name = models.CharField(max_length=125)

class Attribute(models.Model):
    spec_name = models.ForeignKey(SpecificationName, on_delete=models.CASCADE, null=True, related_name='attributes')
    index = models.CharField(max_length=200, blank=True, null=True)
    value = models.CharField(max_length=250, blank=True, null=True)

在 Django admin 中保存对象后,我有一个示例

{
    "name": "Apple Smart Watch",
    "category": "IT",
    "specifications": [
        {
            "name": "Test Data",
            "attributes": [
                {
                    "index": "test",
                    "value": "test2"
                },
                {
                    "index": "test7",
                    "value": "test8"
                },
                {
                    "index": "test9",
                    "value": "test10"
                }
            ]
        },
        {
            "name": "Test Data Continued",
            "attributes": [
                {
                    "index": "bla",
                    "value": "bla1"
                },
                {
                    "index": "bla 2",
                    "value": "bla 4"
                },
                {
                    "index": "test9",
                    "value": "test10"
                }
            ]
        },
        {
            "name": "Test Spec",
            "attributes": []
        }
    ]
}

我需要通过一个请求保存这种对象,但我没有这样做

我的序列化器看起来像这样

class ProductSerializer(serializers.ModelSerializer):
    specifications = SpecNameSerializer(many=True)
    # attributes = AttributeSerializer(many=True, required=False)

class Meta:
    model = Product
    fields = ['name', 'category', 'brand', 'price', 'specifications']

def create(self, validated_data):
    specs = validated_data.pop('specifications')
    instance = Product.objects.create(**validated_data)

    for spec in specs:
        SpecificationName.objects.create(product=instance, **spec)
        print(spec)

    return instance

使用此代码,我得到以下结果,但未达到预期

{
    "name": "Appel watch series",
    "specifications": [
        {
            "name": "Test Data",
            "attributes": []
        },
        {
            "name": "Test Data comn",
            "attributes": []
        },
        {
            "name": "Test Spec",
            "attributes": []
        }
    ]
}

它不能写入属性

我搜索了很多答案,但我没有找到或应用其中的一些,再次它对我没有帮助。我只ListCreateView在视图中使用。请问有没有人可以帮助解决这个问题。提前致谢!

标签: pythondjangopython-3.xdjango-rest-framework

解决方案


解决了

我在这里使用,ModelSerializer而不是我在这里使用Serializer并添加了一些更改我的答案并且它有效

class AttributeSerializer(serializers.Serializer):
    index = serializers.CharField(max_length=200)
    value = serializers.CharField(max_length=200)


class SpecNameSerializer(serializers.ModelSerializer):
    attributes = AttributeSerializer(many=True)

    class Meta:
        model = SpecificationName
        fields = '__all__'


class ProductSerializer(serializers.ModelSerializer):
    specifications = SpecNameSerializer(many=True)


    class Meta:
        model = Product
        fields = ['name', 'category', 'brand', 'price', 'specifications']


    def create(self, validated_data):
        specs = validated_data.pop('specifications')
        instance = Product.objects.create(**validated_data)

        for spec in specs:
            SpecificationName.objects.create(product=instance, **spec)
            attrs = spec.pop('attributes')
            for attr in attrs:
                Attribute.objects.create(spec_name=spec, **attr)

        return instance

推荐阅读