【一文搞懂PGSQL】7. PostgreSQL + repmgr + witness 高可用架构

本文涉及的产品
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
云数据库 Redis 版,标准版 2GB
推荐场景:
搭建游戏排行榜
云数据库 RDS MySQL,集群系列 2核4GB
推荐场景:
搭建个人博客
简介: 该文档介绍了如何构建基于PostgreSQL的高可用架构,利用repmgr进行集群管理和故障转移,并引入witness节点增强网络故障检测能力。repmgr是一款轻量级的开源工具,支持一键部署、自动故障转移及分布式节点管理。文档详细描述了环境搭建步骤,包括配置postgresql参数、安装与配置repmgr、注册集群节点以及配置witness节点等。此外,还提供了故障手动与自动切换的方法及常用命令,确保集群稳定运行。

7. PostgreSQL + repmgr + witness 高可用架构

简介

repmgr是一套开源的PostgreSQL集群管理工具,具有非常轻量级的使用特性。具体表现有以下特点:

  • 配置操作简单,可一键式完成相关部署操作;
  • 支持Auto Failover和Manual Switchover;
  • 分布式管理集群节点,易扩展,可在线增删集群节点。
  • witness节点是处理集群主库和备库之间可能存在网络拥塞、延迟、路由等问题影响,导致主库还在正常工作,而备库无法联系主库的场景。
  • 通过设置witness节点可以针对主库与备库之间切换的检查完整性,即辅助备节点监控程序实施主节点网络可见性检查,避免因网络问题导致的脑裂现象。

环境准备

节点 角色 软件
10.10.8.176 primary pg+repmgr
10.10.8.106 standby pg+repmgr
10.10.8.177 standby pg+repmgr
10.10.8.180 standby pg+repmgr

安装postgresql

安装详见标题 2 源码安装配置

https://repmgr.org

免密登录

rm -rf ~/.ssh
ssh-keygen  #一路回车

cd ~/.ssh
mv id_rsa.pub authorized_keys
scp  -r  ~/.ssh  10.10.8.176:/home/postgres/
scp  -r  ~/.ssh  10.10.8.106:/home/postgres/
scp  -r  ~/.ssh  10.10.8.177:/home/postgres/
scp  -r  ~/.ssh  10.10.8.180:/home/postgres/

ssh postgres@10.10.8.176 date
ssh postgres@10.10.8.106 date 
ssh postgres@10.10.8.177 date 
ssh postgres@10.10.8.180 date

postgresql 重点参数配置 //主库操作

cat  >/pgdata/12/data/postgresql.conf<<'EOF'
# 监听地址
listen_addresses = '0.0.0.0'
# 最大连接数
max_connections = 1000
# 缓冲区大小
shared_buffers = 2GB
# 动态共享内存类型
dynamic_shared_memory_type = posix
# 日志详细程度
wal_level = replica
# 检查点之后第一次页面更改(即使是对提示位进行非关键性的修改)写 FPI 到 WAL 中
wal_log_hints = on
# 重做日志最大物理大小
max_wal_size = 1GB
# 重做日志最小物理大小
min_wal_size = 80MB
# 开启归档
archive_mode = on
# 检查归档
archive_command = 'test ! -f /archive/%f && cp %p /archive/%f'
# 最大从库数 多设置点没事
max_wal_senders = 30
# 重做日志保存数量
wal_keep_segments = 128
# 流复制主机发送数据的超时时间
wal_sender_timeout = 60s
# 开启说明如果作为从库可以读
hot_standby = on
# 流复制的最大延迟时间
max_standby_streaming_delay = 30s
# 复制槽的最大数量(复制槽是自动检查行冲突的)
max_replication_slots = 128
# 向主库报告从库当前状态的最大时间
wal_receiver_status_interval = 10s
# 如果有错误的数据复制,是否向主库反馈
hot_standby_feedback = on
# 日志时区(prc  中华人民共和国)
log_timezone = 'PRC'
# 时间格式
datestyle = 'iso, mdy'
# 数据库时区
timezone = 'PRC'
# 系统错误消息的区域设置
lc_messages = 'C'
# 货币格式的区域设置
lc_monetary = 'C'
# 数字格式设置的区域设置
lc_numeric = 'C'
# 时间格式的区域设置
lc_time = 'C'
# 默认文本搜索配置
default_text_search_config = 'pg_catalog.english'
# 日志输出
log_destination = 'stderr'
# 开启日志采集
logging_collector = on 
# 日志路径
log_directory = '/pgdata/12/log'
# 日志格式
log_filename = 'postgresql-%Y-%m-%d_%H%M%S.log'
# 日志权限
log_file_mode = 0600
EOF

# 添加防火墙规则
cat  >>/pgdata/12/data/pg_hba.conf<<'EOF'
host    all             all             0.0.0.0/0               trust
host    replication     repmgr          0.0.0.0/0               trust
EOF

安装repmgr

/ 所有节点安装repmgr

# 下载包
wget  https://repmgr.org/download/repmgr-5.2.0.tar.gz

# 解压
tar xf repmgr-5.2.0.tar.gz

# 进入目录
cd repmgr-5.2.0

# 配置
./configure

# 编译
make

# 安装
make install

# 创建配置文件目录
mkdir -p  /pgdata/repmgr

# 报错 cannot create regular file ‘/usr/local/pg12/lib/postgresql/repmgr.so’: Permission denied
su - root 
chown -R postgres:postgres /usr/local/pg12

配置repmgr

配置用户 // 主库

# 创建用户
createuser -s repmgr
# 创建库
createdb repmgr -O repmgr
# 修改密码
PGPASSWORD=dyh666 psql  -c "alter user repmgr with password 'dyh666';"
# 修改查找目录
PGPASSWORD=dyh666 psql  -c "alter user repmgr set search_path to repmgr ,\"\$user\",public;"

添加配置文件 // 所有节点执行

cat  >/pgdata/repmgr/repmgr.conf<<'EOF'
# 节点ID,高可用集群各节点标识 // 每个节点不同
node_id=1
# 节点名称,高可用集群各节点名称 // 每个节点不同
node_name='pg01-182'
# 本节点数据库连接信息  // 填写本机的IP地址即可
conninfo='host=10.10.8.182  user=repmgr   dbname=repmgr connect_timeout=2'
# pg数据目录
data_directory='/pgdata/12/data'
# 流复制数据库用户,默认使用repmgr
#replication_user='replica'
# repmgr软件目录
repmgr_bindir='/usr/local/pg12/bin/'
# pg软件目录
pg_bindir='/usr/local/pg12/bin'
# 停机超时时间
#shutdown_check_timeout=10
# 日志输出
log_level=INFO
log_file='/pgdata/repmgr/repmgrd.log'
log_status_interval=10
EOF

配置数据库免密 // 所有机器配置

# 配置主备库的密码文件 .pgpass 互相通信使用 
cat >~/.pgpass<<'EOF'
10.10.8.176:5432:repmgr:repmgr:dyh666
10.10.8.106:5432:repmgr:repmgr:dyh666
10.10.8.177:5432:repmgr:repmgr:dyh666
10.10.8.180:5432:repmgr:repmgr:dyh666
EOF

# 授权 // 所以机器配置
chmod 0600 ~/.pgpass

注册完成后可以使用repmgr用户登录数据库repmgr默认库下查看生成的表来确定集群的状态

或者通过repmgr的命令查看相关的状态信息

主库加入集群

# 主库注册到集群
repmgr primary register -f /pgdata/repmgr/repmgr.conf 

# 查看集群状态
repmgr -f /pgdata/repmgr/repmgr.conf cluster show

克隆到其他节点

# 测试克隆  // 非必要操作如果你想使用现有主从做repmgr 则可以忽略
repmgr  standby clone  -h 10.10.8.183 -Urepmgr -d repmgr -f /pgdata/repmgr/repmgr.conf  --dry-run

# 正式执行   // 这里如果提示你输入密码说明你的配置有问题
repmgr  standby clone  -h 10.10.8.182 -Urepmgr -d repmgr -f /pgdata/repmgr/repmgr.conf 

# 启动pgsql
pg_ctl -D /pgdata/12/data -l logfile  start

从库加入集群

# 将 standby 节点注册到集群  --upstream-node-id=1 //指定primary 节点的ID号  
repmgr  standby register -f /pgdata/repmgr/repmgr.conf --upstream-node-id=1

# 查看集群状态
repmgr -f /pgdata/repmgr/repmgr.conf cluster show

配置 witness 节点

以上操作虽然实现了PostgreSQL的切换功能,但是需要手动去执行才能进行切换,witness 节点是监控节点,他可以监控集群的状态,当主库访问不可达或宕机时,可以通过指定的命令自动切换主库,并在代码中实现了防止脑裂的功能。

如果备节点网络上只是和witness或主节点中的一个节点不通,,则很可能存在网络中断,它不应该切换为主节点。如果备节点和witness节点相通,但和主节点不通,这证明不是网络中断,而是主节点本身不可用,因此它可以切换为主节点。

⚠️: witness节点不能在集群内,必须是独立的节点,必须为独立主库!!!

witness节点上初始化一个实例

# 清理旧实例
pg_ctl stop
rm -rf /pgdata/12/data/*
rm -rf /archive/*


# 生产初始化
initdb -A md5 -D $PGDATA -E utf8 --locale=C -W # 配置管理员密码

配置实例

cat  >/pgdata/12/data/postgresql.conf<<'EOF'
# 监听地址
listen_addresses = '0.0.0.0'
# 最大连接数
max_connections = 1000
# 缓冲区大小
shared_buffers = 2GB
# 动态共享内存类型
dynamic_shared_memory_type = posix
# 日志详细程度
wal_level = replica
# 检查点之后第一次页面更改(即使是对提示位进行非关键性的修改)写 FPI 到 WAL 中
wal_log_hints = on
# 重做日志最大物理大小
max_wal_size = 1GB
# 重做日志最小物理大小
min_wal_size = 80MB
# 开启归档
archive_mode = on
# 检查归档
archive_command = 'test ! -f /archive/%f && cp %p /archive/%f'
# 最大从库数 多设置点没事
max_wal_senders = 30
# 重做日志保存数量
wal_keep_segments = 128
# 流复制主机发送数据的超时时间
wal_sender_timeout = 60s
# 开启说明如果作为从库可以读
hot_standby = on
# 流复制的最大延迟时间
max_standby_streaming_delay = 30s
# 复制槽的最大数量(复制槽是自动检查行冲突的)
max_replication_slots = 128
# 向主库报告从库当前状态的最大时间
wal_receiver_status_interval = 10s
# 如果有错误的数据复制,是否向主库反馈
hot_standby_feedback = on
# 日志时区(prc  中华人民共和国)
log_timezone = 'PRC'
# 时间格式
datestyle = 'iso, mdy'
# 数据库时区
timezone = 'PRC'
# 系统错误消息的区域设置
lc_messages = 'C'
# 货币格式的区域设置
lc_monetary = 'C'
# 数字格式设置的区域设置
lc_numeric = 'C'
# 时间格式的区域设置
lc_time = 'C'
# 默认文本搜索配置
default_text_search_config = 'pg_catalog.english'
# 日志输出
log_destination = 'stderr'
# 开启日志采集
logging_collector = on 
# 日志路径
log_directory = '/pgdata/12/log'
# 日志格式
log_filename = 'postgresql-%Y-%m-%d_%H%M%S.log'
# 日志权限
log_file_mode = 0600
# 自动切换
shared_preload_libraries ='repmgr'
EOF

# 添加防火墙规则
cat  >>/pgdata/12/data/pg_hba.conf<<'EOF'
host    all             all             0.0.0.0/0               trust
host    replication     repmgr          0.0.0.0/0               trust
EOF

# 启动
 pg_ctl -D /pgdata/12/data -l logfile start

创建用户

# 创建用户
createuser -s repmgr
# 创建库
createdb repmgr -O repmgr
# 修改密码
PGPASSWORD=dyh666 psql  -c "alter user repmgr with password 'dyh666';"
# 修改查找目录
PGPASSWORD=dyh666 psql  -c "alter user repmgr set search_path to repmgr ,\"\$user\",public;"

添加 repmgr 配置

cat  >/pgdata/repmgr/repmgr.conf<<'EOF'
# 节点ID,高可用集群各节点标识 // 每个节点不同
node_id=4
# 节点名称,高可用集群各节点名称 // 每个节点不同
node_name='pg04-180'
# 本节点数据库连接信息  // 填写本机的IP地址即可
conninfo='host=10.10.8.180  user=repmgr   dbname=repmgr connect_timeout=2'
# pg数据目录
data_directory='/pgdata/12/data'
# 流复制数据库用户,默认使用repmgr
#replication_user='replica'
# repmgr软件目录
repmgr_bindir='/usr/local/pg12/bin/'
# pg软件目录
pg_bindir='/usr/local/pg12/bin'
# 停机超时时间
#shutdown_check_timeout=10
# 日志输出
log_level=INFO
log_file='/pgdata/repmgr/repmgrd.log'
log_status_interval=10
EOF

注册witness 节点到集群

# 将 witness 节点注册到集群
repmgr  witness register  -f /pgdata/repmgr/repmgr.conf  -h 10.10.8.183  --upstream-node-id=2 -Urepmgr -d repmgr

集群检查

# 集群状态拓扑
repmgr -f /pgdata/repmgr/repmgr.conf cluster show

# ssh 连接检查
repmgr -f /pgdata/repmgr/repmgr.conf cluster matrix

# repmgr连接检查
repmgr -f /pgdata/repmgr/repmgr.conf cluster crosscheck

# 显示节点基本信息和复制状态
repmgr -f /pgdata/repmgr/repmgr.conf node status

# 复制状况检查
repmgr -f /pgdata/repmgr/repmgr.conf node check

故障手动切换

主从切换的效果是将执行的命令的从库提升为主库,其他从库指向新主库,旧主库也指向新主库。

# 切换测试
repmgr -f /pgdata/repmgr/repmgr.conf standby switchover --siblings-follow  --force-rewind --dry-run

# 正式切换
repmgr -f /pgdata/repmgr/repmgr.conf standby switchover --siblings-follow  --force-rewind 

# # 集群状态拓扑
repmgr -f   /pgdata/repmgr/repmgr.conf  cluster show

可能遇见的问题:

fe_sendauth: no password supplied

一般是 pg_hba.conf 文件的防火墙权限配置的有问题

故障自动切换

pgsql 添加配置 // 所有节点

# 添加如下配置
cat >>/pgdata/12/data/postgresql.conf<<'EOF'
# 加载repmgr 
shared_preload_libraries = 'repmgr'
EOF

# 重启pg
pg_ctl  restart

repmgr配置 // 所有节点

# 配置repmgr 配置文件
vim /pgdata/repmgr/repmgr.conf
# 节点ID 唯一的
node_id=4
# 节点名 唯一的
node_name='pg-04-180'
# 本地连接信息
conninfo='host=10.10.8.180 port=5432  user=repmgr dbname=repmgr connect_timeout=2'
# pg数据目录路径
data_directory='/pgdata/12/data/'
# repmgr软件目录
repmgr_bindir='/usr/local/pg12/bin/'
# pg软件目录
pg_bindir='/usr/local/pg12/bin'
# 故障转移方法 自动
failover=automatic
# 等待提升配置
promote_command='/usr/local/pg12/bin/repmgr standby promote -f /pgdata/repmgr/repmgr.conf --log-to-file'
# 故障转移配置
follow_command='/usr/local/pg12/bin/repmgr  standby follow -f /pgdata/repmgr/repmgr.conf --log-to-file --upstream-node-id=%n'
# pg启动命令
service_start_command='pg_ctl -D /pgdata/12/data -l logfile start'
# pg关闭命令
service_stop_command='pg_ctl -D /pgdata/12/data -l logfile stop'
# pg重启命令
service_restart_command='pg_ctl -D /pgdata/12/data -l logfile restart'
# pg重载命令
service_reload_command='pg_ctl -D /pgdata/12/data -l logfile reload'
# pid文件位置
repmgrd_pid_file='/pgdata/repmgr/repmgrd.pid'
# 优先级权重
priority=100
# 日志输出
log_level=ERROR
log_file='/pgdata/repmgr/repmgrd.log'
log_status_interval=10
# 检查主库状态间隔时间
monitor_interval_secs=2
# 探测主库是否可用
connection_check_type='query'
# 尝试连接主库次数
reconnect_attempts=6
# 连接主库失败后再次连接的间隔时间
reconnect_interval=2
# repmgr 启动命令
repmgrd_service_start_command='repmgrd -f /pgdata/repmgr/repmgr.conf'
# repmgr 关闭命令
repmgrd_service_stop_command='kill -9 $(cat /pgdata/repmgr/repmgrd.pid)'
# 启动
repmgrd -f /pgdata/repmgr/repmgr.conf

# 关闭
kill -9 `cat /pgdata/repmgr/repmgrd.pid`

集群检查

# 集群状态拓扑
repmgr -f /pgdata/repmgr/repmgr.conf cluster show

# ssh 连接检查
repmgr -f /pgdata/repmgr/repmgr.conf cluster matrix

# repmgr连接检查
repmgr -f /pgdata/repmgr/repmgr.conf cluster crosscheck

# 显示节点基本信息和复制状态
repmgr -f /pgdata/repmgr/repmgr.conf node status

# 复制状况检查
repmgr -f /pgdata/repmgr/repmgr.conf node check

自动切换

# 主库执行
pg_ctl stop

# 查看集群状态
repmgr -f /pgdata/repmgr/repmgr.conf cluster show

恢复的时候执行不了的直接强制执行

但是一定要注意是什么问题,主从同步的问题就不能强制执行,执行了也报错

repmgr 常用命令

# 查看集群状态
repmgr -f /pgdata/repmgr/repmgr.conf cluster show

# primary 节点注册到集群 //主库
repmgr -f /pgdata/repmgr/repmgr.conf  primary register

# 将 standby 节点注册到集群  --upstream-node-id=1 //指定primary 节点的ID号  
repmgr standby register -f /pgdata/repmgr/repmgr.conf --upstream-node-id=1

# 强制注册一个standby 节点
repmgr  standby register    --force  -d 'host=10.10.8.176 port=5432 user=repmgr password=dyh666'


# 将 witness 节点注册到集群
repmgr -f /pgdata/repmgr/repmgr.conf  -h 10.10.8.176  --upstream-node-id=1 -Urepmgr -d repmgr witness register

# 集群删除一个standby节点
repmgr standby unregister -f /pgdata/repmgr/repmgr.conf --node-id=1

# 集群删除一个primary节点
repmgr primary unregister -f /pgdata/repmgr/repmgr.conf --node-id=1

# 集群删除 witness节点
repmgr witness  unregister -f /pgdata/repmgr/repmgr.conf   --node-id=4

# 检查切换  // 从节点执行
repmgr -f /pgdata/repmgr/repmgr.conf  standby switchover --siblings-follow --force-rewind --dry-run

# 手动切换切换  // 从节点执行
repmgr -f /pgdata/repmgr/repmgr.conf  standby switchover --siblings-follow --force-rewind

# 清理监控数据
repmgr cluster cleanup -f /pgdata/repmgr/repmgr.conf --node-id=4
相关实践学习
使用PolarDB和ECS搭建门户网站
本场景主要介绍基于PolarDB和ECS实现搭建门户网站。
阿里云数据库产品家族及特性
阿里云智能数据库产品团队一直致力于不断健全产品体系,提升产品性能,打磨产品功能,从而帮助客户实现更加极致的弹性能力、具备更强的扩展能力、并利用云设施进一步降低企业成本。以云原生+分布式为核心技术抓手,打造以自研的在线事务型(OLTP)数据库Polar DB和在线分析型(OLAP)数据库Analytic DB为代表的新一代企业级云原生数据库产品体系, 结合NoSQL数据库、数据库生态工具、云原生智能化数据库管控平台,为阿里巴巴经济体以及各个行业的企业客户和开发者提供从公共云到混合云再到私有云的完整解决方案,提供基于云基础设施进行数据从处理、到存储、再到计算与分析的一体化解决方案。本节课带你了解阿里云数据库产品家族及特性。
相关文章
|
18天前
|
存储 Cloud Native 关系型数据库
PolarDB 高可用架构设计与实践
【8月更文第27天】 在现代互联网应用中,数据库作为核心的数据存储层,其稳定性和可靠性尤为重要。阿里云的 PolarDB 作为一款云原生的关系型数据库服务,提供了高可用、高性能和自动化的特性,适用于各种规模的应用。本文将详细介绍 PolarDB 的高可用架构设计,并探讨其实现数据安全性和业务连续性的关键技术。
43 0
|
28天前
|
数据挖掘 关系型数据库 MySQL
Serverless高可用架构的解决方案体验
Serverless高可用架构的解决方案体验
142 6
|
30天前
|
弹性计算 运维 关系型数据库
云上Serverless高可用架构一键部署体验与测评
在数字化转型背景下,Serverless架构因其实现业务敏捷、降低成本及提升服务可靠性而备受青睐。本文以阿里云Serverless应用引擎(SAE)为核心,展示了一种高可用、低成本且易于扩展的解决方案。通过单地域双可用区部署,构建了具备自动伸缩与故障恢复能力的架构。借助阿里云的一键部署功能,大幅简化了搭建流程,实现了快速部署,并通过性能与成本分析验证了其优势。对比传统ECS,SAE在资源利用与运维效率上表现更佳,特别适合平均负载较低的应用场景。
|
30天前
|
弹性计算 运维 关系型数据库
Serverless高可用架构解决方案评测
Serverless高可用架构方案提供卓越效能与极简运维体验,支持服务托管、弹性伸缩及按量付费,有效降低成本并优化性能。一键部署快速启动,流程直观,文档详实;但在高级配置与特定场景实践方面指导有限。方案采用双可用区部署确保高可用性,自动故障切换保障服务连续。成本模型按需计费,减轻企业负担。功能上集成监控、日志与负载均衡,简化运维,加速上线。性能方面,秒级弹性伸缩保证资源高效匹配负载。总体而言,此方案竞争力强,特别推荐给初创公司及需灵活应对流量波动的场景。
135 2
|
30天前
|
运维 监控 负载均衡
如何构建高可用的系统基础架构
【8月更文挑战第15天】构建高可用的系统基础架构是一个复杂而系统的工程,需要综合考虑设计原则、关键技术和实践策略等多个方面。通过冗余设计、分布式架构、自动化与智能化等技术的运用,可以显著提升系统的可用性和稳定性。同时,加强运维团队的能力建设和制定完善的高可用性策略也是确保系统高可用性的重要保障。希望本文能为读者在构建高可用系统时提供有益的参考和借鉴。
|
1月前
|
关系型数据库 Serverless 分布式数据库
阿里云 Serverless 高可用架构
阿里云的《卓越效能,极简运维,Serverless高可用架构》解决方案提供了全托管服务、自动扩展、高可用性、无缝集成以及内置安全等核心功能。该方案通过免除底层基础设施的管理,允许用户专注于应用程序开发,同时确保应用的稳定运行和资源的有效利用。 **核心功能简介**: - **全托管服务**:用户无需关心底层硬件,由阿里云负责维护和扩展计算资源。 - **自动扩展**:根据业务需求自动调整资源,确保应用在高峰期有足够的计算能力,低谷期则节省成本。 - **高可用性**:多地域和多可用区部署,实现故障自动切换,确保业务连续性。 - **无缝集成**:与阿里云的其他服务(如数据库、消息队列等)深度
|
1月前
|
关系型数据库 Serverless 分布式数据库
Serverless高可用架构
PolarDB在《Serverless高可用架构》中展现了零代码改造、极简易用与自适应弹性的特性,提供按需伸缩与计费服务。相比传统架构,它能自动调整资源满足不同负载需求。阿里云Serverless服务简化了开发者的工作流程,让用户专注业务创新。为了优化用户体验,可通过提供最佳实践、深化文档内容、增强社区支持等方式进一步提升。PolarDB不仅降低了迁移难度,还简化了数据库管理,确保资源高效利用,是企业数字化转型的关键技术支撑。
|
14天前
|
负载均衡 关系型数据库 PostgreSQL
【一文搞懂PGSQL】6. PostgreSQL + pgpool-II 实现读写分离
本文介绍了如何使用 PostgreSQL 和 pgpool-II 实现读写分离。pgpool-II 支持连接池、负载均衡等功能,适用于多种模式。文中详细描述了安装、配置及启动过程,并提供了示例命令,帮助读者快速搭建并验证读写分离环境。通过配置 `pgpool.conf` 文件指定监听地址、端口及节点信息等参数,确保系统的高效运行与故障转移。
|
19天前
|
JSON API 网络架构
Django 后端架构开发:DRF 高可用API设计与核心源码剖析
Django 后端架构开发:DRF 高可用API设计与核心源码剖析
32 0
|
2月前
|
运维 负载均衡 关系型数据库
Serverless高可用架构体验评测
Serverless高可用架构体验评测