【问题标题】:Group serializer results based on value根据值对序列化程序结果进行分组
【发布时间】:2016-05-11 14:03:51
【问题描述】:

我对 Django 很陌生,所以我不知道这是否可以使用基于类的视图,但我想根据查询返回的 JSON 中的值对搜索结果进行分组。基本上我希望我的结果是这样的:

{
"id": "0038",
"attributes": [
    {
        "name": "State",
        "values": "CA"
    },
    {
        "name": "Areas",
        "values": "Value 1"
    },
    {
        "name": "Areas",
        "values": "Value 2"
    },
    {
        "name": "Areas",
        "values": "Value 3"
    }]}

到这里:

{"id": "0038",
"attributes": [
    {
        "name": "State Licenses",
        "values": "CA"
    },
    {
        "name": "Areas",
        "values": ["Value 1", "Value 2", "Value 3"]
    }]}

每个“名称/值”对都是 MySQL 数据库中的单独行。我的 models.py 看起来像:

class Attribute(models.Model):
    id = models.AutoField(primary_key=True)
    name = models.CharField(max_length=45, blank=False)
    value = models.CharField(max_length=255, blank=False) 

虽然序列化器看起来像:

class AttributeSerializer(serializers.ModelSerializer):
    name = serializers.CharField(source='name')
    values = serializers.CharField(source='value')
    class Meta:
        model = models.Attribute
        fields= ('name','values')

知道我该怎么做吗? ListSerializer 似乎它可能是一个可能的候选者,并且通过扩展添加many=True 也是如此,但我认为这不能提供我想要的分组行为。有什么想法吗?

【问题讨论】:

  • 您的提议不会起作用,因为哈希表不应该有重复的键,在您的情况下是 values
  • 如果您想要分组,那么默认序列化程序可能无法仅仅因为您想要自定义结果而执行此操作。您可以编写自己的序列化程序。
  • 已编辑以阐明我在寻找什么 JSON。

标签: python django django-rest-framework django-class-based-views


【解决方案1】:

使用常规的Serializer - 也就是说不是ModelSerializer - 并覆盖view's methods 以创建您自己的结构并将其传递给序列化程序。

【讨论】:

    【解决方案2】:

    您需要覆盖ListSerializer.to_representation。在docs 中阅读有关覆盖.to_representation 的更多信息。

    def transform_data(data):
        result = {}
        for item in data:
            name, value = item['name'], item['value']
            if result.get(name):
                result[name].append(value) 
            else:
                result[name] = [value]
        return result
    
    
    class AttributeListSerializer(serializers.ListSerializer):
        def to_representation(self, data):
            data = super(AttributeListSerializer, self).to_representation(data)
            # data is currently in this format:
            # [
            #     {"name": "State", "values": "CA"},
            #     {"name": "Areas", "values": "1"},
            # ]
            # transform_data can be updated to transform the data however you like...
            return transform_data(data)
    
    
    class AttributeSerializer(serializers.ModelSerializer):
        name = serializers.CharField(source='name')
        values = serializers.CharField(source='value')
        class Meta:
            model = models.Attribute
            fields= ('name','values')
            # the below is KEY
            list_serializer_class = AttributeListSerializer
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-12-02
      • 1970-01-01
      • 2012-06-08
      • 1970-01-01
      • 2021-04-06
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多