FilterSet选项
Meta选项
使用model自动生成filter
对于给定model的字段,FilterSet有能力自动生成对应的filters. 类似于Django的ModelForm, filters是基于潜在的模型类字段的类型创建的。model选项必须结合fields(选择哪些字段可供筛选)或者exclude(选择哪些字段不能筛选)选项,就像Django的ModelForm类一样。
class UserFilter(FilterSet):
class Meta:
model = User
fields = ['username', 'last_login']
声明可筛选fields
fields选项可以结合model来自动生成filters。注意生成的filters不会重写FilterSet中声明的filters。fields选项可以接受两种语法:
- 一个字段名的列表
- 一个包括字段名及其可接受的查找方式列表的字典
class UserFilter(FilterSet):
class Meta:
model = User
fields = ['username', 'last_login']
# 或者
class UserFilter(FilterSet):
class Meta:
model = User
fields = {
'username': ['exact', 'contains'],
'last_login': ['exact', 'year__gt']
}
列表语法会为每一个fields的字段创造一个exact查找filter。字典语法会为其中的字段的每一个查询表达式创造一个filter。这些表达式可能包括转换和查找,具体参见Lookup API reference
注意不需要把声明的filters包含进fields列表。在fields字典中添加声明性别名会引发错误
class UserFilter(django_filters.FilterSet):
username = filters.CharFilter()
login_timestamp = filters.IsoDateTimeFilter(field_name='last_login')
class Meta:
model = User
fields = {
'username': ['exact', 'contains'],
'login_timestamp': ['exact'],
}
TypeError("'Meta.fields' contains fields that are not defined on this FilterSet: login_timestamp")
禁用筛选字段exclude
exclude选项接受一个不允许自动生成filter的字段黑名单。注意那些在FilterSet中生命的filters不会被禁用。
class UserFilter(FilterSet):
class Meta:
model = User
exclude = ['password']
自定义filter生成filter_overrides
内部的Meta元类接受可选的参数filter_overrides参数。这是模型字段到filter类的映射。
class ProductFilter(django_filters.FilterSet):
class Meta:
model = Product
fields = ['name', 'release_date']
filter_overrides = {
models.CharField: {
'filter_class': django_filters.CharFilter,
'extra': lambda f: {
'lookup_expr': 'icontains',
},
},
models.BooleanField: {
'filter_class': django_filters.BooleanFilter,
'extra': lambda f: {
'widget': forms.CheckboxInput,
},
},
}
覆盖FIlterSet方法
当覆盖类方法时,引用super(MyFilterSet, cls)可能会引起NameError异常。这是因为FulterSetMetaclass在FilterSet被完全创建之前引用了这些类方法。如果使用python 3.6或者更高的版本,使用无参数的super()语法。
Filter 参考
核心参数
下面是用于所有filters的核心参数。注意这些参数需要结合来创建完整的查询表达式。
field_name
筛选依据的模型字段的名称。如果未提供此参数,则默认为FilterSet类上filter的属性名称。字段名可以通过将关联部分与ORM查找分隔符(__)连接来建立关系。例如产品的manufacturer__name。
lookup_expr
调用filter时执行的字段查找。默认为exact, 如果表达式部分由ORM查找分隔符(__)连接,lookup_expr可以包含转换(transforms)。例如,通过年部分来筛选日期(datetime),year__gt
仅关键字参数
下面的可选参数可以被用来修改全部filters的行为
method
一个可选的参数,告诉filter如何处理queryset。
class BookFilter(FilterSet):
# 通过书籍是否出版来筛选
pubilshed = BooleanFilter(filter_name='published_on', method='filter_published')
def filter_published(self, queryset, name, value):
# 构建完整的查询表达式
lookup = '__'.join[name, 'isnull'] # lookup = f"{name}__isnull"
return queryset.filter(**{look: False})
class Meta:
model = Book
fields = ['pubilshed']
以下代码功能相同
def filter_not_empty(queryset, name, value):
lookup = '__'.join([name, 'isnull'])
return queryset.filter(**{lookup: Flase})
class BookFilter(FilterSet):
# 通过书籍是否出版来筛选
pubilshed = BooleanFilter(filter_name='published_on', method=filter_not_empty)
class Meta:
model = Book
fields = ['published']
Filter
OrderingFilter
让queryset排序。它接受两个用于构建排序选项的附加参数。
fields是{模型字段名: 参数名称}的映射。