如何限制Django模型使用某些外键值?

时间:2019-05-11 18:22:53

标签: django django-models

我正在尝试创建一个具有“ successor”字段的Django模型,这是该模型的外键。我想限制模型,使其无法(1)将实例设置为其自己的后继者,或(2)创建循环的前任-后继关系。

这很简单,如果Django在保存之前调用了clean,但显然没有。

本质上,每当保存模型时,我本质上都想在下面的cleanadd_predecessoradd_successor方法中调用验证器。

class MyModel(models.Model):
    ...
    successor = models.ForeignKey(
        'self',
        null=True,
        blank=True,
        on_delete=models.SET_NULL,
    )

...

    def clean(self):
        if self.successor is self:
            raise Exception("...")

    def add_predecessor(self, predecessor):
        if predecessor is self:
            raise Exception("...")
        if self.successor is predecessor:
            raise Exception("...")
        predecessor.successor = self

    def add_successor(self, successor):
        if successor is self:
            raise Exception("...")
        if successor.successor is self:
            raise Exception("...")
        self.successor = successor

我可以覆盖save,但这似乎是一个笨拙的解决方案。

1 个答案:

答案 0 :(得分:2)

您可以使用pre_save信号:

from django.db.models.signals import pre_save

@receiver(pre_save,sender=MyModel)
def pre_save_handler(sender, instance, *args, **kwargs):
    # some case
    if case_error:
        raise Exception('OMG')

您还可以覆盖MyModel的保存方法:

class MyModel(models.Model):
    ....
    def save(self, *args, **kwargs):
        #check your conditions and raise exception
    ....