mysqldump 备份需显式授予 LOCK TABLES 和 RELOAD 权限,因默认模式执行 FLUSH TABLES WITH READ LOCK(需 RELOAD)和 LOCK TABLES;仅 SELECT 不足,且 host 匹配、库名转义、插件兼容等细节均影响权限生效。

只给 SELECT 权限的账号,mysqldump 会直接报错:Access denied; you need (at least one of) the LOCK TABLES privilege(s) for this operation。备份专用账号必须显式加上 LOCK TABLES 和 RELOAD,否则无法保证一致性——这不是可选优化,是默认行为强制要求。
为什么 mysqldump 报 “LOCK TABLES denied” 却不提示缺 RELOAD?
错误信息只提 LOCK TABLES,但实际执行 mysqldump --single-transaction 以外的备份模式(比如含 MyISAM 表、或没加该参数)时,mysqldump 会先执行 FLUSH TABLES WITH READ LOCK,这需要 RELOAD 权限。漏掉它,就会卡在锁表阶段失败。
-
RELOAD用于FLUSH类命令,不是“重启权限”,别被名字误导 -
LOCK TABLES允许用户显式加表级读锁,不等于能写数据,也不影响只读语义 - 若确定只备份 InnoDB 表且固定加
--single-transaction,可省略这两个权限,仅留SELECT;但生产环境建议保留,避免因表引擎混用或参数遗漏导致备份中断
GRANT 时库名不加反引号或写成 *.* 会暴露系统库
执行 GRANT SELECT ON app_db.* TO 'backup_user'@'192.168.1.%' 看似安全,但如果 app_db 名字含短横线(如 my-app)或关键字(如 order),MySQL 会报语法错误;更隐蔽的问题是:GRANT SELECT ON *.* 不仅让账号能查所有业务库,还会隐式触发 SHOW DATABASES 权限,导致 information_schema 和 mysql 库可见。
面向 CRM 系统的 MySQL 8 数据库模式设计。当用户需要为客户关系管理(CRM)系统设计、评审、优化或生成数据库模式时,应使用此项技能。
- 务必用反引号包裹库名:
GRANT SELECT ON `my-app`.* TO 'backup_user'@'192.168.1.%' - 禁止
GRANT ... ON *.*,哪怕只给SELECT;跨库备份就逐个授权 - MySQL 5.7+ 可配
skip-show-databases关闭全局库列表,但需重启,不如从授权源头控制
host 匹配错误导致权限“给了也白给”
backup_user@'192.168.1.%' 和 backup_user@'localhost' 是两个完全独立的账号。如果 mysqldump 从本机执行却连的是 127.0.0.1(TCP 连接),而你只建了 @'localhost' 账号,就会提示 Access denied —— 因为 MySQL 把 localhost 和 127.0.0.1 当作不同 host。
- 确认连接方式:本地脚本用
-h 127.0.0.1就得授权@'127.0.0.1';用-h localhost(socket 连接)才匹配@'localhost' - 生产环境优先用 CIDR 段限制,如
@'192.168.10.0/24',避免用@'%',尤其禁用公网开放 - MySQL 8.0+ 默认认证插件是
caching_sha2_password,旧客户端可能连不上,建用户时显式指定插件:IDENTIFIED WITH mysql_native_password BY 'xxx'
真正难的不是加哪几个权限,而是把 LOCK TABLES 和 RELOAD 理解成“备份必需的读操作辅助权限”,而不是“写权限苗头”;以及意识到 host 字符串和连接协议强绑定——这两点漏掉一个,备份脚本就只能在测试环境跑通。










