django_filter,Search_Filter,Order_Filter,分页
一.分页drf配置信息:
1.在Lib\site-packages\rest_framework\settings.py中查看:
2.简单分页在项目setting中配置:(所有get请求返回数据每页5条)
#每页五条数据 REST_FRAMEWORK={ 'DEFAULT_PAGINATION_CLASS':'rest_framework.pagination.PageNumberPagination', 'PAGE_SIZE':5 }
二.定制分页:
from rest_framework.pagination import PageNumberPagination #深度定制分页 class GoodsPagination(PageNumberPagination): page_size = 12 page_size_query_param = 'page_size' #名称 page_query_param = 'page' #单页数量最多 max_page_size = 100 class GoodsListViewSet(CacheResponseMixin,mixins.ListModelMixin,mixins.RetrieveModelMixin,viewsets.GenericViewSet): """ 商品详情页,分页,搜索,过滤,排序 """ #配置ip限制访问次数 throttle_classes = (UserRateThrottle,AnonRateThrottle) queryset = Goods.objects.all() serializer_class = GoodsSerializer #分页,调用分页定制类 pagination_class = GoodsPagination
三.过滤:
直接通过get_queryset简单过滤:
lass GoodsListViewSet(mixins.ListModelMixin,viewsets.GenericViewSet): """ 商品详情页 """ serializer_class = GoodsSerializer #分页 pagination_class = GoodsPagination def get_queryset(self):
#接受前端传递的数据
queryset = Goods.objects.all()
min_price = self.request.query_params.get('price_min',0)
if min_price:
queryset=queryset.filter(shop_price__gt=int(min_price)) return queryset
通过filter进行过滤:
安装:pip install django-filter
注册app:把django-filters注册到setting中的install-app中
在view中导入from django_filters.rest_framework import DjangoFilterBackend,并在viewset中写入filter_backends=(DjangoFilterBackend,)
from django_filters.rest_framework import DjangoFilterBackend class GoodsListViewSet(CacheResponseMixin,mixins.ListModelMixin,mixins.RetrieveModelMixin,viewsets.GenericViewSet): """ 商品详情页,分页,搜索,过滤,排序 """ #配置ip限制访问次数 throttle_classes = (UserRateThrottle,AnonRateThrottle) queryset = Goods.objects.all() serializer_class = GoodsSerializer #分页 pagination_class = GoodsPagination #配置认证类,防止公开网页(未登录可查看)不能访问 # authentication_classes = (TokenAuthentication,) filter_backends=(DjangoFilterBackend,filters.SearchFilter,filters.OrderingFilter) #字段过滤(DjangoFilterBackend) # filter_fields = ('name', 'shop_price')
#定制的filter
filter_class=GoodsFilter #搜索过滤(rest_framework.filters.SearchFilter) search_fields = ('name','goods_brief','goods_desc') #排序过滤(rest_frameworkfilters.OrderingFilter) ordering_fields = ('sold_num', 'shop_price') def retrieve(self, request, *args, **kwargs): instance = self.get_object() instance.click_num+=1 instance.save() serializer = self.get_serializer(instance) return Response(serializer.data)
定制的筛选器:
1 import django_filters 2 from django.db.models import Q 3 4 from .models import Goods 5 6 7 class GoodsFilter(django_filters.rest_framework.FilterSet): 8 #help_text--docs:description 9 pricemin=django_filters.NumberFilter(field_name='shop_price',lookup_expr='gte',help_text='最低价格') 10 pricemax=django_filters.NumberFilter(field_name='shop_price',lookup_expr='lte') 11 # name=django_filters.CharFilter(field_name='name',lookup_expr='icontains') 12 top_category=django_filters.NumberFilter(method='top_category_filter') 13 #定制的过滤方法 14 def top_category_filter(self,queryset,name,value): 15 return queryset.filter(Q(category_id=value)|Q(category__parent_category_id=value)|Q(category__parent_category__parent_category_id=value)) 16 17 18 class Meta: 19 model=Goods 20 fields=['pricemin','pricemax','top_category','is_hot','is_new']
四.搜索和排序:
搜索:
from rest_framework import filters class GoodsListViewSet(CacheResponseMixin,mixins.ListModelMixin,mixins.RetrieveModelMixin,viewsets.GenericViewSet): """ 商品详情页,分页,搜索,过滤,排序 """ #配置ip限制访问次数 throttle_classes = (UserRateThrottle,AnonRateThrottle) queryset = Goods.objects.all() serializer_class = GoodsSerializer #分页 pagination_class = GoodsPagination #配置认证类,防止公开网页(未登录可查看)不能访问 # authentication_classes = (TokenAuthentication,) filter_backends=(DjangoFilterBackend,filters.SearchFilter,filters.OrderingFilter) #字段过滤(DjangoFilterBackend) # filter_fields = ('name', 'shop_price') filter_class=GoodsFilter #搜索过滤(rest_framework.filters.SearchFilter) search_fields = ('name','goods_brief','goods_desc') #排序过滤(rest_frameworkfilters.OrderingFilter) ordering_fields = ('sold_num', 'shop_price') def retrieve(self, request, *args, **kwargs): instance = self.get_object() instance.click_num+=1 instance.save() serializer = self.get_serializer(instance) return Response(serializer.data)
排序:
指定可以针对哪些字段进行排序
建议您明确指定API应在订购过滤器中允许哪些字段。您可以通过ordering_fields
在视图上设置属性来执行此操作,如下所示:
class UserListView(generics.ListAPIView):
queryset = User.objects.all()
serializer_class = UserSerializer
filter_backends = (filters.OrderingFilter,)
ordering_fields = ('username', 'email')
这有助于防止意外数据泄漏,例如允许用户针对密码哈希字段或其他敏感数据进行排序。
如果未ordering_fields
在视图上指定属性,则筛选器类将默认允许用户筛选serializer_class
属性指定的序列化程序上的任何可读字段。
如果您确信视图使用的查询集不包含任何敏感数据,则还可以使用特殊值明确指定视图应允许对任何模型字段或查询集合进行排序'__all__'
。
class BookingsListView(generics.ListAPIView):
queryset = Booking.objects.all()
serializer_class = BookingSerializer
filter_backends = (filters.OrderingFilter,)
ordering_fields = '__all__'
指定默认排序
如果ordering
在视图上设置了属性,则将其用作默认排序。
通常,您可以通过设置order_by
初始查询集来控制它,但是使用ordering
视图上的参数允许您以一种方式指定排序,然后可以将其作为上下文自动传递给呈现的模板。如果列标题用于排序结果,则可以自动呈现列标题。
class UserListView(generics.ListAPIView):
queryset = User.objects.all()
serializer_class = UserSerializer
filter_backends = (filters.OrderingFilter,)
ordering_fields = ('username', 'email')
ordering = ('username',)
该ordering
属性可以是字符串或字符串的列表/元组。
from rest_framework import filters class GoodsListViewSet(CacheResponseMixin,mixins.ListModelMixin,mixins.RetrieveModelMixin,viewsets.GenericViewSet): """ 商品详情页,分页,搜索,过滤,排序 """ #配置ip限制访问次数 throttle_classes = (UserRateThrottle,AnonRateThrottle) queryset = Goods.objects.all() serializer_class = GoodsSerializer #分页 pagination_class = GoodsPagination #配置认证类,防止公开网页(未登录可查看)不能访问 # authentication_classes = (TokenAuthentication,) filter_backends=(DjangoFilterBackend,filters.SearchFilter,filters.OrderingFilter) #字段过滤(DjangoFilterBackend) # filter_fields = ('name', 'shop_price') filter_class=GoodsFilter #搜索过滤(rest_framework.filters.SearchFilter) search_fields = ('name','goods_brief','goods_desc') #排序过滤(rest_frameworkfilters.OrderingFilter) ordering_fields = ('sold_num', 'shop_price') def retrieve(self, request, *args, **kwargs): instance = self.get_object() instance.click_num+=1 instance.save() serializer = self.get_serializer(instance) return Response(serializer.data)