python - Django Formset:是否有机会在 CreateView 的 post() 方法中添加缺少的字段内容?
问题描述
我用 a 创建了CreateView
一个modelformset
,添加了一些 js 来添加或删除其他表单。这是从银行预订条目创建预订的视图。而且由于'from_account'很明显(预订是从某个银行预订条目启动并从url中的银行预订交出pk),我不想在表单中显示这个(selection-)字段。所以我将该字段作为隐藏字段放在表单集中,目的是在帖子中填写它。所有这些都按预期工作,直到提交。
现在,在 post() 方法中,我在 formset.error 中正确看到了缺少字段“bank_account_ta”和“from_account”的错误。由于我不知道 total_forms 编号(可能已使用 js 更改),因此在实例化 formset 类时无法预填充它。
使用 js 在模板中工作是可能的,但不是正确的方法......
我宁愿使用 formset.clean() 方法,但无论我尝试什么,formset.error 仍然像以前一样导致not formset.is_valid()
.
我的问题:在 post() 中完成表单集数据 (cleaned_data) 的最简单方法是什么?仍然伤害我的另一点:self.object
在表单集中定义是否有必要或有帮助,如果是,如何定义?我把它设置为 None 如果我未定义它,我会收到一个丢失的对象错误。
先感谢您。
视图.py
class TransactionMulitCreateView(LoginRequiredMixin, CreateView):
model = Transaction
template_name = 'accounting/transaction_formset.html'
extra_context = {'title': model._meta.verbose_name, }
success_url = reverse_lazy('finance:ta_groups')
TaFormset = modelformset_factory(Transaction,
formset=TransactionBaseFormset,
exclude=('validity_period_start', 'validity_period_end', 'ta_group'),
extra=1)
def get(self, request, *args, **kwargs):
self.object = None
ba = BankTransaction.objects.get(pk=self.kwargs['bank_ta_pk'])
form = self.TaFormset(queryset=Transaction.objects.none(), initial=[
{
# commented out, as it was the js approach.
# 'bank_account_ta': ba,
# 'from_account': ba.account.ca_account,
'posting_text': ba.booking_string(),
'valuta': ba.valuta,
'entry_date': ba.entry_date,
'value': ba.amount,
},
], ba=ba)
helper = TransactionMultiFormsetHelper()
return self.render_to_response(self.get_context_data(form=form, helper=helper, bank_ta=ba))
def post(self, request, *args, **kwargs):
self.object = None
ba = BankTransaction.objects.get(pk=self.kwargs['bank_ta_pk'])
# pass in initial to be able to detect changes, see https://docs.djangoproject.com/en/3.1/topics/forms/formsets/
formset = self.TaFormset(request.POST, request.FILES, initial=[
{
# commented out, as it was the js approach.
# 'bank_account_ta': ba,
# 'from_account': ba.account.ca_account,
'posting_text': ba.booking_string(),
'valuta': ba.valuta,
'entry_date': ba.entry_date,
'value': ba.amount,
},
], ba=ba)
formset.clean()
# formset = self.TaFormset()
if formset.is_valid():
instances = formset.save(commit=False)
split = TransactionGroup.objects.create(create_by=self.request.user, update_by=self.request.user)
for instance in instances:
instance.ta_group = split
instance.save()
# BankTransaction.objects.filter(pk=self.kwargs['bank_ta_pk']).update(is_booked=True)
ba.is_booked = True
ba.save()
return HttpResponseRedirect(reverse_lazy('finance:bank_tas'))
# return self.form_valid(formset)
else:
helper = TransactionMultiFormsetHelper()
return self.render_to_response(self.get_context_data(form=formset, helper=helper, bank_ta=ba))
# return self.form_invalid(formset)
表格.py
class TransactionBaseFormset(forms.BaseModelFormSet):
def __init__(self, *args, **kwargs):
# self.ba_pk = kwargs.pop('ba_pk')
try:
self.ba = kwargs.pop('ba')
except KeyError:
self.ba = None
super().__init__(*args, **kwargs)
def clean(self):
data = None
for form in self.forms:
data = form.cleaned_data
data['bank_account_ta'] = self.ba
data['from_account'] = self.ba.account.ca_account
return data
解决方案
知道了!简单的解决方案是排除所有强制字段并将它们填充到函数中clean()
或is_valid()
函数中。
TaFormset = modelformset_factory(Transaction,
formset=TransactionBaseFormset,
exclude=(
'validity_period_start',
'validity_period_end',
'ta_group',
'bank_account_ta',
'from_account',
),
extra=1)
但是,我仍然想知道self.object
在表单集(或模型集)中扮演(或可能扮演)哪些角色?
推荐阅读
- angular - 未插入值时如何在没有自定义管道过滤的情况下显示整个表
- matlab - matlab中使用windows系统命令行运行url
- c++ - 具有 const 指针作为数据成员、析构函数且无默认构造函数的 C++ 类
- ios - 动画 CALayer 边框 alpha
- angular - Angular 6 中 AngularJS 的 ngcookie 等价于什么?
- build - 用 c-ares 构建 libcurl
- java - SDO API:如何使用 XSDHelper.INSTANCE 定义 XSD 模式
正确吗? - php - 无法从php发送邮件
- php - 如何仅将字符串中的数字保存到PHP中的int数组中
- objective-c - 来自 5 个不同 NSMutableArrays 的 Objective-C 均等分布