2010-05-19 5 views
4

je les modèles Django suivantJSON sérialisation d'un modèle Django hérité

class ConfigurationItem(models.Model): 

    path = models.CharField('Path', max_length=1024) 
    name = models.CharField('Name', max_length=1024, blank=True) 
    description = models.CharField('Description', max_length=1024, blank=True) 
    active = models.BooleanField('Active', default=True) 
    is_leaf = models.BooleanField('Is a Leaf item', default=True) 

class Location(ConfigurationItem): 

    address = models.CharField(max_length=1024, blank=True) 
    phoneNumber = models.CharField(max_length=255, blank=True) 
    url = models.URLField(blank=True) 
    read_acl = models.ManyToManyField(Group, default=None) 
    write_acl = models.ManyToManyField(Group, default=None) 
    alert_group= models.EmailField(blank=True) 

Le fichier modèle complet est here si ça aide.

Vous pouvez voir que Company est une classe enfant de ConfigurationItem. J'essaie d'utiliser la sérialisation JSON en utilisant le sérialiseur django.core.serializers ou le sérialiseur WadofStuff.

Les deux serializers me donnent le même problème ...

>>> from cmdb.models import * 
>>> from django.core import serializers 
>>> serializers.serialize('json', [ ConfigurationItem.objects.get(id=7)]) 
    '[{"pk": 7, "model": "cmdb.configurationitem", "fields": {"is_leaf": true, "extension_attribute_10": "", "name": "", "date_modified": "2010-05-19 14:42:53", "extension_attribute_11": false, "extension_attribute_5": "", "extension_attribute_2": "", "extension_attribute_3": "", "extension_attribute_1": "", "extension_attribute_6": "", "extension_attribute_7": "", "extension_attribute_4": "", "date_created": "2010-05-19 14:42:53", "active": true, "path": "/Locations/London", "extension_attribute_8": "", "extension_attribute_9": "", "description": ""}}]' 
>>> serializers.serialize('json', [ Location.objects.get(id=7)]) 
    '[{"pk": 7, "model": "cmdb.location", "fields": {"write_acl": [], "url": "", "phoneNumber": "", "address": "", "read_acl": [], "alert_group": ""}}]' 
>>> 

Le problème est que le modèle sérialisation Company me donne uniquement les champs directement associés à ce modèle, et non pas les champs à partir de son objet parent.

Existe-t-il un moyen de modifier ce comportement ou devrais-je envisager de construire un dictionnaire d'objets et d'utiliser simplejson pour formater la sortie?

Merci à l'avance

~ sm

Répondre

4

Ceci est l'un de ces moments où la réponse peut venir trop tard pour l'affiche originale, mais peut-être utile pour la prochaine Googler.

Si vous avez besoin beaucoup plus sérialisation avancé, je ne peux pas vous aider, mais si vous voulez que l'héritage gracieuse manipulation multi-table, le lieu de regarder dans la section: django/core/serializers/base.py à la classe de base Serializer.

Dans le procédé serialize il y a une ligne:

for field in concrete_model._meta.local_fields:

Monkeypatching ou remplaçant cette classe & remplaçant cette ligne avec:

for field in concrete_model._meta.fields:

Il y a quelques mises en garde de connaître cependant, voir commettre 12716794db dans le repo Git Django & ces deux questions:

https://code.djangoproject.com/ticket/7350

https://code.djangoproject.com/ticket/7202

Longue histoire courte, vous devriez probablement faire attention à faire globalement, bien que l'annulation de ce comportement puisse être acceptable en fonction de votre objectif.

+0

Merci beaucoup! Si quelqu'un essaie de suivre cette suggestion, copiez-vous le contenu de '' base.py'', '' python.py'' et l'un des sérialiseurs concrets (json, xml, etc.). Puis changez la ligne comme @philipk suggéré dans '' base.py'' et remplacez la chaîne d'héritage jusqu'au sérialiseur concret. Vous pouvez également ajouter votre nouveau sérialiseur aux paramètres, regardez dans '' __init __. Py'' (dans le paquet sérialiseurs django) pour plus de détails. Merci encore @philipk, vous avez sauvé ma journée! :-) – Nagasaki45

2

Vous aurez besoin d'un sérialiseur personnalisé pour prendre en charge les champs hérités, car le sérialiseur de Django ne sérialisera que les champs locaux.

Je fini par écrire mon propre en traitant cette question, ne hésitez pas à le copier: https://github.com/zmathew/django-backbone/blob/master/backbone/serializers.py

https://github.com/zmathew/django-backbone/blob/351fc75797bc3c75d2aa5c582089eb39ebb6f19a/backbone/serializers.py

Pour l'utiliser lui-même, vous devez faire:

serializer = AllFieldsSerializer() 
serializer.serialize(queryset, fields=fields) 
print serializer.getvalue() 
+1

Le lien est cassé maintenant .. – abrunet

Questions connexes