【问题标题】:Django Save Incomplete Progress on FormDjango在表单上保存不完整的进度
【发布时间】:2011-05-09 06:43:31
【问题描述】:

我有一个 django webapp,有多个用户登录并填写表格。

一些用户可能会开始填写表单,但缺少一些必需的数据(例如,授权 #)来验证表单(在我们开始处理表单之前)。我希望他们能够填写表格并可以选择保存部分信息(以便他们改天重新登录并完成)或提交完整信息以进行验证。

目前我对我使用的所有表单都使用 ModelForm,并且模型具有确保有效数据的约束(例如,授权 # 必须是唯一的)。但是,我希望他们能够在不进行任何验证的情况下保存这些中间数据。

我想到的解决方案似乎相当不雅且不合 django-ey:创建一个保存 POST 字典的“Save Partial Form”按钮将其转换为 shelf 文件并创建一个“SavedPartialForm”模型连接用户将部分表单保存在书架中。这看起来合乎情理吗?有没有更好的方法将 POST dict 直接保存到数据库中?或者是一个附加模块,可以部分保存表单(这似乎是网络表单的一个相当常见的活动)?

我对我的方法最大的担忧是我希望最终能够在某些 ajax/jquery 方法中自动执行此表单自动保存(例如每 10 分钟一次),而无需实际按下按钮并发送 POST 请求(例如,触发自动保存时不会将用户重定向到页面外)。我对 jquery 不太熟悉,想知道是否可以这样做。

【问题讨论】:

  • 你能做到吗?您能否提供有关如何操作的详细答案。这对其他开发人员将非常有用..

标签: python django django-forms


【解决方案1】:

保存前:

for field in form.fields:
    form.fields[field].required = False

然后:

form.save()

【讨论】:

  • 从尝试这个解决方案我得到一个验证错误,“The form could not be created because the data didn't validate.”知道任何解决方案吗?
【解决方案2】:

问题是您有多个表单。

部分。不完整。完全的。为此做好准备。准备好了。

确实,您有一个工作流的每个阶段的表单。

这完全没有问题。

  1. 找出您在工作流程中的位置。

  2. 填写并呈现下一阶段的表单。

表单可以相互继承以节省重复验证方法。

【讨论】:

  • 谢谢。这是有用的,也是看待它的好方法。我仍然想知道这是否与使用某种 jQuery 代码每隔十分钟左右自动保存部分/不完整表单不兼容。
  • @jimbob:从不。关键是要有一个与工作流的当前阶段相匹配的表单。如果他们无法为他们的工作流程阶段填写适当的数据,则表格无效。如果他们为此阶段填写了足够的信息,则该表格有效。如果他们想填写更多信息,您必须逐步填写相关表格,直到您赶上他们输入的内容。
【解决方案3】:

将以下内容放入您的表单__init__

for field in form.fields:
    form.fields[field].required = False

例如:

class MySexyForm(Form):
    def __init__(self, *args, **kwargs):
        super(MySexyForm, self).__init__(*args, **kwargs)
        for field in self.fields:
            self.fields[field].required = False

然后调用:

form = MySexyForm(...)
form.save()

但是您需要确保您的clean() 方法可以通过有条件地检查它们是否存在于cleaned_data 中来处理任何缺失的属性。例如,如果另一个表单字段验证依赖于customer_id,但您的部分表单没有指定一个,那么customer_id 将不在cleaned_data 中。

如果这是一个模型表单,您可以检查该值是否在cleaned_data 中,如果它丢失,则回退到instance.field

def clean(self):
    inst = self.instance
    customer_id_new = self.cleaned_data.get('customer_id', None)
    customer_id_old = getattr(self.instance, 'customer_id') if inst else None
    customer_id = customer_id_new if customer_id_new else customer_id_old

请记住,值新值几乎肯定不会与旧值采用相同的格式,例如customer_id 实际上可能是模型实例上的RelatedField,但表单数据上的pk int。同样,您需要在 clean 中处理这些类型差异。

这是 Django Forms 真正缺乏的一个领域。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-11-13
    • 1970-01-01
    • 2014-05-19
    • 2017-04-18
    • 1970-01-01
    • 2014-02-01
    • 1970-01-01
    相关资源
    最近更新 更多