知识回顾http://www.cnblogs.com/ctztake/p/8419059.html

这一篇是基于上一篇写的,上一篇谢了认证的具体流程,看懂了上一篇这一篇才能看懂,

当用户访问是 首先执行dispatch函数,当执行当第二部时:

   #2.处理版本信息 处理认证信息 处理权限信息 对用户的访问频率进行限制
self.initial(request, *args, **kwargs)

进入到initial方法:

 def initial(self, request, *args, **kwargs):
"""
Runs anything that needs to occur prior to calling the method handler.
"""
self.format_kwarg = self.get_format_suffix(**kwargs) # Perform content negotiation and store the accepted info on the request
neg = self.perform_content_negotiation(request)
request.accepted_renderer, request.accepted_media_type = neg # Determine the API version, if versioning is in use.
#2.1处理版本信息
version, scheme = self.determine_version(request, *args, **kwargs)
request.version, request.versioning_scheme = version, scheme # Ensure that the incoming request is permitted
#2.2处理认证信息
self.perform_authentication(request)
#2.3处理权限信息
self.check_permissions(request)
#2.4对用户的访问频率进行限制
self.check_throttles(request)
 #2.3处理权限信息
self.check_permissions(request)

下面 开始 权限的具体分析:

进入到check_permissions函数中

 #检查权限
def check_permissions(self, request):
"""
Check if the request should be permitted.
Raises an appropriate exception if the request is not permitted.
"""
#elf.get_permissions()得到的是一个权限对象列表
for permission in self.get_permissions():
#在自定义的Permission中has_permission方法是必须要有的
#判断当前has_permission返回的是True,False,还是抛出异常
#如果是True则表示权限通过,False执行下面代码
if not permission.has_permission(request, self):
#为False的话则抛出异常,当然这个异常返回的提示信息是英文的,如果我们想让他显示我们自定义的提示信息
#我们重写permission_denied方法即可
self.permission_denied(
#从自定义的Permission类中获取message(权限错误提示信息),一般自定义的话都建议写上,如果没有则为默认的(英文提示)
request, message=getattr(permission, 'message', None)
)

查看permission_denied方法(如果has_permission返回True则不执行该方法)

 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)

举例:

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

urlpatterns = [
url(r'^p/', app02_views.Pview.as_view()),
url(r'^mp/', app02_views.Aview.as_view()),
url(r'^jp/', app02_views.Jview.as_view()),
]

urls

from django.shortcuts import render
from rest_framework.views import APIView
from rest_framework.authentication import BaseAuthentication
from rest_framework.permissions import BasePermission
from rest_framework.response import Response
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 MyPermission(object):
message = '登录才可以访问'
def has_permission(self,request, view):
if request.user:
return True
return False class AdminPermission(object):
message = '会员才可以访问'
def has_permission(self,request,view):
if request.user=='ctz':
return True
return False class Pview(APIView):
'''
所有人都可以看
'''
authentication_classes = [MyAuthentication,]
permission_classes = []
def get(self,request):
return Response('图片列表')
def post(self,request):
pass class Aview(APIView):
'''
登录的人可以看
'''
authentication_classes = [MyAuthentication,]
permission_classes = [MyPermission,]
def get(self,request):
return Response('美国电影列表')
def post(self,request):
pass 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) class Jview(APIView):
'''
会员才可以看
'''
authentication_classes = [MyAuthentication,]
permission_classes = [MyPermission,AdminPermission,]
def get(self,request):
return Response('日本电影列表')
def post(self,request):
pass 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)

Views

上面的是局部的只能在当前类中可以用,如果想在全局中用:只需要在settings中配置即可:

from django.shortcuts import render
from rest_framework.views import APIView
from rest_framework.authentication import BaseAuthentication
from rest_framework.permissions import BasePermission
from rest_framework.response import Response
from rest_framework import exceptions from app02.utils import MyPermission
#
#
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 MyPermission(object):
# message = '登录才可以访问'
# def has_permission(self,request, view):
# if request.user:
# return True
# return False
#
# class AdminPermission(object):
# message = '会员才可以访问'
# def has_permission(self,request,view):
# if request.user=='ctz':
# return True
# return False class Pview(APIView):
'''
所有人都可以看
''' permission_classes = []
def get(self,request):
return Response('图片列表')
def post(self,request):
pass class Aview(APIView):
'''
登录的人可以看
'''
# authentication_classes = [MyAuthentication,]
permission_classes = [MyPermission,]
def get(self,request):
return Response('美国电影列表')
def post(self,request):
pass 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) class Jview(APIView):
'''
会员才可以看
'''
# authentication_classes = [MyAuthentication,]
# permission_classes = [MyPermission,AdminPermission,]
def get(self,request):
return Response('日本电影列表')
def post(self,request):
pass 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)

Views

from django.shortcuts import render

from rest_framework.authentication import BaseAuthentication
from rest_framework.permissions import BasePermission
from rest_framework.response import Response
from rest_framework import exceptions
from rest_framework.exceptions import APIException 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 MyPermission(object):
message = '登录才可以访问'
def has_permission(self,request, view):
if request.user:
return True
return False class AdminPermission(object):
message = '会员才可以访问'
def has_permission(self,request,view):
if request.user=='ctz':
return True
return False

utils

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",
],
}

settings

Django rest framework 权限操作(源码分析)的更多相关文章

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

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

  2. Django REST framework —— 认证组件源码分析

    我在前面的博客里已经讲过了,我们一般编写API的时候用的方式 class CoursesView(ViewSetMixin,APIView): pass 这种方式的有点是,灵活性比较大,可以根据自己的 ...

  3. Django rest framework框架——APIview源码分析

    一.什么是rest REST其实是一种组织Web服务的架构,而并不是我们想象的那样是实现Web服务的一种新的技术,更没有要求一定要使用HTTP.其目标是为了创建具有良好扩展性的分布式系统. 可用一句话 ...

  4. DRF框架(一)——restful接口规范、基于规范下使用原生django接口查询和增加、原生Django CBV请求生命周期源码分析、drf请求生命周期源码分析、请求模块request、渲染模块render

    DRF框架    全称:django-rest framework 知识点 1.接口:什么是接口.restful接口规范 2.CBV生命周期源码 - 基于restful规范下的CBV接口 3.请求组件 ...

  5. ElasticSearch Index操作源码分析

    ElasticSearch Index操作源码分析 本文记录ElasticSearch创建索引执行源码流程.从执行流程角度看一下创建索引会涉及到哪些服务(比如AllocationService.Mas ...

  6. Django的settings文件部分源码分析

    Django的settings文件部分源码分析 在编写Django项目的过程中, 其中一个非常强大的功能就是我们可以在settings文件配置许多选项来完成我们预期的功能, 并且这些配置还必须大写, ...

  7. Django(60)Django内置User模型源码分析及自定义User

    前言 Django为我们提供了内置的User模型,不需要我们再额外定义用户模型,建立用户体系了.它的完整的路径是在django.contrib.auth.models.User. User模型源码分析 ...

  8. django的RestFramework模块的源码分析

    一.APIView源码分析 查看源码的前提要知道,找函数方法必须先在自己的类中找,没有再往父类找,一层一层网上找,不能直接按ctrl点击 在我们自己定义的类中没有as_view方法的函数,所以肯定是继 ...

  9. Django——基于类的视图源码分析 二

    源码分析 抽象类和常用视图(base.py) 这个文件包含视图的顶级抽象类(View),基于模板的工具类(TemplateResponseMixin),模板视图(TemplateView)和重定向视图 ...

随机推荐

  1. Atom IDE开发工具, ASCII艺术评论, ninimap 插件

    1 ASCII Art Comments One neat trick is to use ASCII art to create huge comments visible in the minim ...

  2. [剑指Offer] 53.表示数值的字符串

    题目描述 请实现一个函数用来判断字符串是否表示数值(包括整数和小数).例如,字符串"+100","5e2","-123","3.1 ...

  3. 第27天:js-表单获取焦点和数组声明遍历

    一.表单 1.this指事件的调用者2.input.value 表单更换内容3.innerHTML更换盒子里的内容,文字.标签都能换.4.isNaN("12")如果里面的不是个数字 ...

  4. Git的安装与使用(一)

    闲来无事写了个小demo,想上传到GitHub上,发现得使用git进行上传,所以得先了解下git . 1.git是什么 分布式版本控制器 2.svn与git的区别 svn:是集中式的版本控制系统,版本 ...

  5. 3. 无重复字符的最长子串(O(N))

    给定一个字符串,找出不含有重复字符的 最长子串 的长度. 示例: 给定 "abcabcbb" ,没有重复字符的最长子串是 "abc" ,那么长度就是3. 给定  ...

  6. BZOJ5011 & 洛谷4065 & LOJ2275:[JXOI2017]颜色——题解

    https://www.lydsy.com/JudgeOnline/problem.php?id=5011 https://www.luogu.org/problemnew/show/P4065 ht ...

  7. BZOJ5324 & 洛谷4563 & LOJ2545:[JXOI2018]守卫——题解

    https://www.lydsy.com/JudgeOnline/problem.php?id=5324 https://www.luogu.org/problemnew/show/P4563 ht ...

  8. UVA.548 Tree(二叉树 DFS)

    UVA.548 Tree(二叉树 DFS) 题意分析 给出一棵树的中序遍历和后序遍历,从所有叶子节点中找到一个使得其到根节点的权值最小.若有多个,输出叶子节点本身权值小的那个节点. 先递归建树,然后D ...

  9. apache和IIS共享80端口解决办法

    第一步:把iis所发布的网站默认端口由80改为8080:第二步:修改apache的httpd.conf配置文件. 首先,要让apache支持转发也就是做iis的代理那么就要先启 用apache的代理模 ...

  10. Codeforces Round #394 (Div. 2)A水 B暴力 C暴力 D二分 E dfs

    A. Dasha and Stairs time limit per test 2 seconds memory limit per test 256 megabytes input standard ...