Django rest framework實現(xiàn)分頁的示例
第一種分頁PageNumberPagination
基本使用
(1)urls.py
urlpatterns = [
re_path('(?P<version>[v1|v2]+)/page1/', Pager1View.as_view(),) #分頁1
]
(2)api/utils/serializers/pager.py
# api/utils/serializsers/pager.py
from rest_framework import serializers
from api import models
class PagerSerialiser(serializers.ModelSerializer):
class Meta:
model = models.Role
fields = "__all__"
(3)views.py
from api.utils.serializsers.pager import PagerSerialiser
from rest_framework.response import Response
from rest_framework.pagination import PageNumberPagination
class Pager1View(APIView):
def get(self,request,*args,**kwargs):
#獲取所有數(shù)據(jù)
roles = models.Role.objects.all()
#創(chuàng)建分頁對象
pg = PageNumberPagination()
#獲取分頁的數(shù)據(jù)
page_roles = pg.paginate_queryset(queryset=roles,request=request,view=self)
#對數(shù)據(jù)進行序列化
ser = PagerSerialiser(instance=page_roles,many=True)
return Response(ser.data)
(4)settings配置
REST_FRAMEWORK = {
#分頁
"PAGE_SIZE":2 #每頁顯示多少個
}

自定義分頁類
#自定義分頁類
class MyPageNumberPagination(PageNumberPagination):
#每頁顯示多少個
page_size = 3
#默認每頁顯示3個,可以通過傳入pager1/?page=2&size=4,改變默認每頁顯示的個數(shù)
page_size_query_param = "size"
#最大頁數(shù)不超過10
max_page_size = 10
#獲取頁碼數(shù)的
page_query_param = "page"
class Pager1View(APIView):
def get(self,request,*args,**kwargs):
#獲取所有數(shù)據(jù)
roles = models.Role.objects.all()
#創(chuàng)建分頁對象,這里是自定義的MyPageNumberPagination
pg = MyPageNumberPagination()
#獲取分頁的數(shù)據(jù)
page_roles = pg.paginate_queryset(queryset=roles,request=request,view=self)
#對數(shù)據(jù)進行序列化
ser = PagerSerialiser(instance=page_roles,many=True)
return Response(ser.data)

第二種分頁 LimitOffsetPagination
自定義
#自定義分頁類2
class MyLimitOffsetPagination(LimitOffsetPagination):
#默認顯示的個數(shù)
default_limit = 2
#當(dāng)前的位置
offset_query_param = "offset"
#通過limit改變默認顯示的個數(shù)
limit_query_param = "limit"
#一頁最多顯示的個數(shù)
max_limit = 10
class Pager1View(APIView):
def get(self,request,*args,**kwargs):
#獲取所有數(shù)據(jù)
roles = models.Role.objects.all()
#創(chuàng)建分頁對象
pg = MyLimitOffsetPagination()
#獲取分頁的數(shù)據(jù)
page_roles = pg.paginate_queryset(queryset=roles,request=request,view=self)
#對數(shù)據(jù)進行序列化
ser = PagerSerialiser(instance=page_roles,many=True)
return Response(ser.data)


返回的時候可以用get_paginated_response方法
自帶上一頁下一頁


第三種分頁CursorPagination
加密分頁方式,只能通過點“上一頁”和下一頁訪問數(shù)據(jù)
#自定義分頁類3 (加密分頁)
class MyCursorPagination(CursorPagination):
cursor_query_param = "cursor"
page_size = 2 #每頁顯示2個數(shù)據(jù)
ordering = 'id' #排序
page_size_query_param = None
max_page_size = None
class Pager1View(APIView):
def get(self,request,*args,**kwargs):
#獲取所有數(shù)據(jù)
roles = models.Role.objects.all()
#創(chuàng)建分頁對象
pg = MyCursorPagination()
#獲取分頁的數(shù)據(jù)
page_roles = pg.paginate_queryset(queryset=roles,request=request,view=self)
#對數(shù)據(jù)進行序列化
ser = PagerSerialiser(instance=page_roles,many=True)
# return Response(ser.data)
return pg.get_paginated_response(ser.data)


代碼
版本、解析器、序列化和分頁
# MyProject2/urls.py
from django.contrib import admin
from django.urls import path,include
urlpatterns = [
#path('admin/', admin.site.urls),
path('api/',include('api.urls') ),
]
# api/urls.py
from django.urls import path,re_path
from .views import UserView,PaserView,RolesView,UserInfoView,GroupView,UserGroupView
from .views import Pager1View
urlpatterns = [
re_path('(?P<version>[v1|v2]+)/users/', UserView.as_view(),name = 'api_user'), #版本
path('paser/', PaserView.as_view(),), #解析
re_path('(?P<version>[v1|v2]+)/roles/', RolesView.as_view()), #序列化
re_path('(?P<version>[v1|v2]+)/info/', UserInfoView.as_view()), #序列化
re_path('(?P<version>[v1|v2]+)/group/(?P<pk>\d+)/', GroupView.as_view(),name = 'gp'), #序列化生成url
re_path('(?P<version>[v1|v2]+)/usergroup/', UserGroupView.as_view(),), #序列化做驗證
re_path('(?P<version>[v1|v2]+)/pager1/', Pager1View.as_view(),) #分頁1
]
# api/models.py
from django.db import models
class UserInfo(models.Model):
USER_TYPE = (
(1,'普通用戶'),
(2,'VIP'),
(3,'SVIP')
)
user_type = models.IntegerField(choices=USER_TYPE)
username = models.CharField(max_length=32,unique=True)
password = models.CharField(max_length=64)
group = models.ForeignKey('UserGroup',on_delete=models.CASCADE)
roles = models.ManyToManyField('Role')
class UserToken(models.Model):
user = models.OneToOneField('UserInfo',on_delete=models.CASCADE)
token = models.CharField(max_length=64)
class UserGroup(models.Model):
title = models.CharField(max_length=32)
class Role(models.Model):
title = models.CharField(max_length=32)
# api/views.py
import json
from django.shortcuts import render,HttpResponse
from rest_framework.views import APIView
from rest_framework.request import Request
from rest_framework.versioning import URLPathVersioning
from . import models
##########################################版本和解析器#####################################################
class UserView(APIView):
def get(self,request,*args,**kwargs):
#獲取版本
print(request.version)
#獲取處理版本的對象
print(request.versioning_scheme)
#獲取瀏覽器訪問的url,reverse反向解析
#需要兩個參數(shù):viewname就是url中的別名,request=request是url中要傳入的參數(shù)
#(?P<version>[v1|v2]+)/users/,這里本來需要傳version的參數(shù),但是version包含在request里面,所有只需要request=request就可以
url_path = request.versioning_scheme.reverse(viewname='api_user',request=request)
print(url_path)
self.dispatch
return HttpResponse('用戶列表')
# from rest_framework.parsers import JSONParser,FormParser
class PaserView(APIView):
'''解析'''
# parser_classes = [JSONParser,FormParser,]
#JSONParser:表示只能解析content-type:application/json的頭
#FormParser:表示只能解析content-type:application/x-www-form-urlencoded的頭
def post(self,request,*args,**kwargs):
#獲取解析后的結(jié)果
print(request.data)
return HttpResponse('paser')
###########################################序列化###########################################################
from rest_framework import serializers
#要先寫一個序列化的類
class RolesSerializer(serializers.Serializer):
#Role表里面的字段id和title序列化
id = serializers.IntegerField()
title = serializers.CharField()
class RolesView(APIView):
def get(self,request,*args,**kwargs):
# 方式一:對于[obj,obj,obj]
# (Queryset)
# roles = models.Role.objects.all()
# 序列化,兩個參數(shù),instance:Queryset 如果有多個值,就需要加 mangy=True
# ser = RolesSerializer(instance=roles,many=True)
# 轉(zhuǎn)成json格式,ensure_ascii=False表示顯示中文,默認為True
# ret = json.dumps(ser.data,ensure_ascii=False)
# 方式二:
role = models.Role.objects.all().first()
ser = RolesSerializer(instance=role, many=False)
ret = json.dumps(ser.data, ensure_ascii=False)
return HttpResponse(ret)
# class UserInfoSerializer(serializers.Serializer):
# '''序列化用戶的信息'''
# #user_type是choices(1,2,3),顯示全稱的方法用source
# type = serializers.CharField(source="get_user_type_display")
# username = serializers.CharField()
# password = serializers.CharField()
# #group.title:組的名字
# group = serializers.CharField(source="group.title")
# #SerializerMethodField(),表示自定義顯示
# #然后寫一個自定義的方法
# rls = serializers.SerializerMethodField()
#
# def get_rls(self,row):
# #獲取用戶所有的角色
# role_obj_list = row.roles.all()
# ret = []
# #獲取角色的id和名字
# #以字典的鍵值對方式顯示
# for item in role_obj_list:
# ret.append({"id":item.id,"title":item.title})
# return ret
# class UserInfoSerializer(serializers.ModelSerializer):
# type = serializers.CharField(source="get_user_type_display")
# group = serializers.CharField(source="group.title")
# rls = serializers.SerializerMethodField()
#
# def get_rls(self, row):
# # 獲取用戶所有的角色
# role_obj_list = row.roles.all()
# ret = []
# # 獲取角色的id和名字
# # 以字典的鍵值對方式顯示
# for item in role_obj_list:
# ret.append({"id": item.id, "title": item.title})
# return ret
#
# class Meta:
# model = models.UserInfo
# fields = ['id','username','password','type','group','rls']
# class UserInfoSerializer(serializers.ModelSerializer):
# class Meta:
# model = models.UserInfo
# #fields = "__all__"
# fields = ['id','username','password','group','roles']
# #表示連表的深度
# depth = 1
class UserInfoSerializer(serializers.ModelSerializer):
group = serializers.HyperlinkedIdentityField(view_name='gp',lookup_field='group_id',lookup_url_kwarg='pk')
class Meta:
model = models.UserInfo
#fields = "__all__"
fields = ['id','username','password','group','roles']
#表示連表的深度
depth = 0
class UserInfoView(APIView):
'''用戶的信息'''
def get(self,request,*args,**kwargs):
users = models.UserInfo.objects.all()
#這里必須要傳參數(shù)context={'request':request}
ser = UserInfoSerializer(instance=users,many=True,context={'request':request})
ret = json.dumps(ser.data,ensure_ascii=False)
return HttpResponse(ret)
class GroupSerializer(serializers.ModelSerializer):
class Meta:
model = models.UserGroup
fields = "__all__"
class GroupView(APIView):
def get(self,request,*args,**kwargs):
pk = kwargs.get('pk')
obj = models.UserGroup.objects.filter(pk=pk).first()
ser = GroupSerializer(instance=obj,many=False)
ret = json.dumps(ser.data,ensure_ascii=False)
return HttpResponse(ret)
####################################序列化之用戶請求數(shù)據(jù)驗證驗證####################################
#自定義驗證規(guī)則
class GroupValidation(object):
def __init__(self,base):
self.base = base
def __call__(self, value):
if not value.startswith(self.base):
message = "標(biāo)題必須以%s為開頭"%self.base
raise serializers.ValidationError(message)
class UserGroupSerializer(serializers.Serializer):
title = serializers.CharField(validators=[GroupValidation('以我開頭'),])
class UserGroupView(APIView):
def post(self,request,*args, **kwargs):
ser = UserGroupSerializer(data=request.data)
if ser.is_valid():
print(ser.validated_data['title'])
else:
print(ser.errors)
return HttpResponse("用戶提交數(shù)據(jù)驗證")
##################################################分頁###################################################
from api.utils.serializsers.pager import PagerSerialiser
from rest_framework.response import Response
from rest_framework.pagination import PageNumberPagination,LimitOffsetPagination,CursorPagination
# #自定義分頁類1
# class MyPageNumberPagination(PageNumberPagination):
# #每頁顯示多少個
# page_size = 3
# #默認每頁顯示3個,可以通過傳入pager1/?page=2&size=4,改變默認每頁顯示的個數(shù)
# page_size_query_param = "size"
# #最大頁數(shù)不超過10
# max_page_size = 10
# #獲取頁碼數(shù)的
# page_query_param = "page"
#自定義分頁類2
class MyLimitOffsetPagination(LimitOffsetPagination):
#默認顯示的個數(shù)
default_limit = 2
#當(dāng)前的位置
offset_query_param = "offset"
#通過limit改變默認顯示的個數(shù)
limit_query_param = "limit"
#一頁最多顯示的個數(shù)
max_limit = 10
#自定義分頁類3 (加密分頁)
class MyCursorPagination(CursorPagination):
cursor_query_param = "cursor"
page_size = 2 #每頁顯示2個數(shù)據(jù)
ordering = 'id' #排序
page_size_query_param = None
max_page_size = None
class Pager1View(APIView):
def get(self,request,*args,**kwargs):
#獲取所有數(shù)據(jù)
roles = models.Role.objects.all()
#創(chuàng)建分頁對象
pg = MyCursorPagination()
#獲取分頁的數(shù)據(jù)
page_roles = pg.paginate_queryset(queryset=roles,request=request,view=self)
#對數(shù)據(jù)進行序列化
ser = PagerSerialiser(instance=page_roles,many=True)
return Response(ser.data)
# return pg.get_paginated_response(ser.data)
# api/utils/serializsers/pager.py
from rest_framework import serializers
from api import models
class PagerSerialiser(serializers.ModelSerializer):
class Meta:
model = models.Role
fields = "__all__"
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
Python實現(xiàn)對excel文件列表值進行統(tǒng)計的方法
這篇文章主要介紹了Python實現(xiàn)對excel文件列表值進行統(tǒng)計的方法,涉及Python基于win32com組件操作表格文件的相關(guān)技巧,具有一定參考借鑒價值,需要的朋友可以參考下2015-07-07
Python實現(xiàn)識別文字中的省市區(qū)并繪圖
在做NLP(自然語言處理)相關(guān)任務(wù)時,經(jīng)常會遇到需要識別并提取省、城市、行政區(qū)的需求。今天給大家介紹一個模塊,你只需要把字符串傳遞給這個模塊,他就能給你返回這個字符串內(nèi)的省、市、區(qū)關(guān)鍵詞,快來學(xué)習(xí)一下吧2022-06-06
Python基于tkinter canvas實現(xiàn)圖片裁剪功能
這篇文章主要介紹了Python基于tkinter canvas實現(xiàn)圖片裁剪功能,文中通過示例代碼介紹的非常詳細,對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友可以參考下2020-11-11
python爬蟲Scrapy框架:媒體管道原理學(xué)習(xí)分析
這篇文章主要介紹了python爬蟲Scrapy框架:媒體管道原理學(xué)習(xí)分析,有需要的朋友可以借鑒參考,希望可以對廣大一同學(xué)習(xí)的讀者朋友有所幫助2021-09-09
Python+Socket實現(xiàn)基于UDP協(xié)議的局域網(wǎng)廣播功能示例
這篇文章主要介紹了Python+Socket實現(xiàn)基于UDP協(xié)議的局域網(wǎng)廣播功能,結(jié)合實例形式分析了Python+socket實現(xiàn)UDP協(xié)議廣播的客戶端與服務(wù)器端功能相關(guān)操作技巧,需要的朋友可以參考下2017-08-08
詳解Numpy中的數(shù)組拼接、合并操作(concatenate, append, stack, hstack, vstac
這篇文章主要介紹了詳解Numpy中的數(shù)組拼接、合并操作(concatenate, append, stack, hstack, vstack, r_, c_等),具有一定的參考價值,感興趣的小伙伴們可以參考一下2019-05-05

