十年匠心定制 · 商业建站与技术教学双线并行 咨询热线:400-886-1026 service@lmnt.cn
ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

Sanic Extensions 后台日志记录器(Background Logger)实战指南:配置、原理与性能优化

Sanic Extensions 后台日志记录器(Background Logger)实战指南:配置、原理与性能优化 Sanic Extensions 后台日志记录器Background Logger实战指南配置、原理与性能优化【免费下载链接】sanicAccelerate your web app development | Build fast. Run fast.项目地址: https://gitcode.com/gh_mirrors/sa/sanicSanic Extensions 提供的后台日志记录器Background Logger将日志消息从请求处理主进程中剥离通过multiprocessing.Queue交由独立后台进程统一写入日志处理器从而在不改变现有日志配置的前提下降低日志操作对请求性能的影响。本文以 Sanic 官方文档《Background logger》为骨架结合 Sanic 框架源码与相关指南完整讲解该功能的启用方式、底层工作流程、配置参数及其适用前提帮助你判断何时使用它、如何正确配置它。适用版本与前置条件后台日志记录器是 Sanic Extensions 提供的功能启用它需要同时满足两个版本要求Sanic 22.9Sanic Extensionssanic-ext 22.9同时它有一个关键的运行环境限制必须运行在非单进程模式下。也就是说应用必须由 Worker Manager 管理、以多进程方式运行而不能使用--single-process启动。原因在于该功能依赖一个独立的后台进程来消费日志队列而单进程模式下 Manager 不会运行自然也就没有承载该功能的进程环境。如果你还不熟悉多进程模式可以查阅 Worker Manager 指南 了解进程模型关于如何进入单进程模式该文档的 Single process mode 一节给出了三种方式# CLI 方式 sanic path.to.server:app --single-process# 编程方式一 if __name__ __main__: app.run(single_processTrue)# 编程方式二 if __name__ __main__: app.prepare(single_processTrue) Sanic.serve_single()需要说明的是多进程模式下 Sanic 默认使用spawn启动方式因此如果你不是通过 CLI 运行请务必将执行代码包裹在if __name__ __main__:块内否则每个子进程都会重新执行全局作用域代码可能引发端口占用等ServerError。为什么需要后台日志记录器日志记录本身是一种相对廉价的操作但在高并发场景下每次请求都要格式化并写入访问日志累积起来会成为不容忽视的开销。正如 Sanic 官方日志指南 所指出的当请求量很高且性能敏感时访问日志的耗时会被放大官方建议生产环境可考虑app.run(debugFalse, access_logFalse)或把访问日志交由 nginx 等反向代理处理。后台日志记录器提供了另一种思路把日志写出的工作整体移出请求进程。请求进程只负责把日志消息投递到队列入队操作远快于真正的 I/O 写出由后台进程负责读取队列并调用原有日志处理器完成最终输出。这样可以在保留完整日志能力的前提下潜在获得性能收益。启用方式一步配置开箱即用后台日志记录器是默认关闭的需要显式选择启用。启用方式非常简洁只需在 Sanic 应用配置中打开一个开关app.config.LOGGING Trueapp.config是 Sanic 应用的标准配置对象Sanic Extensions 的配置与 Sanic 本身的配置方式完全一致参见 Sanic Extensions 配置指南。实际上Sanic Extensions 从 v21.12 起会在应用初始化时自动挂载只要环境中安装了sanic-ext无需额外代码即可生效。这一自动挂载逻辑在 Sanic 侧由 sanic/application/ext.py 中的setup_ext函数实现它通过import_module(sanic_ext)检测扩展是否安装并用Ext(app, **kwargs)完成初始化对应的开关是app.config.AUTO_EXTEND默认为True见 sanic/config.py。安装方式有两种# 推荐与 Sanic 一起安装 pip install sanic[ext]# 单独安装 pip install sanic-ext工作原理QueueHandler 后台进程启用后扩展会执行以下操作来完成日志的异步化整个过程对开发者几乎透明创建multiprocessing.Queue用于在请求进程与后台日志进程之间传递日志记录。移除默认 Sanic 日志器上的全部处理器所谓默认 Sanic 日志器即 Sanic 开箱提供的五个日志器详见下文与默认日志配置的关系。替换为QueueHandlerPython 标准库logging.handlers.QueueHandler的作用是把每一条日志记录封装后放入队列而不做任何真正的 I/O。后台进程消费队列后台进程持续从队列读取日志记录并把它们转交给原来就配置好的日志处理器执行实际的写出。当一条消息被记录时处理链路为请求进程中的QueueHandler将日志记录放入队列 → 后台进程从队列取出 → 交给原本的处理器如控制台StreamHandler、文件处理器等完成输出。由于最终写出仍由原有处理器完成你依然可以按照常规方式配置日志而它应该开箱即用——这正是该设计的核心价值日志配置的定制方式不发生任何变化只是执行的进程位置变了。一个值得注意的细节由于 Sanic 默认使用spawn方式启动子进程见 Worker Manager 指南后台日志进程与请求进程之间不能共享内存中的普通对象multiprocessing.Queue正是跨进程安全传递日志记录的标准手段。配置项详解后台日志记录器提供两个配置项均通过app.config设置| 配置键 | 类型 | 默认值 | 说明 | |--|--|--|--| |LOGGING|bool|False| 是否启用后台日志记录器 | |LOGGING_QUEUE_MAX_SIZE|int|4096| 队列最大容量超过该值时新消息将被拒绝 |配置示例app Sanic(MyApp) # 启用后台日志记录器 app.config.LOGGING True # 可选调整队列容量默认 4096 app.config.LOGGING_QUEUE_MAX_SIZE 8192关于LOGGING_QUEUE_MAX_SIZE的取值可以结合其语义判断队列容量越大越能缓冲日志洪峰避免消息被拒绝但过大的队列也会占用更多内存。如果应用在极端峰值下频繁丢弃日志可以适当调大该值如果对内存敏感则应保持默认或调小。与默认日志配置的关系后台日志记录器操作的对象是 Sanic 的默认日志器。理解这一点有助于你预判启用后的行为。Sanic 开箱即用提供五个日志器详见 日志最佳实践指南| 日志器名称 | 用途 | |--|--| |sanic.root| 记录内部消息 | |sanic.error| 记录错误日志 | |sanic.access| 记录访问日志 | |sanic.server| 记录服务端日志 | |sanic.websockets| 记录 WebSocket 日志 |这些日志器在 sanic/log.py 中统一导出可从sanic.log导入from sanic.log import logger, error_logger, access_logger, server_logger, websockets_logger logger.info(This is a root logger message)默认的日志配置存放在sanic.log.LOGGING_CONFIG_DEFAULTS中包含console、error_console、access_console三个StreamHandler以及AutoFormatter/AutoAccessFormatter两个格式化器。当后台日志记录器启用后上述日志器上的处理器会被QueueHandler替换而原有的处理器配置被保留并转移到后台进程中使用——这正是日志配置照常工作的机制所在。如果你通过log_config参数传入自定义日志配置或直接修改LOGGING_CONFIG_DEFAULTS这些自定义处理器同样会生效因为它们是在后台进程中被调用的原处理器。使用建议与注意事项综合以上原理在实际使用中应关注以下几点确认运行在多进程模式使用 CLIsanic path.to.server:app默认即多进程编程方式启动时确保未设置single_processTrue。日志配置照旧无论是使用默认配置、传入log_config还是像下面这样替换默认格式化器都不需要因为启用后台日志而额外改动from sanic.log import LOGGING_CONFIG_DEFAULTS LOGGING_CONFIG_DEFAULTS[formatters][generic][class] sanic.logging.formatter.ProdFormatter LOGGING_CONFIG_DEFAULTS[formatters][access][class] sanic.logging.formatter.ProdAccessFormatter app Sanic(logging_example, log_configLOGGING_CONFIG_DEFAULTS) app.config.LOGGING True结合场景评估收益后台日志记录器的价值在于把日志 I/O 移出请求热路径适用于日志量大的生产环境如果应用日志量很小收益有限。它也可以与关闭访问日志access_logFalse等优化手段组合使用。接受消息丢弃的可能性当队列达到LOGGING_QUEUE_MAX_SIZE上限时新消息会被拒绝这是设计内行为——通过有界队列防止内存无限增长代价是极端压力下可能丢失日志需根据业务对日志完整性的要求权衡队列大小。小结后台日志记录器是 Sanic Extensions 提供的一项低成本、低侵入的性能优化手段一行配置即可启用日志配置方式完全不变底层通过multiprocessing.Queue与QueueHandler的组合把日志写出从请求进程迁移到独立后台进程。它要求sanic22.9、sanic-ext22.9且运行于多进程模式两个配置项LOGGING与LOGGING_QUEUE_MAX_SIZE足以覆盖绝大多数使用场景。如果你正在为高并发 Sanic 应用优化请求路径上的开销并且不希望放弃完整的日志能力这个功能值得加入你的工具箱。【免费下载链接】sanicAccelerate your web app development | Build fast. Run fast.项目地址: https://gitcode.com/gh_mirrors/sa/sanic创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表