Rest_framework之版本控制、响应器和分页器
一、访问频率补充
频率:
自定义:
1 定义一个类MyThrottles
allow_request(频率限制的逻辑) ==》这两个函数都是派生出来的,继承的类里面封装的。
wait(返回一个数字,给用户提示,还差多少秒)
2 局部使用:throttle_classes=[MyThrottles,]
3 全局使用:'DEFAULT_THROTTLE_CLASSES':['utils.common.MyThrottles',],
用内置的:(可以控制ip,和userid)
1 写一个类,继承SimpleRateThrottle
属性:scope = 'xxx' ===》scope是源码里的参数,必须要写
重写方法:get_cache_key
from rest_framework.throttling import SimpleRateThrottle class VisitThrottle(SimpleRateThrottle):
# {IP:[]}
# {id:[]}
scope = 'xxx' # 这个必须要写 因为源码里有 def get_cache_key(self, request, view): # 重写get_cache_key方法
# ip=request.META.get('REMOTE_ADDR') 根据IP来限制访问频率 remote_addr如果是用的代理,获取的是代理IP,否则是主机的IP
# 用户一分钟只能访问5次
pk = request.user.pk # 根据用户的主键限制访问频率,默认是通过IP限制,可看源码
return pk
去setting里配置:'DEFAULT_THROTTLE_RATES':{
# 'xxx':'5/m', ===》这里的xxx是scope设定的值。
'xxx':'5/m',
}
2 局部使用:throttle_classes=[MyThrottles,]
3 全局使用:'DEFAULT_THROTTLE_CLASSES':['utils.common.MyThrottles',],
补充:
认证,想局部取消(禁用)===》只需要在认证的地方加上下面的:
authentication_classes=[]
同一个ip一分钟内只能访问三次
{ip1: [12:01:20,12:01:04,12:01:00],ip2: [],ip3: [],}
#(1)取出访问者ip
# (2)判断当前ip不在访问字典里,添加进去,并且直接返回True,表示第一次访问,在字典里,继续往下走
#现在是12:01:30
# (3)循环判断当前时间的列表,有值,并且当前时间减去列表的最后一个时间大于60s,把这种数据pop掉,这样列表中只有60s以内的访问时间,
# (4)判断,当列表小于3,说明一分钟以内访问不足三次,把当前时间插入到列表第一个位置,返回True,顺利通过
# (5)当大于等于3,说明一分钟内访问超过三次,返回False验证失败
代码演示如下:
class MyThrottles():
VISIT_RECORD = {}
def __init__(self):
self.history=None
def allow_request(self,request, view):
#(1)取出访问者ip
# print(request.META)
ip=request.META.get('REMOTE_ADDR')
import time
ctime=time.time()
# (2)判断当前ip不在访问字典里,添加进去,并且直接返回True,表示第一次访问
if ip not in self.VISIT_RECORD:
self.VISIT_RECORD[ip]=[ctime,]
return True
self.history=self.VISIT_RECORD.get(ip)
# (3)循环判断当前ip的列表,有值,并且当前时间减去列表的最后一个时间大于60s,把这种数据pop掉,这样列表中只有60s以内的访问时间,
while self.history and ctime-self.history[-1]>60:
self.history.pop()
# (4)判断,当列表小于3,说明一分钟以内访问不足三次,把当前时间插入到列表第一个位置,返回True,顺利通过
# (5)当大于等于3,说明一分钟内访问超过三次,返回False验证失败
if len(self.history)<3:
self.history.insert(0,ctime)
return True
else:
return False
def wait(self):
import time
ctime=time.time()
return 60-(ctime-self.history[-1])
二、版本控制:
1 127.0.0.1/course/?version=v100000 ===》常用的两种版本书写方式,url带参数形式的
versioning_class = QueryParameterVersioning 只能写成这种形式的,因为源码里不是和处理以前列表形式一样来处理这个
用from rest_framework.versioning import QueryParameterVersioning
在视图类里:
versioning_class=QueryParameterVersioning(**不再是列表)
在setting里配置:
REST_FRAMEWORK={
'VERSION_PARAM':'version',
'DEFAULT_VERSION':'v2',
'ALLOWED_VERSIONS':['v1','v2']
}
视图类里:
request.version ===》 版本号
127.0.0.1/v1/course/ ===》这种形式比较常用
versioning_class = URLPathVersioning
用from rest_framework.versioning import URLPathVersioning
在视图类里:
versioning_class=URLPathVersioning**不再是列表)
在setting里配置:
REST_FRAMEWORK={
'VERSION_PARAM':'version',
'DEFAULT_VERSION':'v2',
'ALLOWED_VERSIONS':['v1','v2']
}
视图类里:
request.version
3 反向解析(了解)
urls
from django.conf.urls import url
from django.contrib import admin
from app01 import views
urlpatterns = [
url(r'^admin/', admin.site.urls),
url(r'^testversion/', views.Test.as_view()),
url(r'^(?P<version>[v1|v2|v3]+)/testversion/', views.Test2.as_view(),name='ttt'),
url(r'^testres', views.Test3.as_view()),
url(r'^page', views.Page.as_view()),
]
settings里相关配置
REST_FRAMEWORK={
'VERSION_PARAM':'version',
'DEFAULT_VERSION':'v2',
'ALLOWED_VERSIONS':['v1','v2']
}
views
from django.shortcuts import render, HttpResponse # Create your views here.
from app01 import models
from rest_framework.views import APIView
from rest_framework.response import Response from rest_framework.versioning import QueryParameterVersioning, URLPathVersioning 版本控制
class Test(APIView):
versioning_class = QueryParameterVersioning def get(self, request, *args, **kwargs):
print(request.version) return Response('ok') from django.urls import reverse 反向解析 仅作了解 用的比较少
class Test2(APIView):
versioning_class = URLPathVersioning def get(self, request, *args, **kwargs):
print(request.version)
url = request.versioning_scheme.reverse(viewname='ttt', request=request)
print(url)
url2 = reverse(viewname='ttt', kwargs={'version': 'v1'})
print(url2) return Response('ok ttest2')
三、响应器:
以后项目中用:(返回的格式,只是json格式)
REST_FRAMEWORK={
'DEFAULT_RENDERER_CLASSES':['rest_framework.renderers.JSONRenderer',],
}
补充一点:
查找模板的时候:先从自己app里找,找不到去项目,再找不到,去各个app里找
views
from rest_framework.renderers import BrowsableAPIRenderer, JSONRenderer, AdminRenderer class Test3(APIView):
renderer_classes=[BrowsableAPIRenderer]
def get(self, request, *args, **kwargs):
return Response({
'name': 'qlz',
'age': 18,
'name1': 'qlz',
'age2': 18,
})
settings
REST_FRAMEWORK = {
'DEFAULT_RENDERER_CLASSES': ['rest_framework.renderers.JSONRenderer'],
}
四、分页
1 简单分页
127.0.0.1/course/page=3
PageNumberPagination
#每页显示多少条api_settings.PAGE_SIZE
#page_size =
#查询指定页码的重命名
#page_query_param = 'page'
#指定每页显示条数
#page_size_query_param = None
#限制每页显示最大条数
#max_page_size = None
2 偏移分页
127.0.0.1/course/offset=10&limit=5
LimitOffsetPagination
# default_limit:默认显示多少条
# max_limit:最大显示多少条
# limit_query_param:重新命名limit(limit=4:表明显示四条,受max_limit的限制)
# offset_query_param:指定查询的标杆名(offset=1:表明从第二条开始,往后偏移)
3 加密分页
后台返回的url:127.0.0.1/course/page=dfgeg
CursorPagination
cursor_query_param = 'cursor':查询的名字
page_size = api_settings.PAGE_SIZE:每页显示的条数
ordering = '-created' :按谁排序
补充:(1)修改数据属性的方式:
1 再setting里配置每页条数
2 写一个类,继承它,属性重写
3 再对象里修改
(2)my_page.get_paginated_response(ser.data)
# 对Response做了封装,返回内容里有总条数,上一页,下一页的链接
views
from rest_framework.serializers import ModelSerializer
from rest_framework import serializers class BookSer(serializers.ModelSerializer):
class Meta:
model = models.Book
fields = '__all__' from rest_framework.pagination import PageNumberPagination, LimitOffsetPagination, CursorPagination # class Page(APIView):
# def get(self,request,*args,**kwargs):
# ret=models.Book.objects.all()
# my_page=PageNumberPagination()
# my_page.page_size=2
# my_page.page_size_query_param='size'
# my_page.max_page_size=5
#
# page_list=my_page.paginate_queryset(ret,request,self)
# ser=BookSer(instance=page_list,many=True)
# # 1 再setting里配置每页条数
# # 2 写一个类,继承它,属性重写
# # 3 再对象里修改
# '''
# 每页显示多少条api_settings.PAGE_SIZE
# page_size =
# 查询指定页码的参数
# page_query_param = 'page'
# 指定每页显示条数
# page_size_query_param = None
# 限制每页显示最大条数
# max_page_size = None
# '''
#
# return Response(ser.data) # class Page(APIView):
# def get(self,request,*args,**kwargs):
# ret=models.Book.objects.all()
# my_page=LimitOffsetPagination()
# my_page.default_limit=3
# my_page.max_limit=5
#
#
# page_list=my_page.paginate_queryset(ret,request,self)
# ser=BookSer(instance=page_list,many=True)
# # 1 再setting里配置每页条数
# # 2 写一个类,继承它,属性重写
# # 3 再对象里修改
# '''
# default_limit:默认显示多少条
# max_limit:最大显示多少条
# limit_query_param:重新命名limit(limit=4:表明显示四条,受max_limit的限制)
# offset_query_param:指定查询的标杆名(offset=1:表明从第二条开始,往后偏移)
# '''
#
# # return Response(ser.data)
# # 对Response做了封装,返回内容里有总条数,上一页,下一页的链接
# return my_page.get_paginated_response(ser.data) class Page(APIView):
def get(self, request, *args, **kwargs):
ret = models.Book.objects.all()
my_page = CursorPagination()
my_page.ordering = 'id'
my_page.page_size = 2
page_list = my_page.paginate_queryset(ret, request, self)
ser = BookSer(instance=page_list, many=True)
# 1 再setting里配置每页条数
# 2 写一个类,继承它,属性重写
# 3 再对象里修改
'''
cursor_query_param = 'cursor':查询的名字
page_size = api_settings.PAGE_SIZE:每页显示的条数
ordering = '-created' :按谁排序
''' # return Response(ser.data)
# 对Response做了封装,返回内容里有总条数,上一页,下一页的链接
return my_page.get_paginated_response(ser.data)
# return Response(ser.data)
Views
自己封装response对象
。。。。
作业:
1 前端操作cookie
2 频率显示中文(去源码里找,替换)
3 版本控制,不在setting里配置,实现
5 redis安装上(windows/linux)
4 axios
5 cc视频 ==》路飞学城用的视频代理,现在一般不自己搞代理,浪费人力物力,买的代理划算。
Rest_framework之版本控制、响应器和分页器的更多相关文章
- DRF(5) - 频率组件、url注册器、响应器、分页器
一.频率组件 1.使用DRF简单频率控制实现对用户进行访问频率控制 1)导入模块,定义频率类并继承SimpleRateThrottle # 导入模块 from rest_framework.throt ...
- Restful 4 -- 认证组件、权限组件、频率组件、url注册器、响应器、分页器
一.认证组件.权限组件.频率组件总结: 只有认证通过的用户才能访问指定的url地址,比如:查询课程信息,需要登录之后才能查看,没有登录,就不能查看,这时候需要用到认证组件 1.认证组件格式 写一个认 ...
- DRF Django REST framework 之 频率,响应器与分页器组件(六)
频率组件 频率组件类似于权限组件,它判断是否给予请求通过.频率指示临时状态,并用于控制客户端可以向API发出的请求的速率. 与权限一样,可以使用多个调节器.API可能会对未经身份验证的请求进行限制,而 ...
- DRF之注册器、响应器、分页器
一.url注册器 通过DRF的视图组件,数据接口逻辑被我们优化到最剩下一个类,接下来,我们使用DRF的url控制器来帮助我们自动生成url,使用步骤如下: 第一步:导入模块 1 from rest_f ...
- django url注册器组件, 响应器组件, 分页器组件
一.url注册器的使用 1.1导入模块 from django.urls import re_path, include from .serializer import views from rest ...
- rest-framework频率组件、url注册器、响应器、分页器
频率组件 import time from rest_framework.throttling import BaseThrottle,SimpleRateThrottle IP_DICT = {} ...
- RestFramework之注册器、响应器与分页器
一.注册器的说明与使用 在我们编写url时经常会因请求方式不同,而重复编写某条url,而rest_framework中的注册器帮我节省了很多代码 下面介绍一下如何使用 # 利用注册器来实现路由分发 f ...
- rest认证组件,权限组件,频率组件,url注册器,响应器组件,分页器组件
1.认证组件 1.1 认证组件利用token来实现认证 1.2 token认证的大概流程 用户登录===>获取用户名和密码===>查询用户表 如果用户存在,生成token,否则返回错误信息 ...
- rest_framework之版本控制
简介 API版本控制可以用来在不同的客户端使用不同的行为.REST框架提供了大量不同的版本设计. 版本控制是由传入的客户端请求决定的,并且可能基于请求URL,或者基于请求头. 有许多有效的方法达到版本 ...
随机推荐
- SQL SERVER 判断是否存在数据库、表、列、视图
SQL SERVER 判断是否存在数据库.表.列.视图 --1. 判断数据库是否存在 IF EXISTS (SELECT * FROM SYS.DATABASES WHERE NAME = '数据库名 ...
- Vijos1221:神秘的配方
背景 每天中午的下课铃一响,浙江镇海中学的同学们都会冲出学校来附近的小饭馆吃饭,刹那间天昏地暗,飞砂走石,家家餐馆内都是一片黑压压的人 .馄饨店.饺子馆,在学校附近开一家红一家.身为镇海中学信息中心首 ...
- day1 java基础回顾-多线程
启动线程方式 方式一:继承Thread. 1. 自定义一个类继承Thread类. 2. 重写Thread的run方法,把自定义线程的任务代码定义在run方法上. 3. 创建Thread子类的对象,并且 ...
- 微信小程序开发之下拉菜单
实现功能:点击维保人员,调出下拉菜单.选择子菜单时,显示右边的图标表示选中,并进行赋值并进行搜索筛选 Wxml: <view class="dtclass" bindtap= ...
- jquery、javascript实现(get、post两种方式)跨域解决方法
一.实现get方式跨域请求数据 浏览器端 <script> $(document).ready(function(){ $.ajax({ url: "http://www.xxx ...
- Git 时光穿梭鸡 管理修改
Git跟踪并管理的是修改,而非文件. 什么是修改? 比如你新增了一行,这就是一个修改, 删除了一行,也是一个修改, 更改了某些字符,也是一个修改, 删了一些又加了一些,也是一个修改, 甚至创建一个新文 ...
- java接口中成员变量和方法的默认修饰符(转)
Java的interface中,成员变量的默认修饰符为:public static final 所以我们在interface中定义成员变量的时候,可以 1:public static final St ...
- mysql 快速导入大SQL文件
进入mysql mysql -u root -p 创建数据库 CREATE DATABASE 数据库名; 设置参数 set sql_log_bin=OFF;//关闭日志 ;//关闭autocommit ...
- MySQL变更之:Online DDL 和 PT-OSC 该选谁?
参考: http://www.fromdual.ch/online-ddl_vs_pt-online-schema-change 在MySQL 5.6版本以前,最昂贵的数据库操作之一就是执行数据定义语 ...
- JS实现简单时钟效果
老师上课需要我们做一个时钟的小作业 ,我把它放在上面记录一下啦 表盘和时针我都是用的背景图的形式,然后绝对定位,通过调整left和top确定时针.分针.秒针的位置,transform-origin设置 ...