]> granicus.if.org Git - postgresql/commitdiff
Fix handling of temp and unlogged tables in FOR ALL TABLES publications
authorPeter Eisentraut <peter@eisentraut.org>
Tue, 16 Apr 2019 08:37:44 +0000 (10:37 +0200)
committerPeter Eisentraut <peter@eisentraut.org>
Thu, 18 Apr 2019 06:55:55 +0000 (08:55 +0200)
If a FOR ALL TABLES publication exists, temporary and unlogged tables
are ignored for publishing changes.  But CheckCmdReplicaIdentity()
would still check in that case that such a table has a replica
identity set before accepting updates.  To fix, have
GetRelationPublicationActions() return that such a table publishes no
actions.

Discussion: https://www.postgresql.org/message-id/f3f151f7-c4dd-1646-b998-f60bd6217dd3@2ndquadrant.com

src/backend/utils/cache/relcache.c
src/test/subscription/t/100_bugs.pl

index 4b884d552786bef7a1282679e01755aa6a94e1ca..bab59f16e68390a9d0b4823c236a159991dd5b87 100644 (file)
@@ -5156,6 +5156,13 @@ GetRelationPublicationActions(Relation relation)
        MemoryContext oldcxt;
        PublicationActions *pubactions = palloc0(sizeof(PublicationActions));
 
+       /*
+        * If not publishable, it publishes no actions.  (pgoutput_change() will
+        * ignore it.)
+        */
+       if (!is_publishable_relation(relation))
+               return pubactions;
+
        if (relation->rd_pubactions)
                return memcpy(pubactions, relation->rd_pubactions,
                                          sizeof(PublicationActions));
index a69634768024e9fb298fd052be63740d42f55fc2..5af9257e0a46eb100908c8951df903a7e495aa5b 100644 (file)
@@ -3,7 +3,7 @@ use strict;
 use warnings;
 use PostgresNode;
 use TestLib;
-use Test::More tests => 1;
+use Test::More tests => 3;
 
 # Bug #15114
 
@@ -63,3 +63,38 @@ $node_publisher->safe_psql('postgres',
 $node_publisher->wait_for_catchup('sub1');
 
 pass('index predicates do not cause crash');
+
+$node_publisher->stop('fast');
+$node_subscriber->stop('fast');
+
+
+# Handling of temporary and unlogged tables with FOR ALL TABLES publications
+
+# If a FOR ALL TABLES publication exists, temporary and unlogged
+# tables are ignored for publishing changes.  The bug was that we
+# would still check in that case that such a table has a replica
+# identity set before accepting updates.  If it did not it would cause
+# an error when an update was attempted.
+
+$node_publisher = get_new_node('publisher2');
+$node_publisher->init(allows_streaming => 'logical');
+$node_publisher->start;
+
+$node_publisher->safe_psql('postgres',
+       "CREATE PUBLICATION pub FOR ALL TABLES");
+
+is( $node_publisher->psql(
+               'postgres',
+               "CREATE TEMPORARY TABLE tt1 AS SELECT 1 AS a; UPDATE tt1 SET a = 2;"),
+       0,
+       'update to temporary table without replica identity with FOR ALL TABLES publication'
+);
+
+is( $node_publisher->psql(
+               'postgres',
+               "CREATE UNLOGGED TABLE tu1 AS SELECT 1 AS a; UPDATE tu1 SET a = 2;"),
+       0,
+       'update to unlogged table without replica identity with FOR ALL TABLES publication'
+);
+
+$node_publisher->stop('fast');