首页/数据/数据库速查/InnoDB 刷盘方式(innodb_flush_method)
性能与调优57 条

InnoDB 刷盘方式(innodb_flush_method)

决定数据文件读写是否绕过 OS page cache:Linux 常见 fsync(默认)与 O_DIRECT;O_DIRECT 减少双重缓存,但不同存储上表现差异大。

数据库速查数据更新于 2026-10-13

刷盘方式是什么

该参数决定 InnoDB 读写数据文件时是否绕开操作系统页缓存。Linux 上的常见取值为 fsync(默认,数据先经页缓存)与 O_DIRECT(直接写盘,避免同一份数据在内存里存两份)。它对 IO 与内存占用的影响很大,但没有普适最优值,必须结合实际存储压测。

基本信息

参数名innodb_flush_method
Linux 典型值fsync(默认)、O_DIRECT、O_DIRECT_NO_FSYNC
平台差异各操作系统实现与可选值不同,参数含义不一致
重启生效该参数属于非动态参数,修改后需要重启实例
影响范围数据文件的读写路径;重做日志的刷盘策略另由其他参数控制

典型使用场景

  • 大内存实例内存吃紧:双份缓存导致内存利用率下降时可试直接读写
  • 本地固态盘部署:直接 IO 常能减少系统缓存带来的额外开销
  • 云盘部署:供应商对直接 IO 的实现差异大,必须实测而非套用经验值
  • 读写混合负载:日志与数据混跑时未必要改成直接 IO,先做基准对比
  • 变更验证:用同一负载对比参数前后的 IO 行为与延迟分布

查看与对比验证

查看与对比验证
mysql -e "SHOW VARIABLES LIKE 'innodb_flush_method';"   # 查看当前取值
# 配置文件修改后需重启实例
# [mysqld]
# innodb_flush_method = O_DIRECT
# 用 fio 观察同一块盘在直接 IO 下的行为(低峰执行,注意数据安全)
fio --name=randread --rw=randread --bs=16k --iodepth=64 \
  --size=4G --filename=/data/testfile --runtime=60 --time_based --direct=0
fio --name=randread_odirect --rw=randread --bs=16k --iodepth=64 \
  --size=4G --filename=/data/testfile --runtime=60 --time_based --direct=1

取值对照

取值行为适用
fsync数据经系统缓存,提交时同步落盘通用默认,行为最可预期
O_DIRECT绕过系统缓存直接读写数据文件大内存或做过实测的环境
O_DIRECT_NO_FSYNC直接读写且减少部分同步调用需要通过压测验证收益
其他平台取值各系统实现不同不要照搬 Linux 的经验值
改成直接读写后,数据文件不再占用系统缓存,这部分内存会释放给其他用途,但读写路径的延迟分布可能变化。
这是需要重启的非动态参数:变更要在维护窗口进行,并准备好回退方案与验证脚本。

易错点

  • 照搬云厂商模板改成直接读写:不同云盘实现差异大,IO 抖动可能比改动前更严重
  • 以为改一个参数就能整体加速:刷盘路径还涉及重做日志与双写,需要整体评估
  • 在生产直接改参数不做压测:重启后发现性能下降,只能再安排一次停机回退
  • 忽略不同平台的取值差异:把 Linux 的经验直接套用到其他系统上

数据来源与参考

  • MySQL 8.0 Reference Manual: innodb_flush_method

相关工具

​‌‌​​‌​​​‌‌​‌‌‌‌​‌‌​​​‌‌​‌‌‌​​‌‌​​‌​‌‌‌​​‌‌‌​​​‌​‌‌​‌​​‌​‌‌‌​​​‌​‌‌​‌​​‌​‌‌​​​‌‌​‌‌‌​‌​​​‌‌​‌‌‌‌​​‌​‌‌‌​​‌‌​​​‌‌​‌‌​‌‌‌‌​‌‌​‌‌​‌