Skip to content

Commit

Permalink
Drop replication slot after failover being demoted to secondary (#43)
Browse files Browse the repository at this point in the history
Replication slot record remains in pg_replication_slots after
primary gets demoted to be secondary. This commit explicitly
removes the record upon demotion.

Fixes #42
  • Loading branch information
mtuncer committed Jul 10, 2019
1 parent 2314ed8 commit 3b2c31b
Show file tree
Hide file tree
Showing 3 changed files with 39 additions and 2 deletions.
7 changes: 7 additions & 0 deletions src/bin/pg_autoctl/fsm_transition.c
Original file line number Diff line number Diff line change
Expand Up @@ -471,6 +471,13 @@ fsm_rewind_or_init(Keeper *keeper)
}
}

if (!primary_drop_replication_slot(postgres, config->replication_slot_name))
{
log_error("Failed to drop replication slot \"%s\" used by the standby failed",
config->replication_slot_name);
return false;
}

return true;
}

Expand Down
11 changes: 11 additions & 0 deletions tests/pgautofailover_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -483,6 +483,17 @@ def disable(self, feature, formation='default'):
name="disable feature",
timeout=COMMAND_TIMEOUT)

def failover(self, formation='default', group=0):
"""
performs manual failover for given formation and group id
"""
failover_commmand_text = "select * from pgautofailover.perform_failover('%s', %s)" %(formation, group)
failover_command = [shutil.which('psql'), '-d', self.database, '-c', failover_commmand_text]
failover_proc = self.vnode.run(failover_command)
wait_or_timeout_proc(failover_proc,
name="manual failover",
timeout=COMMAND_TIMEOUT)



def wait_or_timeout_proc(proc, name, timeout):
Expand Down
23 changes: 21 additions & 2 deletions tests/test_basic_operation.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
from nose.tools import *

cluster = None
monitor = None
node1 = None
node2 = None
node3 = None
Expand All @@ -14,7 +15,8 @@ def teardown_module():
cluster.destroy()

def test_000_create_monitor():
cluster.create_monitor("/tmp/monitor")
global monitor
monitor = cluster.create_monitor("/tmp/monitor")

def test_001_init_primary():
global node1
Expand Down Expand Up @@ -97,6 +99,23 @@ def test_014_add_new_secondary():
assert node3.wait_until_state(target_state="secondary")
assert node2.wait_until_state(target_state="primary")

def test_015_drop_primary():
def test_015_multiple_manual_failover_verify_replication_slot_removed():
monitor.failover()
assert node3.wait_until_state(target_state="primary")
assert node2.wait_until_state(target_state="secondary")
node2_replication_slots = node2.run_sql_query("select count(*) from pg_replication_slots")
assert node2_replication_slots == [(0,)]
node3_replication_slots = node3.run_sql_query("select count(*) from pg_replication_slots")
assert node3_replication_slots == [(1,)]

monitor.failover()
assert node2.wait_until_state(target_state="primary")
assert node3.wait_until_state(target_state="secondary")
node2_replication_slots = node2.run_sql_query("select count(*) from pg_replication_slots");
assert node2_replication_slots == [(1,)]
node3_replication_slots = node3.run_sql_query("select count(*) from pg_replication_slots");
assert node3_replication_slots == [(0,)]

def test_016_drop_primary():
node2.drop()
assert node3.wait_until_state(target_state="single")

0 comments on commit 3b2c31b

Please sign in to comment.