一、简述
0、中间件之重:django中间件是整个django项目的门关。
1、请求进来:需要先经过中间件才能到达后端。
2、响应发出:需要再经过中间件才能回给用户。
二、django自带的七个中间件
1、settings.py:
MIDDLEWARE = [ 'django.middleware.security.SecurityMiddleware', 'django.contrib.sessions.middleware.SessionMiddleware', 'django.middleware.common.CommonMiddleware', 'django.middleware.csrf.CsrfViewMiddleware', 'django.contrib.auth.middleware.AuthenticationMiddleware', 'django.contrib.messages.middleware.MessageMiddleware', 'django.middleware.clickjacking.XFrameOptionsMiddleware', ]
三、自定义中间件的准备
1、文件夹:在主文件夹或app文件夹下创建一个任意命名的文件夹,如,custom_middlewares。
2、py文件:在custom_middlewares文件夹下创建一个任意命名的py文件,如,ex_middlewares.py。
3、必用模块:在ex_middlewares.py中,先导入模块:
from django.utils.deprecation import MiddlewareMixin
4、创建类:在ex_middlewares.py中新建类,该类必须继承MiddlewareMixin 。
5、注册生效:定义好的类,需要将类的路径以字符串的形式,加入settings.py中django自带中间件所在的列表完成注册,方可生效。
四、自定义类的方法
0、基本方法:django封装好了5个方法用于创建自定义类,这5个方法并非限定需要一起使用,根据需求,选择使用其中若干个即可。
1、def process_request(self, request):
①请求来的时候最先经过的就是process_request方法。
②多个中间件的process_request方法的遍历顺序是settings.py中书写顺序自上而下。
③没有定义process_request方法的中间件在这个环节会被跳过。
④若某个中间件的process_request方法返回了HttpResponse对象,那在这个中间件处不会再向下走后续的中间件和视图层,而是直接跳至该中间件的process_response,再依次走完后续的process_response。
2、def process_response(self, request, response):
①响应走的时候最后经过的就是process_response方法。
②多个中间件的process_response方法的遍历顺序是settings.py中书写顺序自下而上。
③没有定义process_response方法的中间件在这个环节会被跳过。
④process_response方法必须返回response参数或另外定义的HttpResponse对象。
3、def process_view(self, request, *args, **kwargs):
①通过process_request方法之后,在执行视图函数之前会经过process_view方法。
②多个中间件的process_view方法的遍历顺序是settings.py中书写顺序自上而下。
③若某个中间件的process_view方法返回了HttpResponse对象,则后续不再经过视图层,而是直接跳至最后一个中间件的process_response,再依次走完后续的process_response。
4、def process_template_response(self, request, response):
①在视图函数中定义render方法,该方法需返回HttpResponse对象,将该对象再作为视图函数返回的HttpResponse对象的render属性。
②带有render属性的HttpResponse对象进入process_template_response方法中,且由该方法再返回,才会触发该方法的执行。
③多个中间件的process_template_response方法的遍历顺序是settings.py中书写顺序自下而上。
5、def process_exception(self, request, exception):
①在视图层出现了异常时才会触发process_exception方法。
②多个中间件的process_xception方法的遍历顺序是settings.py中书写顺序自下而上。
五、csrf跨站请求伪造校验
1、简述:给一个可以提交post请求的页面绑定一个随机且唯一的标识码,当页面提交post请求给后端时,后端会先校验该标识码,若匹配则正常进行后续步骤,若不匹配则直接拒绝访问,并抛出403响应状态码。
2、标识码匹配机制:post请求经过csrf中间件时,该中间件会提取标识码进行校验,视结果放行或拒绝继续访问。
3、form表单绑定标识码:在form表单内书写{% csrf_token %}。
4、ajax请求绑定标识码的三种方式:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> {% load static %} <script src="{% static 'jQuery351.js' %}"></script> <script src="{% static 'csrf_tag.js' %}"></script> <link rel="stylesheet" href="{% static 'Bootstrap337/css/bootstrap.min.css' %}"> <script src="{% static 'Bootstrap337/js/bootstrap.min.js' %}"></script> </head> <body> {#{% csrf_token %}#} <input type="button" value="提交" id="d1"> post后显示:<input type="text" id="d2"> <script> let $d1Ele = $('#d1') let $d2Ele = $('#d2') $d1Ele.on('click', function () { $.ajax({ url: '', type: 'post', {# 方式一 依然要先书写{% csrf_token %},再通过默认储存标识码的标签获取标识码 #} {# data:{'name': 'tom', 'csrf_tag': $('[name=csrfmiddlewaretoken]').val()},#} {# 方式二 利用模板语法获取标识码 #} {# data: {'name':'tom', 'csrfmiddlewaretoken': '{{ csrf_token }}'},#} {# 方式三 通过导入js模块,声明ajax的post请求默认携带标识码 #} data: {'name':'tom'}, success:function (args) { $d2Ele.val(args) } }) }) </script> </body> </html>
六、csrf相关装饰器
1、必用模块:
from django.views.decorators.csrf import csrf_protect,csrf_exempt from django.utils.decorators import method_decorator
2、csrf_protect:全站无需校验标识码的背景下,特殊声明需要校验的视图函数。
①给FBV绑定:在函数上方直接@csrf_protect。
②给CBV绑定:给CBV绑定装饰器的三种法法都适用。
3、csrf_exempt:全站需要校验标识码的背景下,特殊声明无需校验的视图函数。
①给FBV绑定:在函数上方直接@csrf_exempt。
②给CBV绑定:只能用给dispatch绑定的方法。