DRF之权限组件源码分析

【一】权限组件介绍

  • Django REST framework(DRF)中的权限组件用于控制API的访问权限。
  • DRF内置了多个常用的权限类,同时也允许你创建自定义的权限类以满足特定需求。

【二】内置权限类

  • IsAuthenticated:要求用户在访问API时进行身份验证,即用户必须登录。
  • IsAdminUser:要求用户是管理员。
  • IsAuthenticatedOrReadOnly:要求用户在写入数据(例如创建、更新、删除)之前进行身份验证,但允许未经身份验证的用户进行只读操作。
  • IsOwnerOrReadOnly:通常用于处理对象级别的权限。它要求用户在对对象进行写入操作时是对象的所有者,但允许未经身份验证的用户进行只读操作。

【三】执行流程分析

  • DRF的权限组件在视图类的 perform_authentication 方法之后执行。

# 执行视图类中的 校验函数,也就是我们重写的has_permission 方法
# 完成对权限的校验 , 返回 True 或 False 供其他方法进一步判断
# 当返回True 时 ,可以返回一个 User 对象
self.check_permissions(request)
  • 用户发送API请求。

def check_permissions(self, request):
"""
Check if the request should be permitted.
Raises an appropriate exception if the request is not permitted.
"""
# 遍历每一个权限限制类对象
for permission in self.get_permissions(): # 判断权限类中是否重写了 has_permission 校验方法
# 如果没有重写则抛出异常
if not permission.has_permission(request, self):
self.permission_denied(
request,
message=getattr(permission, 'message', None),
code=getattr(permission, 'code', None)
)
  • DRF的身份验证组件(如Token、Session等)会验证用户的身份,并将用户信息添加到请求对象中。

  • 权限组件开始执行。

    • 它会检查请求对象中的用户信息,并根据所选的权限类来判断用户是否有权限访问视图。
def get_permissions(self):
"""
Instantiates and returns the list of permissions that this view requires.
"""
# 将每一个权限类对象返回给上层调用
return [permission() for permission in self.permission_classes]
  • 如果权限验证失败,DRF将返回HTTP 403 Forbidden响应。

【四】内置权限类源码分析

【0】BasePermission

  • BasePermission 类是所有自定义权限类的基类。
  • 它定义了 has_permissionhas_object_permission 两个方法,这些方法用于控制API的访问权限。
from rest_framework.permissions import BasePermission
class BasePermission(metaclass=BasePermissionMetaclass):
"""
A base class from which all permission classes should inherit.
""" # 视图级别的权限检查,它接受 request 和 view 参数,
# 在这个方法中编写自定义的权限逻辑来判断用户是否有权访问整个视图。
def has_permission(self, request, view):
"""
Return `True` if permission is granted, `False` otherwise.
"""
return True # 对象级别的权限检查,它接受 request、view 和 obj 参数
# 在这个方法中编写自定义的权限逻辑来判断用户是否有权访问特定对象(例如数据库中的某个记录)。
def has_object_permission(self, request, view, obj):
"""
Return `True` if permission is granted, `False` otherwise.
"""
return True

【1】IsAuthenticated

  • 要求用户在访问API时进行身份验证,即用户必须登录。
from rest_framework.permissions import IsAuthenticated
class IsAuthenticated(BasePermission):
"""
Allows access only to authenticated users.
""" def has_permission(self, request, view):
return bool(request.user and request.user.is_authenticated)

【2】IsAdminUser

  • 要求用户是管理员。
from rest_framework.permissions import IsAdminUser
class IsAdminUser(BasePermission):
"""
Allows access only to admin users.
""" def has_permission(self, request, view):
return bool(request.user and request.user.is_staff)

【3】IsAuthenticatedOrReadOnly

  • 要求用户在写入数据(例如创建、更新、删除)之前进行身份验证,但允许未经身份验证的用户进行只读操作。
from rest_framework.permissions import  IsAuthenticatedOrReadOnly
class IsAuthenticatedOrReadOnly(BasePermission):
"""
The request is authenticated as a user, or is a read-only request.
""" def has_permission(self, request, view):
return bool(
request.method in SAFE_METHODS or
request.user and
request.user.is_authenticated
)

【4】IsOwnerOrReadOnly

  • 通常用于处理对象级别的权限。它要求用户在对对象进行写入操作时是对象的所有者,但允许未经身份验证的用户进行只读操作。

【五】权限组件使用步骤(固定用法)

【1】创建权限认证类

  • 创建一个自定义的权限认证类,并让它继承自BasePermission

【2】实现has_permission方法

  • 在这个方法中编写自定义的权限逻辑来判断用户是否有权访问整个视图。
  • 在类中写方法:has_permission
    • 如果有权限,就返回True
    • 如果没有权限,就返回False
    • 错误信息是self.message='字符串'

【3】权限认证逻辑

from rest_framework import permissions

class CustomPermission(permissions.BasePermission):
def has_permission(self, request, view):
# 在这里编写视图级别的权限逻辑
return True # 或者根据需求返回 True 或 False def has_object_permission(self, request, view, obj):
# 在这里编写对象级别的权限逻辑
return True # 或者根据需求返回 True 或 False

【4】使用权限认证类

  • 在视图类中,使用认证类

(1)局部使用

  • 在视图类中添加permission_classes属性,并将所需的权限认证类作为其值
  • 这样,在该视图类中只会应用指定的权限认证类。
# 权限认证
class UserDetailView(APIView):
permission_classes = [AdminPermission, ]

(2)全局使用

  • 在配置文件(一般是settings.py)中进行全局配置,将权限认证类添加到DEFAULT_PERMISSION_CLASSES中。
  • 这样,在所有视图类中都会应用该权限认证类。
REST_FRAMEWORK = {
'DEFAULT_PERMISSION_CLASSES': [
'app01.permission.CustomPermission'
],
}

(3)全局使用/局部禁用

  • 当认证组件被全局配置后,可以在视图类中禁用全局认证组件,以实现局部禁用。

    • 如果权限认证组件被全局配置,你仍然可以在某个视图类中禁用全局的权限认证,实现局部禁用的效果。
    • 只需在该视图类中将permission_classes属性设置为空列表即可。
# 权限认证 - 局部禁用
class UserDetailView(APIView):
permission_classes = []

(4)权限认证类的使用顺序

  • 先局部,在视图类定义的 permission_classes
  • 再全局,在DRF中自己配置的 DEFAULT_PERMISSION_CLASSES
  • 最后是,DRF默认配置中的 DEFAULT_PERMISSION_CLASSES

DRF之权限组件源码分析的更多相关文章

  1. DRF的Serializer组件(源码分析)

    DRF的Serializer组件(源码分析) 1. 数据校验 drf中为我们提供了Serializer,他主要有两大功能: 对请求数据校验(底层调用Django的Form和ModelForm) 对数据 ...

  2. DRF的认证组件(源码分析)

    DRF认证组件(源码分析) 1. 数据库建立用户表 在drf中也给我们提供了 认证组件 ,帮助我们快速实现认证相关的功能,例如: # models.py from django.db import m ...

  3. Django REST framework —— 权限组件源码分析

    在上一篇文章中我们已经分析了认证组件源码,我们再来看看权限组件的源码,权限组件相对容易,因为只需要返回True 和False即可 代码 class ShoppingCarView(ViewSetMix ...

  4. Django框架之DRF 认证组件源码分析、权限组件源码分析、频率组件源码分析

    认证组件 权限组件 频率组件

  5. Django框架之drf:8、断点调试,权限、认证、频率组件源码分析,基于APIView编写分页,异常处理

    Django框架之drf 一.断点调式使用 ​ 指,在我们编写代码的时候,程序运行出现报错是无可避免的,当程序 出现报错时,我们需要找到出现报错的代码进行修改,如果时简短的代码很容易就可以找到报错位置 ...

  6. DRF的限流组件(源码分析)

    DRF限流组件(源码分析) 限流,限制用户访问频率,例如:用户1分钟最多访问100次 或者 短信验证码一天每天可以发送50次, 防止盗刷. 对于匿名用户,使用用户IP作为唯一标识. 对于登录用户,使用 ...

  7. 断点调试/认证/权限/频率-源码分析/基于APIView编写分页/异常处理

    内容概要 断点调试 认证/权限/频率-源码分析 基于APIView编写分页 异常处理 断点调试 # 程序以 debug模式运行,可以在任意位置停下,查看当前情况下变量数据的变化情况 # pycharm ...

  8. Django-restframework 源码之认证组件源码分析

    Django-restframework 源码之认证组件源码分析 一 前言 之前在 Django-restframework 的流程分析博客中,把最重要的关于认证.权限和频率的方法找到了.该方法是 A ...

  9. element-ui 组件源码分析整理笔记目录

    element-ui button组件 radio组件源码分析整理笔记(一) element-ui switch组件源码分析整理笔记(二) element-ui inputNumber.Card .B ...

  10. ceph-csi组件源码分析(1)-组件介绍与部署yaml分析

    更多ceph-csi其他源码分析,请查看下面这篇博文:kubernetes ceph-csi分析目录导航 ceph-csi组件源码分析(1)-组件介绍与部署yaml分析 基于tag v3.0.0 ht ...

随机推荐

  1. Oracle锁表及解锁方法

    1. 首先查看数据库中哪些表被锁了,找到session ID: 使用sql: select b.owner,b.object_name,a.session_id,a.locked_modefrom v ...

  2. 【Esp32】为 idf 定制本地 Arduino 组件

    在开始今天的水文前,老周先要奉劝一下国内某些嵌入式砖家和穴者,不要看不起 Arduino,它不是一种开发板,而是一种规范.Arduino 的思想是正确的,把各种开发板封装为统一的 API,让许多开源库 ...

  3. [源码系列:手写spring] IOC第九节:应用上下文ApplicationContext

    内容介绍 在Spring中应用上下文ApplicationContext是相较于BeanFacotry更为先进的IOC容器,BeanFacotry是Spring实现IOC最基础最核心的接口,使得Spr ...

  4. 《机器人SLAM导航核心技术与实战》先导课:SLAM的应用价值与技术难点

    <机器人SLAM导航核心技术与实战>先导课:SLAM的应用价值与技术难点 视频讲解 [先导课]3.SLAM的应用价值与技术难点-视频讲解 [先导课]3.1.SLAM的应用价值与技术难点-S ...

  5. vue-element-admin整合服务端代理api

    1. 找到vue.config.js,在devServer中编辑如下 devServer: { port: port, open: true, overlay: { warnings: false, ...

  6. jmeter返回值作为参数传给后面的步骤使用的方法

    如,系统返回data 通过正则获取data后的数据,且名称定义为id 然后通过${id}的方式传参给需要使用的地方

  7. eolinker校验规则之 Json结构定位:返回结果校验的方法和案例(父参、子参内容校验)

    如下图,订单编号的参数在data父字段内 Eolinker返参校验的写法就需要有些变化 先写Data父参,添加子字段,再写子参 预期结果不支持全局变量 可通过添加绑定,绑定前一个接口返回参数,进行匹配

  8. EFCore(五)——多个DBContext的Code First指定对应的DBContext更新

    此环境为ASP.NET Core的项目 1.在需要更新的DBContext里添加空的构造函数 2.打开Nuget命令行选择对应的目录位置 3.带参数-Context指定对应的DBContext 1.  ...

  9. Ubuntu 使用crontab定时备份log

    rsyslog 在Linux上,默认情况下,所有日志文件都位于/var/log目录下,有几种类型的日志文件存储不同的消息,可以是cron,内核,安全性,事件,用户,这些日志文件大多由rsyslog服务 ...

  10. 【BUG】ELF文件执行时出现段错误Segmentation fault,解决:使用010编辑器修改ELF文件不可执行段权限

    问题:段错误,.eh_frame不可执行. 需求:改执行权限. 工具:010 Editer,我的版本:12.0.1 Windows 10. 工具下载:010编辑器官网下载页. 第一步 查看段的执行权限 ...