Сигнал предварительного сохранения Django не работает

я протестировал сигнал "pre_save" Django следующими способами, но не могу поймать сигнал ни в одном из них.

$

from django.db.models.signals import pre_save
import logging

def my_callback(sender, **kwargs):
    logging.debug("======================================")
pre_save.connect(my_callback)
  1. запустите приведенный выше код в manage.py снаряд: Затем я запускаю свой веб-сайт и вижу модели.save () работает успешно, но функция обратного вызова не запускается.

  2. кроме того, я снова запускаю приведенный выше код в оболочке, а затем запускаю модели.сохранить() в оболочке. "сохранить" снова работает хорошо, но все равно ничего происходит с функцией обратного вызова.

  3. наконец, я вставляю приведенный выше код в __init__.py file и все же запустите функцию save () на веб-сайте. И все же ничего не происходит.

не могли бы вы помочь мне выяснить, почему сигнал pre_save не работает?

4 ответов


вы не устанавливаете класс отправителя для одного.

from django.db.models.signals import pre_save
from myapp.models import MyModel
import logging

def my_callback(sender, **kwargs):
    logging.debug("======================================")
pre_save.connect(my_callback, sender=MyModel)

во-вторых, если вы используете Django 1.3, вы должны использовать новый синтаксис декоратора.

# Inside your models.py
from django.db import models
from django.db.models.signals import pre_save
from django.dispatch import receiver

class MyModel(models.Model):
    field1 = models.TextField()
    field2 = models.IntegerField()

@receiver(pre_save, sender=MyModel)
def mymodel_save_handler(sender, **kwargs):
    logging.debug("======================================")

Это должно сделать это, но я не тестировал код, поэтому дайте мне знать, если он все еще сломан.


ответ Эрика заставил его работать, потому что он заставил вас подключить сигнал внутри models.py, так что при сохранении модели через веб-сайт обработчик сигнала находится в том же процессе, что и сигнальный пожарный.

в примерах 1 и 3 легко понять, почему они не работали - вы сохраняете в другом процессе (веб-сайт), где ваши приемники сигналов слушают.

Я хотел бы лучше понять, почему Пример 2 также сломан, но я просто отладил аналогичная проблема в моем собственном проекте при тестировании сигналов в оболочке, и это определенно связано с тем, что отправители и приемники сигналов не могут "видеть" друг друга.


logging.debug() использует корневой регистратор, уровень обработчика которого по умолчанию 30 ("предупреждение").

=>logging.debug('something') это просто и ничего не делать (уровень отладки-10 http://docs.python.org/2/library/logging.html

такой же тест должен быть сделан с другим пользовательским регистратором, или путем делать:

l = logging.getLogger()
l.setLevel(10)
def my_callback(sender, **kwargs):
    logging.debug("======================================")
pre_save.connect(my_callback)

исходный вопрос не содержит достаточной информации, чтобы знать, является ли это реальной проблемой OP облицовка (или ее часть).
Но, конечно, код OP не будет работать с моим ./manage.py shell


как описано в django сигнализирует doc на pre_save сигнал принимает 3 уникальных аргумента (не аргументы ключевого слова), поэтому вам нужно отредактировать свой my_callback функция должна быть следующей:

def my_callback(sender,instance, using, **kwargs):
    logging.debug("======================================")