django_filters DRF 自定义filter函数
本文最后更新于 2025-08-20,文章内容可能已经过时。
0x01 前言
最近需要设计两个个功能一个是前端输入中文或者拼音,在后端查找对应的字段,另外一个是前端多选框多选,后端返回包含对应多选框参数的数据,翻了一下官方文档和谷歌,网上例子不是很多,边看边摸索用法,随记录下用法,方便有需要的人使用。
0x02 使用流程
django模型类
# models.py
class depart(models.Model):
Name = models.CharField(max_length=64, unique=True, verbose_name="板块名称", help_text="板块名称")
Managers = models.ManyToManyField(to="user", blank=True, verbose_name="关联员工", db_constraint=False, help_text="关联员工")
class Meta:
db_table = "depart"
verbose_name = "板块表"
verbose_name_plural = verbose_name
class user(models.Model):
Id = models.CharField(primary_key=True,max_length=64, verbose_name="员工号" , help_text="员工号")
Name = models.CharField(max_length=64, verbose_name="姓名" , help_text="姓名")
Depart = models.ForeignKey(to=depart, to_field="id", on_delete=models.CASCADE, verbose_name="关联板块", help_text="关联板块")
EMail = models.EmailField(max_length=64, verbose_name="邮箱", help_text="邮箱")
Mobile = models.CharField(max_length=64, blank=True, null=True, verbose_name="手机号", help_text="手机号")
class Meta:
db_table = "user"
verbose_name = "人员表"
verbose_name_plural = verbose_name
此处我将序列化类,过滤器类以及视图类均写在了一个文件夹中,为了方便观看,我把对应功能代码拆分开来,方便理解,文末会放该文件完整代码
序列化类
# views/user.py
from .models import user, depart
from rest_framework import serializers
from dvadmin.utils.serializers import CustomModelSerializer
class userSerializer(CustomModelSerializer):
"""
序列化器
"""
Depart_Name = serializers.CharField(source='Depart.Name', read_only=True)
class Meta:
model = user
fields = "__all__"
class userCreateUpdateSerializer(CustomModelSerializer):
"""
创建/更新时的列化器
"""
class Meta:
model = user
fields = "__all__"
自定义过滤器类
# views/user.py
from uuslug import slugify
import django_filters
class CharInFilter(django_filters.BaseInFilter, django_filters.CharFilter):
"""
字符类型过滤器,多选框过滤
"""
pass
class userFilter(django_filters.FilterSet):
"""
过滤器
"""
search = django_filters.CharFilter(field_name="EMail", method="search_filter")
# 该字段查询需要用逗号分割开,例如Depart=板块1,板块2
Depart = CharInFilter(field_name="Depart", lookup_expr='in')
def search_filter(self, queryset, name, value):
"""
@params queryset: 为user.objects.all()返回的合集, 即视图类中的的queryset
@params name: 为field_name
@params value: 为前端通过search字段传过来的值
"""
lookup = '__'.join([name, 'icontains'])
return queryset.filter(**{
lookup: slugify(value).replace('-', '')
})
class Meta:
model = user
fields = "__all__"
视图类
# views/user.py
from dvadmin.utils.viewset import CustomModelViewSet
class userViewSet(CustomModelViewSet):
"""
list:查询
create:新增
update:修改
retrieve:单例
destroy:删除
"""
queryset = user.objects.all()
serializer_class = userSerializer
filter_class = userFilter
create_serializer_class = userCreateUpdateSerializer
update_serializer_class = userCreateUpdateSerializer
0x03 查询结果
(1) 查询姓名
http://127.0.0.1:8000/api/user/?search=%E7%89%88%E4%B8%BB
{
"code": 2000,
"msg": "success",
"data": {
"page": 1,
"total": 3,
"limit": 10,
"data": [
{
"Id": "10001",
"modifier_name": null,
"Depart_Name": "板块1",
"Name": "版主1",
"EMail": "banzhu1@email.com",
"Mobile": "11011111111",
"Depart": 1
},
{
"Id": "10002",
"modifier_name": null,
"Depart_Name": "板块2",
"Name": "版主2",
"EMail": "banzhu2@email.com",
"Mobile": "11022222222",
"Depart": 3
},
]
}
}
(2) 查询姓名的部分拼音
http://127.0.0.1:8000/api/vulmanager/user/?search=chuli
{
"code": 2000,
"msg": "success",
"data": {
"page": 1,
"total": 2,
"limit": 10,
"data": [
{
"Id": "90001",
"modifier_name": null,
"Depart_Name": "板块1",
"Name": "处理人1",
"EMail": "chuliren1@email.com",
"Mobile": "11111111111",
"Depart": 3
},
{
"Id": "90002",
"modifier_name": null,
"Depart_Name": "板块2",
"Name": "处理人2",
"EMail": "chuliren2@email.com",
"Mobile": "12222222222",
"Depart": 4
}
]
}
}
0x04 完整的类
# views/user.py
from vulmanager.models import user, depart
from rest_framework import serializers
from dvadmin.utils.serializers import CustomModelSerializer
from dvadmin.utils.viewset import CustomModelViewSet
import django_filters
from uuslug import slugify
class userSerializer(CustomModelSerializer):
"""
序列化器
"""
Depart_Name = serializers.CharField(source='Depart.Name', read_only=True)
class Meta:
model = user
fields = "__all__"
class userCreateUpdateSerializer(CustomModelSerializer):
"""
创建/更新时的列化器
"""
class Meta:
model = user
fields = "__all__"
class CharInFilter(django_filters.BaseInFilter, django_filters.CharFilter):
"""
字符类型过滤器,多选框过滤
"""
pass
class userFilter(django_filters.FilterSet):
"""
过滤器
"""
search = django_filters.CharFilter(field_name="EMail", method="search_filter")
Depart = CharInFilter(field_name="Depart", lookup_expr='in')
def search_filter(self, queryset, name, value):
"""
@params queryset: 为user.objects.all()返回的合集, 即视图类中的的queryset
@params name: 为field_name
@params value: 为前端通过search字段传过来的值
"""
lookup = '__'.join([name, 'icontains'])
return queryset.filter(**{
lookup: slugify(value).replace('-', '')
})
class Meta:
model = user
fields = "__all__"
class userViewSet(CustomModelViewSet):
"""
list:查询
create:新增
update:修改
retrieve:单例
destroy:删除
"""
queryset = user.objects.all()
serializer_class = userSerializer
filter_class = userFilter
create_serializer_class = userCreateUpdateSerializer
update_serializer_class = userCreateUpdateSerializer
(要是对你有帮助的话,点个赞和关注吧~)
本文是原创文章,采用 CC BY-NC-ND 4.0 协议,完整转载请注明来自 苇逸
评论
匿名评论
隐私政策
你无需删除空行,直接评论以获取最佳展示效果