主机信息:
ip:port | 版本号 | 角色 |
---|---|---|
197.0.193.198:26000 | 3.0.0 | 发布端 |
197.0.194.194:26000 | 3.0.0 | 订阅端 |
要求: 迁移dbpaasstoredb库下,schema为cust1的表db2_tbs
1. 修改配置文件
发布节点:
$ vi postgresql.conf
wal_level = logical
max_replication_slots = 8
wal_level:设置成logical才支持逻辑复制
max_replication_slots>=每个节点所需的(物理流复制槽数 逻辑复制槽数)
订阅节点:
$ vi postgresql.conf
wal_level = logical
max_replication_slots = 8
2. 发布节点创建逻辑复制用户
必须具有**replication,sysadmin/opradmin** 权限
opengauss=# create user repl replication opradmin login encrypted password 'xxxxx';
3. 发布节点修改pg_hba.conf文件
host replication repl 0.0.0.0/0 md5
4. 发布节点使用gs_dump导出表结构
opengauss=# gs_dump -p 26000 dbpaasstoredb -t cust1.db2_tbs -s -f db2_tbs.sql -f p
注:逻辑复制不会同步ddl操作和原有数据,需要先将发布端表结构和原有数据迁移到订阅端
5. 发布节点创建发布
dbpaasstoredb=# create publication pub1 for table db2_tbs ;
create publication
查询发布信息
opengauss=# select * from pg_publication;
pubname | pubowner | puballtables | pubinsert | pubupdate | pubdelete
--------- ---------- -------------- ----------- ----------- -----------
pub1 | 10 | f | t | t | t
(1 row)
6. 订阅节点上导入表结构
$ gsql -p 26000 -d dbpaasstoredb -f db2_tbs.sql
7. 订阅节点创建加密文件
gs_guc generate -s xxxxx -d $gausshome/bin -o subscription
8. 订阅节点创建订阅
端口号不能使用主端口,应该使用主端口 1端口,否则会与线程池冲突
create subscription sub1 connection 'host=197.0.193.198 port=26001 dbname=dbpaasstoredb user=repl password=xxxxx' publication pub1;
9. 查看发布订阅相关信息
发布节点查看发布信息
dbpaasstoredb=# select * from pg_publication;
发布节点上查看复制槽
dbpaasstoredb=# select slot_name,plugin,slot_type,database,active,restart_lsn from pg_replication_slots where slot_name='sub1';
订阅节点上查看订阅信息
dbpaasstoredb=# select * from pg_subscription;
订阅节点已经在同步数据
添加表
1. 发布端和订阅端分别创建同名表表结构
opengauss=# create table test2(id int,name varchar);
create table
2. 发布端添加test2表至pub2
opengauss=# alter publication pub2 add table test2;
3. 发布端添加数据
opengauss=# insert into test2 values(1,'a');
insert 0 1
opengauss=# insert into test2 values(2,'b');
insert 0 1
opengauss=# select * from test2;
id | name
---- ------
1 | a
2 | b
(2 rows)
4. 订阅端查看数据
删除表
1. 查看此时pub2中发布的表
opengauss=# select * from pg_publication_tables where pubname='pub2';
2. 如果test2表不需要逻辑同步,只需要在发布节点将test2表从发布pub2中去掉即可
# alter publication pub2 drop table test2;
此时两个节点的test2表为独立的表
数据不会同步
发布端插入一条数据:
订阅端未同步:
激活
1. 创建一个订阅,并且不开始复制直到稍后启用复制。
opengauss=# create subscription sub3 connection 'host=197.0.193.198 port=26001 dbname=postgres user=repl password=xxxxx' publication pub2 with (enabled = false);
2. 发布端插入数据
3. 订阅端查看数据并未同步
4. 订阅端激活订阅
opengauss=# alter subscription sub3 set(enabled=true);
5. 发布端插入数据
6. 订阅端同步新增数据
停止
未提供此功能,因为停止后会导致发布端逻辑复制槽无法推进,导致xlog堆积,风险较大,所以暂不提供此功能
范围分区
1. 分别在发布端,订阅端创建range分区表表结构
create table staffs_p1
(
staff_id number(6) not null,
hire_date date
)
partition by range (hire_date)
(
partition hire_19950501 values less than ('1995-05-01 00:00:00'),
partition hire_19950502 values less than ('1995-05-02 00:00:00'),
partition hire_19950503 values less than ('1995-05-03 00:00:00')
);
2. 发布端将staffs_p1表添加至已有的part发布中
opengauss=# alter publication part add table staffs_p1 ;
alter publication
3. 发布端插入数据
opengauss=# insert into staffs_p1 values (1,'1995-04-01 00:00:00');
insert 0 1
4. 订阅端查看,数据已同步
5. 发布端添加分区
opengauss=# alter table staffs_p1 add partition hire_19950504 values less than ('1995-05-04 00:00:00');
6. 订阅端查看
新添加的分区不会同步
间隔分区
1. 分别在发布端,订阅端创建interval分区表表结构
create table sales
(prod_id number(6),
time_id date
)
partition by range (time_id)
interval('1 day')
( partition p1 values less than ('2019-02-01 00:00:00'),
partition p2 values less than ('2019-02-02 00:00:00')
);
2. 发布端将staffs_p1表添加至已有的part发布中
opengauss=# alter publication part add table sales ;
alter publication
3. 发布端插入数据
opengauss=# insert into sales values (1,'1995-04-01 00:00:00');
insert 0 1
opengauss=# insert into sales values (2,'2000-04-01 00:00:00');
insert 0 1
4. 订阅端查看(只能同步不超过创建的分区范围的数据)
官方手册显示,目前不支持interval partition表复制
列表分区
1. 分别在发布端,订阅端创建list分区表表结构
create table test_list (col1 int, col2 int)
partition by list(col1)
(
partition p1 values (2000),
partition p2 values (3000),
partition p3 values (4000),
partition p4 values (5000)
);
2. 发布端将test_list表添加至已有的part发布中
opengauss=# alter publication part add table test_list ;
alter publication
3. 发布端插入数据
opengauss=# insert into test_list values (2000,2000);
insert 0 1
opengauss=# insert into test_list values (3000,3000);
insert 0 1
4. 订阅端查看,数据已同步
5. 发布端添加分区
opengauss=# alter table test_list add partition p5 values (6000);
6. 订阅端查看
哈希分区
1. 分别在发布端,订阅端创建hash分区表表结构
create table test_hash (col1 int, col2 int)
partition by hash(col1)
(
partition p1,
partition p2
);
2. 发布端将test_hash表添加至已有的part发布中
opengauss=# alter publication part add table test_hash ;
alter publication
3. 发布端插入数据
4. 订阅端查看
数据已同步
摘自官方手册:
- 不支持ddl语句解码,在执行特定的ddl语句(如普通表truncate或分区表exchange)时,可能造成解码数据丢失。
- 不支持列存、数据页复制的解码。
- 不支持级联备机进行逻辑解码。
- 当执行ddl语句(如alter table)后,该ddl语句前尚未解码的物理日志可能会丢失。单条元组大小不超过1gb,考虑解码结果可能大于插入数据,因此建议单条元组大小不超过500mb。
- opengauss支持解码的数据类型为:integer、bigint、smallint、tinyint、serial、smallserial、bigserial、float、double precision、date、time[without time zone]、timestamp[without time zone]、char(n)、varchar(n)、text。
- 如果需要ssl连接需要保证前置条件guc参数ssl=on。
- 逻辑复制槽名称必须小于64个字符,且只包含小写字母、数字或者下划线中的一种或几种。
- 当前逻辑复制不支持mot特性。
- 当逻辑复制槽所在数据库被删除后,这些复制槽变为不可用状态,需要用户手动删除。
- 仅支持utf-8字符集。
- 对多库的解码需要分别在库内创建流复制槽并开始解码,每个库的解码都需要单独扫一遍日志。
- 不支持强起,强起后需要重新全量导出数据。
- 备机解码时,switchover和failover时可能出现解码数据变多,需用户手动过滤。quorum协议下,switchover和failover选择升主的备机,需要与当前主机日志同步。不允许主备,多个备机同时使用同一个复制槽解码,否则会产生数据不一致。
- 只支持主机创建删除复制槽。
- 数据库故障重启或逻辑复制进程重启后,解码数据存在重复,用户需自己过滤。
- 计算机内核故障后,解码存在乱码,需手动或自动过滤。
- 当前备机逻辑解码,不支持开启极致rto。
- 请确保在创建逻辑复制槽过程中长事务未启动,启动长事务会阻塞逻辑复制槽的创建。
- 不支持interval partition表复制。
- 不支持全局临时表。
- 在事务中执行ddl语句后,该ddl语句与之后的语句不会被解码。
- 如需进行备机解码,需在对应主机上设置guc参数enable_slot_log = on。
- 禁止在使用逻辑复制槽时在其他节点对该复制槽进行操作,删除复制槽的操作需在该复制槽停止解码后执行。