正如标题所说,我遇到了表单验证问题。表格和表格似乎都“知道”正确的值,但是当它到达视图时,验证失败。
我有工作、成本和供应商,它们都是相互关联的。我要验证的表格是与特定工作相关的成本表的一部分,我要更新的字段是供应商字段,通过下拉菜单,成本表的每一行,带有通过 Javascript 一次提交所有表单的单个更新按钮。
通过打印语句进行大量故障排除,表格和表格似乎都能够打印正确的成本和供应商,但是在验证时,我一直被告知“成本”字段是必填字段,所以我猜这是没有从表单中收到 Cost 对象。
被困在这个问题上太久了,我会很感激一些帮助。
这里的观点:
class CostCreateView(SuccessMessageMixin, SingleTableMixin, CreateView):
model = Cost
fields = ['vendor','description','amount','currency','invoice_status','notes']
template_name = "main_app/cost_form.html"
table_class = CostTable
simple_add_vendor_form = AddVendorToCostForm
cost_form = CostForm
update_vendor_form = UpdateVendorForm
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
self.object=None
currentJob = Job.objects.get(pk=self.kwargs['pk'])
context['currentJob'] = currentJob
context['table'] = self.table_class(currentJob.cost_rel.all())
context['simple_add_vendor_form'] = self.simple_add_vendor_form
context['update_vendor_form'] = self.update_vendor_form
context['cost_form'] = self.cost_form
context['vendors'] = Vendor.objects.filter(jobs_rel = currentJob)
return context
def post(self, request, *args, **kwargs):
self.object = None
context = self.get_context_data(**kwargs)
currentJob = Job.objects.get(pk=self.kwargs['pk'])
...
elif 'update-cost-vendor' in request.POST:
currentJob = Job.objects.get(pk=self.kwargs['pk'])
table = self.table_class(currentJob.cost_rel.all())
forms = []
for i, cost in enumerate(table.data):
prefix = f'form-{i}'
form = self.update_vendor_form(request.POST, prefix=prefix, cost=cost, initial={'cost': cost})
if form.is_valid():
# print(f'cost: {cost}')
# print(f'vendor: {cost.vendor}')
# print(f'cleaned: {form.cleaned_data}')
cost.vendor = form.cleaned_data['vendor']
cost.save()
else:
print('went down to the bottom else')
for form in forms:
print(f'{prefix}: {form.errors}')
print(f'{prefix}: {form.non_field_errors}')
forms.append(form)
return redirect('main_app:cost-add', pk=self.kwargs['pk'])
形式:
class UpdateVendorForm(forms.Form):
vendor = forms.ModelChoiceField(queryset=Vendor.objects.all(), required=False)
cost = forms.ModelChoiceField(queryset=Cost.objects.all(), widget=forms.HiddenInput)
def __init__(self, *args, cost=None, **kwargs):
super().__init__(*args, **kwargs)
cost = self.initial.get('cost')
# print(f'cost from the form side: {cost}')
initial = kwargs.get('initial', {})
initial['cost'] = cost
kwargs['initial'] = initial
桌子:
class CostTable(tables.Table):
edit = tables.TemplateColumn(verbose_name='', template_name="main_app/tables_costsheet_edit_column.html")
job = tables.Column(accessor='job.job_name')
def render_vendor(self, value, record):
form = UpdateVendorForm(initial={'vendor':value, 'cost':record })
return form.as_p()
class Meta:
model = Cost
order_by = 'vendor_initials'
template_name = "django_tables2/bootstrap5.html"
fields = ("job", "vendor", "description", "amount", "invoice", "PO_number", "edit", "id")
模型关系:
class Cost(models.Model):
...
vendor = models.ForeignKey(Vendor, on_delete=models.SET_NULL, null=True, blank=True,)
job = models.ForeignKey('Job', on_delete=models.CASCADE, related_name='cost_rel',
class Job(models.Model):
....
vendors = models.ManyToManyField(Vendor, verbose_name='vendors involved', blank=True, related_name = 'jobs_rel')
....
让我知道你还需要知道什么。在接下来的几天里很难回复,但会提供我能提供的信息。