简体   繁体   English

Django-将值从pre_save传递到模型上的post_save方法

[英]Django - Pass value from pre_save to post_save methods on model

I've got a Django model like so... 我有一个像这样的Django模型...

class Example(models.Model):
    title = models.CharField(...)
    ...

I'm trying to compare two values - the title field before the user changes it, and the title after. 我正在尝试比较两个值-用户更改之前的title字段和之后的title I don't want to save both values in the database at one time (only need one title field), so I'd like to use pre_save and post_save methods to do this. 我不想一次将两个值都保存在数据库中(只需要一个title字段),所以我想使用pre_savepost_save方法来做到这一点。 Is it possible to get the title before the save, then hold this value to be passed into the post_save method? 是否可以在保存之前获取标题,然后保留该值以传递到post_save方法中?

The pre_save and post_save methods look like so... pre_save和post_save方法看起来像这样...

@receiver(pre_save, sender=Example, uid='...')
def compare_title_changes(sender, instance, **kwargs):
    # get the current title name here
    x = instance.title

@receiver(post_save, sender=Example, uid='...')
def compare_title_changes(sender, instance, **kwargs):
    # get the new title name here and compare the difference
    x = instance.title # <- new title
    if x == old_title_name: # <- this is currently undefined, but should be retrieved from the pre_save method somehow
        ...do some logic here...

Any ideas would be greatly appreciated! 任何想法将不胜感激!

Edit 编辑

As was pointed out to me, pre_save and post_save both occur after save() is called. 正如我所指出的,pre_save和post_save都在调用save()之后发生。 What I was looking for is something like pre_save() but before the actual save method is called. 我一直在寻找类似于pre_save()的东西,但是在调用实际的save方法之前。 I set this on the model so that the logic to be performed will be accessible wherever the instance is saved from (either admin or from a user view) 我在模型上进行了设置,以便无论实例保存在哪里(管理员或用户视图),都可以访问要执行的逻辑

Use Example.objects.get(pk=instance.id) to get the old title from the database in the pre_save handler function: 使用Example.objects.get(pk=instance.id)pre_save处理函数中从数据库中获取旧标题:

@receiver(pre_save, sender=Example, uid='...')
def compare_title_changes(sender, instance, **kwargs):

    new_title = instance.title  # this is the updated value
    old_title = Example.objects.get(pk=instance.id)
    # Compare the old and new titles here ...

This trick was proposed here a long time ago. 很久以前在这里提出这个技巧。 I've not tested it with the recent Django version. 我尚未使用最新的Django版本进行测试。 Please let me know whether it's still working. 请让我知道它是否仍在工作。

We can only say object has changed if "save" method passes successfully, so post_save is good to be sure that model object has updated. 我们只能说,如果“保存”方法成功通过,则对象已更改,因此post_save可以确保模型对象已更新。

Setting on the fly attribute on model class instance can do the task, as the same instance is passed from pre_save to post_save. 在模型类实例上设置fly属性可以完成此任务,因为将同一实例从pre_save传递到post_save。

def set_flag_on_pre_save(sender, instance, *args, **kwargs):
    # Check here if flag setting condition satisfies
    set_the_flag = true
    if set_the_flag:  
      instance.my_flag=0


def check_flag_on_post_save(sender, instance, *args, **kwargs):
   try:
      print(instance.my_flag)
      print('Flag set') 
   except AttributeError:
      print('Flag not set')


pre_save.connect(set_flag_on_pre_save, sender=ModelClass)

post_save.connect(check_flag_on_post_save, sender=ModelClass)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM