You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Django中设置必填字段提示仅在提交失败时显示

解决思路

1. 移除手动添加的required属性

你在表单widget里手动给字段加了required='True',这会触发浏览器原生的即时验证提示。Django会根据模型字段的必填性自动处理表单验证,不需要手动添加该属性。修改form.py:

class ElderFlowerChampFormAdmin(ModelForm):
    fieldsets=[
        ("Look",{'fields':[('look_colour','look_clarity','look_effervescence')]}),
    ]  # 修正原代码中的语法错误(多余闭合符)

    widgets = {
        'user': forms.Select(attrs={'class':'form-control'}),
        'look_colour':forms.Select(attrs={'class':'form-control'}),
        # 移除所有手动添加的required属性
    }

2. 控制模板中错误信息的显示时机

默认情况下Django表单会渲染所有字段的错误信息,哪怕是首次加载页面。你需要在模板里判断表单是否已经被提交(form.is_bound),只有提交后才显示错误提示。修改ElderFlowerReview.html中的表单渲染部分:

{% for field in form %}
    <div class="form-group">
        {{ field.label_tag }}
        {{ field }}
        <!-- 仅当表单已提交且字段有错误时显示提示 -->
        {% if form.is_bound and field.errors %}
            <div class="text-danger">
                {% for error in field.errors %}
                    {{ error }}
                {% endfor %}
            </div>
        {% endif %}
    </div>
{% endfor %}

3. 修正视图中的表单初始化逻辑

你的视图在GET请求时直接把表单类赋值给form变量,而非实例化,会导致模板渲染异常;同时全局变量ChampageRating覆盖了模型类,会引发逻辑错误,需要修正:

def elderflowerchamp(request, product_id):
    # 删除全局变量声明,避免覆盖模型类
    product = Product.objects.get(pk=product_id)
    url = request.META.get('HTTP_REFERER')
    submitted = False
    try:
        if request.method == "POST":
            reviews = ChampageRating.objects.get(pk=product_id)
            if request.user.is_superuser:
                form = ElderFlowerChampFormAdmin(request.POST, instance=reviews)
                if form.is_valid():
                        form.save()
                        return redirect('home')
            else:
                form = ElderFlowerChampForm(request.POST, instance=reviews)
                if form.is_valid():
                    # 用新变量名代替ChampageRating,避免覆盖模型类
                    champ_rating = form.save(commit=False)
                    champ_rating.user = request.user
                    champ_rating.save()
                    return redirect('home')
        else:
            # GET请求时实例化表单,而非传入类
            reviews = ChampageRating.objects.get(pk=product_id)
            if request.user.is_superuser:
                form = ElderFlowerChampFormAdmin(instance=reviews)
            else:
                form = ElderFlowerChampForm(instance=reviews)
            if 'submitted' in request.GET:
                submitted = True
    except:
        reviews = None
        form = None
        if request.method == "POST":
            if request.user.is_superuser:
                form = ElderFlowerChampFormAdmin(request.POST)
                if form.is_valid():
                        data = ChampageRating()
                        data.rating = form.cleaned_data['rating']
                        data.look_colour = form.cleaned_data['look_colour']
                        data.ip = request.META.get('REMOTE_ADDR')
                        data.product_id = product_id
                        data.user_id = request.user.id
                        data.save()
                        messages.success(request, 'Thank you! Your review has been submitted.')
                        return redirect('home')
            else:
                form = ElderFlowerChampForm(request.POST)
                if form.is_valid():
                        data = ChampageRating()
                        data.rating = form.cleaned_data['rating']
                        data.look_colour = form.cleaned_data['look_colour']
                        data.ip = request.META.get('REMOTE_ADDR')
                        data.product_id = product_id
                        data.user_id = request.user.id
                        data.save()
                        messages.success(request, 'Thank you! Your review has been submitted.')
                        return redirect('home')
        else:
            # GET请求时初始化空表单
            if request.user.is_superuser:
                form = ElderFlowerChampFormAdmin()
            else:
                form = ElderFlowerChampForm()

    return render(request,"main/ElderFlowerReview.html", {'form':form, 'submitted':submitted,'reviews':reviews, 'product':product})

4. 禁用浏览器原生验证(可选)

如果想完全屏蔽浏览器的原生提示,只使用Django的错误信息,可以在表单标签中添加novalidate属性:

<form method="post" novalidate>
    {% csrf_token %}
    <!-- 表单内容 -->
    <button type="submit">提交</button>
</form>

内容的提问来源于stack exchange,提问作者PhilM

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.25 21:45:36