[afpy/django] Exécution multiple des signaux lorsqu'on les définie dans models.py ?

Stéphane Bunel stephane+djangofr at bpf.st
Sam 16 Mai 18:37:33 CEST 2009


Le vendredi 15 mai 2009 11:57:16, Lior Gradstein a écrit :
> Bonjour,
> 
> J'attache une methode à un signal avec la commande
> "signals.pre_save.connect(ma_methode, sender=MonModele)", que j'inclue dans
> mon fichier models.py:
> 
> def ma_methode(sender, instance, signal, *args, **kwargs):
>    print "Hello world"
> 
> from django.db.models import signals
> signals.pre_save.connect(ma_methode, sender=MyModel)
> 
> 
> Mon problème: si je mets un print dans cette methode, je vois qu'elle est
> appelée plusieurs fois lors de la création de mon modele (soumission de mon
> formulaire), alors qu'il ne devrait y passer qu'une fois.
> 
> La raison: j'ai mis ce signals.pre_save.connect() à la fin de mon models.py,
> ce qui fait qu'il est exécuté dès que dans un autre module je fais un "from
> models import MyModel" (par exemple dans mon form.py, ce que, je suppose,
> tout le monde fait). Pourtant, lorsque je regarde dans ce qui se fait dans
> les autres projets, le placement dans le models.py est recommandé.
> 
> Alors comment est-ce possible ? Je ne souhaite pas que ma méthode soit
> appelée plusieurs fois !

J'ai rencontré ce cas. Il est en fait très logique car le dispatcher est 
sollicité à chaque import et enregistre donc plusieurs fois les signaux.

Pour éviter d'enregistrer plusieurs fois le même signal il suffit de lui donner 
un identifiant au moment de l'enregistrer.

Ainsi le dispatcher pourra alors se rendre compte, grâce à l'identifiant, si 
l'on tente d'enregistrer plusieurs fois le même signale.

Exemple:

signals.post_save.connect( person_post_save_callback,
    sender = Person,
    dispatch_uid = 'person_post_save_callback' )

Je donne le nom de la méthode invoquée comme identifiant mais c'est un choix 
personnel et arbitraire.

Stéphane Bunel.
(...)



Plus d'informations sur la liste de diffusion django