本文介绍了PolarDB PostgreSQL版的并行INSERT功能。
前提条件
支持的PolarDB PostgreSQL版的版本如下:
PostgreSQL 11(内核小版本1.1.17及以上)
PostgreSQL 14(内核小版本14.8.12.0及以上)
您可通过如下语句查看PolarDB PostgreSQL版的内核小版本的版本号:
PostgreSQL 11
show polar_version;
PostgreSQL 14
select version();
简介
PolarDB PostgreSQL版支持弹性跨机并行查询(ePQ)特性,通过利用集群中多个计算节点来提升查询性能。同时,ePQ也支持在读写节点上通过多进程并行写入,实现对INSERT
语句的加速。
ePQ的并行INSERT
功能用于加速INSERT INTO ... SELECT ...
这种读写兼备的SQL。对于SQL中的SELECT
部分,ePQ将启动多个进程并行执行查询;对于SQL中的INSERT
部分,ePQ将在读写节点上启动多个进程并行执行写入。执行写入的进程与执行查询的进程之间通过Motion算子进行数据传递。
支持并行INSERT
的表类型如下:
普通表
分区表
(部分)外部表
并行INSERT
支持动态调整写入并行度(写入进程数量),在查询不成为瓶颈的条件下性能最高能提升三倍。
原理介绍
并行查询和并行写入以流水线的形式同时进行。执行过程如下图所示:ePQ 对并行INSERT
的执行过程如下:
ePQ优化器以查询解析得到的语法树作为输入,产生计划树。
ePQ执行器将计划树分发到各计算节点,并创建并行查询/并行写入进程,开始执行各自负责执行的子计划。
并行查询进程从存储中并行读取各自负责的数据分片,并将数据发送到Motion算子。
并行写入进程从Motion算子中获取数据,向存储并行写入数据。
参数说明
通过
polar_px_dop_per_node
参数调整INSERT INTO ... SELECT ...
中查询的并行度。通过
polar_px_insert_dop_num
参数调整INSERT INTO ... SELECT ...
中写入的并行度。
当查询并行度较低时,逐步提升写入并行度,SQL执行时间将会逐渐下降并趋于平缓,趋于平缓的原因是查询速度跟不上写入速度而成为瓶颈。
当查询并行度较高时,逐步提升写入并行度,SQL执行时间将会逐渐下降并趋于平缓;趋于平缓的原因是并行写入只能在读写节点上进行,写入速度因多个写入进程对表页面扩展锁的争抢而跟不上查询速度,成为瓶颈。
示例
创建两张表
t1
和t2
,并向t1
中插入数据。CREATE TABLE t1 (id INT); CREATE TABLE t2 (id INT); INSERT INTO t1 SELECT generate_series(1,100000);
开启ePQ及并行
INSERT
功能。SET polar_enable_px TO ON; SET polar_px_enable_insert_select TO ON;
通过
INSERT
语句将t1
表中的所有数据插入到t2
表中。查看并行INSERT
的执行计划。EXPLAIN INSERT INTO t2 SELECT * FROM t1; QUERY PLAN ----------------------------------------------------------------------------------------- Insert on t2 (cost=0.00..952.87 rows=33334 width=4) -> Result (cost=0.00..0.00 rows=0 width=0) -> PX Hash 6:3 (slice1; segments: 6) (cost=0.00..432.04 rows=100000 width=8) -> Partial Seq Scan on t1 (cost=0.00..431.37 rows=16667 width=4) Optimizer: PolarDB PX Optimizer (5 rows)
其中的
PX Hash 6:3
表示6个并行查询t1
的进程通过Motion算子将数据传递给3个并行写入t2
的进程。通过参数
polar_px_insert_dop_num
动态调整写入并行度,查看并行INSERT
的执行计划。SET polar_px_insert_dop_num TO 12; EXPLAIN INSERT INTO t2 SELECT * FROM t1; QUERY PLAN ------------------------------------------------------------------------------------------ Insert on t2 (cost=0.00..952.87 rows=8334 width=4) -> Result (cost=0.00..0.00 rows=0 width=0) -> PX Hash 6:12 (slice1; segments: 6) (cost=0.00..432.04 rows=100000 width=8) -> Partial Seq Scan on t1 (cost=0.00..431.37 rows=16667 width=4) Optimizer: PolarDB PX Optimizer (5 rows)
通过执行计划中的
PX Hash 6:12
显示,并行查询t1
的进程数量不变,并行写入t2
的进程数量变为12
。