4. 慢查询日志基础:定义、格式与采集方式

在分布式压测体系中,慢查询日志(Slow Query Log)是数据库性能诊断的核心数据源。对于 Kafka 生产者尾延迟压测而言,慢查询日志直接揭示了生产者将元数据、事务状态或偏移量持久化到数据库时的瓶颈。本节从定义出发,系统梳理慢查询日志的格式规范与采集方法,为后续将慢查询指标关联到生产者尾延迟分析奠定基础。

4.1 慢查询日志的定义

慢查询日志是数据库系统内置的、用于记录执行时间超过预设阈值的 SQL 语句及其执行上下文的功能模块。其核心价值在于:

  • 定位性能瓶颈:直接标记出响应时间异常的查询,避免全量审计带来的性能开销。
  • 量化延迟分布:通过记录实际执行耗时,可构建查询延迟的百分位分布(P50/P99/P999),与生产者端尾延迟指标形成对照。
  • 关联系统行为:慢查询的时间戳可与 Kafka 生产者发送请求的时间窗口对齐,用于判断数据库侧抖动是否传导至生产者端。
关键概念:慢查询日志的阈值通常由数据库参数控制(如 MySQL 的 long_query_time),默认值为 10 秒。在压测场景下,建议将阈值下调至 100ms~500ms,以捕获更多影响尾延迟的微慢查询。

4.2 常见数据库慢查询日志格式

不同数据库的慢查询日志在字段构成、输出格式上存在差异,但核心信息维度一致。下表对比了 MySQL 与 PostgreSQL 的慢查询日志关键字段:

维度 MySQL(5.7+ / 8.0) PostgreSQL(auto_explain + 日志)
时间戳 # Time: 2025-03-15T10:30:45.123456Z 2025-03-15 10:30:45.123 UTC
用户/连接 # User@Host: kafka_user[kafka_user] @ localhost [] LOG: statement: ...(通过 log_line_prefix 配置)
查询耗时 # Query_time: 2.345678(秒) duration: 2345.678 ms
锁等待时间 # Lock_time: 0.001234(秒) 需结合 auto_explain.log_analyze 输出
返回行数 # Rows_sent: 1 rows: 1
扫描行数 # Rows_examined: 50000 需启用 auto_explain.log_buffers
SQL 语句 SELECT * FROM kafka_offsets WHERE ...\G SELECT * FROM kafka_offsets WHERE ...;
执行计划 需手动 EXPLAIN 或使用 performance_schema 内置 auto_explain 模块自动输出
格式差异提示:MySQL 的慢查询日志默认包含 Query_time 和 Lock_time 两个独立耗时字段,而 PostgreSQL 的 duration 是总执行时间。在压测分析时,需注意 MySQL 的 Lock_time 已包含在 Query_time 中,避免重复计算。

4.3 慢查询日志的采集方式

采集方式直接影响日志的完整性、实时性和对生产系统的侵入性。以下从 MySQL 和 PostgreSQL 两个维度分别说明:

4.3.1 MySQL 慢查询日志采集

  • 文件日志模式:通过 slow_query_log=ON 和 slow_query_log_file=/var/log/mysql/slow.log 启用,日志以文本形式追加写入。适合离线分析,但高并发下可能产生 IO 竞争。
  • 表日志模式:设置 log_output=TABLE,慢查询记录写入 mysql.slow_log 表。支持 SQL 查询,但会消耗数据库内部资源。
  • 性能模式(Performance Schema):通过 performance_schema 的 events_statements_history_long 表捕获慢查询,支持更细粒度的等待事件分析,但需要额外开启采集项。

4.3.2 PostgreSQL 慢查询日志采集

  • auto_explain 模块:在 postgresql.conf 中加载 shared_preload_libraries = 'auto_explain',并设置 auto_explain.log_min_duration = 1000(毫秒)。该方式自动记录慢查询及其执行计划,是压测场景的首选。
  • 日志参数组合:通过 log_min_duration_statement = 1000 记录慢查询,配合 log_line_prefix 增加时间戳、进程 ID 等信息。此方式不输出执行计划,适合轻量级采集。
  • pg_stat_statements 视图:虽然不直接输出慢查询日志,但可通过 pg_stat_statements 查询累计统计信息,用于识别高频慢查询模式。
压测采集注意事项:在 Kafka 生产者尾延迟压测期间,数据库慢查询日志的采集应避免使用同步写入模式(如 MySQL 的 log_output=TABLE),防止日志写入本身成为新的延迟瓶颈。推荐使用异步文件日志或性能模式采样。

4.4 慢查询日志采集架构

下图展示了在 Kafka 生产者压测环境中,慢查询日志从数据库产生到最终关联分析的典型采集架构:

慢查询日志采集架构(压测环境) MySQL 数据库 slow_query_log=ON PostgreSQL 数据库 auto_explain 模块 slow.log(文件) 异步追加写入 postgresql.log 含执行计划 日志采集代理 Filebeat / Fluentd 消息队列(Kafka) 日志缓冲与分发 分析存储 Elasticsearch / ClickHouse 生产者尾延迟关联分析 说明: 采集代理从数据库服务器本地日志文件读取增量内容, 发送到消息队列解耦,最终写入分析存储用于压测关联。

4.5 慢查询日志与生产者尾延迟的关联思路

在 Kafka 生产者压测中,慢查询日志并非孤立存在,而是作为数据库侧延迟的精确度量。以下表格总结了慢查询日志中哪些字段可直接用于尾延迟分析:

慢查询字段 生产者尾延迟关联方式 典型场景
Query_time / duration 与生产者发送请求的时间戳对齐,计算数据库响应延迟对端到端延迟的贡献 元数据查询(SELECT ... FROM kafka_brokers)耗时突增
Lock_time 判断锁等待是否导致生产者线程阻塞,进而引发尾延迟 事务状态表行锁竞争
Rows_examined 扫描行数过大导致 CPU/IO 飙升,间接影响生产者请求的数据库响应 偏移量表全表扫描
时间戳 用于与生产者端 kafka-producer-metrics 的时间序列对齐 定位尾延迟发生的精确时间窗口
实践建议:在压测脚本中,除了记录生产者端的发送延迟,还应同步采集数据库慢查询日志的时间戳和耗时。通过将两个时间序列绘制在同一张图上,可以直观判断尾延迟是否由数据库慢查询引发,还是由网络抖动、Kafka Broker 负载等其他因素导致。