概述
数据库锁设计的初衷是处理并发问题
根据加锁的范围,MySQL 里面的锁大致可以分成全局锁、表级锁和行锁三类
全局锁
表级锁
MDL锁的场景分析:
在一个从库上执行–single-transaction 方法做逻辑备份时,如果主库上的一个小表做了一个 DDL(比如给一个表上加了一列)这时候,从库上会看到什么现象?
备份逻辑:
- 开启事务,拿到一致性视图
- 对其他表进行备份
- 针对目标表 t 备份
- 设置回滚点(用于释放表 t 的MDL锁)
- 获取表结构(show create)
- 导出该表数据
- 备份完表 t 后回滚到第一步,释放MDL锁
- 对其他表进行备份
以上就是简单的备份逻辑,需要注意的是:
- 事务启动和锁没有直接关系
- MDL锁的申请时机是 语句开始执行时申请,事务提交后才释放
- 对于上面流程,MDL读锁是在 3-3 语句加入的,到3-4回滚才释放
结论:(根据DDL到达从库时机)
- 在3-2执行前:正常运行,DDL执行完毕,备份拿到的是DDL后的表结构
- 在3-2后3-3之前:DDL执行完毕,由于表结构变更导致执行3-3时异常终止
- 在3-3后:此时DDL被阻塞,因为表 t 的MDL读锁被持有。另外该表的会阻塞所有读写操作。现象:主从延迟,直到3-4执行结束
- 在3-4后:正常运行,备份中的表 t 是DDL前的表结构