ITPub博客

首页 > > > PostgreSQL的流复制

PostgreSQL的流复制

作者:浪花小雨滴 时间:2020-06-17 16:58:02 0 删除 编辑

简介

本文介绍PostgreSQL数据库的流复制(stream replication)。流复制允许备库更新。备库连接主库,其产生的流WAL记录到备库。

在开始本文流复制的构建前,需要在两台机器上安装好PostgreSQL数据库,可以参考PostgreSQL基于源码的安装。其中备库的PostgreSQL可以先不执行initdb命令进行数据库初始化。另外,也可以在一台机器上启动两个PostgreSQL实例来搭建流复制环境。

我们所采用的环境是:

主库:美团云主机pg1,2CPU、2G内存、100G磁盘,IP为10.4.245.150

备库:美团云主机pg2,2CPU、2G内存、100G磁盘,IP为10.4.245.151

OS:CentOS 6.5

DB:PostgreSQL 9.3.5

配置主库

连接主库后,创建复制用户。

CREATE USER repuser REPLICATION LOGIN CONNECTION LIMIT 2 ENCRYPTED PASSWORD 'rep123us345er';

设置pg_hba.conf,添加以下内容。

host   replication     repuser          10.4.245.151/32         trust

设置主库postgresql.conf内容如下。

listen_addresses = '10.4.245.150'       # 设置为内网IP,允许远程登录主机


wal_level = hot_standby     # write ahead log,流复制时为hot_standby


hot_standby = on


max_wal_senders = 2         # 流复制的最大连接数


wal_keep_segments = 16      # 流复制保留的最大xlog数

重启数据库。

pg_ctl restart

查看表空间目录和数据目录。

[postgres@pg1 data]$ psql


psql (9.3.5)


Type "help" for help.




postgres=# \db


       List of tablespaces


    Name    |  Owner   | Location


------------+----------+----------


 pg_default | postgres |


 pg_global  | postgres |


(2 rows)




postgres=# \q


[postgres@pg1 data]$ echo $PGDATA


/opt/PostgreSQL/9.3.5/data

先查看表空间目录和数据目录,是因为这些目录需要在备库主机上手工创建。

配置备库

创建目录并授权。需要确认备库是否有与主库相同的数据目录,如果有,需要先移除。

cd /opt/PostgreSQL/9.3.5/


mv data data20151116


mkdir -p /opt/PostgreSQL/9.3.5/data


chown -R postgres /opt/PostgreSQL/9.3.5/data


chmod 700 /opt/PostgreSQL/9.3.5/data

在postgres根目录下创建.pgpass,加入如下内容。

10.4.245.150:5432:postgres:repuser:rep123us345er

执行如下命令进行授权。

chmod 600 ~/.pgpass

使用pg_backendup生成备库。

su postgres


pg_basebackup -D /opt/PostgreSQL/9.3.5/data -Fp -Xs -v -P -h 10.4.245.150 -p 5432 -U repuser

这时表空间目录和$PGDATA目录已经复制过来了。本文的环境中没有额外的表空间目录。

设置备库recovery.conf。首先执行如下命令生成recovery.conf文件。

cp /opt/PostgreSQL/9.3.5/share/postgresql/recovery.conf.sample $PGDATA/recovery.conf

然后在recovery.conf中添加如下内容。其中,需要确保postgres用户对/data/pgsql目录具有写权限。

standby_mode = 'on'


trigger_file = '/data/pgsql/pg.trigger'


primary_conninfo = ‘host=10.4.245.150 port=5432 user=repuser password=rep123us345er'

启动备库服务。

pg_ctl start

测试主备同步

执行如下命令查看备库进程中有”postgres: wal receiver process”,确认主库中进程有“postgres: wal sender process”。

ps -ef | grep postgres

进入测试数据库testdb,主库上执行如下命令返回f,备库上返回t。

select pg_is_in_recovery();

执行如下命令查看快照,它返回主库记录点、备库记录点;主库每增加一条写入,记录点的值就会加1。

testdb=# select txid_current_snapshot();


 txid_current_snapshot


-----------------------


 1820:1820:


(1 row)




testdb=# insert into ta values(now());


INSERT 0 1


testdb=# select txid_current_snapshot();


 txid_current_snapshot


-----------------------


 1821:1821:


(1 row)


执行如下命令可以查看主备同步状态。

select * from pg_stat_replication;

字段state显示的同步状态有:startup(连接中)、catchup(同步中)、streaming(同步);字段sync_state显示的模式有:async(异步)、sync(同步)、potential(虽然现在是异步模式,但是有可能升级到同步模式)。

在主库中添加测试数据。

testdb=# create table tb (id int4, create_time timestamp(0) without time zone);


CREATE TABLE


testdb=# insert into tb values (1, now());


INSERT 0 1


testdb=# select * from tb;


 id |     create_time


----+---------------------


  1 | 2015-11-16 20:51:13


在备库查看数据。

testdb=# select * from tb;


 id |     create_time


----+---------------------


  1 | 2015-11-16 20:51:13


(1 row)




testdb=# insert into tb values (1, now());


ERROR:  cannot execute INSERT in a read-only transaction


STATEMENT:  insert into tb values (1, now());


备库上执行insert语句会报错,因为备库是只读的。

主备切换

假设主库崩溃了,备库如何从只读状态切换为读写状态呢?只要把备库的postgresql.conf中hot_standby修改为off,并且删除recovery.conf,然后重启库就可以提供服务了。

总结

本文介绍了流复制的主、备库配置和主备同步测试,以及主库崩溃时备库如何提供服务。可见,流复制适合作为备份方案。

tag : PostgreSQL

来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/31537575/viewspace-3137444/ ,如需转载,请注明出处,否则将追究法律责任。

请登录后发表评论 登录
全部评论

注册时间:2018-05-16

  • 博文量
    4259
  • 访问量
    39850