Djangorestframework之认证源码入门分析

认证组件

首先我们来认识一下什么是认证吧

views.py文件

from rest_framework.views import APIView
class MyAuth():
    def authenticate(self,request):
        print('认证方法')

class Books(APIView):
    authentication_classes = [MyAuth, ]
    def get(self,request):
        response ={'code ': 100, 'msg': '获取成功'}
        return Response(response)

url文件:

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

现在我们朝着服务端试着发一下请求,结果如下

再看一下服务端

是不是很神奇 ,想知道究竟的话 ,不妨和我一起去看看源码,我们去看一下APIView的源码,

我们知道路由匹配成功以后会走对应的视图函数或者视图类,也就是走里面的as_view函数

 其实走的是父类view的as_view的方法,

 这时候就走到了APIViewd的dispatch方法,

 获取request时根据列表推导式生成了一个个实例对象:

我们来看看authentication classes 到底是什么呢?

其实就是一个配置文件,所以我们认证的是先走view里面的这个类列表,再找django暴露给用户的settings里面的authentication classes ,最后才是django的配置文件

 

 

 返回的是一个属性

@property
def user(self):

        if not hasattr(self, '_user'):
            with wrap_attributeerrors():
                # 调用  _authenticate  此时的self是request对象
                self._authenticate()
        return self._user


def _authenticate(self):
            # 此时的self是request ,authenticator每一个验证类对象
            for authenticator in self.authenticators:
                try:
                    # 使用authenticator调用它的authenticate() 返回一个元组
                    #元组的第一个值是request.user,第二个值是request.auth
                    user_auth_tuple = authenticator.authenticate(self)
                except exceptions.APIException:
                    # 如果没有验证通过,抛出异常
                    self._not_authenticated()
                    raise

                # 如果 user_auth_tuple  不为空的话,证明authenticator.authenticate(self) 返回了数据
                #  **** 有多个验证类的话,最后一个认证类返回值,其他验证类不要返回
                # 否则,这个验证类之后的所有验证类都不会被执行
                # 如果返回值不为None,赋值后 将会跳出循环
                if user_auth_tuple is not None:
                    self._authenticator = authenticator
                    # 进行赋值
                    self.user, self.auth = user_auth_tuple
                    # 跳出for循环, 验证通过
                    return

            self._not_authenticated()
View Code

局部使用
  在视图类中写
  authentication_classes=[MyAuth,]
全局使用
  在settings.py中配置
  REST_FRAMEWORK={
  "DEFAULT_AUTHENTICATION_CLASSES":["app01.MyAuths.MyAuth",]
  }
局部禁用
  authentication_classes = []
读源码看到的东西:
  如果在项目的setting.py中配置了REST_FRAMEWORK,默认先从项目的setting中取
  如果取不到,才去默认的drf配置文件中取
  如果用户在视图类中配置了某个,先去用户配置的取

承蒙关照
原文地址:https://www.cnblogs.com/guanlei/p/11129210.html