Django 模型嵌套序列化器

Django model nested serializer

我有如下模型结构

class BaseProduct:
   id = models.CharField(max_length=15)
   name = models.CharField(max_length=20)

class Product
   base_product = ForeigKey(BaseProduct)
   name = models.CharField(max_length=20)

class Condition:
   category = models.ForeignKey(Product, related_name='allowed_product')
   check = models.IntegerField(default=0)
   allow = models.PositiveSmallIntegerField(default=1)

查询:

Product.objects.filter(condition__allow=1, condition__check=1)

我想要如下格式 基本产品和该产品列表中的产品 基于允许和检查过滤器

[
    {
        "name": "BaseProduct 1",
        "products": [
            {

                "name": "TV",

            }, {}, ....

        ]
    },
........
]

尝试一下,如果你使用 django rest framework

from rest_framework import serializers
from rest_framework.fields import empty
from django.utils.functional import cached_property


class ProductSerializer(serializers.ModelSerializer):

    class Meta:
        model = Product
        fields = ('name')


class BaseProductSerializer(serializers.ModelSerializer):
        products = serializers.SerializerMethodField()

    class Meta:
        model = BaseProduct
        fields = ('name', 'products')

    def __init__(self, instance=None, data=empty, **kwargs):
        self._condition_allow = kwargs.pop('condition_allow', 1)
        super(BaseProductSerializer, self).__init__(instance=None, data=empty, **kwargs)

    @cached_property
    def _request_data(self):
        request = self.context.get('request')
        # if POST
        # return request.data if request else {}
        # if GET params
        return request.query_params if request else {}

    @cached_property
    def _condition(self):
         return self._request_data.get('CONDITION_PARAM_NAME')

    def get_products(self, obj):
        qs = obj.product_set.filter(condition__allow=self._condition_allow, condition__check=1)
        serializer = ProductSerializer(qs, many=True)
        #                             ^^^^^
        return serializer.data

可见

serialiser(qs, condition_allow=5)

更改您的模型,使外键具有 related_name 反向关系:

class BaseProduct:
   id = models.CharField(max_length=15)
   name = models.CharField(max_length=20)

class Product
   base_product = ForeigKey(BaseProduct, related_name='products')
   name = models.CharField(max_length=20)

class Condition:
   category = models.ForeignKey(Product, related_name='conditions')
   check = models.IntegerField(default=0)
   allow = models.PositiveSmallIntegerField(default=1)

现在您可以在序列化程序中使用它了:

class BaseProductSerializer:
   class Meta:
    model = BaseProduct
    fields = ('name', 'products',)

class ProductSerializer:
   class Meta:
    model = Product
    fields = ('conditions',)

class ConditionSerializer:
   class Meta:
    model = Condition
    fields = '__all__'

最后在你看来,改成这样:

Product.objects.filter(condition__allow=1, condition__check=1)

进入这个:

BaseProduct.objects.filter(products__conditions__allow=1, products__conditions__allow=1)

希望这会生成您要求的格式的 JSON 数据。