diff --git a/src/test/recovery/t/040_standby_failover_slots_sync.pl b/src/test/recovery/t/040_standby_failover_slots_sync.pl index b2bf5072bbf..7d3c82e0a29 100644 --- a/src/test/recovery/t/040_standby_failover_slots_sync.pl +++ b/src/test/recovery/t/040_standby_failover_slots_sync.pl @@ -213,75 +213,19 @@ is( $standby1->safe_psql( ################################################## # Test that the synchronized slot will be dropped if the corresponding remote # slot on the primary server has been dropped. -# -# Note: Both slots need to be dropped for the next test to work ################################################## $primary->psql('postgres', "SELECT pg_drop_replication_slot('lsub2_slot');"); -$primary->psql('postgres', "SELECT pg_drop_replication_slot('lsub1_slot');"); $standby1->safe_psql('postgres', "SELECT pg_sync_replication_slots();"); is( $standby1->safe_psql( 'postgres', - q{SELECT count(*) = 0 FROM pg_replication_slots WHERE slot_name IN ('lsub1_slot', 'lsub2_slot');} + q{SELECT count(*) = 0 FROM pg_replication_slots WHERE slot_name = 'lsub2_slot';} ), "t", 'synchronized slot has been dropped'); -################################################## -# Verify that slotsync skip statistics are correctly updated when the -# slotsync operation is skipped. -################################################## - -# Create a logical replication slot and create some DDL on the primary so -# that the slot lags behind the standby. -$primary->safe_psql( - 'postgres', qq( - SELECT pg_create_logical_replication_slot('lsub1_slot', 'pgoutput', false, false, true); - CREATE TABLE wal_push(a int); -)); -$primary->wait_for_replay_catchup($standby1); - -my $log_offset = -s $standby1->logfile; - -# Enable slot sync worker. -$standby1->append_conf('postgresql.conf', qq(sync_replication_slots = on)); -$standby1->reload; - -# Confirm that the slot sync worker is able to start. -$standby1->wait_for_log(qr/slot sync worker started/, $log_offset); - -# Confirm that the slot sync is skipped due to the remote slot lagging behind -$standby1->wait_for_log( - qr/could not synchronize replication slot \"lsub1_slot\"/, $log_offset); - -# Confirm that the slotsync skip statistics is updated -$result = $standby1->safe_psql('postgres', - "SELECT slotsync_skip_count > 0 FROM pg_stat_replication_slots WHERE slot_name = 'lsub1_slot'" -); -is($result, 't', "check slot sync skip count increments"); - -# Clean the table -$primary->safe_psql( - 'postgres', qq( - DROP TABLE wal_push; -)); -$primary->wait_for_replay_catchup($standby1); - -# Re-create the logical replication slot and sync it to standby for further tests -$primary->safe_psql( - 'postgres', qq( - SELECT pg_drop_replication_slot('lsub1_slot'); - SELECT pg_create_logical_replication_slot('lsub1_slot', 'pgoutput', false, false, true); -)); -$standby1->wait_for_log( - qr/newly created replication slot \"lsub1_slot\" is sync-ready now/, - $log_offset); - -$standby1->append_conf('postgresql.conf', qq(sync_replication_slots = off)); -$standby1->reload; - ################################################## # Test that if the synchronized slot is invalidated while the remote slot is # still valid, the slot will be dropped and re-created on the standby by @@ -337,7 +281,7 @@ $inactive_since_on_primary = # the failover slots. $primary->wait_for_replay_catchup($standby1); -$log_offset = -s $standby1->logfile; +my $log_offset = -s $standby1->logfile; # Synchronize the primary server slots to the standby. $standby1->safe_psql('postgres', "SELECT pg_sync_replication_slots();"); @@ -1043,4 +987,72 @@ $result = $standby1->safe_psql('postgres', is($result, '1', "data can be consumed using snap_test_slot"); +################################################## +# Remove any unnecessary replication slots and clear pending transactions on the +# primary server to ensure a clean environment. +################################################## + +$primary->psql( + 'postgres', qq( + SELECT pg_drop_replication_slot('sb1_slot'); + SELECT pg_drop_replication_slot('lsub1_slot'); + SELECT pg_drop_replication_slot('snap_test_slot'); +)); + +$subscriber2->safe_psql('postgres', 'DROP SUBSCRIPTION regress_mysub2;'); + +# Verify that all slots have been removed except the one necessary for standby2, +# which is needed for further testing. +is( $primary->safe_psql( + 'postgres', + q{SELECT count(*) = 0 FROM pg_replication_slots WHERE slot_name != 'sb2_slot';} + ), + "t", + 'all replication slots have been dropped except the physical slot used by standby2' +); + +# Commit the pending prepared transaction +$primary->safe_psql('postgres', "COMMIT PREPARED 'test_twophase_slotsync';"); +$primary->wait_for_replay_catchup($standby2); + +################################################## +# Verify that slotsync skip statistics are correctly updated when the +# slotsync operation is skipped. +################################################## + +# Create a logical replication slot and create some DDL on the primary so +# that the slot lags behind the standby. +$primary->safe_psql( + 'postgres', qq( + SELECT pg_create_logical_replication_slot('lsub1_slot', 'pgoutput', false, false, true); + CREATE TABLE wal_push(a int); +)); +$primary->wait_for_replay_catchup($standby2); + +$log_offset = -s $standby2->logfile; + +# Enable slot sync worker +$standby2->append_conf( + 'postgresql.conf', qq( +hot_standby_feedback = on +primary_conninfo = '$connstr_1 dbname=postgres' +log_min_messages = 'debug2' +sync_replication_slots = on +)); + +$standby2->reload; + +# Confirm that the slot sync worker is able to start. +$standby2->wait_for_log(qr/slot sync worker started/, $log_offset); + +# Confirm that the slot sync is skipped due to the remote slot lagging behind +$standby2->wait_for_log( + qr/could not synchronize replication slot \"lsub1_slot\"/, $log_offset); + +# Confirm that the slotsync skip statistics is updated +$result = $standby2->safe_psql('postgres', + "SELECT slotsync_skip_count > 0 FROM pg_stat_replication_slots WHERE slot_name = 'lsub1_slot'" +); +is($result, 't', "check slot sync skip count increments"); + done_testing();