You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MariaDB 10.4.21中如何无需保持会话实现表只读锁定

MariaDB备份场景锁表失效问题解决方案

FLUSH TABLES WITH READ LOCK 属于会话级全局读锁,一旦执行命令的会话断开,锁会被自动释放,因此单次通过Ansible command模块执行该命令无法长期生效。
MySQL/MariaDB原生没有无需持续持有会话的全局读锁实现,但是针对备份获取binlog位置的场景,有3种成熟的替代方案可以实现需求:

方案1:使用mysqldump内置参数(推荐,适用于InnoDB引擎为主的场景)

如果你的表绝大多数为InnoDB等支持事务的引擎,直接用mysqldump自带的参数即可实现一致性备份、自动获取binlog位置,无需手动处理锁:

  • 执行命令:
    mysqldump -u root -p --single-transaction --master-data=2 --all-databases > /path/to/backup.sql
  • 说明:
    • --single-transaction 会基于MVCC生成一致性快照,全程不会加全局读锁,不影响业务写入
    • --master-data=2 会将备份时刻的binlog文件名和位置以注释的形式写入备份文件头部,你可以直接用Ansible的grep命令提取对应值存入变量,无需手动执行SHOW MASTER STATUS

方案2:同一会话内执行完整锁+备份流程(适用于存在MyISAM等非事务引擎的场景)

如果必须加全局读锁保证一致性,将锁表、获取binlog位置、备份、解锁的所有逻辑放在同一个MySQL会话内执行即可,示例脚本如下:

mysql -u root -p <<EOF
FLUSH TABLES WITH READ LOCK;
-- 此处输出binlog位置,Ansible可捕获该输出存入变量
SHOW MASTER STATUS;
-- 调用系统命令执行备份,锁会在会话内持续持有
system mysqldump -u root -p --all-databases > /path/to/backup.sql;
UNLOCK TABLES;
EOF

你只需用Ansible的shell模块执行上述脚本一次即可,不会出现会话断开导致锁提前释放的问题。

方案3:设置全局只读状态(临时应急方案)

如果需要实现跨会话的全局写入限制,可以修改全局只读参数,该配置不会随会话断开失效:

  • 锁定写入(仅持有SUPER权限的用户可写入,需确保业务账号无SUPER权限):
    mysql -u root -p -e "SET GLOBAL read_only = 1;"
  • 备份完成、获取binlog位置后解除限制:
    mysql -u root -p -e "SET GLOBAL read_only = 0;"
  • 注意事项:操作完成后必须及时改回只读状态,避免业务长期无法写入。

内容的提问来源于stack exchange,提问作者Unsel

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.05 16:39:03