使用字典插入WTForm字段。金贾2号。异常。未定义错误: 'wtforms.fields.core.UnboundField对象“”没有属性“label”

2024-03-28 09:56:53 发布

您现在位置:Python中文网/ 问答频道 /正文

我试图使用字典中的表单字段填充jinja2中的表单。在

#forms.py
class MyForm(FlaskForm):
    name = StringField('New Name', validators=[DataRequired()])

    fields = {}
    fields['Field1'] = StringField('Field 1', validators=[DataRequired()])
    fields['Field2'] = StringField('Field 2', validators=[DataRequired()])

#routes.py
@app.route('/test', methods=['GET', 'POST'])
def test():
    form = MyForm()
    return render_template('_test.html', form=form)

我的python代码与上面的代码类似。如果我尝试在jinja2中插入name字段,它可以正常工作。在

^{pr2}$

但是,我不知道如何对fields字典中的字段执行相同的操作。如果我使用以下命令,它会给我一个错误。(jinja2.exceptions.UndefinedError: 'wtforms.fields.core.UnboundField object' has no attribute 'label'

{{ form.fields['Field1'].label(class="form-control-label form-control-sm") }}

有没有可能像我试图使用的方式使用字典,或者如果我有大量的字段,是否有替代方法。我使用dictionary的目标是使用jinja2循环遍历dictionary元素以插入所有字段,而无需逐个键入。在


Tags: namepytestformjinja2fieldfields字典
2条回答

你不能这么做。字段需要直接在表单中定义。在

但你不需要。如果只想在字段上迭代,可以这样做,如the WTForms docs所示。在

发行

WTForms不支持在类级别的字典属性中定义字段。Form基类使用FormMeta(来自同一个文件)作为元类来标识类定义中未绑定的WTForm字段并将它们绑定到当前表单,这只会发现类级别的属性。在

解决方案

下面是一个使用表单工厂函数的最小工作示例。在

额外的表单字段通过field_factory参数作为lambda函数传入,这样我们就可以延迟额外字段的创建,直到创建name字段之后(尽管任何返回dict的可调用函数都可以工作)。这是必需的,因为WTForms按创建顺序而不是按在make_form()函数内的itemsdict中提供的顺序对字段进行排序。在

然后,可以通过迭代表单而不是指定手动顺序来呈现它们。在

在python3.7.1上测试。在

from flask import Flask
from flask_wtf import FlaskForm
from wtforms import StringField
from wtforms.validators import DataRequired

app = Flask(__name__)
app.config['SECRET_KEY'] = "secret"


def make_form(field_factory, name="MyForm"):
    items = dict(name=StringField('New Name', validators=[DataRequired()]),
                 **field_factory())
    my_form = type(name, (FlaskForm,), items)
    return my_form


if __name__ == "__main__":
    with app.test_request_context("/"):
        my_form = make_form(field_factory=lambda: dict(
            Field1=StringField('Field 1', validators=[DataRequired()]),
            Field2=StringField('Field 2', validators=[DataRequired()])
        ))

        form = my_form()
        for field in form:
            print(field())


输出

^{pr2}$

相关问题 更多 >