一、中间件

介绍

在 Django 中,中间件(Middleware)是一组轻量级、底层的插件系统,用于全局地改变 Django 的输入和输出。中间件可以在请求被处理之前和响应返回之前执行代码,从而实现各种功能,例如跨域资源共享(CORS)、用户认证、日志记录等。

激活中间件

若要激活中间件,需要添加到settings.MIDDLEWARE

  • 每个中间件组件由字符串表示:指向中间件工厂类的完整 Python 路径。
  • 需求注意中间件的添加顺序。因为中间件有执行顺序,而且中间件之间可能有依赖关系。
  • 中间件的全局执行顺序
    • 请求阶段:按settings.MIDDLEWARE从上到下的顺序执行。
    • 视图处理:请求到达视图函数。
    • 响应阶段:按settings.MIDDLEWARE从下到上的顺序执行。
MIDDLEWARE = [
"corsheaders.middleware.CorsMiddleware", # CORS跨域支持
"django.middleware.security.SecurityMiddleware",
"django.contrib.sessions.middleware.SessionMiddleware",
"django.middleware.locale.LocaleMiddleware", # I18N多语言支持,注意放置顺序
"django.middleware.common.CommonMiddleware",
"django.middleware.csrf.CsrfViewMiddleware",
"django.contrib.auth.middleware.AuthenticationMiddleware",
"django.contrib.messages.middleware.MessageMiddleware",
"django.middleware.clickjacking.XFrameOptionsMiddleware",
# "myapp_system.operate_log.services.OperateLogMiddleware", # 操作日志开关:如果数据库磁盘IO性能一般,建议关闭
]

生命周期

中间件生命周期

  • 请求阶段:process_request(request):在视图函数被调用之前执行,用于处理请求。如果返回 HttpResponse 对象,则后续的中间件和视图不会被调用,直接返回响应。
  • 视图阶段:process_view(request, view_func, view_args, view_kwargs):在视图函数被调用之前执行,可以用于根据视图函数的参数或请求信息进行额外处理。
  • 响应阶段:process_response(request, response):在视图函数返回响应后执行,用于处理响应对象,可以修改响应内容或响应头。
  • 异常阶段:process_exception(request, exception):当视图函数抛出异常时执行,用于处理异常并返回一个 HttpResponse 对象。

内置中间件示例

  • django.contrib.auth.middleware.AuthenticationMiddleware:Django内置的认证中间件,实现将 user 属性添加到每个传入的 HttpRequest 对象中,表示当前已登录的用户
class AuthenticationMiddleware(MiddlewareMixin):
def process_request(self, request):
if not hasattr(request, "session"):
raise ImproperlyConfigured(
"The Django authentication middleware requires session "
"middleware to be installed. Edit your MIDDLEWARE setting to "
"insert "
"'django.contrib.sessions.middleware.SessionMiddleware' before "
"'django.contrib.auth.middleware.AuthenticationMiddleware'."
)
request.user = SimpleLazyObject(lambda: get_user(request))

二、自定义中间件

中间件钩子函数

process_view()中间件钩子函数

  • 语法:process_view(request, view_func, view_args, view_kwargs)
  • 调用顺序:process_view() 只在 Django 调用视图前被调用。
  • 返回
    • 如果它返回 None ,Django 将继续处理这个请求,执行任何其他的 process_view() ,然后执行相应的视图。
    • 如果它返回 HttpResponse 对象,Django 不会去影响调用相应的视图;它会将响应中间件应用到 HttpResponse 并返回结果。

基于类的中间件

基于类的自定义中间件格式

  • 语句response = self.get_response(request),将__call__()方法中的代码分为两部分
class SimpleMiddleware:
def __init__(self, get_response):
# 执行一次性配置和初始化工作
self.get_response = get_response def __call__(self, request):
# 每个请求调用一次,在视图函数被调用之前执行 response = self.get_response(request) # 每个请求调用一次,在视图函数被调用之后执行
return response

三、实战案例

操作日志功能

通过自定义中间件,实现Django操作日志记录功能

  • 第1步:定义类OperateLogMiddleware,方法__init__()中,添加exclude_urls排除不需要记录的URL的列表,和一个字典log_data用于临时存放日志信息。

  • 第2步:在执行视图函数之前,向字典log_data记录请求方法、请求路径、操作IP、浏览器Agent信息等

  • 第3步:在执行视图函数之后,向字典log_data记录用户ID、业务状态码、HTTP状态码、响应数据、返回结果和执行时间

  • 第4步:process_view()中间件钩子函数中,向字典log_data记录视图名称、Action名称、资源ID

第5步:字典log_data记录的操作日志信息,通过Celery异步任务,写入数据库。实现操作日志记录功能。

参考:完整代码地址

参考资料


您正在阅读的是《Django从入门到实战》专栏!关注不迷路~

Django实战:自定义中间件实现全链路操作日志记录的更多相关文章

  1. 微软企业库5.0 学习之路——第九步、使用PolicyInjection模块进行AOP—PART4——建立自定义Call Handler实现用户操作日志记录

    在前面的Part3中, 我介绍Policy Injection模块中内置的Call Handler的使用方法,今天则继续介绍Call Handler——Custom Call Handler,通过建立 ...

  2. 基于SqlSugar的开发框架循序渐进介绍(8)-- 在基类函数封装实现用户操作日志记录

    在我们对数据进行重要修改调整的时候,往往需要跟踪记录好用户操作日志.一般来说,如对重要表记录的插入.修改.删除都需要记录下来,由于用户操作日志会带来一定的额外消耗,因此我们通过配置的方式来决定记录那些 ...

  3. Winform开发框架之权限管理系统改进的经验总结(4)-一行代码实现表操作日志记录

    在前面介绍了几篇关于我的权限系统改进的一些经验总结,本篇继续这一系列主体,介绍如何一行代码实现重要表的操作日志记录.我们知道,在很多业务系统里面,数据是很敏感的,特别对于一些增加.修改.删除等关键的操 ...

  4. JS实战 · 复选框全选操作

    思路: 1.获取被选中checkbox,通过checked属性的状态完成: 2.获取被选中的checkbox的value值: 3.求所有value的和sum: 4.定义span区域存储和sum:   ...

  5. Dubbo 全链路追踪日志的实现

    微服务架构的项目,一次请求可能会调用多个微服务,这样就会产生多个微服务的请求日志,当我们想要查看整个请求链路的日志时,就会变得困难,所幸的是我们有一些集中日志收集工具,比如很热门的ELK,我们需要把这 ...

  6. [编码实践]SpringBoot实战:利用Spring AOP实现操作日志审计管理

    设计原则和思路: 元注解方式结合AOP,灵活记录操作日志 能够记录详细错误日志为运营以及审计提供支持 日志记录尽可能减少性能影响 操作描述参数支持动态获取,其他参数自动记录. 1.定义日志记录元注解, ...

  7. springmvc+log4j操作日志记录,详细配置

    没有接触过的,先了解一下:log4j教程 部分内容来:log4j教程 感谢! 需要导入包: log包:log4j-12.17.jar 第一步:web.xml配置 <!-- log4j配置,文件路 ...

  8. Spring Boot分布式系统实践【基础模块构建3.3】注解轻松实现操作日志记录

    日志注解 前言 spring切面的编程,spring中事物处理.日志记录常常与pointcut相结合 * * Pointcut 是指那些方法需要被执行"AOP",是由"P ...

  9. springAOP实现操作日志记录,并记录请求参数与编辑前后字段的具体改变

    本文为博主原创,未经允许不得转载: 在项目开发已经完成多半的情况下,需要开发进行操作日志功能的开发,由于操作的重要性,需要记录下操作前的参数和请求时的参数, 在网上找了很多,没找到可行的方法.由于操作 ...

  10. .Net Core中间件和过滤器实现错误日志记录

    1.中间件的概念 ASP.NET Core的处理流程是一个管道,中间件是组装到应用程序管道中用来处理请求和响应的组件. 每个中间件可以: 选择是否将请求传递给管道中的下一个组件. 可以在调用管道中的下 ...

随机推荐

  1. unigui如何直接显示一个PDF文件【13】

    这个问题有点搞笑. PDF.js v1.9.426 (build: 2558a58d) 信息:Unexpected server response (204) while retrieving PDF ...

  2. cannot resolve unit......

    Just disable Error Insight (Tools -> Options -> Editor Options -> Code Insight, uncheck Err ...

  3. 【Linux】编译用于exynos4412(ARM)的Linux-3.14内核

    [Linux]编译用于exynos4412(ARM)的Linux-3.14内核 零.准备 1.下载 Linux-3.14内核源代码 下载页面:https://www.kernel.org/pub/li ...

  4. emmy断点调试

    package.cpath = package.cpath .. ';C:/Users/Administrator/AppData/Roaming/JetBrains/IntelliJIdea2021 ...

  5. unity prefab

    1.修改prefab原始资源某组件为enabled或disabled,实例如果起初和原始资源是一样的状态那么修改原始资源会作用到实例上,如果发现不一样那么原始资源的修改不会作用到实例上,而且以后都不会 ...

  6. Java并发编程实战-多线程任务执行

    Executor框架与线程池(ThreadPoolExecutor) Executor框架的组成 组件 作用 Executor 基础接口,仅定义execute(Runnable)方法,用于执行任务. ...

  7. 加减法计算在RB中的应用(比如计算库存)(should be equal as integers指令的使用)

    订单测试过程中,对库存的校验是很关键的步骤 下面这个案例即实现对订单前后库存检查.公式计算.结果匹配,输出测试结果.具体脚本如下图 步骤如下: 1.获取订单前的库存 2.订单流程 3.获取订单后的库存 ...

  8. kettle介绍-Step之Return steps metrics

    Return steps metrics转换步骤信息统计介绍 转换步骤信息统计步骤可以用于统计当前转换中的其它步骤信息,包括步骤执行后的输入行数.输入行数.读入行数.更新行数等.此步骤可以直接拖入转换 ...

  9. mac 系统软件推荐

    幕布: https://mubu.com/home 石墨文档: https://shimo.im

  10. 【ROS】4.1 Turtlebot3仿真Waffle循线跟踪

    原视频 本节内容较多,请根据左侧目录针对性阅读. 一.准备工作 这一章我们先用gazebo仿真做,不使用真小车,使用的是Waffle模型. 需要下载的库gazebo-ros.turtlebot3_si ...