diff --git a/tsl/src/remote/txn_resolve.c b/tsl/src/remote/txn_resolve.c index 997616e64..8d1b316a9 100644 --- a/tsl/src/remote/txn_resolve.c +++ b/tsl/src/remote/txn_resolve.c @@ -28,15 +28,22 @@ remote_txn_resolution(Oid foreign_server, const RemoteTxnId *transaction_id) return REMOTE_TXN_RESOLUTION_ABORT; } -/* Resolve any unresolved 2-pc transaction on a data node. - Since the remote_txn log can be long, and most txn there - will have been resolved, do not iterate that list. - Instead query the data node for the list of unresolved txns - via the pg_prepared_xacts view. Using that list, then check - remote_txn. Use this as an opportunity to clean up remote_txn - as well. -*/ -#define GET_PREPARED_XACT_SQL "SELECT gid FROM pg_prepared_xacts" +/* + * Resolve any unresolved 2-pc transaction on a data node. + * Since the remote_txn log can be long, and most txn there + * will have been resolved, do not iterate that list. + * + * Instead query the data node for the list of unresolved txns + * via the pg_prepared_xacts view. Using that list, then check + * remote_txn. Use this as an opportunity to clean up remote_txn + * as well. + * + * Note that pg_prepared_xacts shared across other databases which + * also could be distributed. Right now we interested only in + * the current one. + */ +#define GET_PREPARED_XACT_SQL \ + "SELECT gid FROM pg_prepared_xacts WHERE database = current_database()" Datum remote_txn_heal_data_node(PG_FUNCTION_ARGS) diff --git a/tsl/test/expected/remote_txn_resolve.out b/tsl/test/expected/remote_txn_resolve.out index f689f8c47..d29c156d1 100644 --- a/tsl/test/expected/remote_txn_resolve.out +++ b/tsl/test/expected/remote_txn_resolve.out @@ -184,3 +184,24 @@ SELECT count(*) FROM _timescaledb_catalog.remote_txn; 0 (1 row) +-- test that healing function does not conflict with other databases +-- +-- #3433 +-- create additional database and simulate remote txn activity +CREATE DATABASE test_an2; +\c test_an2 +BEGIN; +CREATE TABLE unused(id int); +PREPARE TRANSACTION 'ts-1-10-20-30'; +\c :TEST_DBNAME :ROLE_SUPERUSER +-- should not fail +SELECT _timescaledb_internal.remote_txn_heal_data_node((SELECT OID FROM pg_foreign_server WHERE srvname = 'loopback')); + remote_txn_heal_data_node +--------------------------- + 0 +(1 row) + +\c test_an2 +ROLLBACK PREPARED 'ts-1-10-20-30'; +\c :TEST_DBNAME :ROLE_SUPERUSER +DROP DATABASE test_an2; diff --git a/tsl/test/sql/remote_txn_resolve.sql b/tsl/test/sql/remote_txn_resolve.sql index 512a7254a..07d77edaf 100644 --- a/tsl/test/sql/remote_txn_resolve.sql +++ b/tsl/test/sql/remote_txn_resolve.sql @@ -74,3 +74,21 @@ COMMIT PREPARED 'non-ts-txn'; SELECT * FROM table_modified_by_txns; SELECT count(*) FROM pg_prepared_xacts; SELECT count(*) FROM _timescaledb_catalog.remote_txn; + +-- test that healing function does not conflict with other databases +-- +-- #3433 + +-- create additional database and simulate remote txn activity +CREATE DATABASE test_an2; +\c test_an2 +BEGIN; +CREATE TABLE unused(id int); +PREPARE TRANSACTION 'ts-1-10-20-30'; +\c :TEST_DBNAME :ROLE_SUPERUSER +-- should not fail +SELECT _timescaledb_internal.remote_txn_heal_data_node((SELECT OID FROM pg_foreign_server WHERE srvname = 'loopback')); +\c test_an2 +ROLLBACK PREPARED 'ts-1-10-20-30'; +\c :TEST_DBNAME :ROLE_SUPERUSER +DROP DATABASE test_an2;