解决了问题,也引入了新的问题
如跨库查询、分布式事务、分库之后的排序(翻页,函数的计算问题)、全局主键问题、容量规划(二次扩容问题)、技术选型问题
问题一:跨节点数据库Join关联查询
- 数据库切分前,多表关联查询,可以通过sql join进行实现
- 分库分表后,数据可能分布在不同的节点上,sql join带来的问题就比较麻烦
问题二:分库操作带来的分布式事务问题
- 操作内容同时分布在不同库中,不可避免会带来跨库事务问题,即分布式事务
问题三:执行的SQL排序、翻页、函数计算问题
- 分库后,数据分布再不同的节点上, 跨节点多库进行查询时,会出现limit分页、order by排序等问题
- 而且当排序字段非分片字段时,更加复杂了,要在不同的分片节点中将数据进行排序并返回,然后将不同分片返回的结果集进行汇总和再次排序(也会带来更多的CPU/IO资源损耗)
问题四:数据库全局主键重复问题
- 常规表的id是使用自增id进行实现,分库分表后,由于表中数据同时存在不同数据库中,如果用自增id,则会出现冲突问题
问题五:容量规划,分库分表后二次扩容问题
- 业务发展快,初次分库分表后,满足不了数据存储,导致需要多次扩容
问题六:分库分表技术选型问题
- 市场分库分表中间件相对较多,框架各有各的优势与短板,应该如何选择
Mysql数据库常见分库分表
Mysql数据库【垂直分表】
需求:商品表字段太多,每个字段访问频次不一样,浪费了IO资源,需要进行优化
- 垂直分表介绍
- 也就是“大表拆小表”,基于列字段进行的
- 拆分原则一般是表中的字段较多,将不常用的或者数据较大,长度较长的拆分到“扩展表 如text类型字段
- 访问频次低、字段大的商品描述信息单独存放在一张表中,访问频次较高的商品基本信息单独放在一张表中
- 垂直拆分原则
- 把不常用的字段单独放在一张表;
- 把text,blob等大字段拆分出来放在附表中;
- 业务经常组合查询的列放在一张表中
Mysql数据库【垂直分库】
需求:C端项目里面,单个数据库的CPU、内存长期处于90%+的利用率,数据库连接经常不够,需要进行优化
- 垂直分库讲解
- 垂直分库针对的是一个系统中的不同业务进行拆分, 数据库的连接资源比较宝贵且单机处理能力也有限
- 没拆分之前全部都是落到单一的库上的,单库处理能力成为瓶颈,还有磁盘空间,内存,tps等限制
- 拆分之后,避免不同库竞争同一个物理机的CPU、内存、网络IO、磁盘,所以在高并发场景下,垂直分库一定程度上能够突破IO、连接数及单机硬件资源的瓶颈
- 垂直分库可以更好解决业务层面的耦合,业务清晰,且方便管理和维护
- 一般从单体项目升级改造为微服务项目,就是垂直分库
仍然存在的问题:垂直分库分表可以提高并发,但是依然没有解决单表数据量过大的问题
Mysql数据库【水平分表】
需求:当一张表的数据达到几千万时,查询一次所花的时间长,需要进行优化,缩短查询时间
- 都是大表拆小表
- 垂直分表:表结构拆分
- 水平分表:数据拆分
- 水平分表
- 把一个表的数据分到一个数据库的多张表中,每个表只有这个表的部分数据
- 核心是把一个大表,分割N个小表,每个表的结构是一样的,数据不一样,全部表的数据合起来就是全部数据
- 针对数据量巨大的单张表(比如订单表),按照某种规则(RANGE,HASH取模等),切分到多张表里面去
- 但是这些表还是在同一个库中,所以单数据库操作还是有IO瓶颈,主要是解决单表数据量过大的问题
- 减少锁表时间,没分表前,如果是DDL(create/alter/add等)语句,当需要添加一列的时候mysql会锁表,期间所有的读写操作只能等待
Mysql数据库【水平分库】
需求:高并发的项目中,水平分表后依旧在单个库上面,1个数据库资源瓶颈 CPU/内存/带宽等限制导致响应慢,需要进行优化
- 水平分库
- 把同个表的数据按照一定规则分到不同的数据库中,数据库在不同的服务器上
- 水平分库是把不同表拆到不同数据库中,它是对数据行的拆分,不影响表结构
- 每个库的结构都一样,但每个库的数据都不一样,没有交集,所有库的并集就是全量数据
- 水平分库的粒度,比水平分表更大
Mysql数据库分库分表总结
-
技术负责人前瞻性思维
- 需要提前考虑系统一年到两年左右的业务增长情况
- 对数据库服务器的QPS、连接数、容量等做合理评估和规划
- 很多人觉得“分库分表”是宜早不宜迟-----其实不然
-
常规开发里面单表建议1千万内,推荐是百万级别单表存储,常规sql和索引优化先行,然后结合缓存+异步+nosql+mq
-
垂直角度(表结构不一样)
- 垂直分表: 将一个表字段拆分多个表,每个表存储部分字段
- 好处: 避免IO时锁表的次数,分离热点字段和非热点字段,避免大字段IO导致性能下降
- 原则:业务经常组合查询的字段一个表;不常用字段一个表;text、blob类型字段作为附属表
- 垂直分库:根据业务将表分类,放到不同的数据库服务器上
- 好处:避免表之间竞争同个物理机的资源,比如CPU/内存/硬盘/网络IO
- 原则:根据业务相关性进行划分,领域模型,微服务划分一般就是垂直分库
- 垂直分表: 将一个表字段拆分多个表,每个表存储部分字段
-
水平角度(表结构一样)
- 水平分库:把同个表的数据按照一定规则分到不同的数据库中,数据库在不同的服务器上
- 好处: 多个数据库,降低了系统的IO和CPU压力
- 原则
- 选择合适的分片键和分片策略,和业务场景配合
- 避免数据热点和访问不均衡、避免二次扩容难度大
- 水平分表:同个数据库内,把一个表的数据按照一定规则拆分到多个表中,对数据进行拆分,不影响表结构
- 单个表的数据量少了,业务SQL执行效率高,降低了系统的IO和CPU压力
- 原则
- 选择合适的分片键和分片策略,和业务场景配合
- 避免数据热点和访问不均衡、避免二次扩容难度大
- 水平分库:把同个表的数据按照一定规则分到不同的数据库中,数据库在不同的服务器上
-
互联网公司实际使用和跳槽面试
- 公司业务稳定发展,多数情况是为了解决【单库单表】数据量过多问题
- 重点是水平角度的【分库分表】