Serialize to json nested one-to-many (opposite of many to one)

django, django-models

Solution

You can try using django rest framework.

Define a model serializer for Module model and Version model:

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

class ModuleSerializer(serializers.ModelSerializer):
    versions = VersionSerializer(many=True)
    class Meta:
        model = Module
        fields = ('id', ..... , 'versions')

Now define your Install model serialiser:

class InstallSerializer(serializers.ModelSerializer):
    modules = ModuleSerializer(many=True)
    class Meta:
        model = Install
        fields = ('id', ..... , 'modules')

This will serialize install data with all modules for each install and also all versions for each of the modules in a install.

EDIT:

I forgot to mention this, the name of the field of the related model should be the same as the value of related_name in the foreign key field.

For example in the Module model:

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

Now you have to use 'modules' as the name of the field in the serializer.

Problem

I have Installs which have many Modules which each have many Versions. a-la: ``` class Module(Models.Model): install = models.ForeignKey(Install) ``` One Install has many Modules. I want to serialize this whole set to a json structure. I found that I can use the wad of stuff serializer to serialize in this way: ``` serializers.serialize("json", Version.objects.all(), indent=4, relations={'module':{'relations':('install',)}}) ``` But this is starting from the inside out (a many-to-one view - many versions have one module, but I want to know what versions each module has). I get list of Versions at the top level, with each Version calling out it's Module, so the each Module is listed many times: ``` [ { "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", } } } } ] ``` See how the same Module is listed twice. That's "not right". I want to say something like ``` serializers.serialize("json", Install.objects.all(), indent=4, relations={'module':{'relations':('version',)}}) ``` but of course that doesn't work because the Install model does not have a field called "module".

Original source