看完这一篇,ShardingSphere-jdbc 实战再也不怕了 今日热门
2023-03-05 21:19:58 来源:腾讯云
谈到分库分表中间件时,我们自然而然的会想到 ShardingSphere-JDBC 。
【资料图】
这篇文章,我们聊聊 ShardingSphere-JDBC 相关知识点,并实战演示一番。
1 ShardingSphere 生态
Apache ShardingSphere 是一款分布式的数据库生态系统,它包含两大产品:
ShardingSphere-Proxy ShardingSphere-JDBC▍一、ShardingSphere-Proxy
ShardingSphere-Proxy 被定位为透明化的数据库代理端,提供封装了数据库二进制协议的服务端版本,用于完成对异构语言的支持。
代理层介于应用程序与数据库间,每次请求都需要做一次转发,请求会存在额外的时延。
这种方式对于应用非常友好,应用基本零改动,和语言无关,可以通过连接共享减少连接数消耗。
▍二、ShardingSphere-JDBC
ShardingSphere-JDBC 是 ShardingSphere 的第一个产品,也是 ShardingSphere 的前身, 我们经常简称之为:sharding-jdbc 。
它定位为轻量级 Java 框架,在 Java 的 JDBC 层提供的额外服务。它使用客户端直连数据库,以 jar 包形式提供服务,无需额外部署和依赖,可理解为增强版的 JDBC 驱动,完全兼容 JDBC 和各种 ORM 框架。
当我们在 Proxy 和 JDBC 两种模式选择时,可以参考下表对照:
JDBC | Proxy | |
|---|---|---|
数据库 |
| MySQL/PostgreSQL |
连接消耗数 |
| 低 |
异构语言 |
| 任意 |
性能 |
| 损耗略高 |
无中心化 |
| 否 |
静态入口 |
| 有 |
越来越多的公司都在生产环境使用了 sharding-jdbc ,最核心的原因就是:简单(原理简单,易于实现,方便运维)。
2 基本原理
在后端开发中,JDBC 编程是最基本的操作。不管 ORM 框架是 Mybatis 还是 Hibernate ,亦或是 spring-jpa ,他们的底层实现是 JDBC 的模型。
sharding-jdbc 的本质上就是实现 JDBC 的核心接口。
接口 | 实现类 |
|---|---|
DataSource | ShardingDataSource |
Connection | ShardingConnection |
Statement | ShardingStatement |
PreparedStatement | ShardingPreparedStatement |
ResultSet | ShardingResultSet |
虽然我们理解了 sharding-jdbc 的本质,但是真正实现起来还有非常多的细节,下图展示了 Prxoy 和 JDBC 两种模式的核心流程。
1.SQL 解析
分为词法解析和语法解析。 先通过词法解析器将 SQL 拆分为一个个不可再分的单词。再使用语法解析器对 SQL 进行理解,并最终提炼出解析上下文。
解析上下文包括表、选择项、排序项、分组项、聚合函数、分页信息、查询条件以及可能需要修改的占位符的标记。
2.执行器优化
合并和优化分片条件,如 OR 等。
3.SQL 路由
根据解析上下文匹配用户配置的分片策略,并生成路由路径。目前支持分片路由和广播路由。
4.SQL 改写
将 SQL 改写为在真实数据库中可以正确执行的语句。SQL 改写分为正确性改写和优化改写。
5.SQL 执行
通过多线程执行器异步执行。
6.结果归并
将多个执行结果集归并以便于通过统一的 JDBC 接口输出。结果归并包括流式归并、内存归并和使用装饰者模式的追加归并这几种方式。
本文的重点在于实战层面, sharding-jdbc 的实现原理细节我们会在后续的文章一一给大家呈现 。
3 实战案例
笔者曾经为武汉一家 O2O 公司订单服务做过分库分表架构设计 ,当企业用户创建一条采购订单 , 会生成如下记录:
订单基础表t_ent_order:单条记录 订单详情表t_ent_order_detail:单条记录订单明细表t_ent_order_item:N条记录订单数据采用了如下的分库分表策略:
订单基础表按照 ent_id (企业用户编号) 分库 ,订单详情表保持一致;订单明细表按照 ent_id (企业用户编号) 分库,同时也要按照 ent_id (企业编号) 分表。首先创建 4 个库,分别是:ds_0、ds_1、ds_2、ds_3 。
这四个分库,每个分库都包含 订单基础表 , 订单详情表 ,订单明细表 。但是因为明细表需要分表,所以包含多张表。
然后 springboot 项目中配置依赖 :
org.apache.shardingsphere sharding-jdbc-spring-boot-starter 4.1.1 配置文件中配置如下:
配置数据源,上面配置数据源是: ds0、ds1、ds2、ds3 ;配置打印日志,也就是:sql.show ,在测试环境建议打开 ,便于调试;配置哪些表需要分库分表 ,在 shardingsphere.datasource.sharding.tables 节点下面配置:上图中我们看到配置分片规则包含如下两点:
1.真实节点
对于我们的应用来讲,我们查询的**逻辑表**是:t_ent_order_item 。它们在数据库中的真实形态是:`t_ent_order_item_0` 到 `t_ent_order_item_7`。 真实数据节点是指数据分片的最小单元,由数据源名称和数据表组成。订单明细表的真实节点是:`ds$->{0..3}.t_ent_order_item_$->{0..7}` 。2.分库分表算法
配置分库策略和分表策略 , 每种策略都需要配置分片字段( sharding-columns )和分片算法。
4 基因法 & 自定义复合分片算法
分片算法和阿里开源的数据库中间件 cobar 路由算法非常类似的。
假设现在需要将订单表平均拆分到4个分库 shard0 ,shard1 ,shard2 ,shard3 。
首先将 0-1023 平均分为4个区段:0-255,256-511,512-767,768-1023,然后对字符串(或子串,由用户自定义)做 hash, hash 结果对 1024 取模,最终得出的结果 slot落入哪个区段,便路由到哪个分库。
看起来分片算法很简单,但我们需要按照订单 ID 查询订单信息时依然需要路由四个分片,效率不高,那么如何优化呢 ?
答案是:基因法& 自定义复合分片算法。
基因法是指在订单 ID 中携带企业用户编号信息,我们可以在创建订单 order_id时使用雪花算法,然后将 slot的值保存在 10位工作机器 ID里。
通过订单 order_id 可以反查出 slot, 就可以定位该用户的订单数据存储在哪个分片里。
Integer getWorkerId(Long orderId) { Long workerId = (orderId >> 12) & 0x03ff; return workerId.intValue();}下图展示了订单 ID 使用雪花算法的生成过程,生成的编号会携带企业用户 ID 信息。
解决了分布式 ID 问题,接下来的一个问题:sharding-jdbc 可否支持按照订单 ID ,企业用户 ID 两个字段来决定分片路由吗?
答案是:自定义复合分片算法。我们只需要实现 ComplexKeysShardingAlgorithm类即可。
复合分片的算法流程非常简单:
1.分片键中有主键值,则直接通过主键解析出路由分片;
2.分片键中不存在主键值 ,则按照其他分片字段值解析出路由分片。
5 扩容方案
既然做了分库分表,如何实现平滑扩容也是一个非常有趣的话题。
在数据同步之前,需要梳理迁移范围。
1.业务唯一主键;
在进行数据同步前,需要先梳理所有表的唯一业务 ID,只有确定了唯一业务 ID 才能实现数据的同步操作。需要注意的是:业务中是否有使用数据库自增 ID 做为业务 ID 使用的,如果有需要业务先进行改造 。另外确保每个表是否都有唯一索引,一旦表中没有唯一索引,就会在数据同步过程中造成数据重复的风险,所以我们先将没有唯一索引的表根据业务场景增加唯一索引(有可能是联合唯一索引)。2.迁移哪些表,迁移后的分库分表规则;
分表规则不同决定着 rehash 和数据校验的不同。需逐个表梳理是用户ID纬度分表还是非用户ID纬度分表、是否只分库不分表、是否不分库不分表等等。接下来,进入数据同步环节。
整体方案见下图,数据同步基于 binlog ,独立的中间服务做同步,对业务代码无侵入。
首先需要做历史数据全量同步:也就是将旧库迁移到新库。
单独一个服务,使用游标的方式从旧库分片 select 语句,经过 rehash 后批量插入 (batch insert)到新库,需要配置jdbc 连接串参数 rewriteBatchedStatements=true 才能使批处理操作生效。
因为历史数据也会存在不断的更新,如果先开启历史数据全量同步,则刚同步完成的数据有可能不是最新的。
所以我们会先开启增量数据单向同步(从旧库到新库),此时只是开启积压 kafka 消息并不会真正消费;然后在开始历史数据全量同步,当历史全量数据同步完成后,在开启消费 kafka 消息进行增量数据同步(提高全量同步效率减少积压也是关键的一环),这样来保证迁移数据过程中的数据一致。
增量数据同步考虑到灰度切流稳定性、容灾 和可回滚能力 ,采用实时双向同步方案,切流过程中一旦新库出现稳定性问题或者新库出现数据一致问题,可快速回滚切回旧库,保证数据库的稳定和数据可靠。
增量数据实时同步的大体思路 :
1.过滤循环消息
需要过滤掉循环同步的 binlog 消息 ;
2.数据合并
同一条记录的多条操作只保留最后一条。为了提高性能,数据同步组件接到 kafka 消息后不会立刻进行数据流转,而是先存到本地阻塞队列,然后由本地定时任务每X秒将本地队列中的N条数据进行数据流转操作。此时N条数据有可能是对同一张表同一条记录的操作,所以此处只需要保留最后一条(类似于 redis aof 重写);
3.update 转 insert
数据合并时,如果数据中有 insert + update 只保留最后一条 update ,会执行失败,所以此处需要将 update 转为 insert 语句 ;4.按新表合并
将最终要提交的 N 条数据,按照新表进行拆分合并,这样可以直接按照新表纬度进行数据库批量操作,提高插入效率。扩容方案文字来自 《256变4096:分库分表扩容如何实现平滑数据迁移》,笔者做了些许调整。
6 总结
sharding-jdbc 的本质是实现 JDBC 的核心接口,架构相对简单。
实战过程中,需要配置数据源信息,逻辑表对应的真实节点和分库分表策略(分片字段和分片算法)
实现分布式主键直接路由到对应分片,则需要使用基因法 & 自定义复合分片算法。
平滑扩容的核心是全量同步和实时双向同步,工程上有不少细节。
实战代码地址:
https://github.com/makemyownlife/shardingsphere-jdbc-demo
参考资料:
256变4096:分库分表扩容如何实现平滑数据迁移?黄东旭:分布式数据库历史、发展趋势与 TiDB 架构如果我的文章对你有所帮助,还请帮忙点赞、在看、转发一下,你的支持会激励我输出更高质量的文章,非常感谢!
为你推荐
-
看完这一篇,ShardingSphere-jdbc 实战再也不怕了 今日热门
-
热点评!烈火如歌的演员
-
进口新车报道:大众集团公布在华新战略 多款重磅SUV|当前独家
-
世界上最贵的车是什么车?_世界上最贵的车是什么车
-
4月15日,来跑马么!2023张家界武陵源生态马拉松报名启动 每日热闻
-
耀武扬威的近义词是什么啊_耀武扬威的近义词是什么|天天热门
-
2022年中国新能源汽车驱动电机市场产业政策、发展现状、产业链结构、竞争格局及发展前景分析[图] 世界报资讯
-
“日本体验”与中国现代文学思潮 全球新动态
-
要闻:盈翠嘉园
-
银三角是哪三个国家_焦点
-
每日消息!的意思 恐怖_的意思恐怖美女
-
全球速讯:拜礼研究
-
“蛇”族_天天时快讯
-
世界今日讯!兰大“英才计划”十年记:432名中学生走进大学“搞研究”
-
天天简讯:万科企业:2月份实现合同销售金额301.2亿元
-
2023春季全国中小学消防安全直播课几点开始?附入口-焦点速看
-
男生说女生傲娇是什么意思_傲娇是什么意思
-
江苏泰兴市举办女性就业专场招聘会_世界速看料
-
【环球热闻】广东省专业技术人员继续教育管理系统电话_广东省专业技术人员继续教育管理系统
-
2019年大别山 黄冈世界旅游博览会-世界速讯
推荐内容
- 看完这一篇,ShardingSphere-jdbc 实战再也不怕
- 热点评!烈火如歌的演员
- 进口新车报道:大众集团公布在华新战略 多款重磅S
- 世界上最贵的车是什么车?_世界上最贵的车是什么车
- 4月15日,来跑马么!2023张家界武陵源生态马拉松
- 耀武扬威的近义词是什么啊_耀武扬威的近义词是什
- 2022年中国新能源汽车驱动电机市场产业政策、发展
- “日本体验”与中国现代文学思潮 全球新动态
- 要闻:盈翠嘉园
- 银三角是哪三个国家_焦点
- 每日消息!的意思 恐怖_的意思恐怖美女
- 全球速讯:拜礼研究
- “蛇”族_天天时快讯
- 世界今日讯!兰大“英才计划”十年记:432名中学
- 天天简讯:万科企业:2月份实现合同销售金额301.2亿元
- 2023春季全国中小学消防安全直播课几点开始?附入
- 男生说女生傲娇是什么意思_傲娇是什么意思
- 江苏泰兴市举办女性就业专场招聘会_世界速看料
- 【环球热闻】广东省专业技术人员继续教育管理系统
- 2019年大别山 黄冈世界旅游博览会-世界速讯
- 全国最新百家姓排名_新百家姓排名 当前消息
- 天天视讯!虞书欣大量不雅照片惊现网络!图中配有
- 观察:虚拟现实概念:下一个十倍股!可能从这5大
- 回复的英文缩写_回复的英文-每日热门
- 环球热资讯!怀孕女子忍受不了楼上噪音,被骂后开
- 贝斯是什么_贝斯-当前信息
- 环球播报:教育方针_关于教育方针简介
- C/C++语言程序设计实验指导与习题精选
- 国网汉中供电公司:春寒风雪至 特巡保电忙
- win10建行网银盾插上网页弹不出来_建行网银盾插上
- 浪子回头金不换好马不吃回头草是什么意思|天天看
- 当前通讯!电视剧枪战片大全集_电视剧枪战片
- 狼塔在哪里_狼塔
- 陈鲁豫_说一说陈鲁豫的简介 每日快报
- 晚霞中睡美人_熟睡中的女孩霞-精彩看点
- 太豪横!高诗岩宴请辽篮吃大餐,朱荣振现身,韩德
- 焦点观察:广州男职工陪产假多少天?
- 用果冻怎么玩水晶之恋_水晶之恋果冻玩法
- 自考会计证怎么考2014_自考会计证怎么考 全球热头条
- 一加Buds Pro 2轻享版无线耳机即将登场
油气
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
经济
-
中新网通辽10月18日电 (记者 张林虎)18日,记者从内蒙古自治区通辽市奈曼旗公安局获悉,国家一级保护动物--梅花鹿误入当地村民羊群,
-
中新网杭州10月18日电 (王题题 胡燕婕)云天收夏色,浅秋正渐浓。10月18日,浙江杭州市西湖游船有限公司推出的惠民多站点“西湖环湖游
-
中新网福州10月18日电 (记者 龙敏 王东明)福州市晋安区官方18日晚间通报,18日14时47分,晋安区岳峰镇化工路爱摩轮商业广场项目摩天
-
中新网兰州10月18日电 (闫姣 艾庆龙 吉翔)“红山白土头,黄河向西流。”不少人疑问,天下黄河向东流,为何甘肃永靖县这段黄河却向西
-
中新网北京10月18日电 《清华城市健康设施指数》18日在北京发布。报告成果显示,城市健康设施指数领先城市以中心城市和东部沿海城市