Access to related data of newly created model instance using post_save signal handler

北城余情 提交于 2019-12-22 06:50:43

问题


I need to send an e-mail when new instance of Entry model is created via admin panel. So in models.py I have:

class Entry(models.Model):   
    attachments = models.ManyToManyField(to=Attachment, blank=True)
    #some other fields
    #...
    sent = models.BooleanField(editable=False, default=False)

Then I'm registring post_save handler function:

def send_message(sender, instance, **kwargs):
    if not instance.sent:
        #sending an e-mail message containing details about related attachments
        #...
        instance.sent = True
        instance.save()

post_save.connect(send_message, sender=Entry)  

It works, but as I mentioned before, I also need to access related attachments to include their details in the message. Unfortunatelly instance.attachments.all() returns empty list inside send_message function even if attachments were actually added.

As I figured out, when the post_save signal is sent, related data of saved model isn't saved yet, so I can't get related attachments from that place. Question is: am I able to accomplish this using signals, or in any other way, or do I have to put this email sending code outside, for example overriding admin panel change view for Entry model?


回答1:


You should be able to do this by overriding the save_model() method on the ModelAdmin. You could either send your email in there or fire a custom signal which triggers your handler to send the email.

If you have inlines, I believe you need to use save_formset() instead.




回答2:


Maybe you could use the M2M Changed Signal instead? This signal is sent when the M2M field is changed.




回答3:


I tried to use ModelAdmin save_model() method, as shadfc proposed. Anyway newly changed related objects aren't accessible from there either. But save_model takes filled form as a parameter, so I used that. My send_message isn't used as a signal handler anymore and I added related_data parameter.

def send_message(sender, instance, related_data={}):
    #sending e-mail using related_data parameter to access additional related objects
    #...

in admin.py I have:

class EntryAdmin(admin.ModelAdmin):
    def save_model(self, request, obj, form, change):
        obj.save()
        send_message(sender=Entry, instance=obj,
                     related_data={'attachments': form.cleaned_data['attachments']} )


来源:https://stackoverflow.com/questions/5680931/access-to-related-data-of-newly-created-model-instance-using-post-save-signal-ha

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!