【问题标题】:How to handle create/update on multiple nested serializers?如何处理多个嵌套序列化程序的创建/更新?
【发布时间】:2022-12-01 05:09:06
【问题描述】:

我已经能够在嵌套序列化器上创建/更新,但是当有多个嵌套序列化器时,我似乎无法让它工作。

楷模:

class Brand(models.Model):
    name = models.CharField(max_length=500)

class Incentive(models.Model):
    name = models.CharField(max_length=500)
    brands = models.ManyToManyField(Brand, related_name='incentives_brand')
    start_dt = models.DateTimeField(auto_now_add=False, blank=True, null=True)
    end_dt = models.DateTimeField(auto_now_add=False, blank=True, null=True)

class Version(models.Model):
    name = models.CharField(max_length=1000)
    incentives = models.ManyToManyField(Incentive, related_name='versions_incentive', blank=True)
    brands = models.ManyToManyField(Brand, related_name='versions_brand')

序列化程序:

class BrandSerializer(serializers.ModelSerializer):    
    class Meta:
        model = Brand
        depth = 1
        fields = ['id', 'name']

class IncentiveSerializer(serializers.ModelSerializer):
    brands = BrandSerializer(many=True)
    
    class Meta:
        model = Incentive
        # depth = 1
        fields = ['id', 'name', 'brands', 'start_dt', 'end_dt']
    
class VersionSerializer(serializers.ModelSerializer): 
    incentives = IncentiveSerializer(many=True)
    brands = BrandSerializer(many=True)
       
    class Meta:
        model = Version
        fields = ['id', 'name', 'incentives', 'brands']
        
    def create(self, validated_data):
        brands = validated_data.pop('brands', [])
        incentives = validated_data.pop('incentives', [])
        instance = Version.objects.create(**validated_data)
        for brand_data in brands:
            brand = Brand.objects.get(**brand_data)
            instance.brands.add(brand)
        for incentive_data in incentives:
            incentive = Incentive.objects.get(**incentive_data)
            instance.incentives.add(incentive)
        return instance
    
    def update(self, instance, validated_data):
        brands = validated_data.pop('brands', [])
        incentives = validated_data.pop('incentives', [])
        instance = super().update(instance, validated_data)
        brand_objs = []
        incentive_objs = []
        for brand_data in brands:
            brand = Brand.objects.get(**brand_data)
            brand_objs.append(brand)
            instance.brands.set(brand_objs)
        for incentive_data in incentives:
            incentive = Incentive.objects.get(**incentive_data)
            incentive_objs.append(incentive)
            instance.incentives.set(incentive_objs)
        return instance 

我尝试使用与单个嵌套序列化程序相同的格式。现在我遇到了一些不同的错误。从 Create 开始,我得到:

TypeError:字段“id”需要一个数字,但得到了 [OrderedDict([('name', 'Brand Test')])]。

然后用 PUT 我得到:

TypeError:字段“id”需要一个数字但得到了 [OrderedDict([('name', 'Brand Test')]), OrderedDict([('name', 'Brand 2 Test')]), OrderedDict([('名称', '品牌 3 测试')])]

我认为问题就出在这里。如果需要更多代码,请告诉我(例如视图、网址)。我猜在更新中我没有正确清空品牌列表。我只是看不到它。任何帮助,将不胜感激。

【问题讨论】:

  • 你能分享整个回溯吗?
  • 主要问题在 get(**brand_data) ,我需要你的 post api payload

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


【解决方案1】:

您可以使用嵌套字段序列化程序来解决嵌套序列化程序的所有 Django 问题,尝试使用类似DynamicNestedField 的方法

【讨论】:

    猜你喜欢
    • 2022-12-12
    • 1970-01-01
    • 2021-06-13
    • 1970-01-01
    • 2015-02-10
    • 2019-10-13
    • 1970-01-01
    • 1970-01-01
    • 2016-02-09
    相关资源
    最近更新 更多