Django signals for Comment notification

Viewed 421

I am working on django project and I have written a post_save signal to notify post author when commented. Now, I want to add a post_save signal to notify post author & comment user that a comment (reply) is made. How do I approach this? This is because there is a parent-child relationship on my comment model.

Below are my model and signal code. Can someone assist please? I am new on django and have just started learning django signals.

class Comment(models.Model):
    user = models.ForeignKey('auth.User', on_delete=models.CASCADE)
    post = models.ForeignKey('forum.Post',related_name='comments', on_delete=models.CASCADE)
    reply = models.ForeignKey('self', null=True, blank=True, related_name='replies', on_delete=models.CASCADE)
    text = models.TextField(max_length=250, blank=True)


@receiver(post_save, sender=Comment)
def user_comment_post(sender, instance, created, **kwargs):
    if created:
        comment = instance
        post = comment.post
        #reply = comment.reply
        text_preview = comment.text[:90]
        sender = comment.user
        notify = Notification.objects.create(post=post, sender=sender, comment=comment, user=post.author, text_preview=text_preview, notification_type=2)
        notify.save()
2 Answers

From the model structure :

  • A new Comment object to a Post would have Comment.reply field as None
  • A reply (another Comment object) to an existing Comment object would have Comment.reply not as None .Would have a parent Comment object.

So, check in the signal instance if comment.reply is None or not.

  • if comment.reply is None it is a new comment to a post >>> send notification to Post owner only
  • if comment.reply is not None it is a new comment (reply) to an existing comment of a post >>> send notification to Post owner and Comment owner
@receiver(post_save, sender=Comment)
def user_comment_post(sender, instance, created, **kwargs):
    if created:
        comment = instance
        post = comment.post
        text_preview = comment.text[:90]
        sender = comment.user
        notify_post_author = Notification.objects.create(post=post, sender=sender, comment=comment, user=post.author, text_preview=text_preview, notification_type=2)
        notify_post_author.save()

        if comment.reply is not None:
            notify_comment_owner = Notification.objects.create(post=post, sender=sender, comment=comment, user=comment.reply.user, text_preview=text_preview, notification_type=2)
            notify_comment_owner.save()

You could check in the same post_save hook if the comment being saved is a reply by performing an EXISTS query accessing it's related manager:

@receiver(post_save, sender=Comment)
def user_comment_post(sender, instance, created, **kwargs):
    if created and entities.replies.exists():
        # your code here
Related