背景
线上大面积告警,数据库主键超长:
Cause: com.mysql.jdbc.exceptions.jdbc4.MySQLDataException: '2.148269064E9' in column '1' is outside valid range for the datatype INTEGER
心想,这真就碰上了主键用完的情况?话说int类型的数据范围如下表,出问题的表主键使用的类型是int,约么21亿的数据,无符号整型更是高达41亿的数据,我们的业务都这么大量级了?
类型名称 | 字节 | 值范围 |
---|---|---|
int | 4 | -2,147,483,648 到2,147,483,647 |
unsigned int | 4 | 0 到4,294,967,295 |
查看表结构,分明是bigint呀,咋还能超长了呢? 再看逻辑,好家伙!insert之后会给返回对象的id赋值,但是mybatis的mapper.xml代码映射时id的类型写的是integer,因此会抛出异常。
关键修复动作:评估风险后,直接新建一张表,rename表,先保证线上可用,随后再处理影响数据。
惊心动魄后...
不论结果怎样,复盘还是要复盘的。
1、为什么代码映射类型跟数据库类型不一致?
这张表是之前改的,只关注了逻辑处理,没有仔细检查这里。
再往深问,也只能这么回答了,是真的没有仔细审核,测试流程也通过了,提交pr也有人帮check,就...(长叹)
2、这么大的数据量,没有分库分表吗?
其实,这张表就是分库分表改造时加的关系表,哎...
2.1 为什么要分库分表
首先,如果数据库的业务数据量变大的情况下,数据库很容易出现性能瓶颈,诸如:慢sql变多,请求被阻塞,无法存储等等。无论是对于上述系统的读写性能瓶颈,还是我们日常的维护都是一件极为困难的事情。此时,对数据库表进行拆分是一种极为有效的方法。
分库 :分库可以降低单个集群的负载压力,提升整体的读写性能。
分表 :分表可以提高数据操作的效率,尤其是提高读效率。
2.2 什么时候要进行分库分表
《阿里巴巴Java 开发手册》中有提出:单表行数超过500万行或者单表容量超过2GB时,推荐进行分库分表。实际上,分库分表可以根据MySQL配置以及机器硬件来考虑,结合实际需求,在业务初期倒也不必过度设计。
2.3 分库分表怎么做?
这块内容较多,单说吧。
展望未来
好好学习,抓紧跑路🏃