数据库内核月报 - 2021 / 09

PolarDB · 引擎特性 · DDL物理复制优化

PolarDB通过存储计算分离架构,实现了主节点和只读节点共享同一份存储数据,既降低了存储成本,又提高了集群的可用性和可靠性。为实现这一架构,PolarDB采用了业界领先的物理复制技术,不仅实现了共享存储架构上主节点和只读节点间的数据一致性,而且减少了Binlog fsync操作带来的I/O开销。

InnoDB中的数据是通过B-Tree来维护索引的,然而大部分Slow DDL操作(如增加主键或二级索引、optimize table等)往往需要重建或新增B-Tree索引,导致大量物理日志的产生。而针对物理日志进行的操作往往出现在DDL执行的关键路径上,增加了DDL操作的执行时间。此外,物理复制技术要求只读节点解析和应用这些新生成的物理日志,由于DDL操作而产生的大量物理日志可能严重影响只读节点的日志同步进程,甚至导致只读节点不可用等问题。

针对上述问题,PolarDB提供了DDL物理复制优化功能,在主节点写物理日志和只读节点应用物理日志的关键路径上做了全面的优化,使得主节点在执行创建主键DDL操作的执行时间有明显下降,而只读节点除了解析DDL的复制延迟时间有明显下降外,资源消耗也非常平缓无抖动。

性能测试

您需要通过设置innodb_bulk_load_page_grained_redo_enable参数开启DDL物理复制优化功能(该参数将马上默认打开): ON:开启DDL物理复制优化 OFF:关闭DDL物理复制优化(默认值)

测试准备

测试环境 PolarDB MySQL引擎8.0版本的集群(包含1个主节点和1个只读节点)规格为16核128 GB,集群存储空间为50 TB。

测试表结构 通过如下语句创建一张名为t0的表: CREATE TABLE t0(a INT PRIMARY KEY, b INT) ENGINE=InnoDB;

测试表数据 使用如下语句生成随机测试数据:

DELIMITER //
CREATE PROCEDURE populate_t0()
BEGIN
     DECLARE i int DEFAULT 1;
     WHILE (i <= $table_size) DO
             INSERT INTO t0 VALUES (i, 1000000 * RAND());
             SET i = i + 1;
     END WHILE;
END //
DELIMITER ;
CALL populate_t0();

测试结果 - 主节点

经过测试,使用了DDL物理复制优化后,RW上执行DDL的性能有明显上升,具体表现如下。

当innodb_bulk_load_page_grained_redo_enable参数开启或关闭时,测试在不同数据量(1百万、1千万、1亿和10亿)的表中执行add primary key(a)操作所需的时间(单位:秒),结果如下图所示。 1.png

当innodb_bulk_load_page_grained_redo_enable参数开启或关闭时,测试在不同数据量(1百万、1千万、1亿和10亿)的表中执行optimize table操作所需的时间(单位:秒),结果如下图所示。 2.png

测试结果 - 从节点

更为重要的是,开启了DDL物理复制优化后,RO上执行DDL性能非常平稳无抖动,具体表现如下:

innodb_bulk_load_page_grained_redo_enable参数开启的情况下,测试当集群(包含10亿数据量的表)中主节点的并发执行DDL操作数量不同(1、2、4、6和8)时只读节点的性能,结果如下表所示。

innodb_bulk_load_page_grained_redo_enable参数关闭的情况下,测试当集群(包含10亿数据量的表)中主节点的并发执行DDL操作数量不同(1、2、4、6和8)时只读节点的性能,结果如下表所示。