commit 18516b98dc050110df739b6f7aa9d5ef99b5fda5 Author: Simon Riggs Date: Tue Nov 22 15:35:47 2022 +0000 rollback_on_commit.v2.patch diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml index 6ad22a26f8..4dbfd63d01 100644 --- a/doc/src/sgml/config.sgml +++ b/doc/src/sgml/config.sgml @@ -8850,6 +8850,24 @@ COPY postgres_log FROM '/full/path/to/logfile.csv' WITH csv; + + default_rollback_on_commit (boolean) + + rollback on commit + + + rollback_on_commit configuration parameter + + + + + This parameter controls whether a COMMIT + will rollback each transaction (on), or + commit each transaction. The default is off. + + + + default_transaction_deferrable (boolean) diff --git a/src/backend/access/transam/xact.c b/src/backend/access/transam/xact.c index c5852bc7ef..9562681ff7 100644 --- a/src/backend/access/transam/xact.c +++ b/src/backend/access/transam/xact.c @@ -83,6 +83,9 @@ bool XactReadOnly; bool DefaultXactDeferrable = false; bool XactDeferrable; +bool DefaultXactRollbackOnCommit = false; +bool XactRollbackOnCommit; + int DefaultXactNesting; int XactNesting = XACT_NEST_OFF; int XactNestingLevel = 0; @@ -2057,6 +2060,7 @@ StartTransaction(void) XactIsoLevel = DefaultXactIsoLevel; XactNesting = DefaultXactNesting; XactNestingLevel = 0; + XactRollbackOnCommit = DefaultXactRollbackOnCommit; forceSyncCommit = false; MyXactFlags = 0; @@ -3013,6 +3017,7 @@ SaveTransactionCharacteristics(SavedTransactionCharacteristics *s) s->save_XactReadOnly = XactReadOnly; s->save_XactDeferrable = XactDeferrable; s->save_XactNesting = XactNesting; + s->save_XactRollbackOnCommit = XactRollbackOnCommit; } void @@ -3022,6 +3027,7 @@ RestoreTransactionCharacteristics(const SavedTransactionCharacteristics *s) XactReadOnly = s->save_XactReadOnly; XactDeferrable = s->save_XactDeferrable; XactNesting = s->save_XactNesting; + XactRollbackOnCommit = s->save_XactRollbackOnCommit; } @@ -4137,6 +4143,12 @@ EndTransactionBlock(bool chain) s->chain = chain; + if (s->blockState == TBLOCK_END && XactRollbackOnCommit) + { + s->blockState = TBLOCK_ABORT_PENDING; + result = false; + } + return result; } diff --git a/src/backend/utils/misc/guc_tables.c b/src/backend/utils/misc/guc_tables.c index 865013f759..975e149ff8 100644 --- a/src/backend/utils/misc/guc_tables.c +++ b/src/backend/utils/misc/guc_tables.c @@ -1553,6 +1553,15 @@ struct config_bool ConfigureNamesBool[] = false, check_transaction_deferrable, NULL, NULL }, + { + {"rollback_on_commit", PGC_USERSET, CLIENT_CONN_STATEMENT, + gettext_noop("Whether to rollback the current transaction when a COMMIT statement is issued."), + NULL + }, + &DefaultXactRollbackOnCommit, + false, + NULL, NULL, NULL + }, { {"row_security", PGC_USERSET, CLIENT_CONN_STATEMENT, gettext_noop("Enable row security."), diff --git a/src/include/access/xact.h b/src/include/access/xact.h index 1cdc697fe1..acecc6a161 100644 --- a/src/include/access/xact.h +++ b/src/include/access/xact.h @@ -50,6 +50,8 @@ extern PGDLLIMPORT int XactIsoLevel; extern PGDLLIMPORT int DefaultXactNesting; +extern PGDLLIMPORT bool DefaultXactRollbackOnCommit; + /* * We implement three isolation levels internally. * The two stronger ones use one snapshot per database transaction; @@ -157,6 +159,7 @@ typedef struct SavedTransactionCharacteristics bool save_XactReadOnly; bool save_XactDeferrable; int save_XactNesting; + bool save_XactRollbackOnCommit; } SavedTransactionCharacteristics; diff --git a/src/test/regress/expected/transactions.out b/src/test/regress/expected/transactions.out index fffedf49f4..6c92125d07 100644 --- a/src/test/regress/expected/transactions.out +++ b/src/test/regress/expected/transactions.out @@ -1428,6 +1428,17 @@ SELECT * FROM abc ORDER BY 1; (0 rows) RESET nested_transactions; +SET rollback_on_commit = true; +TRUNCATE abc; +BEGIN; +INSERT INTO abc VALUES (1); +COMMIT; +SELECT * FROM abc ORDER BY 1; + a +--- +(0 rows) + +RESET rollback_on_commit; DROP TABLE abc; -- Test for successful cleanup of an aborted transaction at session exit. -- THIS MUST BE THE LAST TEST IN THIS FILE. diff --git a/src/test/regress/sql/transactions.sql b/src/test/regress/sql/transactions.sql index 35ce4ec6ae..325488f6da 100644 --- a/src/test/regress/sql/transactions.sql +++ b/src/test/regress/sql/transactions.sql @@ -773,6 +773,16 @@ SELECT * FROM abc ORDER BY 1; RESET nested_transactions; +SET rollback_on_commit = true; + +TRUNCATE abc; +BEGIN; +INSERT INTO abc VALUES (1); +COMMIT; +SELECT * FROM abc ORDER BY 1; + +RESET rollback_on_commit; + DROP TABLE abc; -- Test for successful cleanup of an aborted transaction at session exit.