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

Django模板中无法通过values_list正确渲染下拉选择框选项

Django多选择省份筛选渲染问题

我是Django新手,希望得到您的技术支持,非常感谢。

models.py

class Province(models.Model):     
    province_name = models.CharField(max_length=100)  # CharField必须指定max_length

class Employee(models.Model):    
    first_name = models.CharField(max_length=100)    
    province = models.ForeignKey(Province, on_delete=models.CASCADE)

filters.py (django-filters)

原代码错误在于给ModelMultipleChoiceFilter的queryset传入了values_list结果,导致渲染时把元组直接转为字符串作为选项值。以下是修正后的代码:

方案1:通过label_from_instance指定显示文本

from django_filters import FilterSet, filters
from .models import Employee, Province

class EmployeeFilter(FilterSet):
    province_name_multi_select = filters.ModelMultipleChoiceFilter(
        field_name="province",  # 直接关联外键字段,无需写province_id
        queryset=Province.objects.all(),
        # 自定义选项显示的文本内容
        label_from_instance=lambda obj: obj.province_name
    )

    class Meta:
        model = Employee
        fields = [
            "id",
            "first_name",
            "province",
        ]

方案2:给Province模型添加__str__方法(更推荐)

先修改Province模型:

class Province(models.Model):     
    province_name = models.CharField(max_length=100)

    def __str__(self):
        return self.province_name

再简化Filter代码:

from django_filters import FilterSet, filters
from .models import Employee, Province

class EmployeeFilter(FilterSet):
    province_name_multi_select = filters.ModelMultipleChoiceFilter(
        field_name="province",
        queryset=Province.objects.all()
    )

    class Meta:
        model = Employee
        fields = [
            "id",
            "first_name",
            "province",
        ]

views.py

class EmployeeListView(FilterView):
    model = Employee
    queryset = Employee.objects.select_related("province")
    form_class = EmployeeForm
    strict = False
    context_object_name = "employees_list"
    filterset_class = EmployeeFilter

employee_filter.html

简化写法(推荐)

直接让表单字段自动渲染完整的select:

<select class="form-select" name="province_name_multi_select" id="multiple-select-field" multiple>  
    {{ filter.form.province_name_multi_select }}
</select>

手动循环写法

如果需要自定义循环逻辑:

<select class="form-select" name="province_name_multi_select" id="multiple-select-field" multiple>  
    {% for choice_id, choice_name in filter.form.province_name_multi_select.field.choices %}
        <option value="{{ choice_id }}">{{ choice_name }}</option>
    {% endfor %}
</select>

问题说明

原代码中{{ element.tag }}生成了<option value="[1], 'abc province']" </option>的错误结果,期望生成<option value="1">abc province</option>。核心原因是ModelMultipleChoiceFilter需要接收模型实例的查询集,而非values_list返回的元组集合,否则会错误地将元组对象转为字符串作为选项值。

内容的提问来源于stack exchange,提问作者Cương Vũ Thế

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.17 20:32:35