2016-07-17 9 views
1

Ich habe ein django-polymorphic Modell und möchte ein post_save Signal implementieren, um automatisch ein verwandtes Modell zu erstellen, das auch polymorph ist.Wie benutzt man einen post_save-Empfänger mit Django-Polymorph?

Es ist so etwas wie der Code unten, das entsprechende Stück von nicht funktionierenden Code ist die dekoriert work_post_save Methode. Das Problem ist, dass die Instanz eine ctype_id und kein Objekt ist.

from django.db import models 
from django.db.models import signals 
from django.dispatch import receiver 
from polymorphic.models import PolymorphicModel 

from mygallery.models import Album 

# Work Parent PolymorphicModel 
class Work(PolymorphicModel): 
    title = models.CharField(blank=True,max_length=256) 
    slug = models.SlugField(max_length=256) 

@receiver(signals.post_save, sender=Work) 
def work_post_save(sender, instance, signal, created, **kwargs): 
    album, new = Album.objects.get_or_create(title=instance.title + ' Stills', slug=instance.slug + '-stills') 
    work_album, new = WorkAlbum.objects.get_or_create(work=instance, album=album, is_key=True) 


class ArtProject(Work): 
    manifesto = models.CharField(blank=True,max_length=256) 

class CodeProject(Work): 
    code = models.CharField(blank=True,max_length=256) 


# Content Parent PolymorphicModel 
class WorkContent(PolymorphicModel): 
    is_key = models.BooleanField(default=False, unique=True, default=False) 


class WorkAlbum(WorkContent): 
    work = models.ForeignKey(Work, related_name='work_albums') 
    album = models.ForeignKey(Album, related_name='album_works') 

Antwort

0

Ich habe getüftelt nur für ein bisschen mit diesem um, damit ich nicht zu 100% sicher bin, was die richtige Art und Weise des Umgangs mit dieser ist.

Was ich tun gelandet ist nicht die sender in der @receiver Anmerkung erklärt. Dies hat zur Folge, dass der Callback von jedem post_save Signal ausgelöst wird. Dann im Callback überprüfe ich isinstance() mit meinem Elternmodell (in Ihrem Fall Work), so dass der Rückruf nur ausgeführt wird, nachdem ein Modell, das mich interessiert, gespeichert wird. Wenn der Rückruf ausgeführt wird, ist der Parameter instance ein untergeordnetes Modell (in Ihrem Fall ArtProject oder CodeProject).

@receiver(signals.post_save) 
def work_post_save(sender, instance, signal, created, **kwargs): 
    if isinstance(instance, Work): 
     # instance is either ArtProject or CodeProject 
     album, new = Album.objects.get_or_create(title=instance.title + ' Stills', slug=instance.slug + '-stills') 
     work_album, new = WorkAlbum.objects.get_or_create(work=instance, album=album, is_key=True) 

Auslösen direkt auf der übergeordneten save() ist offenbar not supported.