站长必避的3个MySQL设计陷阱
|
跟产品吵的,去年劳动节那天下午三点。他举着Figma里那个「用户成长值实时排行榜」,说“就加个字段,顺手的事”,我盯着他指甲缝里那点黑灰,想伸手把他手里的iPad翻过来扣桌上——这事儿真不是顺手。 第一个陷阱:TEXT 当万能桶塞 VARCHAR 里。上周帮一个站长救首屏,FCP卡在三百七十二 KB 的响应体上死活不走,Lighthouse 跑分截图发到群里没人回,PM在隔壁工位嚼口香糖嚼了十七分钟没咽下去。查下来是用户签到日志表,存了七百万条,每个字段都是 TEXT,哪怕存的是“2024-05-01”这种八位字符串。我原以为改字段类型就行,结果 ALTER TABLE 持续锁表四小时十七分钟,主库 IO 刷到98%,监控报警邮件堆成山。这个我敢打包票:TEXT 类型会让 optimizer 在二级索引里绕远路,尤其你带 WHERE + ORDER BY + LIMIT 的时候,它宁可全表扫描也不用覆盖索引。后来换成 CHAR(10),查询从 3.2 秒压到十八毫秒,但中间有三分钟我站在机房门口等备份恢复,对面后端换了一根Type-C充电线,亮绿灯,我盯了整整四十七秒。 第二个陷阱:自增ID当业务ID用。那个站长非说“ID看着整齐好记”,于是订单号、商品SKU、活动码全部取自同一张流水表的AUTO_INCREMENT。结果五一前夜凌晨一点二十三分,他的分销系统崩了——因为上游渠道商批量导入时手抖多点了两次“同步库存”,MySQL 把两个并发 INSERT 给了同一个 ID(间隙锁没锁对),下游服务拿到重复ID后把A渠道的返佣算进B渠道账上。财务组凌晨三点打来电话,我边听边关掉桌面那个没关的录屏,声音还在响:“……你确定是数据库层的问题?不是你们缓存没清?”我说不是,是INSERT语句里显式指定了ID值还设了ON DUPLICATE KEY UPDATE,但WHERE条件写的却是`status = 'pending'`——而status根本不在唯一键里。这个我说不准是不是他故意埋的坑,但我知道他上周刚把“订单状态机”文档删了重建,理由是“旧版太重”。
文章配图,仅供参考 第三个陷阱:JSON字段里藏索引幻觉。前天下午倒水回来,看见前端在调试一个用户偏好页,加载慢得像拖着生锈链条爬坡。查SQL发现他在WHERE里写`JSON_CONTAINS(preference, '"dark"', '$.theme')`,表里八百多万行,EXPLAIN出来type=ALL。他理直气壮:“不是说8.0支持JSON索引吗?”我说是,但你建的是虚拟列索引还是函数索引?他眨眨眼:“……我都建了。”我让他SHOW CREATE TABLE,结果他建的是两个独立索引:一个在`preference->>"$.theme"`上,另一个在`preference`整个字段上。我让他删掉后一个——删完之后慢查询从每天三千二百条降到二十七条。但就在敲DROP INDEX命令前两分钟,我突然想起去年双十一我们自己也干过类似的事,也是JSON字段,也是两个重叠索引,当时DBA没吭声,直到某天凌晨三点他老婆打电话问他“家里电闸跳了你知不知道”,他才发现MySQL在后台做Online DDL的时候偷偷占满磁盘IOPS。这事我没跟别人提过,说了也没人信。说到CDN账单,上个月他们用了七点六TB流量,其中三块八是404图片,源头全指向用户头像URL拼接逻辑里少了个正则替换——但这事跟我现在讲的三个陷阱没关系。反正已经岔开了,就不拉回来了。 其实最要命的不是这三个。是你明知道不该这么干,可每次上线前PM抱着需求文档坐你对面说“就今晚一版,老板要看数据看板”,你点头那一刻,所有陷阱都自动解封了。我试过把CREATE TABLE语句发给新人,让他找错误,他盯了半小时指出五处语法问题,却漏掉了主键上没加NOT NULL。我说没事,我当年也一样——第一次上线用TIMESTAMP做默认时间戳,结果夏令时切换那天丢了两万条埋点,服务器日志里全是乱码,而那天下午三点,我泡的枸杞茶凉透了没人动,杯底浮着三颗完整的枸杞,像没被选中的备选方案。 现在你要是问我“到底怎么避”,我没法给你标准答案。我只建议你下次ALTER TABLE之前,先看看监控里有没有正在执行的SELECT FOR UPDATE,再摸摸自己左手小指关节——如果那里有老茧,说明你曾经徒手kill过至少一次被阻塞的会话。别的,随缘吧。 (编辑:站长网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |


当交互设计挣脱模板,独特性即用户留存的首要引擎
嵌入式UI设计:资源受限设备的极致美学
多媒体开发必修:视觉惊艳与秒开兼得的网站设计法则
Linux与Windows服务器选型的5大性能陷阱
鸿蒙开发者必修:MySQL运维设计实战
MySQL高可用架构实战:20年经验打造自动容灾方案
Go服务器性能调优:9年实战破选型陷阱,QPS翻倍