bdr: add bdr_test_replication_connection(...)
authorCraig Ringer <craig@2ndquadrant.com>
Fri, 6 Feb 2015 11:31:19 +0000 (00:31 +1300)
committerAndres Freund <andres@anarazel.de>
Thu, 12 Feb 2015 09:16:58 +0000 (10:16 +0100)
bdr_remotecalls.c
expected/identifier.out
extsql/bdr--0.8.0.7--0.9.0.0.sql
sql/identifier.sql

index 108cd0a739abdc0963eb7c4ec48a3ba54fcf7455..d0557f65a8e34ebacec9be27aa39ab475b18d9d4 100644 (file)
 #include "utils/syscache.h"
 
 PGDLLEXPORT Datum bdr_get_remote_nodeinfo(PG_FUNCTION_ARGS);
+PGDLLEXPORT Datum bdr_test_replication_connection(PG_FUNCTION_ARGS);
 
 PG_FUNCTION_INFO_V1(bdr_get_remote_nodeinfo);
+PG_FUNCTION_INFO_V1(bdr_test_replication_connection);
 
 /*
  * Make standard postgres connection, ERROR on failure.
@@ -288,3 +290,50 @@ bdr_get_remote_nodeinfo(PG_FUNCTION_ARGS)
 
    PG_RETURN_DATUM(HeapTupleGetDatum(returnTuple));
 }
+
+/*
+ * Test a given dsn as a replication connection, appending the replication
+ * parameter.
+ *
+ * If non-null, the node identity information arguments will be checked
+ * against the identity reported by the connection.
+ *
+ * This can be used safely against the local_dsn, as it does not enforce
+ * that the local node ID differ from the identity on the other end.
+ */
+Datum
+bdr_test_replication_connection(PG_FUNCTION_ARGS)
+{
+   const char  *conninfo = text_to_cstring(PG_GETARG_TEXT_P(0));
+   TupleDesc   tupleDesc;
+   HeapTuple   returnTuple;
+   PGconn      *conn;
+   NameData    appname;
+   uint64      remote_sysid;
+   TimeLineID  remote_tlid;
+   Oid         remote_dboid;
+   Datum       values[3];
+   bool        isnull[3] = {false, false, false};
+   char        sysid_str[33];
+
+   if (get_call_result_type(fcinfo, NULL, &tupleDesc) != TYPEFUNC_COMPOSITE)
+       elog(ERROR, "return type must be a row type");
+
+   strncpy(NameStr(appname), "BDR test connection", NAMEDATALEN);
+
+   conn = bdr_connect(conninfo, &appname, &remote_sysid, &remote_tlid,
+                      &remote_dboid);
+
+   snprintf(sysid_str, sizeof(sysid_str), UINT64_FORMAT, remote_sysid);
+   sysid_str[sizeof(sysid_str)-1] = '\0';
+
+   values[0] = CStringGetTextDatum(sysid_str);
+   values[1] = ObjectIdGetDatum(remote_tlid);
+   values[2] = ObjectIdGetDatum(remote_dboid);
+
+   returnTuple = heap_form_tuple(tupleDesc, values, isnull);
+
+   PQfinish(conn);
+
+   PG_RETURN_DATUM(HeapTupleGetDatum(returnTuple));
+}
index 1564cddd82169f90cc36042c1dfc621fbaf577e7..c0322129cdd14bed76fdc2d01f5c6f12891d1ac5 100644 (file)
@@ -39,3 +39,25 @@ FROM bdr.bdr_get_remote_nodeinfo('dbname='||current_database()) r;
  t
 (1 row)
 
+-- Test probing for replication connection
+SELECT
+   r.sysid = l.sysid,
+   r.timeline = l.timeline,
+   r.dboid = (SELECT oid FROM pg_database WHERE datname = 'postgres')
+FROM bdr.bdr_test_replication_connection('dbname=postgres') r,
+     bdr.bdr_get_local_nodeid() l;
+ ?column? | ?column? | ?column? 
+----------+----------+----------
+ t        | t        | t
+(1 row)
+
+-- Probing replication connection for the local dsn will work too
+-- even though the identifier is the same.
+SELECT
+   r.dboid = (SELECT oid FROM pg_database WHERE datname = current_database())
+FROM bdr.bdr_test_replication_connection('dbname='||current_database()) r;
+ ?column? 
+----------
+ t
+(1 row)
+
index 4feaf86e97aa6c8b7902e3f1f9f24eef2368192b..6843d0db485f1db727a6338093d7c17be422a402 100644 (file)
@@ -13,6 +13,14 @@ REVOKE ALL ON FUNCTION bdr_get_remote_nodeinfo(text) FROM public;
 
 COMMENT ON FUNCTION bdr_get_remote_nodeinfo(text) IS 'Get node identity and BDR info from a remote server by dsn';
 
+CREATE FUNCTION bdr_test_replication_connection(dsn text, sysid OUT text, timeline OUT oid, dboid OUT oid)
+RETURNS record LANGUAGE c AS 'MODULE_PATHNAME';
+
+REVOKE ALL ON FUNCTION bdr_test_replication_connection(text) FROM public;
+
+COMMENT ON FUNCTION bdr_test_replication_connection(text)
+IS 'Make a replication-mode connection to the specified DSN and get its node identity.';
+
 RESET bdr.permit_unsafe_ddl_commands;
 RESET bdr.skip_ddl_replication;
 RESET search_path;
index 36276947458a73b8412c5d89433d3231a97e5b0c..58a3a8f2064d2b36f9a7337e295cb3cfc8bd9e87 100644 (file)
@@ -22,3 +22,17 @@ FROM bdr.bdr_get_remote_nodeinfo('dbname=postgres') r,
 SELECT
     r.dboid = (SELECT oid FROM pg_database WHERE datname = current_database())
 FROM bdr.bdr_get_remote_nodeinfo('dbname='||current_database()) r;
+
+-- Test probing for replication connection
+SELECT
+   r.sysid = l.sysid,
+   r.timeline = l.timeline,
+   r.dboid = (SELECT oid FROM pg_database WHERE datname = 'postgres')
+FROM bdr.bdr_test_replication_connection('dbname=postgres') r,
+     bdr.bdr_get_local_nodeid() l;
+
+-- Probing replication connection for the local dsn will work too
+-- even though the identifier is the same.
+SELECT
+   r.dboid = (SELECT oid FROM pg_database WHERE datname = current_database())
+FROM bdr.bdr_test_replication_connection('dbname='||current_database()) r;