如何使用 WTForms 绘制没有 id 属性的输入?
How to draw inputs without the id attribute using WTForms?
在我的 Flask 应用程序中,我必须在同一页面上多次绘制表单。这导致我在页面上有多个具有相同 id 的输入字段的问题。例如:
class ChannelForm(flask_wtf.Form):
name = StringField('name')
连同此模板:
<form>
{{ form.name }}
</form>
...
<form>
{{ form.name }}
</form>
导致两个相同的输入元素id
:
<input id="name" name="name" value="" type="text">
是否有官方方法来禁用添加 id
属性?
我认为您可以像这样将自定义 ID 传递给字段构造函数:
<form>
{{ form.name(id_='yourId') }}
</form>
...
<form>
{{ form.name(id_='yourId2') }}
</form>
快又脏:
我发现以下方法效果很好:我没有直接使用字段,而是将它们包装在 jinja 宏中:
{% macro render_field(field) %}
<label>
<span>{{ _field.label.text }} </span>
{{ field(id=False, **kwargs) }}
</label>
{% endmacro %}
可以这样使用:
{% from "_formhelpers.html" import render_field %}
{{ render_field(form.name) }}
这里的技巧是在渲染字段时传递id=False
。
使用元对象:
_Auto = object()
class NoIdAttributeMeta(DefaultMeta):
"""
Surpresses rendering the `id' attribute.
"""
def bind_field(self, form, unbound_field, options):
"""
Raises TypeError in case 'id' is given as a positional arg when constructing a field.
If this happens, make this code smarter or pass `id' as a keyword arg.
"""
# we check `id' at rendering time and if it is still _Auto, do not render it
unbound_field.kwargs.setdefault('id', _Auto)
return super().bind_field(form, unbound_field, options)
def render_field(self, field, render_kw):
if field.id is _Auto:
field.id = False
return super().render_field(field, render_kw)
class MyForm(flask_wtf.Form):
Meta = NoIdAttributeMeta
或务实:
您还可以为表单的每个实例添加不同的前缀,因此您将拥有唯一的 ID:
my_form = MyForm(prefix="form1")
pass
您不需要 id=False,因为您已经可以在调用 render_field()
时设置 id
{% macro render_field(_field) %}
<label>
<span>{{ _field.label.text }} </span>
{{ _field(**kwargs) }}
</label>
{% endmacro %}
用法:
{{ render_field(field, id=False) }}
说明:
因为你有 ****kwargs**,所以你可以使 id=False,这样会更动态。您可以选择何时删除 ID。
希望这对那些用谷歌搜索过这个解决方案的人有所帮助
在我的 Flask 应用程序中,我必须在同一页面上多次绘制表单。这导致我在页面上有多个具有相同 id 的输入字段的问题。例如:
class ChannelForm(flask_wtf.Form):
name = StringField('name')
连同此模板:
<form>
{{ form.name }}
</form>
...
<form>
{{ form.name }}
</form>
导致两个相同的输入元素id
:
<input id="name" name="name" value="" type="text">
是否有官方方法来禁用添加 id
属性?
我认为您可以像这样将自定义 ID 传递给字段构造函数:
<form>
{{ form.name(id_='yourId') }}
</form>
...
<form>
{{ form.name(id_='yourId2') }}
</form>
快又脏:
我发现以下方法效果很好:我没有直接使用字段,而是将它们包装在 jinja 宏中:
{% macro render_field(field) %}
<label>
<span>{{ _field.label.text }} </span>
{{ field(id=False, **kwargs) }}
</label>
{% endmacro %}
可以这样使用:
{% from "_formhelpers.html" import render_field %}
{{ render_field(form.name) }}
这里的技巧是在渲染字段时传递id=False
。
使用元对象:
_Auto = object()
class NoIdAttributeMeta(DefaultMeta):
"""
Surpresses rendering the `id' attribute.
"""
def bind_field(self, form, unbound_field, options):
"""
Raises TypeError in case 'id' is given as a positional arg when constructing a field.
If this happens, make this code smarter or pass `id' as a keyword arg.
"""
# we check `id' at rendering time and if it is still _Auto, do not render it
unbound_field.kwargs.setdefault('id', _Auto)
return super().bind_field(form, unbound_field, options)
def render_field(self, field, render_kw):
if field.id is _Auto:
field.id = False
return super().render_field(field, render_kw)
class MyForm(flask_wtf.Form):
Meta = NoIdAttributeMeta
或务实:
您还可以为表单的每个实例添加不同的前缀,因此您将拥有唯一的 ID:
my_form = MyForm(prefix="form1")
pass
您不需要 id=False,因为您已经可以在调用 render_field()
时设置 id{% macro render_field(_field) %}
<label>
<span>{{ _field.label.text }} </span>
{{ _field(**kwargs) }}
</label>
{% endmacro %}
用法:
{{ render_field(field, id=False) }}
说明: 因为你有 ****kwargs**,所以你可以使 id=False,这样会更动态。您可以选择何时删除 ID。 希望这对那些用谷歌搜索过这个解决方案的人有所帮助