django入门进阶09_中间件

django的中间件(middleware)是一个轻量级的插件系统,在django中的请求和响应中,可以利用中间件干预视图的请求和响应。

如何启用中间件

若要启用中间件组件,请将其添加到 Django 配置文件settings.py的 MIDDLEWARE 配置项列表中。

五大钩子函数

传统方式自定义中间件其实就是在编写五大钩子函数:

1
2
3
4
5
process_request(self,request)
process_response(self, request, response)
process_view(self, request, view_func, view_args, view_kwargs)
process_exception(self, request, exception)
process_template_response(self,request,response)

可以实现其中的任意一个或多个!

中间件的顺序问题

从上一部分可以看出,中间件是有多个的,既然有多个必然涉及到优先级或顺序问题,顺序大体上符合先来后到(不存在插队类型的优先级,要么正序,要么逆序,不能插队跳跃执行)
MIDDLEWARE 的顺序很重要,具有先后关系,因为有些中间件会依赖其他中间件。例如: AuthenticationMiddleware 需要在会话中间件中存储的经过身份验证的用户信息,因此它必须在 SessionMiddleware 后面运行 。
在请求阶段,调用视图之前,Django 按照定义的顺序执行中间件 MIDDLEWARE,自顶向下。
你可以把它想象成一个洋葱:每个中间件类都是一个“皮层”,它包裹起了洋葱的核心–实际业务视图。如果请求通过了洋葱的所有中间件层,一直到内核的视图,那么响应将在返回的过程中以相反的顺序再通过每个中间件层,最终返回给用户。
如果某个层的执行过程认为当前的请求应该被拒绝,或者发生了某些错误,导致短路,直接返回了一个响应,那么剩下的中间件以及核心的视图函数都不会被执行


图上一部分标识错误了,已经标注出来(view的执行在路由后,view视图函数前)

更为详细的执行流

可以做什么

Cache:缓存中间件
如果启用了该中间件,Django会以CACHE_MIDDLEWARE_SECONDS 配置的参数进行全站级别的缓存。

Common:通用中间件
禁止DISALLOWED_USER_AGENTS中的用户代理访问服务器
自动为URL添加斜杠后缀和www前缀功能。如果配置项 APPEND_SLASH 为True ,并且访问的URL 没有斜杠后缀,在URLconf中没有匹配成功,将自动添加斜杠,然后再次匹配,如果匹配成功,就跳转到对应的url。 PREPEND_WWW 的功能类似。
为非流式响应设置Content-Length头部信息。

GZip:内容压缩中间件
用于减小响应体积,降低带宽压力,提高传输速度。
该中间件必须位于其它所有需要读写响应体内容的中间件之前。

Locale:本地化中间件
用于处理国际化和本地化,语言翻译。

Message:消息中间件
基于cookie或者会话的消息功能,比较常用。

Security:安全中间件

Site:站点框架。
这是一个很有用,但又被忽视的功能。
它可以让你的Django具备多站点支持的功能。
通过增加一个site属性,区分当前request请求访问的对应站点。
无需多个IP或域名,无需开启多个服务器,只需要一个site属性,就能搞定多站点服务。 `

Authentication:认证框架
Django最主要的中间件之一,提供用户认证服务。

CSRF protection:提供CSRF防御机制的中间件

X-Frame-Options:点击劫持防御中间件

可能遇到问题

全局异常object() takes no parameters
错误信息如下

1
2
3
4
5
#  File "C:\python\lib\site-packages\django\core\handlers\wsgi.py", line 151, in __init__
# self.load_middleware()
# File "C:\python\lib\site-packages\django\core\handlers\base.py", line 82, in load_middleware
# mw_instance = middleware(handler)
# TypeError: object() takes no parameters

出错原始代码:

1
2
3
4
# from django.http import HttpResponse
# class MyException(object):
# def process_exception(request,response, exception):
# return HttpResponse(exception.message)

正确代码1:

1
2
3
4
5
6
7
8
9
# class MyException(object):
# def __init__(self, get_response):
# self.get_response = get_response
#
# def __call__(self, request):
# return self.get_response(request)
#
# def process_exception(self, request, exception):
# return HttpResponse(exception)

正确代码2

1
2
3
4
5
6
from django.http import HttpResponse
from django.utils.deprecation import MiddlewareMixin

class MyException(MiddlewareMixin):
def process_exception(self, request, exception):
return HttpResponse(exception)

兼容 Django新版本和旧版本

1
2
3
4
5
6
7
8
9
10
11
try:
from django.utils.deprecation import MiddlewareMixin # Django 1.10.x
except ImportError:
MiddlewareMixin = object # Django 1.4.x - Django 1.9.x

class SimpleMiddleware(MiddlewareMixin):
def process_request(self, request):
pass

def process_response(request, response):
pass

参考

Django(十二):Django框架中的middleware中间件:https://blog.csdn.net/qq_40558166/article/details/102467833
Django框架全面讲解 – 中间件(MiddleWare):https://blog.csdn.net/shentong1/article/details/78829599
Django 中间件:https://www.runoob.com/django/django-middleware.html
Django之Middleware(中间件):https://www.cnblogs.com/Alexephor/p/11272839.html
Django中间件:https://www.liujiangblog.com/blog/45/
Django 中间件:https://code.ziqiangxuetang.com/django/django-middleware.html
Python Django,中间件,中间件函数,全局异常处理:https://blog.csdn.net/houyanhua1/article/details/85028983
django全局异常捕获保存和输出,logger配置:https://hhyo.github.io/2018/04/16/django-traceback/
django中间件修改,以及TypeError: object() takes no parameters的异常处理:https://my.oschina.net/u/4374968/blog/3899317

django系列
django入门进阶01学习笔记01
django入门进阶02学习笔记02
django入门进阶03学习笔记03
django入门进阶04学习笔记04
django入门进阶05快捷复习手册
django入门进阶06静态文件和模板
django入门进阶07用户模块与权限系统
django入门进阶08数据库事务
django入门进阶09中间件
django入门进阶10部署上线(nginx,uwsgi,supervisor)
django入门进阶11websocket
django入门进阶12信号
django入门进阶13异常之makemigrations

Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×