ThinkPHP 6 中需通过自定义中间件实现请求日志统计,推荐在 before/after 阶段采集耗时、状态码等信息并写入日志或数据库,注意异步写库、JSON 结构化输出及敏感字段脱敏。

如何在 ThinkPHP 6 中开启并自定义请求日志统计
ThinkPHP 6 默认不记录完整请求日志(如 URL、耗时、状态码),需手动扩展中间件或日志驱动。核心思路是:用中间件拦截请求生命周期,在 before 和 after 阶段采集时间戳与响应信息,再写入日志文件或数据库。
用中间件实现请求耗时与状态码统计(推荐)
这是最轻量、侵入性最小的方式,适合快速上线。注意中间件必须注册为全局中间件,且顺序靠前(确保能捕获所有请求)。
创建中间件:app/middleware/RequestStat.php
namespace app\middleware;
<p>use think\Response;
use think\facade\Log;</p><p>class RequestStat
{
public function before($request)
{
$request->startTime = microtime(true);
$request->startMemory = memory_get_usage();
}</p><pre class="brush:php;toolbar:false;">public function after(Response $response)
{
$time = round((microtime(true) - $request->startTime) * 1000, 2);
$memory = round(($request->startMemory ? memory_get_usage() - $request->startMemory : 0) / 1024, 2);
Log::info(sprintf(
'[%s] %s %s %s %sms %skb %s',
date('Y-m-d H:i:s'),
$request->method(),
$request->url(true),
$response->getCode(),
$time,
$memory,
$request->header('user-agent', 'unknown') ?: 'unknown'
));
}}
注册到 app/middleware.php:
- 确保该中间件在
think\middleware\CheckRequestCache::class之后、其他业务中间件之前 - 不要放在
throttle或auth之后——否则未授权请求可能不触发after - 若使用 Swoole,
microtime(true)仍可靠,但memory_get_usage()在常驻内存模式下意义变弱
如何把请求统计存进数据库而非日志文件
当需要聚合分析(如 QPS、慢请求排行、错误率趋势),写数据库比查日志更高效。关键点:避免阻塞主请求流,建议异步写入或批量缓存后定时刷库。
推荐做法(非事务敏感场景):
- 在
after中构造统计数组,用cache('req_stat_queue', $data, 300)缓存(5 分钟过期) - 单独起一个命令行任务(
php think req:flush),每 30 秒拉取缓存、批量写入sys_request_log表 - 表结构至少含:
id,method,path,status_code,cost_ms,created_at - 避免在
after中直接调用Db::insert()—— 数据库慢或连接失败会导致响应延迟甚至超时
为什么 Log::info() 写出来的日志难以做统计分析
纯文本日志无法直接按字段筛选,比如“找出所有耗时 >2000ms 的 POST /api/v1/order 请求”,grep 效率低、易漏匹配。真正可运营的请求统计需要结构化输出。
解决方案:
- 改用 JSON 格式写日志:在
config/log.php中为某个通道设置'format' => '[{date}] {level} {message}'→ 替换为'format' => '{json}',并确保message是json_encode()后的数组 - 或者用第三方驱动(如
monolog/monolog+elasticsearchhandler),但会增加部署复杂度 - 注意:JSON 日志中不要包含用户敏感字段(如 token、手机号),务必脱敏后再记录
真正难的不是记下一次请求,而是让这些数据能被快速查询、聚合、告警。字段设计、存储介质、采样策略(比如只记录 5% 的慢请求)比代码本身更值得花时间权衡。
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











