PolarDB for PostgreSQL は、Object Storage Service (OSS) 外部テーブルの並列書き込みおよびクエリ用のElastic Parallel Query (ePQ) 機能をサポートしています。
前提条件
次のいずれかのバージョンを実行するPolarDB for PostgreSQLクラスターが作成されます。
マイナーバージョンが14.9.13.0以降のPostgreSQL 14
マイナーバージョンが1.1.35以降のPostgreSQL 11
次のいずれかのステートメントを実行して、PolarDB for PostgreSQLクラスターのマイナーバージョンを表示できます。
PostgreSQL 14
select version();PostgreSQL 11
ショーpolar_version;
背景情報
PolarDB for PostgreSQL では、OSS_fdw拡張子を使用してoss外部テーブルを作成できます。 外部テーブルは物理的にOSSに格納され、外部テーブルのメタデータのみがデータベースに格納されます。 これにより、データベースで頻繁に使用されない履歴データまたはコールドデータを外部テーブルとしてOSSにアーカイブして、データベースのストレージコストを削減できます。 PolarDB for PostgreSQL で使用される外部データラッパー (FDW) 標準は、指定された条件下で標準SQLステートメントを実行することで、OSS外部テーブルの読み取りと書き込みを継続できるようにします。
データアーカイブのためにローカルテーブルからOSS外部テーブルにデータを書き込むと、デフォルトでPolarDB for PostgreSQL がOSS外部テーブルにデータを書き込むプロセスを開始します。 この場合、単一のプロセスを使用して、ネットワーク経由でOSSにデータをアップロードします。 大量のデータをアーカイブする必要があるシナリオでは、ネットワーク帯域幅の使用率が低いため、単一プロセス書き込みモードは非効率的です。
OSS外部テーブルの履歴アーカイブデータをクエリすると、デフォルトでPolarDB for PostgreSQL がOSS外部テーブルの全データをクエリするプロセスを開始します。 この場合、単一のプロセスを使用して、ネットワーク経由でOSSからデータをダウンロードします。 大量のアーカイブデータを照会する必要があるシナリオでは、ネットワーク帯域幅の使用率が低いため、単一プロセス照会モードは非効率的です。
上記の問題を解決するために、PolarDB for PostgreSQL は、OSS外部テーブルの並列書き込みとクエリのePQをサポートしています。
ePQオプティマイザは、複数のプロセスのOSS外部テーブルへの並列データ書き込みの実行計画を生成できます。 ePQオプティマイザは、読み書きノードで複数のプロセスを開始して、OSS外部テーブルにデータを並列に書き込みます。
ePQオプティマイザは、複数のプロセスでOSS外部テーブルの並列データクエリの実行プランを生成できます。 ePQオプティマイザは、読み書きノードで複数のプロセスを開始して、OSS外部テーブルのデータを並列にクエリします。
このように、単一プロセスのアップロードおよびダウンロードモードは、マルチプロセスのアップロードおよびダウンロードモードに最適化される。 これにより、OSSのネットワーク帯域幅リソースを最大限に活用し、コールドデータのアーカイブとクエリのパフォーマンスを向上させます。
手順
データの準備
t_localという名前のローカルテーブルを作成し、特定の量のデータをテーブルに挿入します。CREATE TABLE t_local (id INT、age INT、msg TEXT、detail TEXT); INSERT INTO t_local 選択 ランダム () * 1000000、 ランダム () * 10000、 md5 (ランダム ():: テキスト) 、 md5 (ランダム ()::TEXT) FROM generate_series(1, 2000000);ローカルテーブル
t_localと同じスキーマを持つt_OSSという名前のoss外部テーブルを作成します。拡張の作成oss_fdw; CREATE SERVER ossserver外国データラッパーoss_fdw オプション (ホスト 'oss -cn-xxx.aliyuncs.com '、バケット 'mybucket' 、id 'xxx' 、key 'xxx'); CREATE FOREIGN TABLE t_oss (id INT, age INT, msg TEXT, detail TEXT) サーバーossserverオプション (dir 'archive/');
OSS外部テーブルへのデータの並列書き込み
次のコマンドを実行して、ePQを無効にします。
polar_enable_pxをオフに設定します。次のコマンドを実行して、ローカルテーブル
t_localからOSS外部テーブルt_ossにデータをインポートします。 次のサンプルコードは、実行計画の例を示し、消費時間を示しています。EXPLAIN (コストオフ) INSERT INTO t_oss SELECT * FROM t_local; クエリ計画 --------------------------- t_ossに挿入 -> Seqスキャンでt_local (2行) INSERT INTO t_oss SELECT * FROM t_local; INSERT 0 2000000 時間: 8861.708 ms (00:08.862)前述の実行計画に従って、エグゼキュータはローカルテーブルをスキャンすると同時にOSS外部テーブルにデータを書き込むプロセスを開始します。 消費される合計時間は8861.708ミリ秒です。
次のコマンドを実行してePQと並列
INSERT機能を有効にし、ローカルテーブルの並列クエリの並列度とOSS外部テーブルへの並列書き込みの並列度を16に設定します。SET polar_enable_pxをオンにします。polar_px_enable_insert_selectをオンに設定します。polar_px_dop_per_nodeを16に設定します。SET polar_px_insert_dop_numに16;次のコマンドを再度実行します。 次のサンプルコードは、実行計画の例を示し、消費時間を示しています。
EXPLAIN (コストオフ) INSERT INTO t_oss SELECT * FROM t_local; クエリ計画 --------------------------------------------------- t_ossに挿入 -> 結果 -> PXハッシュ32:16 (slice1; セグメント: 32) -> t_localの部分Seqスキャン Optimizer: PolarDB PX Optimizer (5行) INSERT INTO t_oss SELECT * FROM t_local; INSERT 0 2000000 時間: 1321.212 ms (00:01.321)上記の実行計画では、
segments: 32は、エグゼキュータがslice1を実行するために32のプロセスを開始することを示します。Partial Seq Scanは、ローカルテーブルが並列にスキャンされることを示します。PX Hash 32:16は、Motion演算子を使用して、OSS外部テーブルへの並列書き込みのために16のプロセスにデータを分散することを示します。 消費される合計時間は1321.212ミリ秒であり、シングルプロセスモードでのデータ書き込みと比較して大幅に短縮されます。
OSS外部テーブルのデータを並行してクエリ
次のコマンドを実行して、ePQを無効にします。
polar_enable_pxをオフに設定します。次のコマンドを実行して、OSS外部テーブル
t_ossの完全なデータを照会します。 次のサンプルコードは、実行プランの例を示し、クエリ結果を示しています。EXPLAIN SELECT COUNT(*) FROM t_oss; クエリ計画 ------------------------------------------------------------------------------- 集計 (コスト=1366687.96 .. 1366687.97行=1幅=8) -> 外部スキャンt_oss (コスト=0.00 .. 1334280.40行=12963024幅=0) OSS上のディレクトリ: archive / OSSファイルの数: 17 OSSファイルの合計サイズ: 297 MB (5行) 選択カウント (*) からt_oss; カウント --------- 4000000 (1行) 時間: 36230.325 ms (00:36.230)前述の実行計画に従って、エグゼキュータはOSS外部テーブル内の17個のOSSオブジェクトをスキャンするプロセスを開始します。 OSSオブジェクトの合計サイズは297 MBです。 消費される合計時間は36230.325ミリ秒です。
次のコマンドを実行してePQを有効にし、並列クエリの並列度を8に設定します。
SET polar_enable_pxをオンにします。SET polar_px_dop_per_nodeに8;次のコマンドを再度実行します。 次のサンプルコードは、実行プランの例を示し、クエリ結果を示しています。
EXPLAIN SELECT COUNT(*) FROM t_oss; クエリ計画 --------------------------------------------------------------------------------------- 集計 (コスト=0.00 .. 431.00行=1幅=8) -> PXコーディネーター16:1 (slice1; セグメント: 16) (コスト=0.00 .. 431.00行=1 width=1) -> t_ossの部分外部スキャン (コスト=0.00 .. 431.00行=1幅=1) OSS上のディレクトリ: archive / OSSファイルの数: 17 OSSファイルの合計サイズ: 297 MB Optimizer: PolarDB PX Optimizer (7行) 選択カウント (*) からt_oss; カウント --------- 4000000 (1行) 時間: 18100.894 ms (00:18.101)上記の実行計画では、
segments: 16は、エグゼキュータがslice1を実行するために16のプロセスを開始することを示します。Partial Foreign Scanは、OSS外部テーブルが並行してスキャンされることを示します。 OSSオブジェクトは、並列クエリのために16のプロセスに分散されます。PXコーディネーター16:1は、すべてのプロセスのクエリ結果が、データクエリを開始するプロセスに集約され、Motion演算子を使用して返されることを示します。 合計時間は18100.894ミリ秒で、シングルプロセスモードのデータクエリと比較して大幅に短縮されます。