执行的SQL排序,翻页,函数计算问题
问题:
- 分库后,数据分布再不同的节点上,跨节点多库进行查询时,会出现limit分页,order by排序等问题。
- 而且当前排序字段非分片字段时,更加复杂了,要在不同的的分片节点中将数据进行排序并返回,然后将不同分片返回的结果集进行汇总和再次排序(也会带来更多的CPU/IO资源损耗)。
解决方法:
- 业务上要设计合理,利用好PartitionKey,查询的数据分布同个数据节点上,避免跨节点多库进行查询时。
- sharding-jdbc在结果合并层自动帮我们解决很多问题(流式归并和内存归并)。
数据库全局主键重复问题
问题:
- 常规表的id是使用自增id进行实现,分库分表后,由于表中数据同时存在不同数据库中,如果用自增id,则会出现冲突问题。
解决方法:
- UUID
- 自研发号器redis
- 雪花算法
分库分表技术选型问题
问题:
市场分库分表中间件相对较多,框架各有各的优势与短板,应该如何选择?
解决方式:
开源产品:注意是Mycat和ShardingJdbc区别,也是被面试官问比较多的,两者设计理念相同,主流都是SQL解析->SQL路由->改写->结果归并。
shardingJDBC(推荐):基于jdbc驱动,不用额外的proxy,在本地应用层重写jdbc原生的方法,实现数据分片形式。是基于JDBC接口的扩展,是以jar包的形式提供轻量级服务的,性能高。代码有侵入性。
Mycat:是基于Proxy,它复写了Mysql协议,将Mycat Server伪装成一个Mysql数据库。客户端所以的jdbc请求都必须要交给Mycat,再由Mycat转发到具体的真实服务器。缺点是效率偏低,中间包装了一层,代码无侵入性。
跨节点数据库join关联查询
问题:跨节点数据库join关联查询和多维度查询。
数据库切分前,多表关联查询,可以通过sql join进行实现。分库分表后,数据可能分布在不同的节点上,sql join带来的问题就比较麻烦。不同维度查看数据,利用的partitionKey是不一样的。
解决方式:
- 冗余字段
- 广播表
- NOSQL汇总
分库分表带来的分布式事务问题
问题:操作内容同时分布在不同库中,不可避免带来跨库事务问题,即分布式事务。
解决方式:
- 2pc和3pc
- tcc
- 事务消息
分布式事务框架:
- TX-LCN
- Seata
- RocketMq
容量规划,分库分表后二次扩容问题
问题:业务发展快,初次分库分表后,满足不了数据存储,导致需要多长扩容,数据迁移问题。
Range范围:时间不用考虑扩容 迁移,区域:调整分片粒度,需要全量迁移。
Hash取模:业务最多是hash取模分片,因扩分库分表涉及到rehash过程,分片数量建议可以成倍扩容策略,只需要迁移部分数据即可。旧节点的数据,有一般要迁移至一个新增节点中。
解决方式1:
该方案通过 MySQL 自带的主从同步能力实现数据迁移,核心流程如下:新增从库 A2、A3,分别建立主从同步关系(A0=>A2、A1=>A3),先手工同步早期数据;发布新程序后,通过 MQ 存储后续的 CUD(增删改)操作;随后关闭主从同步,校验基础数据一致性,消费 MQ 中存储的 CUD 操作以补全增量数据,同时配置并生效新分片规则;最后基于 gmt_modified 字段完成数据校验与修复 —— 筛选该字段值大于迁移开始时间(如 2022-01-01 00:00:00)的修改数据,删除各节点冗余数据(gmt_modified 字段需为常规数据表必备,由数据库自行维护,可根据业务场景修复对应数据)。
优点:借助 MySQL 原生主从同步能力,方案逻辑简单,开发代码量相对较少;缺点:同步过程中会产生大量最终需删除的冗余数据,迁移启动时间越晚成本越高(扩容期间需存储的数据量更大),且大多需要代码侵入、加锁等操作支持。
解决方式2:
该方案适用于证券、银行等对数据严格一致性有要求的场景,核心方式为对外发布停机公告后,在服务不可用的窗口期完成全量数据迁移。
优点:操作最便捷,数据一致性有绝对保障,安全性高;缺点:停机期间服务完全不可用,会对业务造成直接影响,且数据校验工作需在停机时间段内完成,相关人员面临较大时间压力。

1432

被折叠的 条评论
为什么被折叠?



