ThinkPHP6的level参数是日志级别白名单,仅过滤已进入管道的日志;真正决定日志是否写入的是channels.file.path是否有效、channels.file.close是否为false、default通道是否指向file,以及全局close开关。

ThinkPHP6 的 level 参数控制哪些日志级别会被记录,但它**不直接决定日志是否写入文件或是否生效**——真正起作用的是日志通道(如 channels.file)是否启用、路径是否可写、以及全局开关是否关闭。
level 是过滤器,不是开关
level 配置在 config/log.php 中,本质是日志“白名单”。它只对已进入日志管道的日志做筛选:
- 设为
['error', 'warning']→ 只保留 error 和 warning 级别,Log::info()不会写入 - 设为空数组
[]→ 记录所有级别(debug/info/sql/warning/error 等) - 包含
'sql'→ 才可能记录 SQL 语句(但还需database.logger.sql => true和log.level ≥ debug)
常见 level 组合与用途
不同场景推荐的 level 设置:
-
开发调试:
['debug', 'info', 'sql', 'warning', 'error']—— 全量捕获,便于排查逻辑和 SQL -
生产环境:
['warning', 'error', 'critical']—— 避免日志爆炸,聚焦异常 -
审计 SQL: 必须含
'sql',且确保database.logger.sql => true和log.level包含debug或更高(因为 sql 日志内部按 debug 级别投递) -
静默运行: 设为
[]并配合'close' => true可彻底禁用(但注意:后者优先级更高)
容易踩坑的细节
仅改 level 很可能没效果,必须同步检查:
-
channels.file.close是否为false(默认是 false,但有人会误设为 true) -
channels.file.path是否有效 —— 空值时 fallback 到runtime/log/,但该目录必须存在且 PHP 进程有写权限 -
default通道是否指向file;若设为'socket'或'none',level 再全也无日志落地 - 使用 Swoole/RoadRunner 时,
runtime/log/下的文件需手动查看,不会实时刷屏
SQL 日志要额外加一层条件
哪怕 level 包含 'sql',若没开启数据库日志开关,SQL 仍不会进日志:
- TP6.1+:确认
config/database.php中'logger' => ['sql' => true] - 旧版 TP6:检查是否有
'log_sql' => true - 同时
log.level至少含debug(因为 SQL 日志内部以 debug 级别触发)
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











