Django Nested Admin 验证来自父表单的嵌套内联

Django Nested Admin validation of nested inlines from parent forms

我想做的是断言子表单的 start_date 在父表单的 start_date 之后。

比如我有以下型号:

class Parent(models.Model):
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
    starts_at = models.DateTimeField(blank=True, null=True)


class Child(models.Model):
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
    parent = models.ForeignKey(Parent, on_delete=models.CASCADE, related_name='children')
    starts_at = models.DateTimeField(null=True, blank=True)

管理表单设置如下:

class ChildInline(nested_admin.NestedTabularInline):
    model = models.Child
    extra = 0


@admin.register(models.Parent)
class ParentAdmin(nested_admin.NestedModelAdmin):
    inlines = [ChildInline]

我将如何根据父项验证子项(反之亦然)?

到目前为止我已经探索过:

  1. Form.clean() - 但这不包括 child/parent 个实例。
  2. Formset.clean() - 但尽管制作了表单集,但 django-nested-admin 似乎忽略了它们并且从未使用过它们的干净方法。

有没有人找到解决此类问题的方法?

看来您仍然可以使用 model.clean() 方法进行表单验证:

from django.core.exceptions import ValidationError


class Child(models.Model):
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
    parent = models.ForeignKey(Parent, on_delete=models.CASCADE, related_name='children')
    starts_at = models.DateTimeField(null=True, blank=True)

    def clean(self):
        parent_start = self.parent.starts_at
        child_start = self.starts_at
        if parent_start and child_start < parent_start:
            raise ValidationError(f'This group cannot start before the season starts')

这将使 ValidationError 出现在 Child 表单上。在 Parent 表单上使用 clean 方法也是可能的,并且会给出该级别的错误。