4

I have these models:

class Projects(models.Model):
    projectName =models.CharField(max_length = 100,unique=True,db_index=True)
    projectManager = EmbeddedModelField('Users')

class Teams(models.Model):
    teamType = models.CharField(max_length =100)
    teamLeader = EmbeddedModelField('Users')
    teamProject = EmbeddedModelField('Projects')

class Users(models.Model):
    name = models.CharField(max_length = 100,unique=True)
    designation = models.CharField(max_length =100 )
    teams = ListField(EmbeddedModelField('Teams'))

I need to return JSON from my view for all Projects objects which further has relations with Users and Teams.My views.py has this code

from django.core import serializers

data = serializers.serialize('json', Projects.objects.all())

This output JSON only for project object and doesnot return JSON for USer object like this

[{"pk": "4eb3b7d0e814520db4000000", "model": "RESTAPI.projects", "fields": {"projectName": "HELLO", "projectManager": "Users object"}}]

How do I convert the User object into JSON as well ?

Anshul
  • 7,914
  • 12
  • 42
  • 65

2 Answers2

1

I've hit this problem some time ago, and I created a snippet to help me out:

def get_values(instance, go_into={}, exclude=(), extra=()):
    """
    Transforms a django model instance into an object that can be used for
    serialization. Also transforms datetimes into timestamps.

    @param instance(django.db.models.Model) - the model in question
    @param go_into - relations with other models that need expanding
    @param exclude - fields that will be ignored
    @param extra - additional functions/properties which are not fields

    Usage:
    get_values(MyModel.objects.get(pk=187),
               {'user': {'go_into': ('clan',),
                         'exclude': ('crest_blob',),
                         'extra': ('get_crest_path',)}},
               ('image'))

    """

So you could use something like this:

simplejson.dumps(get_values(Projects.objects.all(),
    go_into={'projectManager': {'go_into': 'teams'}}))

disclaimer: I made the script for my own purposes; it may not be perfect, it may require further modifications to fit your own needs.

Gabi Purcaru
  • 30,940
  • 9
  • 79
  • 95
  • It is very very good! I think if you added 'include' and made it accept a list of objects it would be incredible. – Denzo Oct 28 '12 at 07:00
  • @Denzo I'm sorry, this was ~2 years ago and I may be wrong, but I think the `extra` argument should work. You can change this yourself though, the code is not too long – Gabi Purcaru Oct 28 '12 at 07:59
0

I had the same problem, here is my case:

Tl;dr: You need to make a serializer for each embedded model you use, and set it into the "father" serializer. That way your output will serialize your embedded model.

models.py

class Log(models.Model):
    status    = models.CharField(max_length=10, default='Sending')
    requested = models.DateTimeField(default=timezone.now)
    sent      = models.DateTimeField(null=True, default=None)
    log       = ListField(EmbeddedModelField('Log_Event'))

class Log_Message(models.Model):
    channel = models.ForeignKey(Channel)
    to      = models.CharField()
    message = models.CharField()

class Log_Event(models.Model):
    type    = models.CharField()
    message = models.CharField()
    date    = models.DateTimeField(default=timezone.now)

serializers.py

from rest_framework import serializers
from models         import Log, Log_Event, Log_Message

class LogMessageSerializer(serializers.HyperlinkedModelSerializer):
    class Meta:
        model  = Log_Message
        fields = ('channel', 'to', 'message')

class LogEventSerializer(serializers.HyperlinkedModelSerializer):
    class Meta:
        model  = Log_Event
        fields = ('type', 'message', 'date')


class LogSerializer(serializers.HyperlinkedModelSerializer):
    message = LogMessageSerializer()
    log     = LogEventSerializer()

    class Meta:
        model  = Log
        fields = ('status', 'requested', 'sent', 'log')

views.py

from models         import Log
from rest_framework import viewsets, filters
from serializers    import LogSerializer

class LogViewSet(viewsets.ModelViewSet):
    queryset         = Log.objects.all()
    serializer_class = LogSerializer
    filter_fields    = ('system', 'message', 'status', 'requested', 'sent', 'log')

JSON output

{
    "status": "Sent", 
    "requested": "2014-07-25T18:06:00.653", 
    "sent": "2014-07-25T18:06:03.707", 
    "log": [
        {
            "type": "starting...", 
            "message": "Trying to send...", 
            "date": "2014-07-25T18:06:00.659"
        }, 
        {
            "type": "success", 
            "message": "Mail SENT!", 
            "date": "2014-07-25T18:06:03.707"
        }
    ]
}
Lordn__n
  • 328
  • 2
  • 11