zoukankan      html  css  js  c++  java
  • Django Rest framework 之 分页

    一、实例

    分页有三种方式

    • 普通分页,看第n页,每页显示m条数据;
    • 切割分页,在n个位置,向后查看m条数据;
    • 加密分页,这与普通分页方式相似,不过对url中的请求页码进行加密。

    1、路由

    <1>、主路由

    from django.urls import include
    from django.conf.urls import url
    
    urlpatterns = [
        url(r'^api/', include('api.urls', namespace='api') ),
    ]
    
    

    <2>、app路由

    from django.urls import include
    from django.conf.urls import url
    
    urlpatterns = [
        url(r'^page/$', PageView.as_view()),
    ]
    

    2、视图

    在不使用django rest framework中的分页组件仍能够达到目的

    from rest_framework import serializers
    from rest_framework.views import APIView
    from rest_framework.response import Response
    
    class PagerSerializer(serializers.ModelSerializer):
        class Meta:
            model = Role
            fields = "__all__"
    
    
    class PageView(APIView):
        def get(self, request , *args, **kwargs):
            roles = Role.objects.get_queryset().order_by('id')
            roles_ser = PagerSerializer(instance=roles, many=True)
    
            return Response(roles_ser.data)  # 只返回数据
    
    

    返回结果

    二、使用普通分页

    1、自定义分页类

    from rest_framework.pagination import PageNumberPagination
    
    class MyPageNumberPagination(PageNumberPagination):
        page_size = 2
        max_page_size = 5
        page_size_query_param = 'size'
        page_query_param = 'page'
    
    • page_query_param:表示url中的页码参数
    • page_size_query_param:表示url中每页数量参数
    • page_size:表示每页的默认显示数量
    • max_page_size:表示每页最大显示数量,做限制使用,避免突然大量的查询数据,数据库崩溃

    2、视图

    class PagerSerializer(serializers.ModelSerializer):
        class Meta:
            model = Role
            fields = "__all__"
    
    class PageView(APIView):
        def get(self, request , *args, **kwargs):
            roles = Role.objects.get_queryset().order_by('id')
            page = MyPageNumberPagination()
            page_roles = page.paginate_queryset(queryset=roles, request=request, view=self)
            roles_ser = PagerSerializer(instance=page_roles, many=True)
    
            # return Response(roles_ser.data)  # 只返回数据
            return page.get_paginated_response(roles_ser.data)  # 返回前后夜url
    
    • 首先需要实例化我们定义的分页类
    • 并且对实例化类进行传参控制
    • 最后将分页后的对象作序列化

    3、测试结果

    <1>、正常测试

    http://127.0.0.1:8000/api/page/

    <2>、page、size测试

    http://127.0.0.1:8000/api/page/?page=2&size=3 表示第二页,每页显示三条数据

    三、使用普通分页

    1、自定义分页类

    from rest_framework.pagination import LimitOffsetPagination
    
    class MyLimitOffsetPagination(LimitOffsetPagination):
        default_limit = 2
        limit_query_param = 'limit'
        offset_query_param = 'offset'
        max_limit = 5
    
    • default_limit:表示默认每页显示几条数据
    • limit_query_param:表示url中本页需要显示数量参数
    • offset_query_param:表示从数据库中的第几条数据开始显示参数
    • max_limit:表示每页最大显示数量,做限制使用,避免突然大量的查询数据,数据库崩溃

    2、视图

    class PagerSerializer(serializers.ModelSerializer):
        class Meta:
            model = Role
            fields = "__all__"
    
    class PageView(APIView):
        def get(self, request , *args, **kwargs):
            roles = Role.objects.get_queryset().order_by('id')
            page = MyLimitOffsetPagination()
            page_roles = page.paginate_queryset(queryset=roles, request=request, view=self)
            roles_ser = PagerSerializer(instance=page_roles, many=True)
    
            # return Response(roles_ser.data)  # 只返回数据
            return page.get_paginated_response(roles_ser.data)  # 返回前后夜url
    
    • 首先需要实例化我们定义的分页类
    • 并且对实例化类进行传参控制
    • 最后将分页后的对象作序列化

    3、测试结果

    <1>、测试结果一

    http://127.0.0.1:8000/api/page/?

    <2>、测试结果二

    http://127.0.0.1:8000/api/page/?offset=2&limit=3表示从数据库中的第二条数据开始查询三条数据

    四、使用加密分页

    使用加密分页的原因:如果使用普通分页时,由于向用户提供了可选参数page,用户可以直接跳到数据分页之后的任意页码。但是这样做的后果就是,数据库的负载变大,返回结果的效率缓慢。但是一旦使用加密之后,虽然提供可选参数cursor,但是对页码进行加密,用户无法知道当前页,而是以上一页下一页的方式翻阅数据。有效避免了数据库的负荷。但是就需要向用户提供上一页下一页的url

    1、自定义分页类

    from rest_framework.pagination import LimitOffsetPagination
    
    class MyCursorPagination(CursorPagination):
    
        cursor_query_param = 'cursor'
        page_size = 2  
        ordering = 'id'
        page_size_query_param = 'size' 
        max_page_size = 5  
    
    • default_limit:表示默认每页显示几条数据
    • cursor_query_param:表示url中页码的参数
    • page_size_query_param:表示每页显示数据量的参数
    • max_page_size:表示每页最大显示数量,做限制使用,避免突然大量的查询数据,数据库崩溃
    • ordering:表示返回数据的排序方式

    2、视图

    class PagerSerializer(serializers.ModelSerializer):
        class Meta:
            model = Role
            fields = "__all__"
    
    class PageView(APIView):
        def get(self, request , *args, **kwargs):
            roles = Role.objects.get_queryset().order_by('id')
            page = MyCursorPagination()
            page_roles = page.paginate_queryset(queryset=roles, request=request, view=self)
            roles_ser = PagerSerializer(instance=page_roles, many=True)
    
            return page.get_paginated_response(roles_ser.data)  # 返回前后夜url
    
    • 首先需要实例化我们定义的分页类
    • 并且对实例化类进行传参控制
    • 最后将分页后的对象作序列化
    • 由于要想用户提供可用的上下页接口,所以只能用return page.get_paginated_response(roles_ser.data)做返回

    3、测试结果

    <1>、测试结果一

    http://127.0.0.1:8000/api/page/?

    <2>、测试结果二

    http://127.0.0.1:8000/api/page/?cursor=cD0z&size=3这里直接点击下一页url并追加每页显示数据量参数size

    五、总结

    三种分页中,普通分页与django中的分页基本没有区别。不过要做分页返回给前端数据,就要从数据库中取出数据,然后在做分页序列化。如果用户一下在前几页请求数据库中的最后几页数据,对查询数据库的时延,对数据库的负载较大,就会出现问题,这个时候就可以使用加密分页,限制用户的访问,只提供前一页和后一页的接口。

  • 相关阅读:
    win7网络共享原来如此简单,WiFi共享精灵开启半天都弱爆了!
    JQUERY UI Datepicker Demo
    Official online document, install svn server in centOS
    JAVE not work in linux
    AMR 转mp3 失败
    XD, XR, DR 股票
    Linux 下MySql 重置密码
    Difinition Of Done
    Apache, Tomcat, JK Configuration Example
    Linux 安装tomcat
  • 原文地址:https://www.cnblogs.com/welan/p/9952801.html
Copyright © 2011-2022 走看看