每个发布物可以选择性地指定每个表的哪些列被复制到订阅者。订阅者一方的表必须至少包含所有已发布的列。如果未指定列列表,则复制发布者上的所有列。有关语法详细信息,请参阅CREATE PUBLICATION。
列的选择可以基于行为或性能原因。但是,不要依赖此功能来保证安全性:恶意订阅者能够获取未明确发布的列中的数据。如果安全性是一个考虑因素,则可以在发布者一方应用保护措施。
如果未指定列列表,则以后添加到表中的任何列都会自动复制。这意味着具有列出所有列的列列表与根本没有列列表并不相同。
列列表只能包含简单的列引用。列表中列的顺序不会保留。
当发布物也发布FOR TABLES IN SCHEMA
时,不支持指定列列表。
对于分区表,发布物参数publish_via_partition_root
决定使用哪个列列表。如果publish_via_partition_root
为true
,则使用根分区表的列列表。否则,如果publish_via_partition_root
为false
(默认值),则使用每个分区的列列表。
如果发布物发布UPDATE
或DELETE
操作,则任何列列表都必须包含表的副本标识列(请参阅REPLICA IDENTITY
)。如果发布物仅发布INSERT
操作,则列列表可以省略副本标识列。
列列表对TRUNCATE
命令没有影响。
在初始数据同步期间,仅复制已发布的列。但是,如果订阅者来自 15 之前的版本,则在初始数据同步期间会复制表中的所有列,忽略任何列列表。
目前不支持包含多个发布物的订阅,其中同一张表已使用不同的列列表发布。CREATE SUBSCRIPTION不允许创建此类订阅,但仍然可以通过在创建订阅后更改发布者一方的列列表来进入这种情况。
这意味着更改已订阅的发布物上表的列列表可能会导致订阅者一方抛出错误。
如果订阅受到此问题的影响,恢复复制的唯一方法是调整发布者一方的一个列列表,使其全部匹配;然后,要么重新创建订阅,要么使用ALTER SUBSCRIPTION ... DROP PUBLICATION
删除其中一个有问题的发布物并重新添加。
创建一个表t1
,在以下示例中使用。
test_pub=# CREATE TABLE t1(id int, a text, b text, c text, d text, e text, PRIMARY KEY(id)); CREATE TABLE
创建一个发布物p1
。为表t1
定义了一个列列表,以减少将要复制的列的数量。请注意,列列表中列名的顺序无关紧要。
test_pub=# CREATE PUBLICATION p1 FOR TABLE t1 (id, b, a, d); CREATE PUBLICATION
psql
可用于显示每个发布物(如果已定义)的列列表。
test_pub=# \dRp+ Publication p1 Owner | All tables | Inserts | Updates | Deletes | Truncates | Via root ----------+------------+---------+---------+---------+-----------+---------- postgres | f | t | t | t | t | f Tables: "public.t1" (id, a, b, d)
psql
可用于显示每个表(如果已定义)的列列表。
test_pub=# \d t1 Table "public.t1" Column | Type | Collation | Nullable | Default --------+---------+-----------+----------+--------- id | integer | | not null | a | text | | | b | text | | | c | text | | | d | text | | | e | text | | | Indexes: "t1_pkey" PRIMARY KEY, btree (id) Publications: "p1" (id, a, b, d)
在订阅者节点上,创建一个表t1
,该表现在只需要发布者表t1
上的一组列,并创建订阅s1
来订阅发布物p1
。
test_sub=# CREATE TABLE t1(id int, b text, a text, d text, PRIMARY KEY(id)); CREATE TABLE test_sub=# CREATE SUBSCRIPTION s1 test_sub-# CONNECTION 'host=localhost dbname=test_pub application_name=s1' test_sub-# PUBLICATION p1; CREATE SUBSCRIPTION
在发布者节点上,向表t1
插入一些行。
test_pub=# INSERT INTO t1 VALUES(1, 'a-1', 'b-1', 'c-1', 'd-1', 'e-1'); INSERT 0 1 test_pub=# INSERT INTO t1 VALUES(2, 'a-2', 'b-2', 'c-2', 'd-2', 'e-2'); INSERT 0 1 test_pub=# INSERT INTO t1 VALUES(3, 'a-3', 'b-3', 'c-3', 'd-3', 'e-3'); INSERT 0 1 test_pub=# SELECT * FROM t1 ORDER BY id; id | a | b | c | d | e ----+-----+-----+-----+-----+----- 1 | a-1 | b-1 | c-1 | d-1 | e-1 2 | a-2 | b-2 | c-2 | d-2 | e-2 3 | a-3 | b-3 | c-3 | d-3 | e-3 (3 rows)
仅复制发布物p1
的列列表中的数据。
test_sub=# SELECT * FROM t1 ORDER BY id; id | b | a | d ----+-----+-----+----- 1 | b-1 | a-1 | d-1 2 | b-2 | a-2 | d-2 3 | b-3 | a-3 | d-3 (3 rows)
如果您在文档中看到任何不正确的内容,与您对特定功能的体验不符,或者需要进一步澄清,请使用此表单报告文档问题。