[Django]-Post_save signal isn't called

36👍

When would post_save be fired?

What the document says: At the end of the save method.

What it really means: At the end of the successful completion of the save method.

When would the signal not be fired?

  1. If the save method does not successfully save the object (such as when an IntegrityError occurs)
  2. When you call MyModel.objects.update()
  3. When you override the save method and forget to call the superclass method.
  4. When your signal receiver hasn’t been successfully registered.

How to register the receiver

Simplest is to use the @receiver decorator as you have done. The alternative is to use

from django.db.models.signals import pre_save

pre_save.connect(order_save, sender='app_label.MyModel')

Where should this code be placed?

Nowadays, the manual states that

Strictly speaking, signal handling and registration code can live
anywhere you like, although it’s recommended to avoid the
application’s root module and its models module to minimize
side-effects of importing code.

That is probably why in this instance you have created a file called signals.py and place your code inside that and gone to all that trouble with the AppConfig class and the ready method. But funnily enough, the Django 1.6 manual says:

You can put signal handling and registration code anywhere you like.
However, you’ll need to make sure that the module it’s in gets
imported early on so that the signal handling gets registered before
any signals need to be sent. This makes your app’s models.py a good
place to put registration of signal handlers.

So if you are having trouble getting your signal receiver registered you can actually try putting your code in models.py or views.py and leave out the bits from AppConfig (maybe even remove AppConfig completely)

If you want to carry out the registration in AppConfig, and you are having trouble with @reciever and/or imports, you can try

from django.db.models.signals import pre_save
from app_label.signals import my_reciever

def ready(self):
    pre_save.connect(my_reciever, sender='app_label.MyModel')

How to avoid repeats?

Does the signal get fired twice? Make sure that you register the receiver only once. If you register it in AppConfig, leave it out of models.py and vice verce

👤e4c5

6👍

Are you aaaaaabsolutely sure the correct signals is imported? (print('hi, signals here') in the module?)

You might want to use an absolutely qualified import (import orders.signals) or a relative one (import .signals as signals), too.

👤AKX

4👍

Do you have another app also named signals?

Try relative import in the ready method: from . import signals

Leave a comment