为什么分布式数据库需要的是编队作战,而不是单一军种一拥而上?
文章开始前推荐2个学习环境:
1、欢迎使用镜像快速体验PostgreSQL/DuckDB强大功能:《最好的PostgreSQL学习镜像》
2、欢迎使用云起实验室: 《免费体验PolarDB开源数据库》
3、PolarDB开源数据库内核、应用等学习图谱: https://www.aliyun.com/database/openpolardb/activity
为什么SQL不能动态分组计算?
https://www.bilibili.com/video/BV1pq4y1F7uy/
什么是动态分组?
汽车有两个指标动力输出的平顺性、瞬间的爆发力.
企业会按职能划分成若干个部门, 每个部门各司其职, 体现了工作的平顺性. 但是当某个部门人力资源不足时, 只能向外招聘, 无法跨部门调派人力.
原因是其他部门的人可能跨领域了, 根本不熟悉无法帮忙.
原因也可能是, 某些能支持的其他部门人力也紧张, 调派后影响其他部门的业务.
动态分组解决什么问题?
资源有效利用的问题.
体现在汽车上的爆发力、企业中的敏捷性、数据库中的稳定性和爆发性(典型的HTAP场景, OLTP要求RT平稳, OLAP大量计算和IO要求大规模并发计算来提高性能).
动态分组计算的先决条件是什么?
参与动态分组的单元有足够的跨领域能力, 否则还得培训再上岗.
数据库不能动态分组的原因是什么?
数据库的计算节点要参与任意SQL的计算, 那么每个节点都要能访问所有数据, 否则就需要搬迁数据, 相当于培训上岗, 效率低下.
社区版本:
Greenplum, 表的数据必须hash分布在所有计算节点中. (使用DISTRIBUTED REPLICATED的复制表除外)
查询时, 所有节点都要参与计算. (含分区键条件的查询、使用DISTRIBUTED REPLICATED的复制表的查询除外.)
citus, pg-xc 可以创建节点分组, 然后将表的数据分布在指定的分组内.
查询时, SQL中涉及的表所在的分组包含的计算节点需要参与计算. (含分区键条件的查询、复制表的查询除外.)
如果遇到跨分组表JOIN(JOIN 的表分布在不同的逻辑分组内), 无法使用多阶段优化( 《HybridDB PostgreSQL "Sort、Group、distinct 聚合、JOIN" 不惧怕数据倾斜的黑科技和原理 - 多阶段聚合》 ), 必须跨多个分组重分布数据, 造成大量网络开销.
pg-xc: CREATE NODE GROUP cluster_group WITH Datanode1, Datanode2;
[
DISTRIBUTE BY { REPLICATION | ROUNDROBIN | { [HASH | MODULO ] ( column_name ) } } |
DISTRIBUTED { { BY ( column_name ) } | { RANDOMLY } |
DISTSTYLE { EVEN | KEY | ALL } DISTKEY ( column_name )
]
[ TO { GROUP groupname | NODE ( nodename [, ... ] ) } ]
citus: tables - distributed by column 记录映射到 shards
shards 映射到 nodes
多表shard对齐 : colocate tables shards
哪些分组将会参与计算? 取决于建表时的指定, 不管怎么指定, 数据分布都是静态对应到某些节点的.
每个分组中的每个节点只包含了部分数据.
计算通常需包含所有节点(以greenplum为例)
shared nothing数据库在多节点计算方面存在什么可改进点?
所有节点都参与计算, 一个大的SQL查询容易把资源打满, 影响其他查询性能, RT抖动比较严重.
Greenplum通过resource group来隔离资源, 尽量减少这样的影响
网络开销较大, 指PG-XC、citus, 如果遇到跨分组表JOIN(JOIN 的表分布在不同的逻辑分组内), 无法使用多阶段优化, 必须跨多个分组重分布数据, 造成大量网络开销.
PolarDB:
所有节点(RW, RO)共享一份存储, 当SQL需要用到多节点并行计算能力时, 可以多个实例共同出力(包括RW, RO), 出力是动态的, 所以可以满足SQL动态分组计算的前提.
多少个节点参与计算? 是动态的
可以所有节点, 也可以指定某些节点.
节点要出多少力? 是动态的
每个节点可以自主分配多少个work, 都可以动态配置.
为什么PolarDB满足SQL动态分组计算的前提?
所有节点共享一份数据, 任意节点想出力都行, 不需要跨节点传输数据, 不存在shared nothing的弊端.
任意节点可以组合成1组gang (动态指定一批计算节点处理某一个SQL, 业务区分. sql hint、guc)
PolarDB SQL动态分组计算的典型应用场景:
不同业务域的SQL同时跑在不同的节点集合上, 物理上隔绝干扰. (存储层是分布式块存储, 为所有PolarDB集群服务, 理论上可以认为是无限大、无限能力, 可以认为不存在存储层瓶颈)
HTAP 分时混合业务场景, 例如白天OLTP, 晚上T+1数据分析. 白天可以使用读写分离, 处理高并发小事务. 晚上可以用MPP特性, 调动所有节点的算力, 加速处理分析型SQL请求.
节点级动态算力分配: 当某个节点负载较高时, 可以给这个节点分配较少的算力. (通过SQL Hint, 参数等实现, 动态扫描则是自动实现的.)
《一起学PolarDB - 第13期 - 为什么木桶有短板?》
结合AI for DB, PolarDB 的SQL动态分组计算能力, 可以实现更加智能化的自动数据库驾驶.
本期问题1:
为什么shared nothing架构无法实现动态的节点算力调度?
a. shared nothing数据库的分布算法是hash算法.
b. shared nothing数据库需要每个节点参与计算, 使得每一次SQL查询都可以用到所有计算能力.
c. shared nothing数据库每个节点只能访问本地数据, 除了带分布键的查询或复制表的查询以为, 其他的查询都需要所有节点的参与, 无法动态调动指定节点参与.
d. shared nothing数据库的存储分布在所有的计算节点, 每一次SQL查询都需要访问所有计算节点, 才能访问到完整的数据.
答案:
c
解释:
参考本文内容
本期问题2:
为什么PolarDB可以实现动态的节点算力调度?
a. 共享数据, 任意节点都能访问完整的数据, 都可以参与计算
b. 支持类似MPP 的SQL优化器, 可以让多个计算节点参与计算
c. 支持通过HINT或参数控制每条SQL调动的算力
d. 查询时, 通过数据重分布实现跨节点动态计算
答案:
abc
解释:
参考本文内容
本期问题3:
动态的节点算力调度有什么益处?
a. 隔离不同的业务域, 不同业务域可以使用不同的节点分组进行计算
b. 每个节点都可以动态分配算力, 避免某些节点成为瓶颈(短板)
c. 适合混合负载, 白天oltp, 夜晚htap
d. 在需要时, 投入更多算力提高性能
答案:
abcd
解释:
参考本文内容
欢迎关注我的github (https://github.com/digoal/blog) , 学习数据库不迷路.
近期正在写公开课材料, 未来将通过视频号推出, 欢迎关注视频号:
文章中的参考文档请点击阅读原文获得.