认证组件

局部视图认证

在app01.service.auth.py:

class Authentication(BaseAuthentication):

    def authenticate(self,request):
token=request._request.GET.get("token")
token_obj=UserToken.objects.filter(token=token).first()
if not token_obj:
raise exceptions.AuthenticationFailed("验证失败!")
return (token_obj.user,token_obj)

在views.py:

def get_random_str(user):
import hashlib,time
ctime=str(time.time()) md5=hashlib.md5(bytes(user,encoding="utf8"))
md5.update(bytes(ctime,encoding="utf8")) return md5.hexdigest() from app01.service.auth import * from django.http import JsonResponse
class LoginViewSet(APIView):
authentication_classes = [Authentication,]
def post(self,request,*args,**kwargs):
res={"code":1000,"msg":None}
try:
user=request._request.POST.get("user")
pwd=request._request.POST.get("pwd")
user_obj=UserInfo.objects.filter(user=user,pwd=pwd).first()
print(user,pwd,user_obj)
if not user_obj:
res["code"]=1001
res["msg"]="用户名或者密码错误"
else:
token=get_random_str(user)
UserToken.objects.update_or_create(user=user_obj,defaults={"token":token})
res["token"]=token except Exception as e:
res["code"]=1002
res["msg"]=e return JsonResponse(res,json_dumps_params={"ensure_ascii":False})

全局视图认证组件

settings.py配置如下:

REST_FRAMEWORK={
"DEFAULT_AUTHENTICATION_CLASSES":["app01.service.auth.Authentication",]
}

权限组件

局部视图权限

在app01.service.permissions.py中:

from rest_framework.permissions import BasePermission
class SVIPPermission(BasePermission):
message="SVIP才能访问!"
def has_permission(self, request, view):
if request.user.user_type==3:
return True
return False

在views.py:

from app01.service.permissions import *

class BookViewSet(generics.ListCreateAPIView):
permission_classes = [SVIPPermission,]
queryset = Book.objects.all()
serializer_class = BookSerializers

全局视图权限

settings.py配置如下:

REST_FRAMEWORK={
"DEFAULT_AUTHENTICATION_CLASSES":["app01.service.auth.Authentication",],
"DEFAULT_PERMISSION_CLASSES":["app01.service.permissions.SVIPPermission",]
}

throttle(访问频率)组件

局部视图throttle

在app01.service.throttles.py中:

from rest_framework.throttling import BaseThrottle

VISIT_RECORD={}
class VisitThrottle(BaseThrottle): def __init__(self):
self.history=None def allow_request(self,request,view):
remote_addr = request.META.get('REMOTE_ADDR')
print(remote_addr)
import time
ctime=time.time() if remote_addr not in VISIT_RECORD:
VISIT_RECORD[remote_addr]=[ctime,]
return True history=VISIT_RECORD.get(remote_addr)
self.history=history while history and history[-1]<ctime-60:
history.pop() if len(history)<3:
history.insert(0,ctime)
return True
else:
return False def wait(self):
import time
ctime=time.time()
return 60-(ctime-self.history[-1])

在views.py中:

from app01.service.throttles import *

class BookViewSet(generics.ListCreateAPIView):
throttle_classes = [VisitThrottle,]
queryset = Book.objects.all()
serializer_class = BookSerializers

全局视图throttle

REST_FRAMEWORK={
"DEFAULT_AUTHENTICATION_CLASSES":["app01.service.auth.Authentication",],
"DEFAULT_PERMISSION_CLASSES":["app01.service.permissions.SVIPPermission",],
"DEFAULT_THROTTLE_CLASSES":["app01.service.throttles.VisitThrottle",]
}

内置throttle类

在app01.service.throttles.py修改为:

class VisitThrottle(SimpleRateThrottle):

    scope="visit_rate"
def get_cache_key(self, request, view): return self.get_ident(request)

settings.py设置:

REST_FRAMEWORK={
"DEFAULT_AUTHENTICATION_CLASSES":["app01.service.auth.Authentication",],
"DEFAULT_PERMISSION_CLASSES":["app01.service.permissions.SVIPPermission",],
"DEFAULT_THROTTLE_CLASSES":["app01.service.throttles.VisitThrottle",],
"DEFAULT_THROTTLE_RATES":{
"visit_rate":"5/m",
}
}

根据访问频率组件Throttle 设计一个程序:

每分钟同一个IP只能访问十次
from django.db import models

# Create your models here.

class Userinfo(models.Model):
name=models.CharField(max_length=32,verbose_name='用户名')
pwd=models.CharField(max_length=32,verbose_name='密码')
token=models.CharField(max_length=64,null=True) def __str__(self):
return self.name

models

from django.shortcuts import render

# Create your views here.

import time

from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework.throttling import BaseThrottle
from rest_framework import exceptions # Create your views here. AllOW = {} class MyThrottle(BaseThrottle):
'''
限制每分钟访问10次
'''
ip = '127.0.0.1'
def allow_request(self, request, view):
ctime = time.time() # 当前时间。
ip = self.ip # IP。
if ip not in AllOW: # 如果IP不在ALLOW里面。
AllOW[ip] = [ctime, ] # 为IP设置一个当前时间。
else:
time_list = AllOW[ip] # IP对应的访问时间。
while True:
if not time_list: # 这里加判断是为了防止,在time_list中没有值的时候会报错。
break
if ctime - 60 > time_list[-1]: # 当当前的时间减去60,大于最初的时间。
time_list.pop() # 自动去掉最初的一条记录。
else:
break
if len(AllOW[ip]) > 9: # 如果一分钟内,IP的访问次数超过10次。
return False
AllOW[ip].insert(0, ctime)
return True def wait(self):
ip = self.ip
ctime = time.time()
first_in_time = AllOW[ip][-1]
wt = 60 - (ctime - first_in_time) # 等待时间,当前时间减去最后一次的时间得到的一个数,然后再使用60秒减去这个数。
return wt class Limitview(APIView):
throttle_classes = [MyThrottle,] # 请求频率的设置为MyThrottle def get(self, request):
return Response('欢迎进入python的世界!!!') def throttled(self, request, wait):
class InnerThrottled(exceptions.Throttled):
default_detail = '您的请求已被限制.'
extra_detail_singular = 'Expected available in {wait} second.'
extra_detail_plural = '请耐心等待{wait}秒' raise InnerThrottled(wait)

view.py

urlpatterns = [
url(r'^admin/', admin.site.urls),
url(r'^Limitview/',views.Limitview.as_view())
]

urls

REST_FRAMEWORK = {
'UNAUTHENTICATED_USER': None,
'UNAUTHENTICATED_TOKEN': None,
"DEFAULT_AUTHENTICATION_CLASSES": [
# "app01.utils.MyAuthentication",
# "app02.utils.MyAuthentication",
],
"DEFAULT_PERMISSION_CLASSES":[
# "app02.utils.MyPermission",
# "app02.utils.AdminPermission",
],
"DEFAULT_THROTTLE_RATES":{
'tiga':'10/m',
}
}

settings

那么我们还可以把认证,权限与频率组合起来进行一个访问频率限制:

from django.shortcuts import render
from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework.authentication import BaseAuthentication
from rest_framework.permissions import BasePermission
from rest_framework.throttling import SimpleRateThrottle
from rest_framework import exceptions from app01 import models # Create your views here.
class MyAuthentication(BaseAuthentication):
def authenticate(self, request):
token=request.query_params.get(‘token‘)
user=models.Userinfo.objects.filter(token=token).first()
if user:
return (user.name,user)
return None class UserPermission(BasePermission):
message=‘登录用户才可以访问‘
def has_permission(self, request, view):
if request.user:
return True
return False
class AdminPermission(BasePermission):
message=‘管理员才能访问‘
def has_permission(self, request, view):
if request.user ==‘ctz‘:
return True
return False class AnnoThrottle(SimpleRateThrottle):
scope = ‘anno‘
def get_cache_key(self, request, view):
#如果是匿名用户则执行
if not request.user:
return self.get_ident(request)
#如果不是匿名用户则让他执行
return None class UserThrottle(SimpleRateThrottle):
scope = ‘user‘ def get_cache_key(self, request, view):
#当前用户登陆了,并且当前用户不是管理员
if request.user and request.user!=‘ctz‘:
return self.get_ident(request)
#如果是匿名用户和管理员 则让他继续执行
return None class AdminThrottle(SimpleRateThrottle):
scope = ‘admin‘ def get_cache_key(self, request, view):
#如果是管理员
if request.user==‘ctz‘:
return self.get_ident(request)
#不是管理员
return None class IndexView(APIView):
‘‘‘
要求,所有用户都能访问,匿名用户5/m,普通用户10/m,管理员不限
‘‘‘
authentication_classes = [MyAuthentication,]
permission_classes = []
throttle_classes = [AnnoThrottle,UserThrottle,AdminThrottle]
def get(self,request):
return Response(‘首页‘) def throttled(self, request, wait):
class UserInnerThrottled(exceptions.Throttled):
default_detail = ‘请求被限制.‘
extra_detail_singular = ‘Expected available in {wait} second.‘
extra_detail_plural = ‘还需要再等待{wait}秒‘
raise UserInnerThrottled(wait) class UserView(APIView):
‘‘‘
要求:登录用户能访问,普通用户10/m,管理员20/m
‘‘‘
authentication_classes = [MyAuthentication,]
permission_classes = [UserPermission,]
throttle_classes = [UserThrottle,AdminThrottle]
def get(self,request):
return Response(‘用户界面‘) def permission_denied(self, request, message=None):
"""
If request is not permitted, determine what kind of exception to raise.
""" if request.authenticators and not request.successful_authenticator:
raise exceptions.NotAuthenticated(‘无权访问‘)
raise exceptions.PermissionDenied(detail=message) def throttled(self, request, wait):
class UserInnerThrottled(exceptions.Throttled):
default_detail = ‘请求被限制.‘
extra_detail_singular = ‘Expected available in {wait} second.‘
extra_detail_plural = ‘还需要再等待{wait}秒‘
raise UserInnerThrottled(wait) class ManageView(APIView):
‘‘‘
要求:只有管理园能访问,5/m
‘‘‘
authentication_classes = [MyAuthentication,]
permission_classes = [AdminPermission,]
throttle_classes = [AdminThrottle]
def get(self,request):
return Response(‘管理员界面‘) def permission_denied(self, request, message=None):
"""
If request is not permitted, determine what kind of exception to raise.
""" if request.authenticators and not request.successful_authenticator:
raise exceptions.NotAuthenticated(‘无权访问‘)
raise exceptions.PermissionDenied(detail=message) def throttled(self, request, wait):
class UserInnerThrottled(exceptions.Throttled):
default_detail = ‘请求被限制.‘
extra_detail_singular = ‘Expected available in {wait} second.‘
extra_detail_plural = ‘还需要再等待{wait}秒‘
raise UserInnerThrottled(wait)

view.py

from django.db import models

# Create your models here.
class Userinfo(models.Model):
name=models.CharField(max_length=32,verbose_name=‘用户名‘)
pwd=models.CharField(max_length=32,verbose_name=‘密码‘)
token=models.CharField(max_length=64,null=True) def __str__(self):
return self.name

models

REST_FRAMEWORK = {
‘UNAUTHENTICATED_USER‘: None,
‘UNAUTHENTICATED_TOKEN‘: None,
"DEFAULT_AUTHENTICATION_CLASSES": [
# "app01.utils.MyAuthentication",
"app02.utils.MyAuthentication",
],
"DEFAULT_PERMISSION_CLASSES":[
"app02.utils.MyPermission",
"app02.utils.AdminPermission",
],
"DEFAULT_THROTTLE_RATES":{
‘tiga‘:‘10/m‘,
‘anno‘:‘5/m‘,
‘user‘:‘10/m‘,
‘admin‘:‘20/m‘,
}
}

settings

   url(r‘^index/‘, views.IndexView.as_view()),
url(r‘^user/‘, views.UserView.as_view()),
url(r‘^manage/‘, views.ManageView.as_view()),

urls

REST framwork之认证,权限与频率的更多相关文章

  1. DRF 认证 权限 视图 频率

    认证组件 使用:写一个认证类,继承BaseAuthentication 在类中写authenticate方法,把request对象传入 能从request对象中取出用户携带的token根据token判 ...

  2. restful知识点之三restframework认证-->权限-->频率

    认证.权限.频率是层层递进的关系 权限业务时认证+权限 频率业务时:认证+权限+频率 局部认证方式 from django.conf.urls import url,include from djan ...

  3. rest-framework框架——认证、权限、频率组件

    一.rest-framework登录验证 1.models.py添加User和Token模型 class User(models.Model): name = models.CharField(max ...

  4. restful(3):认证、权限、频率 & 解析器、路由控制、分页、渲染器、版本

    models.py中: class UserInfo(models.Model): name = models.CharField(max_length=32) psw = models.CharFi ...

  5. Rest_Framework之认证、权限、频率组件源码剖析

    一:使用RestFramwork,定义一个视图 from rest_framework.viewsets import ModelViewSet class BookView(ModelViewSet ...

  6. 实战-DRF快速写接口(认证权限频率)

    实战-DRF快速写接口 开发环境 Python3.6 Pycharm专业版2021.2.3 Sqlite3 Django 2.2 djangorestframework3.13 测试工具 Postma ...

  7. django-rest-framework 基础三 认证、权限和频率

    django-rest-framework 基础三 认证.权限和频率 目录 django-rest-framework 基础三 认证.权限和频率 1. 认证 1.1 登录接口 1.2 认证 2. 权限 ...

  8. DRF 权限和频率

    Django Rest Framework 权限组件 DRF的权限 权限组件源码解析 我们之前说过了DRF的版本和认证~也知道了权限和频率跟版本认证都是在initial方法里初始化的~~ 其实我们版本 ...

  9. drf6 权限和频率控制组件

    对某件事情决策的范围和程度,我们叫做权限,权限是我们在项目开发中非常常用到的. DRF框架给我们提供的权限组件 权限组件 之前DRF的版本和认证,知道了权限和频率跟版本认证都是在initial方法里初 ...

  10. DRF的权限和频率

    DRF的权限 权限组件源码 权限和频率以及版本认证都是在initial方法里初始化的 我们的权限类一定要有has_permission方法~否则就会抛出异常~~这也是框架给我提供的钩子~~ 在rest ...

随机推荐

  1. [转]Jboss基础

    查看JBoss控制台JMX-Console //可以通过这个页面进行对 JBOSS 的各服务的配置和管理. http://localhost:8080/jmx-console/ 查看发布的WebSer ...

  2. vue cli 3.x 设置4个空格缩进

    vue cli 3.x 设置4个空格缩进: 文件.editorconfig中,indent_size = 2修改为indent_size = 4 文件 .eslintrc.js 添加一行:'inden ...

  3. python5-10 检查用户名

    检查用户名5-10 current_users = ['Tom', 'bob', 'Alice', 'zhangsan', 'Lisi', 'John'] new_users = ['zhangsan ...

  4. docker 运行java程序时区问题

    如果 docker  上面 java  的当前时间比,真实时间慢了8 小时,那估计就是时区问题了, 需要在 打包docker镜像的时候 带上 localtime 和  timezone.(这2 个文件 ...

  5. [转] nginx配置优化+负载均衡+动静分离(附带参数解析)

    #指定nginx进程运行用户以及用户组user www www;#nginx要开启的进程数为8worker_processes  8;#全局错误日志文件#debug输出日志最为详细,而crit输出日志 ...

  6. NDK学习笔记(二)

    花了点时间把pixeliop的部分看完了,拿到开发文档提供的案例稍事修改,把画面左半边压暗. 这个案例重点在于理清pixel_engine()函数中的坐标与scanline的关系. y代表当前正在调用 ...

  7. Ubuntu 安装以及web服务器配置

    1.安装实在没必要说,连系统都装不了,干脆下岗算了 2.Apache2 安装 //安装 sudo apt-get install apache2 Apache安装完成后,默认的网站根目录是" ...

  8. PrintWriter中的write与println方法居然就是这些区别

    为什么循环中分别用write方法和println方法效果一样呢? import java.io.*; public class WriteLog { private BufferedReader bf ...

  9. [蓝桥杯]ALGO-95.算法训练_2的次幂表示

    题目描述: 问题描述 任何一个正整数都可以用2进制表示,例如:137的2进制表示为10001001. 将这种2进制表示写成2的次幂的和的形式,令次幂高的排在前面,可得到如下表达式:=^+^+^ 现在约 ...

  10. 流媒体技术笔记(DarwinStreamingServer相关)

    简介 Darwin Streaming Server简称DSS.DSS是Apple公司提供的开源实时流媒体播放服务器程序.整个程序使用C++编写,在设计上遵循高性能,简单,模块化等程序设计原则,务求做 ...