预热解决什么问题
实例重启后缓冲池是空的,所有热数据都要重新从磁盘读进来,这段时间性能处于低谷。InnoDB 的做法是「关门时记名单、开门时按名单预热」:关闭时把缓冲池中的页号列表写入数据目录下的 ib_buffer_pool 文件,启动时按这份名单异步加载。MySQL 8.0 下这两件事默认都是开启的。
基本信息
| 关闭时导出 | innodb_buffer_pool_dump_at_shutdown,默认 ON |
|---|---|
| 启动时加载 | innodb_buffer_pool_load_at_startup,默认 ON |
| 名单文件 | datadir/ib_buffer_pool,只记录页号,体积很小 |
| 手动触发 | innodb_buffer_pool_dump_now / innodb_buffer_pool_load_now |
| 进度查看 | SHOW STATUS LIKE 'Innodb_buffer_pool_load_status' |
典型使用场景
- 计划内重启或版本升级前,先把热点页名单落盘
- 主从切换演练后评估新主的性能恢复速度
- 机房迁移、实例重建后缩短冷启动的低谷期
- 重启后发现数据库明显变慢,确认预热是否已经完成
- 临时中断预热:磁盘吃紧时先保证线上业务稳定
状态与手动操作
状态与手动操作
SHOW VARIABLES LIKE 'innodb_buffer_pool_dump%';
SHOW VARIABLES LIKE 'innodb_buffer_pool_load%';
SET GLOBAL innodb_buffer_pool_dump_now = ON; -- 立即导出热点页名单
SET GLOBAL innodb_buffer_pool_load_now = ON; -- 立即按名单预热
SHOW STATUS LIKE 'Innodb_buffer_pool_load_status';
-- 需要中断预热时:
SET GLOBAL innodb_buffer_pool_load_abort = ON;相关参数读法
| 参数 | 默认值 | 说明 |
|---|---|---|
| dump_at_shutdown | ON | 关闭实例时自动写热点页名单 |
| load_at_startup | ON | 启动时自动按名单加载页面 |
| dump_pct | 25 | 每次导出占缓冲池的比例,过大延长关闭时间 |
| load_status | 无 | 查看预热进度,finished 表示已完成 |
| ib_buffer_pool | datadir 下 | 只含页号列表,不是数据文件 |
预热是异步的:服务可用不等于预热完成。重启后立刻放开全量流量会造成物理读风暴,正确做法是盯住 load_status,看到 finished 之后再逐步放量;数据量大的实例,预热可能持续几分钟到几十分钟。
导出名单本身也要花时间和 IO:关闭超时或被强制 kill 时名单可能写不完整,重启后的预热效果会打折扣。维护窗口要为此留出余量,不要用 kill -9 结束实例。
主从切换时尤其要注意:从库承接流量前先确认预热状态,否则「切换后性能上不去」的锅很容易被错误地扣在架构设计上。演练时把预热耗时一并记进切换手册,才能给出可信的切换时间预估。