中间件

  django的中间件是一个全局范围内处理django的请求和响应的框架级别的钩子。

  作用:对于一个请求到达视图函数的前后进行处理

  本质:中间件的本质是一个类,类中定义了特定的方法,Django框架会在特定时间去执行这些方法处理请求。

  中间件的五个方法以及四个特征:

    五个方法:

      1、process_request(self, request)

      2、process_response(self, request, response)

      3、process_view(self, request, view_func, view_args, view_kwargs)

      4、process_exception(self, request, exception)

      5、process_template_response(self, request, response)

    四个特征:

      1、执行时间(触发条件):何时执行(何时被触发)

      2、参数:每个参数代表的含义

      3、执行顺序:在多个中间件都有某一个方法的时候,方法执行的先后顺序

      4、返回值:不同的返回,会得到怎样的结果

自定义中间件

  自定义中间件的步骤:

    1、在需要自定义中间件的app路径下创建一个文件夹存放定义中间件文件(文件夹命名最好见名知意)

    2、创建一个py文件,在该文件内编写中间件代码

    3、中间件是一个类,定义时需要继承MiddlewareMixin,然后定义需要用到的方法

      from django.utils.deprecation import MiddlewareMixin
      class MyMiddleWare(MiddlewareMixin):

      def process_request(self, request):
      pass

    4、注册中间件,使其生效

      在settings中的MIDDLEWARE列表中,添加自定义中间件即可

        格式:app文件夹.中间件文件夹.中间件文件.需要注册的中间件类

        'right_manage.middlewares.mymiddleware.MyMiddleWare'

中间件的五个方法和四个特征

  1、process_request(self, request)

    作用:在一个请求到达视图函数之前(也就是路由匹配前),对该请求做相关处理。(可以实现登录认证的功能)

    执行时间:在请求到达视图函数之前(路由匹配前)

    参数:

      request是一个请求对象,和后续视图函数接收的是同一个对象。(可以打印它们的id值验证)

    执行顺序:按照中间件注册的先后顺序执行

    返回值:

      返回None时,表示整个请求流程正常执行(后续接着执行其他中间件方法、路由匹配、视图函数)

      返回一个响应对象时,不执行后续操作(包括其他中间件方法、路由匹配、视图函数);

        如果当前中间件定义有process_response方法,那么执行该方法后返回结果给浏览器;

        如果当前中间件没有定义process_response方法,直接将当前响应对象返回给浏览器。

  

  2、process_response(self, request, response)    

    作用:对一个响应对象返回给浏览器前,做相关处理。

    执行时间:在视图函数处理完请求之后

    参数:

      request是一个请求对象,和视图函数接收的是同一个对象。(可以打印它们的id值验证)

      response是一个响应对象,中间件接收到的response可能是视图函数返回的响应对象,也可能是其他中间件处理后的响应对象 或 自定义的一个响应对象

    执行顺序:

      按照中间件注册的先后顺序,倒序执行

      也就是从最后一个定义了process_response方法的中间件开始往上执行

      所以,处于中间位置的中间件接收的response可能是视图函数返回的响应对象(尾部的中间件没对其做任何处理),也可能尾部中间件处理后的response

    返回值:

      必须是一个响应对象,否则报错

  3、process_view(self, request, view_func, view_args, view_kwargs)

    作用:在一个请求经过路由匹配,到达视图函数之前,对该视图函数的参数以及请求对象做处理

    执行时间:路由匹配之后,视图函数之前,且在其他中间件的process_request之后

    参数:

      request是一个请求对象,和视图函数接收的是同一个对象。(可以打印它们的id值验证)

      view_func:路由匹配得到的对应视图函数的内存地址

      view_args:对应视图函数的位置参数

      view_kwargs:对应视图函数的关键字参数

    执行顺序:

      按照中间件的注册顺序执行

    返回值:

      返回None时,处理请求的流程正常执行

      返回一个响应对象时,后续的视图函数和其他中间件的process_view都不执行,直接执行process_response(从最后一个中间件开始倒序执行该方法)

    如果路由匹配不成功(输入的地址有误),那么就不会执行process_view,直接执行的process_response(从最后一个中间件开始倒序执行该方法)

  4、process_exception(self, request, exception)

    作用:处理视图函数中发生的异常

    触发条件:视图中出现异常才会执行,所以执行时间在视图函数之后,也就在process_request和process_view之后,且在process_response之前

    参数:

      request是一个请求对象,和视图函数接收的是同一个对象。(可以打印它们的id值验证)

      exception就是视图函数中出现的异常,该变量是字符串,返回一个错误信息(如invalid literal for int() with base 10: 'abc')

    执行顺序:

      按照中间件注册的先后顺序,倒序执行(凡是在视图函数处理完后执行的中间件方法都是倒序执行)

    返回值:

      返回一个None时,表示当前中间件的process_exception方法并没有对异常进行处理,而是将该异常交给下一个执行该方法的中间件。如果没有任何一个中间件对异常进行处理,那么django默认就会将异常抛出在终端显示;

      返回一个响应对象时,表示当前中间件已经对该异常进行了处理,后续的中间件不再执行该方法。后续中间件直接执行process_response方法。

  5、process_template_response(self, request, response)

    作用:处理视图函数中返回的TemplateResponse对象

    触发条件:视图函数中返回的对象是TemplateResponse对象,执行时间在视图函数之后,也就是在process_request和process_view之后,且在process_response之前。如果视图中出现异常则不执行该方法。(出现异常会执行process_exception)

    执行顺序:按照中间件注册的先后顺序,倒序执行

    参数:

      request是一个请求对象,和视图函数接收的是同一个对象。(可以打印它们的id值验证)

      response是视图函数返回的TemplateResponse对象

    返回值:

      必须返回一个response对象,否则报错

    

    补充:render 和 TemplateResponse:

      render方法内部实现了模板文件的相应字符串的替换功能,返回值就是一个替换过字符串的HttpResponse对象。也就是说再视图函数处理阶段对应的数据已经成型了。

      而TemplateResponse可以根据不同的需要,在中间件的process_template_response阶段对相应的模板和数据进行处理

      例如:

        在该阶段可以修改指定模板文件或者数据字典中的数据  

          response.template_name = 'base.html'
          response.context_data = {}

      还可以实现:

        1、根据不同设备(PC、手机)返回不同模板文件(响应式布局则不需要考虑)

        2、对于多个不同的模板文件需要使用到同一份数据,只需要在该方法内获取到需要的数据即可实现

  总结:

    这五个方法的执行的先后顺序:

      process_request——>process_view——>process_exception、process_template_response——>process_response

最新文章

  1. (转)ArcGIS制图技巧
  2. 【原】javascript执行环境及作用域
  3. Mysql 全文索引
  4. STL之stack栈
  5. session共享
  6. js confirm用法
  7. ADO.NET访问SQL Server调用存储过程带回参
  8. JavaScript(class0526)
  9. Java之反射的应用
  10. 浙江大学PAT上机题解析之1015. 德才论 (25)
  11. (转)Autotrace工具使用——小工具,大用场
  12. table边框不显示
  13. Qt 5.2.0 和 VS 2012集成
  14. unity3d教程动态创建简单平面地形
  15. linux下让irb实现代码自动补全的功能
  16. PHPCMS V9 添加二级导航
  17. bzoj4337: BJOI2015 树的同构 树哈希判同构
  18. prototype和_proto_
  19. XSS小游戏通关Writeup
  20. Spring Security编程模型

热门文章

  1. Java编程系列文章序言
  2. 理解Java中的final关键字
  3. springboot之logback配置
  4. 两年银行经验的阿里、头条社招面经分享(已拿offer)
  5. lombok使用(给自己看的,只为不要忘记自己用过的技术)
  6. 刷题[WUSTCTF2020]CV Maker
  7. Java基础——克隆
  8. Spring循环依赖的问题
  9. Java知识系统回顾整理01基础04操作符06三元运算符
  10. C++中cout和cerr