Hologres では、トランザクションはすべてのデータ定義言語 (DDL) 文と一部のデータ操作言語 (DML) 文をサポートします。デフォルトでは、単一の SQL 文を 1 つのトランザクションで実行できます。このトピックでは、Hologres のトランザクション機能について説明します。
サポートされるシナリオ
このセクションでは、Hologresにおけるトランザクションの使用シナリオについて説明します。
トランザクション内での複数のDDLステートメントの実行
複数のテーブル作成文を実行するトランザクションを作成できます。エラーが発生すると、トランザクションはロールバックされます。サンプルコードは次のとおりです:
begin; drop table if exists ddl_test; create table ddl_test( uid text not null, name text not null); commit;1 つのトランザクションでの複数の DML 文の実行 (ベータ版)
Hologres V2.0以降では、複数のDMLステートメントを1つのトランザクションで実行できます。これにより、SQL操作における複数のDMLステートメントの原子性と一貫性が保証されます。トランザクションは、DMLステートメントを使用してデータを書き込む際、データの一貫性を保証します。これにより、Hologresは軽量トランザクション処理に適しています。ただし、トランザクションに複数のDMLステートメントが含まれている場合、Hologresの分散機能を sepenuhnya 活用することはできません。その結果、高いクエリ/秒(QPS)の要件を満たすことができません。
シナリオ:複数のDMLステートメントを1つのトランザクションで実行して、INSERT、UPDATE、およびDELETEステートメントにおけるデータの一貫性を確保できます。
注意事項:
複数のDMLステートメントを含むトランザクションは、QPSが低いシナリオでのみ使用でき、高並列性のシナリオには適していません。テストを実行して、複数のDMLステートメントが実行されるトランザクションでサポートされる最大QPSを取得できます。
トランザクションに書き込み操作とクエリ操作の両方が含まれる場合、クエリのパフォーマンスはトランザクションを使用しない場合よりも低くなります。実際のパフォーマンス低下はシナリオによって異なります。
トランザクションでテーブルのデータの読み取り、書き込み、削除、または更新を行う場合、テーブルはロックされます。同じテーブルに対するトランザクションは、次の図に示すように順番に実行されます。
重要書き込み対象のテーブルだけでなく、クエリ対象のテーブルにもロックが適用されることにご注意ください。例:
ユーザー A が次の SQL 文を実行します:
set hg_experimental_enable_transaction = on; BEGIN ; delete from dml_test; insert into dml_test SELECT * FROM base_tbl; COMMIT;ユーザー B が次の SQL 文を実行します:
set hg_experimental_enable_transaction = on; BEGIN ; delete from dml_test_2; insert into dml_test_2 SELECT * FROM base_tbl; COMMIT;
この場合、base_tbl テーブルもロックされます。ユーザー B が送信した SQL 文は、ユーザー A のトランザクションが終了するのを待ってから開始する必要があります。したがって、複数文の DML トランザクションを有効にすると、競合が発生した場合に SQL の実行時間が大幅に増加します。これにより、タイムアウトエラーが発生することさえあります。
1 つのトランザクションで複数の DML 文を実行する場合、既知の問題が存在します。DML 文をキャンセルした後にロールバック操作を実行すると、トランザクションは削除されず、トランザクションによって取得されたテーブルレベルのロックはリリースされません。サンプル文:
set hg_experimental_enable_transaction = on; begin; insert into dml_test select i from generate_series(1,100000) t(i); -- INSERT INTO 文をキャンセルします。 rollback; -- dml_test テーブルはロックされます。
使用上の注意:
混合 DML トランザクションはデフォルトで無効になっていますが、次の GUC パラメーターを使用して有効にできます:
set hg_experimental_enable_transaction = on;混合 DML トランザクションを有効にすると、1 つのトランザクションに複数の DML 文を含めることができます:
トランザクション内の1つのDMLステートメントが失敗した場合、システムはトランザクション内のすべてのDMLステートメントを自動的にロールバックし、他のDMLステートメントも失敗します。
正常に実行されているDMLステートメントをロールバックする場合、DMLステートメントが実行されているトランザクションをロールバックできます。このようにして、トランザクション内のすべてのDMLステートメントがロールバックされます。
set hg_experimental_enable_transaction = on; begin ; delete from dml_test; insert into dml_test values (1,'sss'); rollback;
Hologresは、DDLステートメントとDMLステートメントの両方を含むトランザクションをサポートしていません。
例えば、同じトランザクションに DDL 文と DML 文を含めると、次のエラーが報告されます:
ERROR: INSERT in ddl transaction is not supported now。begin; drop table if exists dml_test; create table dml_test ( uid text not null, name text not null); insert into dml_test values('1','tom'); commit;