如何在Django 4.2.9表单验证失败时为输入框添加额外类
Django 4.2.9:表单验证失败时为输入字段添加CSS类
问题描述
使用Django 4.2.9,需实现表单验证失败时,为text输入字段追加is-invalid CSS类。目前已能设置常规场景的类,但不知如何处理验证错误的情况。
现有ItemForm代码:
class ItemForm(forms.models.ModelForm): class Meta: model = Item fields = ("text", ) widgets = { "text": forms.widgets.TextInput( attrs={ "placeholder": "Enter a to-do item", "class": "form-control form-control-lg", } ), } error_messages = {"text": {"required": EMPTY_ITEM_ERROR}} def save(self, for_list): self.instance.list = for_list return super().save()
期望验证失败时,text输入框的class变为form-control form-control-lg is-invalid,当前表单渲染后的HTML:
<form method="POST" action="/lists/8/"> <input type="text" name="text" value="Buy wellies" placeholder="Enter a to-do item" class="form-control form-control-lg" required id="id_text"> <input type="hidden" name="csrfmiddlewaretoken" value="vcojkMtz3GeonURczjMwIsbsDPQUbeKgrXrPIxZY4jIJSfuUKKGVgaj7wLQBatsd"> <div class="invalid-feedback"><ul class="errorlist"><li>You've already got this in your list</li></ul></div> </form>
解决方案
方法1:重写表单__init__方法
在表单初始化阶段检查字段错误,动态追加CSS类:
class ItemForm(forms.models.ModelForm): class Meta: model = Item fields = ("text", ) widgets = { "text": forms.widgets.TextInput( attrs={ "placeholder": "Enter a to-do item", "class": "form-control form-control-lg", } ), } error_messages = {"text": {"required": EMPTY_ITEM_ERROR}} def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) # 检查text字段是否存在验证错误 if self.errors.get('text'): current_classes = self.fields['text'].widget.attrs.get('class', '') self.fields['text'].widget.attrs['class'] = f"{current_classes} is-invalid" def save(self, for_list): self.instance.list = for_list return super().save()
方法2:模板层面直接处理
无需修改表单类,在模板渲染时判断字段状态并添加类:
<form method="POST" action="/lists/8/"> {% csrf_token %} {% with field=form.text %} <input type="text" name="{{ field.name }}" value="{{ field.value|default:'' }}" placeholder="Enter a to-do item" class="form-control form-control-lg {% if field.errors %}is-invalid{% endif %}" required id="{{ field.id_for_label }}"> {% endwith %} {% if form.text.errors %} <div class="invalid-feedback"> {{ form.text.errors }} </div> {% endif %} </form>
方法3:自定义Widget类
如果多个表单需要该功能,可封装通用Widget复用:
class CustomTextInput(forms.TextInput): def get_context(self, name, value, attrs): context = super().get_context(name, value, attrs) # 获取表单实例,检查当前字段是否有错误 form_instance = context['widget']['form'] if form_instance and form_instance.errors.get(name): current_classes = context['widget']['attrs'].get('class', '') context['widget']['attrs']['class'] = f"{current_classes} is-invalid" return context # 在表单中使用自定义Widget class ItemForm(forms.models.ModelForm): class Meta: model = Item fields = ("text", ) widgets = { "text": CustomTextInput( attrs={ "placeholder": "Enter a to-do item", "class": "form-control form-control-lg", } ), } error_messages = {"text": {"required": EMPTY_ITEM_ERROR}} def save(self, for_list): self.instance.list = for_list return super().save()
内容的提问来源于stack exchange,提问作者Marco Frost
相关产品推荐
相关产品推荐

