原创作者: 孙正方

4月12日,GOPS全球运维大会在深圳隆重召开,全球运维大会是国内第一个运维行业大会,爱可开源社区在基础架构及DevOps解决方案专场分享了《基于分布式中间件的SQL改造指南》的主题演讲。

本文由根据演讲内容进行整理,希望有助于大家对分布式架构的理解及SQL改造实践。

一.中间件中的简单SQL

1.简单SQL的分类

在一般SQL中,一个单表查询的SQL往往是最简单的,而在中间件中也没什么区别,中间件中将一个对于单表的字段查询作为最简单的SQL进行处理。

2.中间件对于简单SQL的处理方式

下面先来简单的回顾下中间件中的表格处理的最基础方式。

中间件会按照在配置文件中既定的数据拆分的设置,对于“用户表”这个表格的数据进行拆分,将每条通过中间件插入的数据按照规则进行分布,图上给的例子是按照“用户表”的ID奇偶性进行了数据的拆分。

有了合理的数据分布之后就是中间件是如何在需要的时候取用数据,在中间件中,对于基础SQL,也就是单表的数据查询分为一下两个情况:

  • 带有分片信息的数据查询:下图展示了一个例子,在单表查询的过程中,如果存在影响数据分布的查询条件(在此例子中为用户的ID=1),

在查询的简单SQL附带有分片条件时,中间件根据SQL语义解析的结果,根据这个分片条件对于数据可能存在的DB进行计算,最终把SQL转发到对应的DB中进行执行,查询出最终的正确结果。

  • 不带有分片信息的数据查询(广播):当查询的SQL不带有分片条件时,中间件只好把SQL内容发送到表格涉及到的所有DB中,并从每个DB中返回数据并整合。

在这个过程中就存在一个现象,即“这一个查询需要等待最慢的那个DB查询结束”。

3.简单SQL的注意事项

上文中有提及广播类型的简单SQL存在一个特征“需要等待最慢的那个DB查询结束”,当分片数量持续上升的时候,如下图所示的场景,需要等待的连接数量会持续变多。

可以通过概率的方法分析下当连接数量增长的时候会发生什么变化:

通过Matlab对于中间件广播查询的场景进行了如下的模拟,可以发现在随着需要等待连接数量的上升,整体的中间件响应速度会有一个成倍的下降,从单个连接平均5ms的查询延迟一直上升到100连接时候的接近15ms的整体延迟。

针对以上的场景,提出在中间件中进行单表查询的时候,尽量降低单个SQL涉及到的后端DB数量,具体方法是在SQL中给表格添加分片列的限定条件,就像select * from 用户表 where ID = 1中的这个条件ID =1。

二.中间件中的ER表格JOIN

1.中间件中ER关系的定义

单表查询不能覆盖应用对于SQL的需求,中间件中就引入了ER关系的概念。

ER关系指的是两个表格在逻辑上就拥有的从属关系,如下图中所示的用户表和订单表:

当两个表或者更多的表格存在这样逻辑上的从属关系的时候,在中间件中把这些关系定义为ER关系,并且当一个查询语句有且仅有存在ER关系的表格关联组成的时候,这个SQL被称为“ER表格JOIN”。

2.中间件对于ER表格JOIN的处理方式

当两个表格能够被定义为ER关系的时候,中间件能够按照之间的关联关系组织数据的存储,最后的存储方式如下图所示:

可以看到大致的结果就是子表(订单表)的数据会被存放在父表(用户表)对应数据的DB节点。

当出现这种数据分布的时候,就可以在DB1中查询到上例中张三的用户和他的所有数据,所以中间件就能直接把SQL语句下发到对应节点进行执行。

3.ER关联SQL的注意事项

可以看到ER的这种查询方式是有一定的局限的,需要把查询的表格声明为ER关系,并且ER关系还是单向的,就是一个表只能是某一个表的子表,一个分片表不能拥有两个父表。

其次就是由于这个ER关联的查询处理是和上文的简单查询在本质上是一样的,就是查询SQL下发到DB中来执行,所以在注意事项上也是一致的,尽量在使用的时候提供能够确定分片的限定条件。

三.中间件中的跨库表格JOIN

1.跨库表格JOIN的定义

事实上上文所有的查询方法限制都是非常大的,但是往往应用的SQL无法满足于被限制在这么局限的范围内,那中间件中就有另一种机制来实现更广泛意义上的SQL执行,跨库表格关联查询。

当我的SQL内容无法被定义进入上文的两个“简单SQL”或者是“ER SQL”的时候,中间件就会使用这种跨库表格JOIN的方式来处理这个问题,当然并非所有的中间件都有实现对应的功能,在这里仅讨论实现的部分中间件的实现逻辑。

2.中间件中跨库表格JOIN的执行

以下是在中间件中执行跨库表查询的这么一个大致执行逻辑图,图中可以看到整体的执行逻辑是从每个DB中分别取TABLEA和TABLEB的数据,最终在中间件中进行数据的整理组织和对比:

具体的跨库查询的执行过程可以被归纳为以下的几个步骤:

  • 根据配置文件中对于TABLEA和TABLEB的描述将表格的数据分别从DB中进行查询
  • 对于查询得到的表格数据进行整理,分别按照ID的值(关联列的值)进行排序和归档
  • 对于归档完成的数据进行ID值的对比,计算关联结果

在这个过程中会产生几个方面的资源消耗:

  • 组织数据产生的临时内存存储消耗
  • 对比数据产生的CPU消耗
  • 查询每一个存在DB中的表数据产生的连接数以及网络消耗

另一个方面就是中间件由于不能存储真实的数据,所以无法像MySQL优化器一样提前计算不同表格的聚合代价,这么一来,中间件就直接按照SQL中原有的表格聚合顺序进行数据的聚合和整理,这可能带来以下的SQL执行的计划。

案例中用户表由于表格顺序的问题先和没有直接关系的商品表进行了表关联,这样一来这里的中间结果就出现了一个笛卡尔积,也就是无条件无字段的关联结果,其结果为双边数据的乘积:

1000X1000=1000000

如果SQL中的表格顺序进行进一步的优化,则可以在同样的SQL中获得以下图中的执行顺序。

这次我们优化完成之后的查询中间结果将由用户表和有关系的订单表优先聚合完成,因为他们之间的关系,最多存在2000条中间结果,相比与上例中的1000000条来说,整个SQL执行效率上得到了很大的优化

3.跨库JOIN的注意事项

针对以上的几种消耗类型,可以通过以下的几个手段进行降低消耗的量以获取最好的执行效果:

  • 添加足够的限定条件
  • 使用重复率低的列进行关联
  • 通过手动调整SQL中表格顺序的手段来进行执行计划的调整

四.通篇总结

从DB存储到真正成熟的分布式DB,分布式中间件的架构是整个过程中的重要一环,在分布式架构的过程中,对SQL的规范和使用存在一些特别要求,应用在向这方面进行改造和适应的过程中需要更多的考虑到中间件架构带来的限制及相关注意事项。整体归纳可分为以下内容:

1.在中间件中尽量使用分片条件进行数据的查询,不论整个SQL是属于简单SQL,ER查询或者是复杂查询。

2.在复杂查询的状态下,优化方向为中间件中处理的数据尽量少,此目标可以通过给表格添加限定条件,选择更加重复率低的关联列以及调整SQL中的表格关联顺序来达成。

sql 拆分_技术分享 | 基于分布式中间件的SQL改造指南相关推荐

  1. mysql优化说出九条_技术分享 | MySQL 优化:为什么 SQL 走索引还那么慢?

    原标题:技术分享 | MySQL 优化:为什么 SQL 走索引还那么慢? 背景 2019-01-11 9:00-10:00 一个 MySQL 数据库把 CPU 打满了. 硬件配置:256G 内存,48 ...

  2. mysql 走索引 很慢_技术分享 | MySQL优化:为什么SQL走索引还那么慢?

    作者:胡呈清 背景 2019-01-11 9:00-10:00 一个 MySQL 数据库把 CPU 打满了. 硬件配置:256G 内存,48 core 分析过程 接手这个问题时现场已经不在了,信息有限 ...

  3. 基于python的搜索引擎论文_技术分享 - 基于python构建搜索引擎系列——(四)检索模型...

    构建好倒排索引之后,就可以开始检索了. 检索模型有很多,比如向量空间模型.概率模型.语言模型等.其中最有名的.检索效果最好的是基于概率的BM25模型. 给定一个查询Q和一篇文档d,d对Q的BM25得分 ...

  4. 银行客户用户画像_技术分享 | 基于数据中台的银行客户画像体系构建

    背景 1.金融消费行为的改变,企业无法接触到客户 80后.90后总计3.4亿人口,日益成为金融企业主要的消费者,但是他们的金融消费习惯正在改变,他们不愿意到金融网点办理业务,不喜欢被动接受金融产品和服 ...

  5. date转timestamp格式_技术分享 | MySQL:timestamp 时区转换导致 CPU %sy 高的问题

    作者:高鹏文章末尾有他著作的<深入理解 MySQL 主从原理 32 讲>,深入透彻理解 MySQL 主从,GTID 相关技术知识.本文为学习记录,可能有误请谅解. 本文建议PC端观看,效果 ...

  6. 大表与大表join数据倾斜_技术分享|大数据技术初探之Spark数据倾斜调优

    侯亚南 数据技术处 支宸啸 数据技术处 在大数据计算中,我们可能会遇到一个很棘手的问题--数据倾斜,此时spark任务的性能会比预期要差很多:绝大多数task都很快执行完成,但个别task执行极慢或者 ...

  7. mongodb 排序_技术分享 | MongoDB 一次排序超过内存限制的排查

    本文目录: 一.背景 1. 配置参数检查 2. 排序字段是否存在索引 二.测试环境模拟索引对排序的影响 1. 测试环境信息 2. 报错语句的执行计划解释 3. 建立新的组合索引进行测试 三.引申的组合 ...

  8. python个人博客搭建说明书_技术分享|利用Python Django一步步搭建个人博客(二)...

    原标题:技术分享|利用Python Django一步步搭建个人博客(二) Hello,欢迎来到我们的"利用Python Django一步步搭建个人博客"系列的第二部分.在第一部分中 ...

  9. 对称加密算法_技术分享丨这是一篇简单的小科普——什么是对称加密算法?(下)...

    大家好~我是贾正经,又到了干货满满的技术分享趴啦~ 上期我们讲解了对称加密算法的小知识,并介绍了国密算法中SM4算法的原理.(上集回顾) 本期带大家了解一下分组密码的五个模式. 分组密码的模式 首先了 ...

最新文章

  1. 2010.8.12 CString最大可以多大?
  2. django中的admin组件
  3. c++ winpcap开发(2)
  4. 初一数学下册电子课本_七年级数学下册人教版-数学七年级下册电子课本-精品下载...
  5. 2019秋季学习计划
  6. redis cluster节点挂掉后_深入浅出—Redis集群的相关详解
  7. Atitit 判断判断一张图片是否包含另一张小图片
  8. 程序员的数学系列(一)
  9. android x86 5.1 .iso,凤凰OS5.1通用ISO1.5.0
  10. java文件 空心_解决Eclipse中java文件的图标变成空心J的问题
  11. et中计算机的快捷键,et文件怎么打开,教您怎么打开et文件
  12. 二进制 八进制 十进制 十六进制 相互转化法
  13. Kernel wmb/mb宏的作用
  14. 关于Mysql8.0时区表问题解决
  15. 财报前被香港证监会点名,富途内控再受拷问
  16. 逆向分析系列——查壳侦壳工具
  17. 利用python爆破mysql数据库
  18. 双环形图表_excel两个环形图怎么画
  19. iomanip I/O流类库操纵符
  20. 401状态码的含义和处理

热门文章

  1. R语言dataframe数据列格式转换(从整型integer转化为浮点型float)
  2. 安装没有在R包仓库CRAN上托管的R包
  3. java矩形碰撞检测_旋转矩形的Java碰撞检测?
  4. 嵌入式开发有年龄限制吗_2021年考监理工程师有年龄限制吗?女生可以考监理工程师吗?...
  5. tensorflow 加载下载波士顿房价数据集
  6. Fail to find the dnn implementation. [Op:CudnnRNN]解决办法
  7. gitk、Git GUI 图形化工具中文显示乱码的解决方案
  8. 8.Map集合(HashMapTreeMap)
  9. 三值网络--Trained Ternary Quantization
  10. 快速人脸验证--MobileFaceNets: Efficient CNNs for Accurate Real-time Face Verification on Mobile Devices