首页 > 解决方案 > Django中有条件“ON DELETE CASCADE”这样的东西吗?

问题描述

是否有一种简单的方法,使用on_delete, 在删除 ForeignKey 时删除包含 ForeignKey 的对象(通常会这样做),但如果满足某些条件(通常会这样做),则models.CASCADE只是与 ForeignKey 的关系。Nonemodels.SET_NULL

这是一些代码:

class SomeThing(models.Model):
    user = models.ForeignKey(
        settings.AUTH_USER_MODEL, 
        related_name="things", 
        on_delete=models.CONDITIONAL_CASCADE,  # obviously this is wrong
    )
    is_private = models.BooleanField(default=False)
>>> user = User(username="bob").save()
>>> public_thing = SomeThing(is_private=False)
>>> private_thing = SomeThing(is_private=True)
>>> user.things.add(public_thing)
>>> user.things.add(private_thing)
>>> user.delete()

什么时候user被删除我想private_thing和 w/ 一起被删除,user被删除并且被设置为.public_thingpublic_thing.userNone

谢谢。


编辑:

感谢@Jarad 的建议,我最终编写了以下通用函数:


def CONDITIONAL_CASCADE(collector, field, sub_objs, using, **kwargs):
    
    condition = kwargs.get("condition", {})
    default_value = kwargs.get("default_value", None)

    sub_objs_to_cascade = sub_objs.filter(**condition)
    sub_objs_to_set = sub_objs.exclude(**condition)

    models.CASCADE(collector, field, sub_objs_to_cascade, using)
    collector.add_field_update(field, default_value, sub_objs_to_set)

并像这样使用它:

CASCADE_PRIVATE_THINGS_ONLY = partial(
    CONDITIONAL_CASCADE,
    condition={"is_private": True},
    default_value=None
)

标签: djangoforeign-keys

解决方案


推荐阅读