中间件的认识

一、django的请求过程

  • 1、图解

    django请求过程

  • 2、文字解说

    • 1.用户在客户端(浏览器)请求,http解析域名到wsgi服务器(就是socket端)将用户数据进行初步封装,然后交给web服务器(djangoflask)类的框架
    • 2.首先进入中间件中,中间件主要作用是对wsgi封装的数据进行校验及添加其它的信息
    • 3.通过中间件后就会路由匹配,查找到对应的视图类或者视图函数
    • 4.视图函数或者类会根据内在逻辑使用model进行页面渲染
    • 5.视图类渲染完成后,返回给中间件,中间件可能进一步添加点内容返回给客户端
    • 6.最后通过wsgi封装能被浏览器识别的内容返回给客户端

二、关于中间件的理解

  • 1、关于中间件的认识官网
  • 2、从官网的介绍中间件是:中间件是Django请求/响应处理的钩子框架。它是一个轻巧的低级"插件"系统,用于全局改变Django的输入或输出。这里说的输入是指request,输出是指response

三、django中中间件的介绍

  • 1、只有放在settings.pyMIDDLEWARE_CLASSES里面的中间件才算是激活了,才有效果
  • 2、创建项目自带的中间件

    MIDDLEWARE_CLASSES = (
        'django.middleware.security.SecurityMiddleware',
        'django.contrib.sessions.middleware.SessionMiddleware',
        'django.middleware.common.CommonMiddleware',
        'django.middleware.csrf.CsrfViewMiddleware',
        'django.contrib.auth.middleware.AuthenticationMiddleware',
        'django.contrib.auth.middleware.SessionAuthenticationMiddleware',
        'django.contrib.messages.middleware.MessageMiddleware',
        'django.middleware.clickjacking.XFrameOptionsMiddleware',
    )
    
  • 3、中间件排序是有要求的,执行顺序是从上到下的参考文档

四、温习python的反射导包机制

  • 1、demo的目录结构

    test
      foo
        __init__.py
        foo.py
      __init__.py
      test.py
    
  • 2、foo.py的代码

    name = '张三'
    
    def foo():
        return 'foo函数'
    
  • 3、test.py的代码

    import importlib
    # 利用反射查找到文件,实现导包
    foo = importlib.import_module('foo.foo')
    
    print(foo.name)
    # 函数的调用
    print(foo.foo())
    
  • 4、django的中间件就是利用反射的机制实现导包的,手动导包如下:

    from django.middleware.clickjacking import XFrameOptionsMiddleware
    

五、自定义中间件

  • 1、中间件要继承一个类MiddlewareMixin

    from django.utils.deprecation import MiddlewareMixin
    
  • 2、中间件要实现的方法有:主要是process_requestprocess_response

    • process_request(self,request)
    • process_view(self, request, view_func, view_args, view_kwargs)
    • process_template_response(self,request,response)
    • process_exception(self, request, exception)
    • process_response(self, request, response)
  • 3、自定义中间件的示例

    from django.utils.deprecation import MiddlewareMixin
    
    class Md1(MiddlewareMixin):
    
        def process_request(self, request):
            print('md1的request方法')
    
        def process_response(self, request, response):
            print('md1的response方法')
            return response
    
  • 4、在settings.py中配置

    MIDDLEWARE = [
        ...
        'middle.md1.Md1',
    ]
    

六、关于中间件中几个函数的认识

  • 1、process_request(self,request)客户端请求进入django服务器的过程

    • 1.参数request和视图函数或者视图类中的request一样的,可以获得到session的参数的
    • 2.当返回值为None(不写返回值python中默认返回None)的时候会按照顺序执行下一个中间件中的process_request函数,以此类推
    • 3.当返回HttpResponse对象的时候,就不继续执行到视图类中,直接返回HttpResponse来渲染页面
    • 4.中间件的process_request方法是在执行视图函数之前执行的
    • 5.当配置多个中间件时,会按照MIDDLEWARE中的注册顺序,也就是列表的索引值,从前到后依次执行的
    • 6.不同中间件之间传递的request都是同一个对象
  • 2、process_response(self, request, response)响应返回给客户端

    • 1.request参数和上面process_request中的一样
    • 2.response是视图函数返回的HttpResponse对象。该方法的返回值也必须是HttpResponse对象
    • 3.如果自己定义返回HttpResponse对象的时候就会取代视图中返回的response
    • 4.process_response函数是在视图函数或者视图类之后执行的
    • 5.如果多个中间件的时候执行顺序也是根据先注册的先执行
  • 3、process_view(self, request, view_func, view_args, view_kwargs)

    • 1.Django会在调用视图函数之前调用process_view方法,但是是在process_request之后调用
    • 2.request参数和上面介绍的一样
    • 3.view_funcDjango即将使用的视图函数(它是实际的函数对象,而不是函数的名称作为字符串)
    • 4.view_args是将传递给视图的位置参数的列表
    • 5.view_kwargs是将传递给视图的关键字参数的字典。
    • 6.view_argsview_kwargs都不包含第一个视图参数(request
    • 7.如果返回None,Django将继续处理这个请求,执行任何其他中间件的process_view方法,然后在执行相应的视图
    • 8.如果返回一个HttpResponse对象,Django不会调用适当的视图函数。它将执行中间件的process_response方法并将应用到该HttpResponse并返回结果。
  • 4、process_exception(self, request, exception)当视图函数或者类发生异常的时候才会触发

    • 1.requestHttpRequest对象
    • 2.exception是视图函数异常产生的Exception对象
    • 3.触发条件这个方法只有在视图类中发生异常的时候才会触发执行
    • 4.如果返回None,则交给下一个中间件的process_exception方法来处理异常
    • 5.如果返回HttpResponse对象,Django将调用模板和中间件中的process_response方法,并返回给浏览器,否则将默认处理异常
    • 6.如果视图函数中无异常,process_exception方法不执行
  • 5、process_template_response(self, request, response)

    • 1.request是一个HttpRequest对象
    • 2.responseTemplateResponse对象(由视图函数或者中间件产生)
    • 3.process_template_response是在视图函数执行完成后立即执行,但是它有一个前提条件,那就是视图函数返回的对象有一个render()方法(或者表明该对象是一个TemplateResponse对象或等价方法)

七、使用中间件做登陆拦截的案例

  • 1、视图类

    from django.shortcuts import render, redirect
    
    # Create your views here.
    
    from django.views import View
    
    from .models import UserModel
    
    class LoginView(View):
        """
        用户登陆视图类
        """
    
        def get(self, request, *args, **kwargs):
            return render(request, 'login.html')
    
        def post(self, request, *args, **kwargs):
            username = request.POST.get('username', None)
            password = request.POST.get('password', None)
            if username and password:
                user = UserModel.objects.filter(username=username, password=password).first()
                if user:
                    request.session['user'] = user
                    # 获取登陆前的url
                    next_url = request.GET.get('next', None)
                    if next_url:
                        return redirect(next_url)
                    else:
                        return redirect('index')
                else:
                    return redirect('/login/')
            else:
                return redirect('/login/')
    
    class IndexView(View):
        """
        主页
        """
    
        def get(self, request, *args, **kwargs):
            return render(request, 'index.html', locals())
    
  • 2、中间件

    from django.utils.deprecation import MiddlewareMixin
    from django.shortcuts import redirect
    
    class AuthMD(MiddlewareMixin):
        def process_request(self, request):
            user = request.session.get('user')
            if user:
                pass
            else:
                return redirect('/login/')
    

results matching ""

    No results matching ""