【问题标题】:django python dynamic max_length based on select list value基于选择列表值的django python动态max_length
【发布时间】:2015-09-25 09:29:31
【问题描述】:

我正在使用 django 1.7 和 python 2.7。

我有一个模型类,它允许用户输入文本区域和文本框。

If用户在选择列表中选择0,then文本框显示给用户输入,文本区域隐藏else文本区域显示,文本框对用户隐藏.

文本框和文本区域都具有完全相同的输入。在文本框中输入的内容会出现在文本区域中,反之亦然。

文本框和文本区域都有不同的 maxlength/max_length 值。

文本框最大长度为250,文本区域最大长度为5000。

我有客户端验证工作,但我很难让服务器端验证工作。

当文本框和文本区域的 max_length 值不同但输入长度相同时,如何在 forms.py 文件中启用/禁用对我的模型的服务器端验证?

我知道可以在 forms.py 上分配 max_length,但我无法正确获取代码语法。

这是我的 models.py 代码:

workplace_training_display_type = models.PositiveIntegerField(.....)
workplace_training_certificationTB = models.CharField(null=False, blank=False)
workplace_training_certificationTA = models.TextField(null=False, blank=False)

通常我会将max_length=250 放到workplace_training_certificationTBmax_length=5000workplace_training_certificationTA 以上模型字段。但是,我认为这必须在 forms.py 文件中动态完成。

编辑 如果我将 max_length 设置为 workplace_training_certificationTBworkplace_training_certificationTA 的模型,因为这两个字段具有完全相同的输入,那么将触发服务器端验证之一,这就是我想动态设置值的原因.

这是我的 forms.py 文件代码:

def clean(self):

    cd_wrtdf = super(WorkplaceRelatedTrainingDetailsForm, self).clean()

    if 'workplace_training_display_type' in cd_wrtdf and cd_wrtdf['workplace_training_display_type'] != 0:

        #  if the workplace_training_display_type is not zero, remove the max_length=250 from the textbox.

        #  if the workplace_training_display_type is not zero, add the max_length=5000 to the textarea.

    else:

        #  if the workplace_training_display_type is zero, add the max_length=250 to the textbox.

        #  if the workplace_training_display_type is zero, remove the max_length=5000 from the textarea.

    return cd_wrtdf

我已尝试搜索 SO 和 Google,但找不到任何有用的信息。

【问题讨论】:

  • 为什么不在服务器上让两个字段的长度一样?
  • dan-klasson - 因为如果两个字段的输入长度相同且文本区域有 1000 个字符,则触发文本框的服务器端验证最大长度(250 个字符)。跨度>
  • @user3354539 如果您在模型级别设置 max_length,django 将自动验证您的要求
  • Alvaro - 我在帖子中添加了一个编辑来解释。
  • 如果您使用的是 PostgreSQL,则 char 和 text 字段之间没有性能问题。另外,如果我没记错的话,如果您的最大长度值很大,但实际长度很小,大多数数据库系统都不会出现问题。因此,您可以简单地删除模型字段之一(最好是较小的)。在客户端,您需要添加一个文本输入,其余部分保持不变,因为两个输入始终具有相同的值。

标签: python django validation django-models django-forms


【解决方案1】:

在模型中包含重复字段并不是真正的正确方法。您应该将模型更改为只有一个字段,一个文本字段,最大长度为 5000。然后在 forms.py 中,您可以使用 len(input) 检查输入的长度。然后,您可以根据其他选定的字段来决定它是否在限制范围内。

在你的 clean 方法中,调用super() 会自动检查它是否在 5000 以内,然后你会检查它是否需要小于 250。如果是,那么只需查看 if len(input) > 250: raise ValidationError('Too long for type')

【讨论】:

  • electrometro,感谢您的回复。它让我看到你的方法是多么简单。我确实必须保留重复的字段,因为当我尝试使用replacewith 换出文本框/文本区域时出现问题。它现在可以按我的需要工作。
  • 您应该可以使用一些 javascript 轻松做到这一点。
【解决方案2】:

您的模型字段中不能有动态长度,因为这些是在数据库级别实现的。当您在字段上设置最大长度时,它会将其转换为等效的 SQL,从而限制可以存储在数据库级别的数据量。

正如@electrometro 提到的,我还建议在您的模型中使用一个长度为 5000 的 CharField。

由于这似乎更像是一个用户界面问题,您应该使用 Javascript 执行此操作,并根据您提到的用户选择替换您需要的类型的输入。只要表单输入发布具有相同名称的数据,Django 表单仍将按预期运行。

您可以执行类似于this toggle behavior 的操作,除非您将在用户从您的列表中选择一个选项时触发它。还要确保输入/文本区域 ID 和名称与表单字段相同,以便表单能够清理数据。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2020-01-09
    • 1970-01-01
    • 1970-01-01
    • 2016-02-13
    • 1970-01-01
    • 2012-12-08
    • 2021-05-10
    • 1970-01-01
    相关资源
    最近更新 更多