允许Django模型

时间:2018-04-27 03:46:59

标签: python django django-models

当一个字段不存在时,任何人都知道如何防止Django在保存时引发TypeError?我在下面列出了简化模型。基本上,我想在创建标签时传递'name'属性。然后,自定义保存操作将使用名称get_or_创建TagDetail并创建关联。

class TagDetail(models.Model):
    name = models.CharField(max_length=100, unique=True)

class Tag(models.Model):
    detail = models.ForeignKey(TagDetail, on_delete=models.CASCADE)
    content_type = models.ForeignKey(ContentType, on_delete=models.CASCADE)
    object_id = models.PositiveIntegerField()
    content_object = GenericForeignKey('content_type', 'object_id')

    class Meta:
        abstract = True

3 个答案:

答案 0 :(得分:0)

尝试为该字段设置blank=True。如果您以后需要它,您可以在表单上设置它。

答案 1 :(得分:0)

您的代码模型中有一些字段是必需的,并且不能为空,content_typeobject_id

  

你:你想传递一个名字'创建标记时的属性。然后,自定义保存操作将使用名称get_or_创建TagDetail并创建关联

该过程是您为模型调用save(),然后调用get_or_create方法创建名称为TagDetails ...到目前为止没有问题

但是当您保存代码时,即使使用关联detail= tag_details_instance,实际上您也会将这些字段content_typeobject_id清空。您没有告诉db为这些字段设置空白或null

解决方案#1
如果您有这些字段的数据,则在创建标记时,请确保为其分配值。

解决方案#2
使用以下命令修改标记模型:

class Tag(models.Model):
    detail = models.ForeignKey(TagDetail, on_delete=models.CASCADE)
    content_type = models.ForeignKey(ContentType, on_delete=models.SET_NULL,
        blank=True,null=True)
    object_id = models.PositiveIntegerField(blank=True,null=True)
    content_object = GenericForeignKey('content_type', 'object_id')

如果你非常关心在content_type字段中保持与on_delete = models.CASCADE相同的行为,你可以添加信号pre/post_delete

答案 2 :(得分:0)

尝试覆盖模型save()方法,如下所示

class TagDetail(models.Model):
    name = models.CharField(max_length=100, unique=True)


class Tag(models.Model):
    detail = models.ForeignKey(TagDetail, on_delete=models.CASCADE)
    content_type = models.ForeignKey(ContentType, on_delete=models.CASCADE)
    object_id = models.PositiveIntegerField()
    content_object = GenericForeignKey('content_type', 'object_id')

    class Meta:
        abstract = True

    def save(self, *args, **kwargs):
        tag_detail, created = TagDetail.objects.get_or_create(name=self.detail)
        self.detail = tag_detail
        super().save(*args, **kwargs)