@@ -205,17 +205,14 @@ sub reactive_slots_change_hfs_and_wait_for_xmins
205
205
206
206
change_hot_standby_feedback_and_wait_for_xmins($hsf , $invalidated );
207
207
208
- $handle =
209
- make_slot_active($node_standby , $slot_prefix , 1, \$stdout , \$stderr );
210
-
211
208
# reset stat: easier to check for confl_active_logicalslot in pg_stat_database_conflicts
212
209
$node_standby -> psql(' testdb' , q[ select pg_stat_reset();] );
213
210
}
214
211
215
212
# Check invalidation in the logfile and in pg_stat_database_conflicts
216
213
sub check_for_invalidation
217
214
{
218
- my ($slot_prefix , $log_start , $test_name ) = @_ ;
215
+ my ($slot_prefix , $log_start , $test_name , $checks_active_slot ) = @_ ;
219
216
220
217
my $active_slot = $slot_prefix . ' activeslot' ;
221
218
my $inactive_slot = $slot_prefix . ' inactiveslot' ;
@@ -231,13 +228,17 @@ sub check_for_invalidation
231
228
$log_start ),
232
229
" activeslot slot invalidation is logged $test_name " );
233
230
234
- # Verify that pg_stat_database_conflicts.confl_active_logicalslot has been updated
235
- ok( $node_standby -> poll_query_until(
236
- ' postgres' ,
237
- " select (confl_active_logicalslot = 1) from pg_stat_database_conflicts where datname = 'testdb'" ,
238
- ' t' ),
239
- ' confl_active_logicalslot updated'
240
- ) or die " Timed out waiting confl_active_logicalslot to be updated" ;
231
+ if ($checks_active_slot )
232
+ {
233
+ # Verify that pg_stat_database_conflicts.confl_active_logicalslot has
234
+ # been updated
235
+ ok( $node_standby -> poll_query_until(
236
+ ' postgres' ,
237
+ " select (confl_active_logicalslot = 1) from pg_stat_database_conflicts where datname = 'testdb'" ,
238
+ ' t' ),
239
+ ' confl_active_logicalslot updated'
240
+ ) or die " Timed out waiting confl_active_logicalslot to be updated" ;
241
+ }
241
242
}
242
243
243
244
# Launch $sql query, wait for a new snapshot that has a newer horizon and
@@ -250,7 +251,11 @@ sub check_for_invalidation
250
251
# seeing a xl_running_xacts that would advance an active replication slot's
251
252
# catalog_xmin. Advancing the active replication slot's catalog_xmin
252
253
# would break some tests that expect the active slot to conflict with
253
- # the catalog xmin horizon.
254
+ # the catalog xmin horizon. Even with the above precaution, there is a risk
255
+ # of xl_running_xacts record being logged and replayed before the VACUUM
256
+ # command, leading to the test failure. So, we ensured that replication slots
257
+ # are not activated for tests that can invalidate slots due to 'rows_removed'
258
+ # conflict reason.
254
259
sub wait_until_vacuum_can_remove
255
260
{
256
261
my ($vac_option , $sql , $to_vac ) = @_ ;
@@ -532,11 +537,8 @@ sub wait_until_vacuum_can_remove
532
537
$node_subscriber -> stop;
533
538
534
539
# #################################################
535
- # Recovery conflict: Invalidate conflicting slots, including in-use slots
540
+ # Recovery conflict: Invalidate conflicting slots
536
541
# Scenario 1: hot_standby_feedback off and vacuum FULL
537
- #
538
- # In passing, ensure that replication slot stats are not removed when the
539
- # active slot is invalidated.
540
542
# #################################################
541
543
542
544
# One way to produce recovery conflict is to create/drop a relation and
@@ -550,10 +552,6 @@ sub wait_until_vacuum_can_remove
550
552
$node_primary -> safe_psql(' testdb' ,
551
553
qq[ INSERT INTO decoding_test(x,y) SELECT 100,'100';] );
552
554
553
- $node_standby -> poll_query_until(' testdb' ,
554
- qq[ SELECT total_txns > 0 FROM pg_stat_replication_slots WHERE slot_name = 'vacuum_full_activeslot']
555
- ) or die " replication slot stats of vacuum_full_activeslot not updated" ;
556
-
557
555
# This should trigger the conflict
558
556
wait_until_vacuum_can_remove(
559
557
' full' , ' CREATE TABLE conflict_test(x integer, y text);
@@ -562,19 +560,11 @@ sub wait_until_vacuum_can_remove
562
560
$node_primary -> wait_for_replay_catchup($node_standby );
563
561
564
562
# Check invalidation in the logfile and in pg_stat_database_conflicts
565
- check_for_invalidation(' vacuum_full_' , 1, ' with vacuum FULL on pg_class' );
563
+ check_for_invalidation(' vacuum_full_' , 1, ' with vacuum FULL on pg_class' , 0 );
566
564
567
565
# Verify reason for conflict is 'rows_removed' in pg_replication_slots
568
566
check_slots_conflict_reason(' vacuum_full_' , ' rows_removed' );
569
567
570
- # Ensure that replication slot stats are not removed after invalidation.
571
- is( $node_standby -> safe_psql(
572
- ' testdb' ,
573
- qq[ SELECT total_txns > 0 FROM pg_stat_replication_slots WHERE slot_name = 'vacuum_full_activeslot']
574
- ),
575
- ' t' ,
576
- ' replication slot stats not removed after invalidation' );
577
-
578
568
$handle =
579
569
make_slot_active($node_standby , ' vacuum_full_' , 0, \$stdout , \$stderr );
580
570
@@ -639,7 +629,7 @@ sub wait_until_vacuum_can_remove
639
629
" invalidated logical slots do not lead to retaining WAL" );
640
630
641
631
# #################################################
642
- # Recovery conflict: Invalidate conflicting slots, including in-use slots
632
+ # Recovery conflict: Invalidate conflicting slots
643
633
# Scenario 2: conflict due to row removal with hot_standby_feedback off.
644
634
# #################################################
645
635
@@ -660,7 +650,7 @@ sub wait_until_vacuum_can_remove
660
650
$node_primary -> wait_for_replay_catchup($node_standby );
661
651
662
652
# Check invalidation in the logfile and in pg_stat_database_conflicts
663
- check_for_invalidation(' row_removal_' , $logstart , ' with vacuum on pg_class' );
653
+ check_for_invalidation(' row_removal_' , $logstart , ' with vacuum on pg_class' , 0 );
664
654
665
655
# Verify reason for conflict is 'rows_removed' in pg_replication_slots
666
656
check_slots_conflict_reason(' row_removal_' , ' rows_removed' );
@@ -696,7 +686,7 @@ sub wait_until_vacuum_can_remove
696
686
697
687
# Check invalidation in the logfile and in pg_stat_database_conflicts
698
688
check_for_invalidation(' shared_row_removal_' , $logstart ,
699
- ' with vacuum on pg_authid' );
689
+ ' with vacuum on pg_authid' , 0 );
700
690
701
691
# Verify reason for conflict is 'rows_removed' in pg_replication_slots
702
692
check_slots_conflict_reason(' shared_row_removal_' , ' rows_removed' );
@@ -720,6 +710,10 @@ sub wait_until_vacuum_can_remove
720
710
reactive_slots_change_hfs_and_wait_for_xmins(' shared_row_removal_' ,
721
711
' no_conflict_' , 0, 1);
722
712
713
+ # As this scenario is not expected to produce any conflict, so activate the slot.
714
+ # See comments atop wait_until_vacuum_can_remove().
715
+ make_slot_active($node_standby , ' no_conflict_' , 1, \$stdout , \$stderr );
716
+
723
717
# This should not trigger a conflict
724
718
wait_until_vacuum_can_remove(
725
719
' ' , ' CREATE TABLE conflict_test(x integer, y text);
@@ -763,7 +757,7 @@ sub wait_until_vacuum_can_remove
763
757
$node_standby -> restart;
764
758
765
759
# #################################################
766
- # Recovery conflict: Invalidate conflicting slots, including in-use slots
760
+ # Recovery conflict: Invalidate conflicting slots
767
761
# Scenario 5: conflict due to on-access pruning.
768
762
# #################################################
769
763
@@ -788,7 +782,7 @@ sub wait_until_vacuum_can_remove
788
782
$node_primary -> wait_for_replay_catchup($node_standby );
789
783
790
784
# Check invalidation in the logfile and in pg_stat_database_conflicts
791
- check_for_invalidation(' pruning_' , $logstart , ' with on-access pruning' );
785
+ check_for_invalidation(' pruning_' , $logstart , ' with on-access pruning' , 0 );
792
786
793
787
# Verify reason for conflict is 'rows_removed' in pg_replication_slots
794
788
check_slots_conflict_reason(' pruning_' , ' rows_removed' );
@@ -832,7 +826,7 @@ sub wait_until_vacuum_can_remove
832
826
$node_primary -> wait_for_replay_catchup($node_standby );
833
827
834
828
# Check invalidation in the logfile and in pg_stat_database_conflicts
835
- check_for_invalidation(' wal_level_' , $logstart , ' due to wal_level' );
829
+ check_for_invalidation(' wal_level_' , $logstart , ' due to wal_level' , 1 );
836
830
837
831
# Verify reason for conflict is 'wal_level_insufficient' in pg_replication_slots
838
832
check_slots_conflict_reason(' wal_level_' , ' wal_level_insufficient' );
0 commit comments