【问题标题】:Should default model fields be set by the Form or the Model?默认模型字段应该由表单还是模型设置?
【发布时间】:2014-07-09 17:31:12
【问题描述】:

哪个选项最好,1 还是 2?

1.

class TopicForm(forms.Form):

    name = forms.CharField(required=True)
    body = RichTextFormField(required=True)

    def save(self, request):
        t = models.Topic(user=request.user,
                         site=get_current_site(request),
                         name=self.cleaned_data['name'],
                         body=self.cleaned_data['body'])
        t.slug = slugify(self.name)
        t.body_html = seo.nofollow(seo.noindex(self.body))
        t.ip = utils.get_client_ip(request)
        t.save()

或 2.

class Topic(models.Model):
    ...   

    def save(self, *args, **kwargs):
        self.slug = slugify(self.name)
        self.body_html = seo.nofollow(seo.noindex(self.body))
        self.ip = utils.get_client_ip(request)
        super(Topic, self).save(*args, **kwargs)

【问题讨论】:

  • 也许有更多知识的人可以编辑此问题标题以反映问题。这有点模棱两可,似乎没有反映这个问题。

标签: django forms models


【解决方案1】:

不同之处在于第一个版本仅在通过表单修改对象时应用,而第二个版本在保存模型时应用(尽管这仍然是在 Django 中可以修改数据库行的所有方法的子集)。即使您目前只通过表单创建对象,我认为这仍然是一个有用的区别,需要牢记。

在我看来,在你的情况下,两者的混合是有意义的。 slug 是您始终希望基于 name 设置的东西 - 也就是说,它是模型本身固有的。另一方面,client_ip 的概念似乎与通过 Web 请求创建具有表单的对象的概念密不可分。

当然,您可以更好地了解此模型的细节,但这是我处理问题的一般方式。

【讨论】:

    【解决方案2】:

    你不应该使用 2. 最好使用 pre-save 或 post-save 之类的信号

    来源:https://docs.djangoproject.com/en/dev/topics/signals/

        @receiver(pre_save, sender=Topic)
        def topic_pre_save_handler(sender, instance, **kwargs):
            instance.slug = slugify(self.name)
            instance.body_html = seo.nofollow(seo.noindex(self.body))
            instance.ip = utils.get_client_ip(request)
    

    【讨论】:

      【解决方案3】:

      我个人更喜欢第二种选择。模型也应该定义业务逻辑,而表单应该只处理用户 I/O。这样,即使以编程方式使用(从其他代码导入和调用),您的应用程序也将保持一致。

      【讨论】:

        【解决方案4】:

        这取决于。如果这应该应用于每个模型,那么在模型中会更好。它将向您保证每个 Topic 对象都将具有正确的值,即使是您从管理界面编辑的值。

        该表单应仅用于检查来自用户的数据,并且该模型适合自动执行此类任务(在保存对象之前生成数据)。请注意,这不应引发异常或使数据无效。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2021-10-19
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多