如何最好地在保存之前验证总反向关系的数量

How best to validate number of total reverse relationships before saving

我有一个与其他两个模型(ItemComponent 和/或 ItemComponentCategory)反向相关的项目模型。这个想法是我希望能够在保存之前验证 Items 与其他两个模型的关系不超过 4 个。

class Item(models.Model):
    name = models.CharField(max_length=40, unique=True)

class ItemComponent(models.Model):
    parent_item = models.ForeignKey(Item, related_name='components')

class ItemComponentCategory(models.Model):
    parent_item = models.ForeignKey(Item, related_name='categories')

如果保存的对象将导致它们之间存在 >4 个对象关系,我想创建一个在保存 Item、ItemComponent 或 ItemComponentCategory 对象之前引发错误的验证。

我已经尝试将类似这样的内容添加到所有三个的清理方法中:

    def clean(self):

        if (self.parent_item.components.count() + self.parent_item.categories.count()) > 4:
            raise ValidationError(_(f'Items can have no more than 4 components and/or component categories'))

只要项目及其关系已经用 4 保存并且您正在尝试添加更多关系,这似乎就可以工作。

但是,如果我在 ItemAdmin 中创建一个 TabularInline 来添加这些 'sub types,',如果您愿意的话。我可以创建一个新项目并添加尽可能多的这些子类型并保存它没有问题。

我在这里错过了什么?

看来我的问题与进程的时间和顺序有关。

保存带有内联引用的管理页面时,会先保存主页模型,然后再保存内联对象。这在尝试使用模型的 clean() 方法来验证关系时会造成问题,因为它根本不存在。

正如THIS文章中提到的,我的解决方案似乎是修改modelAdmin函数以确保先保存内联对象,然后在保存后验证主要对象。

另外,我认为这个 save_related modelAdmin 的方法会派上用场。