バキューム処理によるストレージ容量の再利用
PostgreSQL のマルチバージョン同時実行制御 (MVCC) は、トランザクションがコミットまたはロールバックされるまで、更新または削除された行の内部コピーを保存することで、データの整合性を維持するのに役立ちます。これらのコピーはタプルとも呼ばれ、定期的にクリーンアップしないとテーブルが肥大化する原因となります。PostgreSQL インスタンスはトランザクション ID でトランザクションを順序付けます。PostgreSQL はトランザクション ID ベースの MVCC を使用してタプルの可視性を制御し、トランザクションを分離します。各トランザクションはデータのスナップショットを確立し、各タプルにはバージョンがあります。スナップショットとバージョンはどちらもトランザクション ID ベースです。
データをクリーンアップするために、VACUUM
ユーティリティは PostgreSQL で 4 つの主な関数を実行します。
-
VACUUM
– 期限切れの行バージョンを削除し、スペースを再利用できるようにします。 -
VACUUM FULL
– デッド行バージョンを削除してテーブルを圧縮することで、完全なデフラグメンテーションを実現し、サイズを縮小して効率を向上させます。 -
VACUUM FREEZE
– 古い行バージョンをフリーズとしてマークすることで、トランザクション ID の循環の問題から保護します。 -
VACUUM ANALYZE
– デッド行バージョンを削除し、データベースのクエリ計画統計を更新します。これは、VACUUM
関数とANALYZE
関数の組み合わせです。Aurora PostgreSQL Limitless Database でのANALYZE
処理の仕組みの詳細については、「ANALYZE」を参照してください。
MVCC と同様に、Aurora PostgreSQL でのバキューム処理はトランザクション ID ベースです。バキュームの開始時に進行中のトランザクションがある場合、そのトランザクションに表示されている行は削除されません。
VACUUM
ユーティリティの詳細については、PostgreSQL ドキュメントの「VACUUMVACUUM
のサポートの詳細については、「VACUUM」を参照してください。
トピック
AUTOVACUUM
Aurora PostgreSQL は、VACUUM
および AUTOVACUUM
ユーティリティを使用して不要なタプルを削除します。AUTOVACUUM
と手動 VACUUM
の基盤となるメカニズムは同じです。唯一の違いは自動化です。
Aurora PostgreSQL および Aurora PostgreSQL Limitless Database の AUTOVACUUM
は、VACUUM
と ANALYZE
ユーティリティの組み合わせです。AUTOVACUUM
は、デッドタプルの割合や挿入数など、事前定義されたルールに従って、クリーンアップするデータベースとテーブルを決定します。
例えば、AUTOVACUUM
は定期的に「ウェイクアップ」してクリーンアップを実行します。この間隔は、autovacuum_naptime
パラメータで制御されます。デフォルト値は 1 分です。Aurora PostgreSQL Limitless Database の AUTOVACUUM
および VACUUM
設定パラメータのデフォルト値は、Aurora PostgreSQL と同じです。
AUTOVACUUM
デーモンが有効になっている場合、テーブルの内容が一定以上変更されるたびに自動的に ANALYZE
コマンドを発行します。Aurora PostgreSQL Limitless Databaseでは、AUTOVACUUM
はルーターとシャードの両方で ANALYZE
を発行します。
AUTOVACUUM
に関連付けられているAUTOVACUUM
デーモンとテーブルストレージパラメータの詳細については、PostgreSQL ドキュメントの「The autovacuum daemon
Aurora PostgreSQL Limitless Database での時間ベースのバキューム処理
Aurora PostgreSQL Limitless Database は分散システムです。つまり、トランザクションに複数のインスタンスが関与する可能性があります。したがって、トランザクション ID ベースの可視性は適用されません。代わりに、Aurora PostgreSQL Limitless Database は時間ベースの可視性を使用します。トランザクション ID はインスタンス間で「統一」されませんが、時間はインスタンス間で「統一」できるからです。各トランザクションスナップショットと各タプルバージョンは、トランザクション ID ではなく時刻に従います。具体的には、トランザクションスナップショットにはスナップショットの開始時刻があり、タプルには作成時刻 (INSERT
または UPDATE
が発生した時刻) と削除時刻 (DELETE
が発生した時刻) があります。
DB シャードグループ内のインスタンス間でデータ整合性を維持するために、Aurora PostgreSQL Limitless Database は、DB シャードグループ内のアクティブなトランザクションに表示されているタプルがバキューム処理によって削除されないようにする必要があります。したがって、Aurora PostgreSQL Limitless Database でのバキューム処理も時間ベースです。VACUUM
のその他の側面は同じです。例えば、特定のテーブルで VACUUM
を実行するには、ユーザーがそのテーブルにアクセスできる必要があります。
注記
長時間トランザクションを開いたままにしないことを強くお勧めします。
時間ベースのバキューム処理は、トランザクション ID ベースのバキューム処理よりも多くのメモリを消費します。
次の例は、時間ベースのバキューム処理の仕組みを示しています。
-
顧客テーブルは 4 つのシャードに分散されています。
-
トランザクション 1 は繰り返し可能な読み取りで始まり、1 つのシャード (シャード 1) のみをターゲットとします。このトランザクションは開いたままです。
トランザクション 1 は、その後に開始された他のトランザクションよりも古くなります。
-
トランザクション 2 が後で開始され、テーブルからすべてのタプルを削除してからコミットします。
-
AUTOVACUUM
または手動VACUUM
がデッドタプルをクリーンアップしようとすると (トランザクション 2 によってデッド)、何も削除されません。これはシャード 1 だけでなく、シャード 2~4 にも当てはまります。トランザクション 1 が引き続きこれらのタプルにアクセスする必要がある可能性があるためです。MVCC のため、これらのタプルはトランザクション 1 に引き続き表示されます。
最後のステップは同期によって達成されます。これにより、トランザクション 1 はすべてのシャードに認識されますが、トランザクション 1 はすべてのシャードにアクセスするわけではありません。
データベース統計を使用したバキューム処理
クリーンアップが必要なタプルに関する情報を取得するには、pg_stat_all_tables
SELECT * FROM rds_aurora.limitless_stat_all_tables WHERE relname LIKE '%customer%';
同様に、データベース統計には pg_stat_database
テーブルのディスク使用量を確認するには、pg_relation_size
SELECT * FROM rds_aurora.limitless_stat_relation_sizes('public','customer');
Aurora PostgreSQL Limitless Database で VACUUM
オペレーションの進行状況を追跡するには、pg_stat_progress_vacuum
SELECT * FROM rds_aurora.limitless_stat_progress_vacuum;
詳細については、Aurora PostgreSQL Limitless Database ビューおよびAurora PostgreSQL Limitless Database 関数を参照してください。
Aurora PostgreSQL と Aurora PostgreSQL Limitless Database のバキューム動作の違い
Aurora PostgreSQL と Aurora PostgreSQL Limitless Database のバキューム処理の動作には、他に以下のような違いがあります。
-
Aurora PostgreSQL は、最も古い進行中のトランザクションまでのトランザクション ID に対して
VACUUM
オペレーションを実行します。データベースに進行中のトランザクションがない場合、VACUUM
は最後のトランザクションまでオペレーションを実行します。 -
Aurora PostgreSQL Limitless Database は、最も古い時間のスナップショットを 10 秒ごとに同期します。そのため、
VACUUM
は過去 10 秒以内に実行されたトランザクションに対してオペレーションを実行しない可能性があります。
Aurora PostgreSQL Limitless Database での VACUUM
のサポートの詳細については、「Aurora PostgreSQL Limitless Database リファレンス」の「VACUUM」を参照してください。