supervisordb \
upgrade \
identifier \
+ pause \
$(DDLREGRESSCHECKS) \
dml/basic dml/contrib dml/delete_pk dml/extended dml/missing_pk dml/toasted \
$(REGRESSTEARDOWN)
PGDLLEXPORT Datum bdr_apply_pause(PG_FUNCTION_ARGS);
PGDLLEXPORT Datum bdr_apply_resume(PG_FUNCTION_ARGS);
+PGDLLEXPORT Datum bdr_apply_is_paused(PG_FUNCTION_ARGS);
PGDLLEXPORT Datum bdr_version(PG_FUNCTION_ARGS);
PGDLLEXPORT Datum bdr_version_num(PG_FUNCTION_ARGS);
PGDLLEXPORT Datum bdr_min_remote_version_num(PG_FUNCTION_ARGS);
PG_FUNCTION_INFO_V1(bdr_apply_pause);
PG_FUNCTION_INFO_V1(bdr_apply_resume);
+PG_FUNCTION_INFO_V1(bdr_apply_is_paused);
PG_FUNCTION_INFO_V1(bdr_version);
PG_FUNCTION_INFO_V1(bdr_version_num);
PG_FUNCTION_INFO_V1(bdr_min_remote_version_num);
PG_RETURN_VOID();
}
+Datum
+bdr_apply_is_paused(PG_FUNCTION_ARGS)
+{
+ PG_RETURN_BOOL(BdrWorkerCtl->pause_apply);
+}
+
Datum
bdr_version(PG_FUNCTION_ARGS)
{
</entry>
</row>
+ <row>
+ <entry>&bdr;/&udr;</entry>
+ <entry>
+ <indexterm>
+ <primary>bdr.bdr_apply_is_paused</primary>
+ </indexterm>
+ <literal><function>bdr.bdr_apply_is_paused()</function></literal>
+ </entry>
+ <entry>boolean</entry>
+ <entry>
+ Report whether replay is paused (e.g. with
+ <function>bdr.bdr_apply_pause()</function>). A false return
+ does not mean replay is actually progressing, only that
+ it's not intentionally paused.
+ </entry>
+ </row>
+
<row id="function-bdr-replicate-ddl-command" xreflabel="bdr.bdr_replicate_ddl_command">
<entry>&bdr;/&udr;</entry>
<entry>
--- /dev/null
+\ccc regression
+invalid command \ccc
+SELECT bdr.bdr_apply_is_paused();
+ bdr_apply_is_paused
+---------------------
+ f
+(1 row)
+
+SELECT bdr.bdr_replicate_ddl_command('CREATE TABLE public.pause_test(x text primary key);');
+ bdr_replicate_ddl_command
+---------------------------
+
+(1 row)
+
+INSERT INTO pause_test(x) VALUES ('before pause');
+SELECT pg_xlog_wait_remote_apply(pg_current_xlog_location(), 0);
+ pg_xlog_wait_remote_apply
+---------------------------
+
+(1 row)
+
+\cc postgres
+invalid command \cc
+SELECT bdr.bdr_apply_is_paused();
+ bdr_apply_is_paused
+---------------------
+ f
+(1 row)
+
+SELECT bdr.bdr_apply_pause();
+ bdr_apply_pause
+-----------------
+
+(1 row)
+
+SELECT bdr.bdr_apply_is_paused();
+ bdr_apply_is_paused
+---------------------
+ t
+(1 row)
+
+-- It's necessary to wait for a latch timeout on apply workers
+-- until bdr_apply_pause gets taught to set their latches.
+SELECT pg_sleep(6);
+ pg_sleep
+----------
+
+(1 row)
+
+\ccc regression
+invalid command \ccc
+INSERT INTO pause_test(x) VALUES ('after pause before resume');
+\cc postgres
+invalid command \cc
+-- Give more time for a row to replicate if it's going to
+-- (it shouldn't)
+SELECT pg_sleep(1);
+ pg_sleep
+----------
+
+(1 row)
+
+-- Pause state is preserved across sessions
+SELECT bdr.bdr_apply_is_paused();
+ bdr_apply_is_paused
+---------------------
+ t
+(1 row)
+
+-- Must not see row from after pause
+SELECT x FROM pause_test;
+ x
+---------------------------
+ before pause
+ after pause before resume
+(2 rows)
+
+SELECT bdr.bdr_apply_resume();
+ bdr_apply_resume
+------------------
+
+(1 row)
+
+\ccc regression
+invalid command \ccc
+INSERT INTO pause_test(x) VALUES ('after resume');
+SELECT pg_xlog_wait_remote_apply(pg_current_xlog_location(), 0);
+ pg_xlog_wait_remote_apply
+---------------------------
+
+(1 row)
+
+\cc postgres
+invalid command \cc
+-- Must see all three rows
+SELECT x FROM pause_test;
+ x
+---------------------------
+ before pause
+ after pause before resume
+ after resume
+(3 rows)
+
ALTER FUNCTION bdr.table_set_replication_sets(p_relation regclass, p_sets text[])
SET bdr.permit_unsafe_ddl_commands = true;
+CREATE OR REPLACE FUNCTION bdr.bdr_apply_is_paused()
+RETURNS boolean LANGUAGE c AS 'MODULE_PATHNAME';
RESET bdr.permit_unsafe_ddl_commands;
RESET bdr.skip_ddl_replication;
ALTER FUNCTION bdr.table_set_replication_sets(p_relation regclass, p_sets text[])
SET bdr.permit_unsafe_ddl_commands = true;
+CREATE OR REPLACE FUNCTION bdr.bdr_apply_is_paused()
+RETURNS boolean LANGUAGE c AS 'MODULE_PATHNAME';
RESET bdr.permit_unsafe_ddl_commands;
RESET bdr.skip_ddl_replication;
--- /dev/null
+\ccc regression
+
+SELECT bdr.bdr_apply_is_paused();
+
+SELECT bdr.bdr_replicate_ddl_command('CREATE TABLE public.pause_test(x text primary key);');
+INSERT INTO pause_test(x) VALUES ('before pause');
+SELECT pg_xlog_wait_remote_apply(pg_current_xlog_location(), 0);
+
+\cc postgres
+
+SELECT bdr.bdr_apply_is_paused();
+SELECT bdr.bdr_apply_pause();
+SELECT bdr.bdr_apply_is_paused();
+-- It's necessary to wait for a latch timeout on apply workers
+-- until bdr_apply_pause gets taught to set their latches.
+SELECT pg_sleep(6);
+
+\ccc regression
+
+INSERT INTO pause_test(x) VALUES ('after pause before resume');
+
+\cc postgres
+
+-- Give more time for a row to replicate if it's going to
+-- (it shouldn't)
+SELECT pg_sleep(1);
+
+-- Pause state is preserved across sessions
+SELECT bdr.bdr_apply_is_paused();
+
+-- Must not see row from after pause
+SELECT x FROM pause_test;
+
+SELECT bdr.bdr_apply_resume();
+
+\ccc regression
+
+INSERT INTO pause_test(x) VALUES ('after resume');
+SELECT pg_xlog_wait_remote_apply(pg_current_xlog_location(), 0);
+
+\cc postgres
+
+-- Must see all three rows
+SELECT x FROM pause_test;