Django - 我何时应该使用信号(signal),何时应该重写(save)保存方法?

17

就我个人而言,我喜欢使用信号

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

class MyModel(models.Model):

    ...

def custom_action_before_saving(sender, instance, *args, **kwargs):
    ...

pre_save.connect(custom_action_before_saving, sender=MyModel)

但我想知道有没有一些时间或任务,更好地在模型类中覆盖保存方法:

from django.db import models

class MyModel(models.Model):
    ...

    def save(self):
        ...
        super(MyModel, self).save()
我问这个问题是因为在Django文档页面中有一个覆盖save()方法的示例(链接在上面提供),所以我认为这不是一种不好的做法。
pre_save()为例,文档表示:

这会在模型的save()方法开始时发送。

那么,覆盖save是否对性能产生与使用信号相同的影响?

@luke_aus,使用if self....:覆盖保存以避免在某些情况下执行代码不是一回事吗? - Gocht
@luke_aus 这是一个很好的观点,批量方法会触发信号吗? - Gocht
@Gocht fixtures做法,bulk_create()不确定。 - lukeaus
@luke_aus 来自文档模型的save()方法不会被调用,也不会发送pre_save和post_save信号。 - Gocht
显示剩余2条评论
2个回答

28

你不会发现任何性能差异。它们都不是hack或"错误"的编码方法。这完全取决于您的喜好。

如果在覆盖保存方法或从其他地方保存时出现循环导入,可以使用信号。

我遵循一个模式,如果更改属于同一模型,则覆盖保存方法,否则如果它们属于与当前模型没有链接(通过一对一或一对多)的不同模型,则使用信号。


非常漂亮的模式(Y) - Symon

4
选择覆盖保存方法或利用信号并不是关于性能或最佳实践的问题。如文档所述,信号主要是一种保持应用程序解耦的好方式,同时仍然能够相互通信。
与覆盖保存方法相比,使用信号更容易与Celery结合,将某些处理转移到后台进行,这也更加自然。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接