我有一个表单中的ChoiceField,并希望将它的值保存在模型中。问题是,如果需要字段,表单就永远无效。当我将必需设置为False时,表单是有效的,但不包含任何数据--它只是空白。
models.py:
class CVSS(models.Model):
av = models.CharField(
max_length=10,
null=True,
)forms.py:
class CVSSForm(forms.ModelForm):
AV = [
(u'N', u'Network'),
(u'A', u'Adjacent'),
(u'L', u'Local'),
(u'P', u'Physical'),
]
av = forms.ChoiceField(
# required=False,
widget=forms.RadioSelect(),
choices=AV,
)
class Meta:
model = CVSS
fields = ['av',]views.py:
def edit(request, fid):
cvss = get_object_or_404(CVSS, finding_id=fid)
cvss_form = CVSSForm(instance=cvss)
if request.method == 'POST':
cvss_form = CVSSForm(request.POST, instance=cvss)
if cvss_form.is_valid():
cvss_form.save()edit.html:
<div class="table-responsive">
{% include "dojo/form_fields.html" with form=cvss_form %}
</div>表单是从form_fields.html呈现的:
{% elif field|is_radio %}
{% if field.auto_id %}
<label class="col-sm-4 control-label {% if field.field.required %}{{ form.required_css_class }}{% endif %}">
{{ field.label }}{% if field.field.required%}<sup>*</sup>{% endif %}
</label>
{% endif %}
<div class="col-sm-8 {{ classes.value }}">
{% for choice in field %}
<div class="radio">
<label>
{{ choice.tag }}
{{ choice.choice_label }}
</label>
</div>
{% endfor %}
{% for error in field.errors %}
<span class="help-block {{ form.error_css_class }}">{{ error }}</span>
{% endfor %}
{% if field.help_text %}
<i class="fa fa-question-circle has-popover" data-trigger="hover" data-content="{{ field.help_text }}" data-placement="right" data-container="body">
</i>
{% endif %}
</div>
{% else %}发布于 2018-05-15 10:00:18
您可以按以下方式更改模型和表单
models.py
class CVSS(models.Model):
AV_CHOICES = AV = [
(u'N', u'Network'),
(u'A', u'Adjacent'),
(u'L', u'Local'),
(u'P', u'Physical'),
]
av = models.CharField(
choices=AV_CHOICES
max_length=1,
null=True,
)forms.py
class CVSSForm(forms.ModelForm):
def __init__(self, *args, **kwargs):
super(CVSSForm, self).__init__(*args, **kwargs)
self.fields['av'].widget = forms.RadioSelect()
class Meta:
model = CVSS
fields = ['av',]views.py
def edit(request, fid):
cvss = get_object_or_404(CVSS, finding_id=fid)
cvss_form = CVSSForm(instance=cvss)
if request.method == 'POST':
cvss_form = CVSSForm(instance=cvss, data=request.POST)
if cvss_form.is_valid():
cvss_form.save()template.html
{{ form }}发布于 2018-05-15 10:04:52
你说过
如果需要该字段,则该表单永远无效。
这里所要求的术语是矛盾的。Django有两个不同的选择配置必需字段或可选字段。
空 如果是True,Django将将空值作为NULL存储在数据库中。默认是假的。
Null属性用于控制在数据库级别上声明字段的方式。Django doc还明确指出:
避免在基于字符串的字段(如CharField和TextField )上使用null。如果一个基于字符串的字段有null=True,这意味着它有两个可能的值: no data : NULL和空字符串。在大多数情况下,对于no数据有两个可能的值是多余的;Django约定是使用空字符串,而不是NULL。一个例外是当一个CharField同时设置了unique=True和blank=True。在这种情况下,在保存具有空值的多个对象时,需要null=True来避免唯一的约束冲突。
此外,另一个字段控制Django本身如何对链接到此模型字段的表单字段执行验证:
空白 如果为真,则允许字段为空。默认是假的。
请注意,这与null不同。null是纯数据库相关的,而空白是与验证相关的。如果字段有blank=True,表单验证将允许输入空值。如果字段具有blank=False,则需要该字段。
发布于 2022-06-08 15:04:16
我遇到了同样的问题。当我打印出request.POST时,我可以验证MultipleChoiceField的数据是否被传输。但是当我手动选择它(request.POST“字段名”)时,它只输出最后一个元素。
我很确定有一个序列化问题,信息会正确释放,但可能不会被接收到。来自Django的forms部件在某个地方不喜欢输出,也不会正确验证(可能它需要一个列表,但得到一个Integer?!)。在我看来,主要问题在于形式部分。就我个人而言,我还没有修复,但将尝试从上面的Charfield选择选项。不过,我认为这是一个问题,应该解决!
编辑: Charfield不适合我,因为我需要多个答案选项。
我现在已经构建了一个最小的测试,它的工作非常好。
我还找到了原因,为什么我只能得到列表中的最后一个元素:
print(request.body)输出:长字节.+ "&fieldname=2&fieldname=3“
Django只使用最后一个。我仍然不明白为什么它在一个简单的版本中工作,为什么在更复杂的版本中按上面的方式格式化。但是,现在我有个解决办法。
https://stackoverflow.com/questions/50347080
复制相似问题