Django 序列化为json嵌套的一对多(与多对一相反)

Django 序列化为json嵌套的一对多(与多对一相反),django,django-models,Django,Django Models,我安装了许多模块,每个模块都有许多版本 a-la: 一次安装有多个模块 我想将整个集合序列化为json结构 我发现我可以使用以下方式序列化: serializers.serialize("json", Version.objects.all(), indent=4, relations={'module':{'relations':('install',)}}) 但这是从内部开始的(多对一视图-许多版本都有一个模块,但我想知道每个模块都有哪些

我安装了许多模块,每个模块都有许多版本

a-la:

一次安装有多个模块

我想将整个集合序列化为json结构

我发现我可以使用以下方式序列化:

 serializers.serialize("json", Version.objects.all(), indent=4, 
                        relations={'module':{'relations':('install',)}})
但这是从内部开始的(多对一视图-许多版本都有一个模块,但我想知道每个模块都有哪些版本)。我在顶层得到了版本列表,每个版本都会调用它的模块,因此每个模块都会被多次列出:

[
    {
        "pk": 1, 
        "model": "cmh_server.version", 
        "fields": {
            "name": "v1", 
            "module": {
                "pk": 1, 
                "model": "cmh_server.module", 
                "fields": {
                    "install": {
                        "pk": 1, 
                        "model": "cmh_server.install", 
                        "fields": {
                            "name": "CMBN"
                        }
                    }, 
                    "name": "CMBN", 
                }
            }
        },
        "pk": 2, 
        "model": "cmh_server.version", 
        "fields": {
            "name": "v1.1", 
            "module": {
                "pk": 1, 
                "model": "cmh_server.module", 
                "fields": {
                    "install": {
                        "pk": 1, 
                        "model": "cmh_server.install", 
                        "fields": {
                            "name": "CMBN"
                        }
                    }, 
                    "name": "CMBN", 
                }
            }
        }
    }
]
查看同一模块如何列出两次。这是“不对的”

我想说

serializers.serialize("json", Install.objects.all(), indent=4, 
                      relations={'module':{'relations':('version',)}})

但是这当然不起作用,因为安装模型没有名为“module”的字段。

您可以尝试使用django rest框架

为模块模型和版本模型定义模型序列化程序:

class VersionSerializer(serializers.ModelSerializer):
    class Meta:
        model = Version

class ModuleSerializer(serializers.ModelSerializer):
    versions = VersionSerializer(many=True)
    class Meta:
        model = Module
        fields = ('id', ..... , 'versions')
现在定义您的安装模型serialiser:

class InstallSerializer(serializers.ModelSerializer):
    modules = ModuleSerializer(many=True)
    class Meta:
        model = Install
        fields = ('id', ..... , 'modules')
这将序列化每个安装的所有模块的安装数据,以及安装中每个模块的所有版本

编辑:

我忘了提到这一点,相关模型字段的名称应该与外键字段中相关名称的值相同

例如,在模块模型中:

class Module(Models.Model):
    install = models.ForeignKey(Install, related_name='modules')

现在,您必须使用“modules”作为序列化程序中字段的名称。

这看起来非常吸引人。主要的缺点似乎是,如果类本身被修改,这些seralizer类必须被修改,对吗?我的意思是-字段列表必须手动更新?要在模型序列化程序中包含一个字段,而该字段不是模型中的实际字段,您需要在元类中显式定义字段属性。为了避免列出模型序列化程序的实际字段,可以使用model.\u meta.fields生成模型字段名称列表。这样你就不用担心手动更新fields属性了。我想InstallSerializer中的模型应该是Install?当我尝试
I=Install.objects.get时(pk=1);InstalLSerializer(i).data
我得到“AttributeError:'Install'对象没有属性'modules'”是的,没错。谢谢你的更正。另外,我已经编辑了我的答案,请重命名序列化程序中的字段名。您可以阅读此页面,DRF有很棒的文档。
class Module(Models.Model):
    install = models.ForeignKey(Install, related_name='modules')