ChoiceField表单无效并返回“太多值以解压缩”

时间:2014-01-10 10:43:44

标签: django forms templates choicefield

所以,我正在使用这个表单,在下拉列表中显示所有应用程序模型的列表,并期望用户选择一个以显示其字段。下面是我的表单和models()方法,它创建了作为参数传递给我的ChoiceField的模型列表。

*forms.py*
class dbForm(forms.Form):
    model_classes_field = forms.ChoiceField(choices=models(), required=True,)

def models():
apps = get_app('Directories')
m_id = 0
for model in get_models(apps):
    m_id += 1
    model_classes.append({
        'model_name': model._meta.verbose_name,
        'model_id': m_id,
        'model_table': model._meta.db_table,
        'model_object': model.objects.all()  
    })
return model_classes

在我的views.py中,我尝试处理POST数据,但不幸的是由于某种原因,表单无效,我无法操纵任何数据。此外,form.errors根本不显示任何内容。

*views.py*
def index(request): 
if request.method == 'POST': # If the form has been submitted...
    form = dbForm(request.POST) # A form bound to the POST data
    if form.is_valid(): # All validation rules pass
            model_classes_field = form.cleaned_data['model_classes_field']
            return HttpResponseRedirect('/list/') # Redirect after POST
    else:
            print "form: ", form.errors
else:
    form = dbForm() # An unbound form
    print "form: ", form.errors
    print "not valid form"

return render(request, 'Directories/index.html', {
            'form': form,
    })

此外,在模板中,每当我尝试提交表单时,它都会返回一条错误消息“解压得太多值”并且不会将我重定向到下一个模板(list.html)。

*index.html*
{% block content%} 
<div id="content" align="center">                
    <h2> Welcome! this is Directories app! </h2> 
    <form action="" method="post">{% csrf_token %}
{{ form.model_classes_field.errors }}
<label for="id_model_classes_field">Choose from one of the existing tables:</label> 
<select id="id_model_classes_field" name="model_classes_field">         
{% for choice in form.fields.model_classes_field.choices %}
        <option name="m_id" value="{{ choice.model_table }}">{{choice.model_id}}: {{choice.model_name}}</option> 
{% endfor %} 
</select> <br /> 
<input type="submit" value="Change" name="_change" />
</form>
</div>
<div id="bottom">

</div>
{% endblock %}

我在此找到的唯一解决方法是使用要重定向的模板(即action =“list”)填充表单操作,而不是使用return HttpResponseRedirect('/list/')在视图中执行此操作。但是,我认为这不能解决问题,因为表单仍然无效,我无法使用form.cleaned_data处理数据。尽管表格无效,但发送后期数据仍然很奇怪。

*

编辑:解决方案

我改变了我的models()方法:

def models():
    apps = get_app('Directories')
    for model in get_models(apps):
        model_classes.append( (model._meta.verbose_name, model._meta.db_table), )
    return model_classes

所以我按照@Rohan的指示包含了一个元组,并在对我的index.html稍作修改之后:

...
{% for choice in form.fields.model_classes_field.choices %}
        <option name="m_id" value="{{choice.0}}">{{choice.0}}</option> 
{% endfor %} 
...

表单有效,现在可以处理我的数据。

*

1 个答案:

答案 0 :(得分:2)

choices的值应该是包含具有2个元素的项的列表/元组。但是你正在创建可能导致问题的dicts列表。

for model in get_models(apps):
    m_id += 1
    model_classes.append({
        'model_name': model._meta.verbose_name,
        'model_id': m_id,
        'model_table': model._meta.db_table,
        'model_object': model.objects.all()  
    })

因此,您可能希望更新models()方法以返回适当的列表/元组。