连载中 19/20

踩坑实录:七个分库分表事故清单

2026-07-27 · 3807 阅读 · 0 评论 · 0 赞

知道,和做到之间

老规矩,收官前的事故复盘。这一系列讲的机制,出事时团队几乎都「知道」——评审提过、review 标过、复盘写回过。七个案例形态取自真实事故的常见样貌,数据脱敏。

事故一:一条没带分片键的扫荡查询

现象:运营后台一个「导出当日订单」按钮,一点全站接口变慢,DB 连接池告警。根因:这条查询按时间过滤、没带分片键,被广播到 8 库 32 表,每张表都全索引扫描,64 个连接瞬间占满(第 9 篇的连接风暴)。修复:导出走从库加异步任务,查询强制带上时间分区;教训:上线前的 SQL 审计要拦「无分片键全片路由」,中间件日志里广播路由要打告警标。

事故二:跨片分页拖死订单列表

现象:运营侧订单列表翻到几十页后,页面加载 30 秒起,翻得越深越慢。根因:跨片 limit 分页的改写放大——第 100 页要各分片送回前 1010 条归并(第 10 篇的账本)。修复:改游标分页加深度限制;教训:跨片查询不支持任意跳页是设计约束,产品方案期就要对齐,别让技术兜底产品的默认想象。

事故三:分片键选错的卖家视角

现象:商家后台上线后,头部商户的「店铺订单」页面打不开,小商户却一切正常。根因:分片键选了 buyer_id,卖家维度的查询全部广播;头部商户订单多,广播归并的量被商户规模放大。修复:卖家维度建异构索引表(按 seller_id 分片存订单 ID 列表),查询先走索引再回主库;教训:分片键的维度覆盖要在设计期用查询分布数据验证——第 5 篇说的「把访问日志拉出来聚类」,就是给这次事故打的预防针。

事故四:自增主键撞车

现象:分片上线两周,偶发订单插入报主键冲突,重试也不行。根因:迁移时图省事保留了各分片 AUTO_INCREMENT,两张表各自发号,ID 区间重叠。修复:全面切分布式 ID 发号器,存量冲突数据按区间修偏;教训:分片表禁用自增要写进建表规范,评审拦截。

事故五:双写不同步的数据错乱

现象:迁移期间部分订单状态在两个库里不一致,对账差异越滚越多。根因:业务代码双写只写了成功路径,异常分支新库写入被吞掉且没进重试队列——静默丢写。修复:双写失败必须落补偿队列,加实时对账;教训:双写不是 try-catch 里加一行,失败路径和对账是方案的组成部分(第 14 篇的两条纪律)。

事故六:广播表忘同步

现象:商品类目调整后,部分分片返回旧类目,用户看到的数据分裂。根因:类目表是 32 份广播副本,运营改了主副本,其余 31 份的同步任务挂了没人发现。修复:广播表变更加同步校验告警,副本数与一致性进监控;教训:广播表的便利建立在「变更链路可靠」上,它不是免维护的,是换了一种维护方式。

事故七:归档任务打挂主库

现象:凌晨三点主库 CPU 100%,大量查询超时,罪魁是一条无 limit 的归档 DELETE。根因:归档脚本一把梭——单条 DELETE 删两千万行,undo 暴涨、锁范围失控。修复:归档全部改为小批次加限速(第 17 篇的纪律),上线前用影子库演练;教训:任何批量任务在大表上都要问一句:这一把下去,undo 和锁会怎样。

七个事故,七条教训,全能在前面十七篇里找到机制原型——事故不是新知识,是没被执行的旧知识。下一篇收官,把二十篇收进一张作战地图。

☕
503

10 年全栈工程师 · 503咖啡馆主理人

#踩坑实录#分片事故#广播表#双写一致#批量删除

评论 (0)

热门推荐

连载中 11/22

主从搭建实操:从零配出一主两从

光讲原理不过瘾?手把手搭一主两从:my.cnf 六个参数、复制账号、GTID、CHANGE REPLICATION SOURCE TO、SHOW REPLICA STATUS 验收,附翻车排查清单。

#MySQL#主从复制#GTID#主从搭建#高可用
2026-05-07 · 10100 阅读 · 0 评论 · 0 赞
连载中 16/22

连接池:HikariCP 参数与连接风暴

连接池不是越大越好:8 核机器配 1000 连接反而更慢的数学原理,HikariCP 四个必调参数,maxLifetime 与 wait_timeout 的隐形陷阱。

#MySQL#连接池#HikariCP#maxLifetime#连接风暴
2026-05-10 · 9872 阅读 · 0 评论 · 0 赞
连载中 4/16

缓存穿透:恶意 ID 打穿 MySQL 的四道防线

请求的数据在缓存和数据库里都不存在时,缓存形同虚设。聊聊参数校验、空值缓存、布隆过滤器、限流熔断四道防线的原理与组合打法。

#Redis#缓存穿透#布隆过滤器#高可用
2026-05-16 · 9293 阅读 · 21 评论 · 287 赞