1. 索引操作背后的锁机制真相
第一次在线上环境执行ALTER TABLE ADD INDEX时,我的手心全是汗。按照教科书式的理解,这种DDL操作应该会锁住整张表,导致业务停摆。但当我战战兢兢按下回车键后,监控大屏上的QPS曲线居然纹丝不动——那一刻我才意识到,自己可能掉进了"索引必锁表"的认知陷阱。
现代MySQL(5.6+)的索引操作早已不是当年的"暴力锁表"模式。以InnoDB引擎为例,创建二级索引时默认采用Online DDL模式,其核心原理是在表上创建临时日志文件记录增量数据变更,待索引构建完成后应用这些变更。整个过程仅在最后元数据切换时有毫秒级锁等待,这才是监控曲线没有波动的根本原因。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. Online DDL技术深度解析
2.1 三种索引创建方式对比
先看一个生产环境常见的索引添加语句:
sql复制ALTER TABLE user_orders ADD INDEX idx_user_id (user_id);
在MySQL 5.5与8.0版本中,这个简单语句的执行方式天差地别:
| 执行方式 | 锁级别 | 阻塞写入 | 空间占用 | 版本要求 |
|---|---|---|---|---|
| COPY算法 | 表级排他锁 | 完全阻塞 | 2倍空间 | 所有版本 |
| INPLACE算法 | 元数据锁 | 短暂阻塞 | 临时空间 | 5.5+ |
| ONLINE算法(默认) | 行级意向锁 | 不阻塞 | 日志文件 | 5.6+ InnoDB |
关键提示:从MySQL 8.0开始,所有ADD INDEX操作默认使用INPLACE算法,且除非显式指定ALGORITHM=COPY,否则不会触发全表锁
2.2 Online DDL执行流程拆解
以在500万行的订单表上添加索引为例,内核实际执行流程如下:
-
初始化阶段(10ms)
- 获取MDL元数据锁(阶段1)
- 创建临时日志文件(frm.ibd)
- 分配新的索引树内存结构
-
**扫描构建阶
