目录
1 文档概述
本文档说明电信云虚拟机Ubuntu系统部署PostgreSQL一主多备集群。
2 阅读对象
数据库运维、数据库管理员、应用开发人员等系统运维相关。
3 系统架构
3.1 高可用架构
PostgreSQL高可用集群组件包括中间件,数据库两部分,中间件采用Keepalive,HAProxy,数据库高可用组件etcd、patroni。
- Etcd:存储数据库集群元数据,集群状态信息。
- Patroni:集群管理、切换,故障转移,对外提供数据库状态查询接口。
- Keepalived:VIP绑定、VIP failover漂移,HAProxy服务故障切换。
- HAProxy:接受客户端访问,通过patroni访问接口确定数据库节点主备状态,分发读写、只读请求到数据库端primary、standby节点。
- PostgreSQL:数据库高可用集群,通过原生流复制实现一主多备。
3.2 限制条件
- 云管平台功能:
虚拟机EIP配置、分发与绑定,手工修改虚拟机IP无效。
VIP与虚拟机绑定,指定VIP漂移虚拟机节点。不支持ip add方式配置VIP,
VIP漂移通过keepalived配置VIP漂移。
放通安全组规则,放通绑定虚拟IP的弹性云服务器所在的安全组,即放通对端入向安全组规则协议为Any。 - 操作系统:
建议使用系统原生apt命令安装系统组件包。
3.3 安装要求
本次部署的一主四备集群,环境配置如下:
服务器数量 | 操作系统 | CPU | 内存 | 硬盘 | 网络 |
---|---|---|---|---|---|
5虚拟机(电信云自建) | Ubuntu 22.04.2 LTS (Jammy) x86_64 | 64 cores x86_64 | 256GB | 3TB | 万兆以上 |
3.4 软件配置
可选择数据库软件安装程序如下:
软件名称 | 安装包名称 |
---|---|
PostgreSQL | 13.16/14.13 |
Etcd | 3.3.25 |
Patroni | 4.0.2 |
Keepalived | v2.2.4 |
HAProxy | 2.4.24 |
3.5 硬件配置
集群名称 | 节点类型 | 节点IP | 主机名 | 网络 |
---|---|---|---|---|
Cluster01 | 数据库 | 10.24.57.10 | pg01 | |
Cluster01 | 数据库 | 10.24.57.11 | pg02 | |
Cluster01 | 数据库 | 10.24.57.12 | pg03 | |
Cluster01 | 数据库/keepalived/haproxy | 10.24.57.13 | pg04 | - |
Cluster01 | 数据库/keepalived/haproxy | 10.24.57.14 | epg05 | - |
Cluster01 | VIP | 10.24.57.101 | (虚拟IP) |
集群名称 | 节点类型 | 节点IP | 主机名 | 网络 |
---|---|---|---|---|
Cluster02 | 数据库 | 10.24.57.20 | pg06 | |
Cluster02 | 数据库 | 10.24.57.21 | pg07 | |
Cluster02 | 数据库 | 10.24.57.22 | pg08 | |
Cluster02 | VIP | 10.24.57.100 | (虚拟IP) |
3.6 端口配置
数据库集群使用的默认端口号如下,如冲突可调整。需注意各端口用途及说明,对待部署集群的环境提前申请开通各端口访问权限:
节点类型 | 端口号 | 端口类别 | 用途 | 说明 |
---|---|---|---|---|
数据库节点 | 5432 | 对外端口 | 数据库提供HAProxy、Patroni访问 | HAProxy、Patroni访问数据库节点 |
数据库节点 | 8008 | 对内端口 | 数据库提供HAProxy访问 | HAProxy访问数据库节点 |
数据库节点 | 2379, 2380 | 对内端口 | Etcd通信 | 数据库集群各节点之间 |
HAProxy | 5000/5001 | 对外端口 | 外网访问 | 应用程序到HAProxy服务器 |
Keepalived | 112 | 对内端口 | Keepalived VRRP | Keepalived各节点之间互通即可 |
请注意:
- 对外端口指的是需要从外部网络访问的端口,可能需要在防火墙或安全组中开放。
- 对内端口指的是仅用于集群内部通信的端口,通常不需要对外开放,但需要确保集群内部网络允许这些端口的通信。
根据实际部署环境的需求,可能需要调整上述端口号以避免冲突,并确保相应的端口访问权限已正确配置。
3.7 目录规划
各节点软件安装使用以下路径,也可按需调整。
节点类型 | 目录名称 | 所属用户 | 目录路径 | 权限 | 文件系统 |
---|---|---|---|---|---|
数据库节点 | 数据库软件目录 | root | /usr/lib/postgresql | 755 | ext4 |
数据库节点 | 数据库home目录 | postgres | /var/lib/postgresql | 755 | ext4 |
数据库节点 | 挂载目录 | postgres | /data/ | 755 | ext4 |
数据库节点 | 数据库数据目录 | postgres | /pgdata/pgdata | 700 | ext4 |
数据库节点 | 数据库备份目录 | postgres | /pgbackup | 755 | ext4 |
请注意:
- 权限列中的数字(如755、700)代表Linux文件权限设置,具体含义如下:
755
:所有者可读写执行,组用户和其他用户可读可执行。700
:只有所有者可读写执行,其他用户无任何权限。
- 文件系统指的是挂载该目录的文件系统类型,例如ext4是常见的Linux文件系统类型。
- 根据实际需求和环境配置,目录路径和权限设置可能需要进行相应调整。
3.8 绑定存储(新系统未分配的情况)
在部署PostgreSQL集群时,需要对磁盘进行格式化、挂载以及配置自动挂载。以下是具体的操作步骤:
格式化磁盘
使用mkfs.ext4
命令对磁盘进行格式化。请根据实际环境中的磁盘设备名称(如/dev/sda
)替换命令中的内容。
mkfs.ext4 /dev/sda
注意:
/dev/sda
是示例磁盘设备名称,请根据实际情况替换为对应的磁盘路径。- 格式化操作会清空磁盘上的所有数据,请确保已备份重要数据。
挂载目录
将格式化后的磁盘挂载到指定目录(如/data
),并验证挂载是否成功。
mount /dev/sda /data
df -h
/dev/sda
:格式化后的磁盘设备名称。/data
:目标挂载路径,请根据实际需求替换。df -h
:查看挂载情况,确认磁盘是否成功挂载。
配置自动挂载
为了确保系统重启后磁盘能够自动挂载,需要编辑/etc/fstab
文件,添加挂载配置。
-
打开
/etc/fstab
文件:sudo vim /etc/fstab
-
在文件的最后一行添加以下内容:
/dev/sda /data ext4 defaults 0 1
参数说明:
/dev/sda
:磁盘设备名称。/data
:挂载路径。ext4
:文件系统类型。defaults
:挂载选项,表示默认设置。0
:是否启用dump备份工具(0表示不启用)。1
:是否启用文件系统检查(1表示启用,根分区通常为1,其他分区可设为2)。
验证自动挂载配置
完成/etc/fstab
配置后,可以通过以下命令测试配置是否正确:
sudo mount -a
df -h
sudo mount -a
:重新加载/etc/fstab
配置,模拟系统启动时的挂载操作。- 如果没有报错且
df -h
显示挂载信息,则说明配置成功。
4 部署基础软件
4.1 主机名设置
(可选)可设置各节点主机名称如下:
hostnamectl set-hostname new_hostname01
hostnamectl set-hostname new_hostname02
hostnamectl set-hostname new_hostname03
设置各节点/etc/hosts:
192.168.100.1 new_hostname01
192.168.100.2 new_hostname02
192.168.100.3 new_hostname03
4.2基础包安装
更新镜像源并安装系统包:
sudo apt update
sudo apt-get install aptitude vim net-tools build-essential uuid-dev libtool libpcre3 libpcre3-dev zlib1g-dev openssl libssl-dev libreadline-dev ntp etcd libdpkg-perl bzip2 unzip ntpdate python3-pip python3-dev language-pack-en cron keepalived haproxy
4.3系统字符集配置
修改默认语言集:
--- 修改默认语言集
sudo vim /etc/default/locale
LANG="en_US.UTF-8"
--- 检查当前语言集
# locale
LANG=C.UTF-8
LANGUAGE=
LC_CTYPE="C.UTF-8"
LC_NUMERIC="C.UTF-8"
LC_TIME="C.UTF-8"
LC_COLLATE="C.UTF-8"
LC_MONETARY="C.UTF-8"
LC_MESSAGES="C.UTF-8"
LC_PAPER="C.UTF-8"
LC_NAME="C.UTF-8"
LC_ADDRESS="C.UTF-8"
LC_TELEPHONE="C.UTF-8"
LC_MEASUREMENT="C.UTF-8"
LC_IDENTIFICATION="C.UTF-8"
LC_ALL=
--- 安装en_US.UTF-8语言
# sudo locale-gen en_US.UTF-8
Generating locales (this might take a while)...
en_US.UTF-8... done
Generation complete.
#
--- 退出重新登录
# exit
--- 检查当前语言集
# locale
LANG=en_US.UTF-8
LANGUAGE=
LC_CTYPE="en_US.UTF-8"
LC_NUMERIC="en_US.UTF-8"
LC_TIME="en_US.UTF-8"
LC_COLLATE="en_US.UTF-8"
LC_MONETARY="en_US.UTF-8"
LC_MESSAGES="en_US.UTF-8"
LC_PAPER="en_US.UTF-8"
LC_NAME="en_US.UTF-8"
LC_ADDRESS="en_US.UTF-8"
LC_TELEPHONE="en_US.UTF-8"
LC_MEASUREMENT="en_US.UTF-8"
LC_IDENTIFICATION="en_US.UTF-8"
LC_ALL=
# env|grep LANG
LANG=en_US.UTF-8
#
4.4Patroni安装
安装Patroni及相关依赖:
# pip3 install -i https://mirrors.aliyun.com/pypi/simple --upgrade pip
# sudo pip3 install -i https://mirrors.aliyun.com/pypi/simple patroni[etcd]
# sudo pip3 install -i https://mirrors.aliyun.com/pypi/simple psycopg2-binary
# pip3 list
Package Version
--------------------- -------------
attrs 21.2.0
Babel 2.8.0
blinker 1.4
certifi 2020.6.20
chardet 4.0.0
click 8.0.3
cloud-init 23.1.2
colorama 0.4.4
configobj 5.0.6
cryptography 3.4.8
dbus-python 1.2.18
distro 1.7.0
distro-info 1.1build1
dnspython 2.6.1
httplib2 0.20.2
idna 3.3
importlib-metadata 4.6.4
jeepney 0.7.1
Jinja2 3.0.3
jsonpatch 1.32
jsonpointer 2.0
jsonschema 3.2.0
keyring 23.5.0
launchpadlib 1.10.16
lazr.restfulclient 0.14.4
lazr.uri 1.0.6
MarkupSafe 2.0.1
more-itertools 8.10.0
netifaces 0.11.0
oauthlib 3.2.0
patroni 4.0.2
pip 24.2
prettytable 3.11.0
psutil 6.0.0
psycopg2-binary 2.9.9
PyGObject 3.42.1
PyJWT 2.3.0
pyparsing 2.4.7
pyrsistent 0.18.1
pyserial 3.5
python-apt 2.4.0+ubuntu1
python-dateutil 2.9.0.post0
python-etcd 0.4.5
pytz 2022.1
PyYAML 5.4.1
requests 2.25.1
SecretStorage 3.3.1
setuptools 59.6.0
six 1.16.0
ssh-import-id 5.11
systemd-python 234
ubuntu-drivers-common 0.0.0
unattended-upgrades 0.1
urllib3 1.26.5
wadllib 1.3.6
wcwidth 0.2.13
wheel 0.37.1
xkit 0.0.0
ydiff 1.3
zipp 1.0.0
#
4.5安装PG
安装PostgreSQL 14:
--- install postgresql online
sudo apt install -y postgresql-common
sudo /usr/share/postgresql-common/pgdg/apt.postgresql.org.sh
sudo apt install postgresql-14
--- check postgresql install
# dpkg -l |grep postgresql
ii postgresql-14 14.13-1.pgdg22.04+1 amd64 The World's Most Advanced Open Source Relational Database
ii postgresql-client-14 14.13-1.pgdg22.04+1 amd64 front-end programs for PostgreSQL 14
ii postgresql-client-common 238 all manager for multiple PostgreSQL client versions
ii postgresql-common 238 all PostgreSQL database-cluster manager
#
--- disable postgresql service(patroni start/stop postgresql database)
# systemctl disable postgresql
Synchronizing state of postgresql.service with SysV service script with /lib/systemd/systemd-sysv-install.
Executing: /lib/systemd/systemd-sysv-install disable postgresql
Removed /etc/systemd/system/multi-user.target.wants/postgresql.service.
#
--- uuid-ossp扩展确认
# su - postgres
postgres@localhost:~$ psql
psql (14.13 (Ubuntu 14.13-1.pgdg22.04+1))
Type "help" for help.
postgres=# create extension "uuid-ossp" ;
CREATE EXTENSION
postgres=# \dx
List of installed extensions
Name | Version | Schema | Description
-----------+---------+------------+-------------------------------------------------
plpgsql | 1.0 | pg_catalog | PL/pgSQL procedural language
uuid-ossp | 1.1 | public | generate universally unique identifiers (UUIDs)
(2 rows)
postgres=#
--- 数据目录授权
mkdir /data/pgdata
chown postgres.postgres –R /data
chmod 755 /data
chmod 700 /data/pgdata
4.6 开通端口
在部署PostgreSQL高可用集群时,需要确保各节点之间的通信端口已正确开通。以下是默认端口列表及开通方法:
默认端口列表
用途 | 类型 | 默认端口 |
---|---|---|
PG节点(Etcd) | TCP | 2379、2380 |
HAProxy到PG节点(Patroni) | TCP | 5432、8008 |
Keepalived节点 | UDP | 112 |
外部访问HAProxy | TCP | 5000、5001、7000 |
关闭防火墙(可选)
如果环境允许关闭防火墙,可以通过以下命令停止并禁用ufw
防火墙服务:
systemctl stop ufw
systemctl disable ufw
验证防火墙状态:
sudo ufw status verbose
输出示例:
Status: inactive
注意:
- 关闭防火墙适用于测试环境或受控网络环境。生产环境中建议通过开放特定端口的方式管理防火墙规则。
开启特定端口(推荐)
在生产环境中,建议仅开放必要的端口,而不是完全关闭防火墙。以下是针对不同节点的端口开放命令:
数据库节点(DB节点)
为数据库节点(包括Etcd和Patroni)开放所需端口:
sudo ufw allow 2379/tcp # Etcd通信端口
sudo ufw allow 2380/tcp # Etcd通信端口
sudo ufw allow 5432/tcp # PostgreSQL数据库端口
sudo ufw allow 8008/tcp # Patroni API端口
Keepalived和HAProxy节点
为Keepalived和HAProxy节点开放所需端口:
sudo ufw allow 5000/tcp # HAProxy外部访问端口
sudo ufw allow 5001/tcp # HAProxy外部访问端口
sudo ufw allow 7000/tcp # HAProxy监控端口(可选)
sudo ufw allow 112/udp # Keepalived VRRP通信端口
验证端口状态
完成端口配置后,可以通过以下命令查看当前的防火墙规则:
sudo ufw status
输出示例:
Status: active
To Action From
-- ------ ----
2379/tcp ALLOW Anywhere
2380/tcp ALLOW Anywhere
5432/tcp ALLOW Anywhere
8008/tcp ALLOW Anywhere
5000/tcp ALLOW Anywhere
5001/tcp ALLOW Anywhere
7000/tcp ALLOW Anywhere
112/udp ALLOW Anywhere
4.7 设置系统时区
在部署PostgreSQL集群时,确保所有节点使用统一的时区非常重要。以下是设置系统时区的操作步骤:
sudo timedatectl set-timezone Asia/Shanghai
验证时区设置是否成功:
timedatectl show
输出示例:
Timezone=Asia/Shanghai
LocalRTC=no
CanNTP=no
NTP=no
NTPSynchronized=yes
TimeUSec=Thu 2024-09-19 12:38:39 CST
RTCTimeUSec=Thu 2024-09-19 12:38:39 CST
注意:
Asia/Shanghai
是示例时区,请根据实际需求替换为其他时区(如UTC
等)。
4.8 系统时间同步
为了确保数据库主备节点之间的时间一致性,建议配置时间同步服务。以下是具体配置方法:
检查时间配置
执行以下命令检查当前系统时间状态:
timedatectl show
输出示例:
Timezone=Asia/Shanghai
LocalRTC=no
CanNTP=no
NTP=no
NTPSynchronized=yes
TimeUSec=Thu 2024-09-19 12:38:39 CST
RTCTimeUSec=Thu 2024-09-19 12:38:39 CST
配置crontab任务同步
如果使用ntpdate
进行时间同步,可以通过添加crontab任务实现定时同步:
* * * * * /usr/sbin/ntpdate -s ntp.tyyun.cn && /usr/sbin/hwclock --systohc --verbose >/dev/null 2>&1
注意:
ntp.tyyun.cn
是示例NTP服务器地址,请根据实际环境替换为可用的NTP服务器地址。ntpdate
和ntpd
不能同时使用,请根据需求选择其中一种方式。
配置NTP同步服务
如果使用ntpd
服务进行时间同步,请按以下步骤操作:
-
编辑
/etc/ntp.conf
文件,添加或修改NTP服务器配置:pool ntp.tyyun.cn iburst
-
重启
ntpd
服务以应用更改:systemctl restart ntp
-
验证NTP同步状态:
ntpq -p
输出示例:
remote refid st t when poll reach delay offset jitter ============================================================================== ntp.tyyun.cn .POOL. 16 p - 64 0 0.000 +0.000 0.000
4.9 系统参数优化
为了提升PostgreSQL集群的性能,需要对系统内核参数和用户资源限制进行优化。以下是具体配置方法:
4.9.1 内核参数
编辑/etc/sysctl.conf
文件,添加以下内容:
#### PG ENV ####
net.ipv4.tcp_keepalive_intvl = 10
net.ipv4.tcp_keepalive_probes = 3
net.ipv4.tcp_keepalive_time = 60
fs.aio-max-nr=1048576
fs.file-max= 76724600
net.core.netdev_max_backlog = 10000
net.core.rmem_default = 262144
net.core.rmem_max = 4194304
net.core.wmem_default = 262144
net.core.wmem_max = 4194304
net.core.somaxconn = 4096
net.ipv4.tcp_fin_timeout = 5
vm.overcommit_memory = 0
vm.swappiness = 10
fs.nr_open = 20480000
net.ipv4.tcp_max_syn_backlog = 2048
应用配置:
sysctl -p
4.9.2 用户资源限制
编辑/etc/security/limits.conf
文件,添加以下内容:
#### PG ENV ####
postgres soft nproc unlimited
postgres hard nproc unlimited
postgres soft nofile 102400
postgres hard nofile 102400
postgres soft stack unlimited
postgres hard stack unlimited
postgres soft core unlimited
postgres hard core unlimited
postgres soft memlock unlimited
postgres hard memlock unlimited
4.10 etcd配置
在PostgreSQL高可用集群中,etcd
用于存储集群元数据和状态信息。以下是etcd
的详细配置步骤。
4.10.1 etcd配置文件
编辑/etc/etcd.conf
文件,完成etcd
的基本配置。请根据实际节点的IP地址替换红色字体部分。
vi /etc/etcd.conf
添加以下内容:
ETCD_NAME="etcd04"
ETCD_DATA_DIR="/var/lib/etcd/default.etcd"
ETCD_LISTEN_PEER_URLS="http://10.24.57.13:2380"
ETCD_ADVERTISE_CLIENT_URLS="http://10.24.57.13:2379"
ETCD_LISTEN_CLIENT_URLS="http://10.24.57.13:2379,http://127.0.0.1:2379"
ETCD_INITIAL_ADVERTISE_PEER_URLS="http://10.24.57.13:2380"
ETCD_INITIAL_CLUSTER="etcd01=http://10.24.57.10:2380,etcd02=http://10.24.57.11:2380,etcd03=http://10.24.57.12:2380,etcd04=http://10.24.57.13:2380,etcd05=http://10.24.57.14:2380"
ETCD_INITIAL_CLUSTER_STATE="new"
ETCD_INITIAL_CLUSTER_TOKEN="k8s-etcd-cluster"
ETCD_ENABLE_V2="true"
注意:
ETCD_NAME
:当前节点的名称,请确保每个节点的名称唯一。ETCD_LISTEN_PEER_URLS
和ETCD_ADVERTISE_CLIENT_URLS
:替换为当前节点的实际IP地址。ETCD_INITIAL_CLUSTER
:列出所有etcd
节点的名称和IP地址,确保与集群规划一致。
4.10.2 etcd服务文件
创建并编辑/etc/systemd/system/etcd.service
文件,定义etcd
的服务启动方式。
vi /etc/systemd/system/etcd.service
添加以下内容:
[Unit]
Documentation=https://github.com/etcd-io/etcd
Description=Etcd Server
After=network.target
After=network-online.target
Wants=network-online.target
[Service]
Type=simple
WorkingDirectory=/var/lib/etcd
EnvironmentFile=-/etc/etcd.conf
# set GOMAXPROCS to number of processors
ExecStart=/bin/bash -c "GOMAXPROCS=$(nproc) /usr/bin/etcd"
Type=notify
Restart=on-failure
LimitNOFILE=65536
[Install]
WantedBy=multi-user.target
说明:
WorkingDirectory
:指定etcd
的工作目录。EnvironmentFile
:加载/etc/etcd.conf
配置文件。ExecStart
:启动etcd
服务,并动态设置GOMAXPROCS
以优化性能。
4.10.3 etcd服务自启动
完成配置后,启用etcd
服务并设置开机自启动。
-
清除旧的
etcd
服务配置(如果存在):systemctl disable etcd
-
添加新的
etcd
服务配置:systemctl enable etcd
-
启动
etcd
服务:systemctl start etcd
-
检查
etcd
服务状态:systemctl status etcd
输出示例:
● etcd.service - Etcd Server
Loaded: loaded (/etc/systemd/system/etcd.service; enabled; vendor preset: enabled)
Active: active (running) since Thu 2024-09-19 12:38:39 CST; 1min ago
Docs: https://github.com/etcd-io/etcd
Main PID: 1234 (etcd)
Tasks: 10 (limit: 4915)
Memory: 50.0M
CPU: 2.5s
CGroup: /system.slice/etcd.service
└─1234 /usr/bin/etcd
注意:
- 如果服务启动失败,请检查日志排查问题:
journalctl -u etcd
4.11 Patroni配置
在PostgreSQL高可用集群中,Patroni
用于管理数据库实例的生命周期(如启动、停止、故障切换等)。以下是Patroni
的详细配置步骤。
4.11.1 Patroni配置文件
编辑/etc/patroni/pg.yml
文件,完成Patroni
的基本配置。请根据实际节点的IP地址、端口、初始用户名称等参数替换红色字体部分。
vi /etc/patroni/pg.yml
添加以下内容:
scope: PGCluster
namespace: /pgsql/
name: pg05 # 替换为本节点唯一标识
restapi:
listen: 10.24.57.14:8008 # 替换为本节点IP
connect_address: 10.24.57.14:8008 # 替换为本节点IP
etcd:
hosts: 10.24.57.10:2379,10.24.57.11:2379,10.24.57.12:2379,10.24.57.13:2379,10.24.57.14:2379
bootstrap:
dcs:
ttl: 30
loop_wait: 10
retry_timeout: 10
maximum_lag_on_failover: 1048576
master_start_timeout: 300
synchronous_mode: true
postgresql:
use_pg_rewind: true
use_slots: true
parameters:
listen_addresses : '0.0.0.0'
max_connections : 3000
hot_standby : 'on'
max_locks_per_transaction : 1024
max_prepared_transactions : 1024
max_replication_slots : '10'
max_wal_senders : '10'
max_worker_processes : '8'
port : 5432
track_commit_timestamp : 'off'
wal_keep_size : '10240MB'
wal_level : 'logical'
postgresql:
listen: 0.0.0.0:5432
connect_address: 10.24.57.14:5432 # 替换为本节点IP
data_dir: /data/pgdata
bin_dir: /usr/lib/postgresql/14/bin
pgpass: /var/lib/postgresql/.pgpass
authentication:
replication:
username: replicator
password: Leven@@
superuser:
username: postgres
password: Leven528625@
tags:
nofailover: false
noloadbalance: false
clonefrom: false
nosync: false
注意:
scope
:定义集群范围,确保所有节点使用相同的值。name
:每个节点的唯一名称,请确保在集群中唯一。listen
和connect_address
:替换为当前节点的实际IP地址。etcd.hosts
:列出所有etcd
节点的IP地址和端口。
配置完成后,确保postgres
用户对配置文件有读写权限:
chown postgres.postgres -R /etc/patroni/
4.11.2 Patroni配置检查
使用以下命令验证Patroni
配置文件是否正确:
patroni --validate-config /etc/patroni/pg.yml
如果配置正确,无任何提示;如果有错误提示,请根据提示调整配置。
示例输出(错误示例):
postgresql.data_dir /data/pgdata didn't pass validation: doesn't look like a valid data directory
4.11.3 Patroni服务文件
创建并编辑/etc/systemd/system/patroni.service
文件,定义Patroni
的服务启动方式。
vi /etc/systemd/system/patroni.service
添加以下内容:
[Unit]
Description=Vastbase HAS server daemon
After=network.target network-online.target
[Service]
Type=simple
User=postgres
ExecStart=/usr/local/bin/patroni /etc/patroni/pg.yml
TimeoutStopSec=600
Restart=no
LimitMEMLOCK=infinity
LimitNOFILE=1024000
[Install]
WantedBy=multi-user.target
说明:
User
:指定运行Patroni
服务的用户(通常为postgres
)。ExecStart
:指定Patroni
的启动命令及配置文件路径。
4.11.4 Patroni服务自启动
完成配置后,启用Patroni
服务并设置开机自启动。
-
清除旧的
Patroni
服务配置(如果存在):systemctl disable patroni
-
添加新的
Patroni
服务配置:systemctl enable patroni
-
启动
Patroni
服务:systemctl start patroni
-
检查
Patroni
服务状态:systemctl status patroni
输出示例:
● patroni.service - Vastbase HAS server daemon
Loaded: loaded (/etc/systemd/system/patroni.service; enabled; vendor preset: enabled)
Active: active (running) since Thu 2024-09-19 12:38:39 CST; 1min ago
Main PID: 5678 (patroni)
Tasks: 10 (limit: 4915)
Memory: 100.0M
CPU: 5.2s
CGroup: /system.slice/patroni.service
└─5678 /usr/local/bin/patroni /etc/patroni/pg.yml
注意:
- 如果服务启动失败,请检查日志排查问题:
journalctl -u patroni
4.12 Keepalived配置
在PostgreSQL高可用集群中,Keepalived
用于实现VIP漂移,配合HAProxy
服务实现数据库读写分离。以下是Keepalived
的详细配置步骤。
前提条件:
Keepalived
服务节点通信需要管控平台开通为ANY。- 配置抢占模式以确保主备切换时VIP能够正确漂移。
4.12.1 Keepalived配置文件
Master节点配置
编辑/etc/keepalived/keepalived.conf
文件,完成Master节点的配置:
vi /etc/keepalived/keepalived.conf
添加以下内容:
! Configuration File for keepalived
global_defs {
router_id my_router
vrrp_garp_interval 3
vrrp_gna_interval 3
}
vrrp_script check_haproxy {
script "/etc/keepalived/check_haproxy.sh" # 用shell命令检查haproxy服务是否运行
interval 1 # 时间间隔为1秒检测一次
# weight -2 # 当haproxy的服务不存在了,就把当前的权重-2
}
vrrp_instance VI_1 {
state BACKUP # 设置初始状态均为"BACKUP"
nopreempt
interface eth0 # 设置绑定 VIP 的网卡,例如 eth0
virtual_router_id 51 # 配置集群 virtual_router_id 值
priority 100 # 两设备是相同值的等权重节点
advert_int 5
authentication {
auth_type PASS
auth_pass 1111
}
unicast_src_ip 10.24.57.22 # 设置本机内网IP地址
unicast_peer {
10.24.57.21 # 对端设备的 IP 地址
}
virtual_ipaddress {
10.24.57.100 # 设置高可用虚拟 VIP
}
track_script {
check_haproxy
}
garp_master_delay 1 # 设置当切为主状态后多久更新 ARP 缓存
garp_master_refresh 5 # 设置主节点发送 ARP 报文的时间间隔
track_interface {
eth0 # 使用绑定 VIP 的网卡,例如 eth0
}
}
Backup节点配置
编辑/etc/keepalived/keepalived.conf
文件,完成Backup节点的配置:
vi /etc/keepalived/keepalived.conf
添加以下内容:
! Configuration File for keepalived
global_defs {
router_id my_router
vrrp_garp_interval 3
vrrp_gna_interval 3
}
vrrp_script check_haproxy {
script "/etc/keepalived/check_haproxy.sh" # 用shell命令检查haproxy服务是否运行
interval 1 # 时间间隔为1秒检测一次
# weight -2 # 当haproxy的服务不存在了,就把当前的权重-2
}
vrrp_instance VI_1 {
state BACKUP # 设置初始状态均为"BACKUP"
nopreempt
interface eth0 # 设置绑定 VIP 的网卡,例如 eth0
virtual_router_id 51 # 配置集群 virtual_router_id 值
priority 100 # 两设备是相同值的等权重节点
advert_int 5
authentication {
auth_type PASS
auth_pass 1111
}
unicast_src_ip 10.24.57.21 # 设置本机内网IP地址
unicast_peer {
10.24.57.22 # 对端设备的 IP 地址
}
virtual_ipaddress {
10.24.57.100 # 设置高可用虚拟 VIP
}
track_script {
check_haproxy
}
garp_master_delay 1 # 设置当切为主状态后多久更新 ARP 缓存
garp_master_refresh 5 # 设置主节点发送 ARP 报文的时间间隔
track_interface {
eth0 # 使用绑定 VIP 的网卡,例如 eth0
}
}
注意:
state
:设置初始状态均为BACKUP
,避免抢占冲突。priority
:优先级相同的情况下,nopreempt
确保不会强制抢占。unicast_src_ip
和unicast_peer
:分别替换为本机和对端设备的实际IP地址。
检查脚本配置
创建并编辑/etc/keepalived/check_haproxy.sh
脚本,用于检查HAProxy
服务是否正常运行:
vi /etc/keepalived/check_haproxy.sh
添加以下内容:
#!/usr/bin/bash
A=`ps -C haproxy --no-header | wc -l`
if [ $A -ge 1 ]; then
exit 0
else
exit 1
fi
赋予脚本执行权限:
chmod +x /etc/keepalived/check_haproxy.sh
4.12.2 Keepalived服务文件
编辑/lib/systemd/system/keepalived.service
文件,定义Keepalived
的服务启动方式:
vi /lib/systemd/system/keepalived.service
添加以下内容:
[Unit]
Description=Keepalive Daemon (LVS and VRRP)
After=network-online.target
Wants=network-online.target
# Only start if there is a configuration file
ConditionFileNotEmpty=/etc/keepalived/keepalived.conf
[Service]
Type=simple
# Read configuration variable file if it is present
EnvironmentFile=-/etc/default/keepalived
ExecStart=/usr/sbin/keepalived --dont-fork $DAEMON_ARGS
ExecReload=/bin/kill -HUP $MAINPID
[Install]
WantedBy=multi-user.target
4.12.3 Keepalived服务自启动
启用Keepalived
服务并设置开机自启动:
systemctl enable keepalived
启动Keepalived
服务:
systemctl start keepalived
检查服务状态:
systemctl status keepalived
输出示例:
● keepalived.service - Keepalive Daemon (LVS and VRRP)
Loaded: loaded (/lib/systemd/system/keepalived.service; enabled; vendor preset: enabled)
Active: active (running) since Thu 2024-09-19 12:38:39 CST; 1min ago
Main PID: 9876 (keepalived)
Tasks: 5 (limit: 4915)
Memory: 20.0M
CPU: 2.1s
CGroup: /system.slice/keepalived.service
├─9876 /usr/sbin/keepalived --dont-fork
└─9877 /usr/sbin/keepalived --dont-fork
注意:
- 如果服务启动失败,请检查日志排查问题:
journalctl -u keepalived
4.13 HAProxy配置
在PostgreSQL高可用集群中,HAProxy
用于实现负载均衡和读写分离。以下是HAProxy
的详细配置步骤。
注意事项:
primary
和standby
绑定IP配置时,即使VIP不漂移,HAProxy
服务仍需保持运行状态。
4.13.1 HAProxy配置文件
编辑/etc/haproxy/haproxy.cfg
文件,完成HAProxy
的基本配置:
vi /etc/haproxy/haproxy.cfg
添加以下内容:
global
maxconn 20480
defaults
mode tcp
log global
option tcplog
retries 3
timeout queue 1m
timeout connect 5s
timeout client 60m
timeout server 60m
timeout check 5s
listen stats
mode http
bind *:7000
stats enable
stats uri /
listen primary
bind *:5000
option httpchk OPTIONS /master
http-check expect status 200
default-server inter 3s fall 3 rise 2 on-marked-down shutdown-sessions
server ecmjzgmiddlepg01 10.24.57.20:5432 check port 8008
server ecmjzgmiddlepg02 10.24.57.21:5432 check port 8008
server ecmjzgmiddlepg03 10.24.57.22:5432 check port 8008
listen standby
bind *:5001
balance roundrobin
option httpchk OPTIONS /replica
http-check expect status 200
default-server inter 3s fall 3 rise 2 on-marked-down shutdown-sessions
server ecmjzgmiddlepg01 10.24.57.20:5432 check port 8008
server ecmjzgmiddlepg02 10.24.57.21:5432 check port 8008
server ecmjzgmiddlepg03 10.24.57.22:5432 check port 8008
说明:
listen stats
:定义了HAProxy的状态监控页面,可通过http://<IP>:7000/
访问。listen primary
:主节点负载均衡配置,绑定端口5000
,仅转发到主数据库。listen standby
:从节点负载均衡配置,绑定端口5001
,采用轮询方式分发请求到从数据库。server
:列出所有数据库节点的IP地址和端口,请根据实际环境替换。
4.13.2 HAProxy服务文件
编辑/lib/systemd/system/haproxy.service
文件,定义HAProxy
的服务启动方式:
vi /lib/systemd/system/haproxy.service
添加以下内容:
[Unit]
Description=HAProxy Load Balancer
Documentation=man:haproxy(1)
Documentation=file:/usr/share/doc/haproxy/configuration.txt.gz
After=network-online.target rsyslog.service
Wants=network-online.target
[Service]
EnvironmentFile=-/etc/default/haproxy
EnvironmentFile=-/etc/sysconfig/haproxy
Environment="CONFIG=/etc/haproxy/haproxy.cfg" "PIDFILE=/run/haproxy.pid" "EXTRAOPTS=-S /run/haproxy-master.sock"
ExecStartPre=/usr/sbin/haproxy -Ws -f $CONFIG -c -q $EXTRAOPTS
ExecStart=/usr/sbin/haproxy -Ws -f $CONFIG -p $PIDFILE $EXTRAOPTS
ExecReload=/usr/sbin/haproxy -Ws -f $CONFIG -c -q $EXTRAOPTS
ExecReload=/bin/kill -USR2 $MAINPID
KillMode=mixed
Restart=always
SuccessExitStatus=143
Type=notify
[Install]
WantedBy=multi-user.target
说明:
Environment
:指定配置文件路径、PID文件路径以及其他选项。ExecStartPre
:在启动前检查配置文件是否正确。ExecStart
:启动HAProxy
服务。Restart=always
:确保服务异常退出后自动重启。
4.13.3 HAProxy服务自启动
启用HAProxy
服务并设置开机自启动:
systemctl enable haproxy
启动HAProxy
服务:
systemctl start haproxy
检查服务状态:
systemctl status haproxy
输出示例:
● haproxy.service - HAProxy Load Balancer
Loaded: loaded (/lib/systemd/system/haproxy.service; enabled; vendor preset: enabled)
Active: active (running) since Thu 2024-09-19 12:38:39 CST; 1min ago
Main PID: 12345 (haproxy)
Tasks: 5 (limit: 4915)
Memory: 30.0M
CPU: 3.5s
CGroup: /system.slice/haproxy.service
├─12345 /usr/sbin/haproxy -Ws -f /etc/haproxy/haproxy.cfg -p /run/haproxy.pid -S /run/haproxy-master.sock
└─12346 /usr/sbin/haproxy -Ws -f /etc/haproxy/haproxy.cfg -p /run/haproxy.pid -S /run/haproxy-master.sock
注意:
- 如果服务启动失败,请检查日志排查问题:
journalctl -u haproxy
5.PostgreSQL集群部署
5.1 设置postgres环境变量
编辑.profile文件:
su – postgres
vi .profile
export PGROOT=/usr/lib/postgresql/14 # according install path
export PATH=$PGROOT/bin:$PATH
export PGDATA=/data/pgdata # according data path
export LD_LIBRARY_PATH=$PGROOT/lib:$LD_LIBRARY_PATH
5.2免密配置
创建.pgpass文件并设置权限:
--- 文件权限600,replicator用户登录primary节点replication、postgres库免密
# su - postgres
vi .pgpass
*:5432:*:replicator:Leven528625
chmod 600 .pgpass
5.3 初始化数据目录
确认字符集en_US.UTF-8与原始数据库相同:
su – postgres
initdb
5.4 pg_hba.conf
编辑 $PGDATA/pg_hba.conf 文件:
--- 注意事项:默认replicator用户节点间不需要认证,patroni加认证无法重建节点
vi $PGDATA/pg_hba.conf
# TYPE DATABASE USER ADDRESS METHOD
# "local" is for Unix domain socket connections only
local all all trust
# IPv4 local connections:
host all all 127.0.0.1/32 trust
host all all 0.0.0.0/0 scram-sha-256
# IPv6 local connections:
host all all ::1/128 trust
# Allow replication connections from localhost, by a user with the
# replication privilege.
local replication all trust
host replication all 127.0.0.1/32 trust
host replication replicator 0.0.0.0/0 trust
5.5 PostgreSQL配置文件
在Patroni
集群中,PostgreSQL参数文件的应用顺序如下:
postgresql.base.conf
postgresql.conf
postgresql.auto.conf
- 运行时参数(通过命令行指定,例如
-o --name=value
)
pg_wal目录WAL文件限制参数应用原则
- 如果配置
wal_keep_size > 0
,则该参数值控制pg_wal
目录中WAL文件的数量,数据库执行checkpoint
操作时会回收WAL文件。 - 如果配置
wal_keep_size = 0
,则max_slot_wal_keep_size
参数值控制pg_wal
目录中WAL文件的数量。
注意事项:
- 修改
postgresql.conf
文件后,使用patronictl reload
使配置生效。- 登录数据库执行
SHOW wal_keep_size
检查配置是否生效。
数据库参数优化
根据系统内存和运维管理要求优化数据库参数。清理默认配置、注释行和空行:
grep -v ^# postgresql.base.conf | grep -v '^\s*#' | grep -v '^$'
编辑$PGDATA/postgresql.conf
文件:
listen_addresses = '*' # 监听所有IP地址
max_connections = 3000 # 最大连接数(需要重启生效)
password_encryption = md5 # 密码加密方式(scram-sha-256或md5)
shared_buffers = 64GB # 共享缓冲区大小(最小128kB)
work_mem = 16MB # 单个查询可用的工作内存(最小64kB)
maintenance_work_mem = 2GB # 维护操作内存(最小1MB)
dynamic_shared_memory_type = posix # 动态共享内存类型
effective_io_concurrency = 1 # IO并发数(0禁用预取)
wal_level = logical # WAL级别(minimal, replica, 或 logical)
wal_log_hints = on # 启用非关键更新的全页写入
checkpoint_timeout = 15min # 检查点超时时间(范围30秒到1天)
max_wal_size = 10GB # WAL最大大小
min_wal_size = 80MB # WAL最小大小
archive_mode = on # 启用归档模式
archive_command = '/bin/true' # 归档命令
wal_keep_size = 10240 # WAL保留大小(单位:MB;0禁用)
max_slot_wal_keep_size = 50000 # 复制槽保留的最大WAL大小(单位:MB;-1禁用)
synchronous_standby_names = '*' # 同步备用服务器
hot_standby_feedback = on # 启用热备反馈
effective_cache_size = 192GB # 有效缓存大小
log_destination = 'csvlog' # 日志目标
logging_collector = on # 启用日志收集器
log_filename = 'postgresql-%d.log' # 日志文件名模式
log_rotation_size = 0 # 禁用日志自动轮转
log_truncate_on_rotation = on # 轮转时截断日志
log_min_duration_statement = 10000 # 记录执行时间超过10秒的SQL语句
log_autovacuum_min_duration = 10min # 记录autovacuum活动
log_checkpoints = on # 记录检查点信息
log_connections = on # 记录连接信息
log_line_prefix = '%m [user:%u] [database:%d] [application:%a] [host:%r] [pid:%p] [queryid:%Q] [tid:%x] [SQLtate:%e] '
log_lock_waits = on # 记录锁等待信息
log_statement = 'ddl' # 记录DDL语句
log_temp_files = 0 # 记录临时文件信息
log_timezone = 'Asia/Shanghai' # 日志时区
track_io_timing = on # 跟踪IO时间
autovacuum_vacuum_threshold = 1000 # 自动清理阈值
autovacuum_vacuum_insert_threshold = 1000 # 插入操作自动清理阈值
autovacuum_analyze_threshold = 1000 # 自动分析阈值
autovacuum_vacuum_scale_factor = 0.02 # 自动清理比例因子
autovacuum_vacuum_insert_scale_factor = 0.02 # 插入操作自动清理比例因子
autovacuum_analyze_scale_factor = 0.01 # 自动分析比例因子
datestyle = 'iso, mdy' # 日期格式
timezone = 'Asia/Shanghai' # 数据库时区
lc_messages = 'en_US.UTF-8' # 系统错误消息语言环境
lc_monetary = 'en_US.UTF-8' # 货币格式语言环境
lc_numeric = 'en_US.UTF-8' # 数字格式语言环境
lc_time = 'en_US.UTF-8' # 时间格式语言环境
default_text_search_config = 'pg_catalog.english'
5.6 创建初始用户
注意事项:
- 初始用户为集群高可用功能用户,不可修改密码。
- 业务用户需使用其他用户名。
启动PostgreSQL并创建初始用户:
pg_ctl start
psql
执行以下SQL语句:
CREATE USER replicator WITH REPLICATION PASSWORD 'Leven@@';
ALTER USER postgres PASSWORD 'Leven528625@';
停止PostgreSQL服务:
pg_ctl stop
5.7 启动etcd服务
启动etcd集群
在所有节点上启动etcd服务:
systemctl start etcd
检查etcd集群状态
选择任一节点,使用版本3访问etcd集群:
export ETCDCTL_API=3
etcdctl member list --write-out=table
输出示例:
+------------------+---------+--------+------------------------+------------------------+
| ID | STATUS | NAME | PEER ADDRS | CLIENT ADDRS |
+------------------+---------+--------+------------------------+------------------------+
| 399c570414ca40e7 | started | etcd03 | http://10.24.57.12:2380 | http://10.24.57.12:2379 |
| 5d50533ae476fa9c | started | etcd05 | http://10.24.57.14:2380 | http://10.24.57.14:2379 |
| 9260cfdb7100411a | started | etcd02 | http://10.24.57.11:2380 | http://10.24.57.11:2379 |
| d11825e0fdf39ac4 | started | etcd01 | http://10.24.57.10:2380 | http://10.24.57.10:2379 |
| e5390a5792c85baa | started | etcd04 | http://10.24.57.13:2380 | http://10.24.57.13:2379 |
+------------------+---------+--------+------------------------+------------------------+
检查etcd集群健康状态:
export ENDPOINTS=10.24.57.10:2379,10.24.57.11:2379,10.24.57.12:2379,10.24.57.13:2379,10.24.57.14:2379
etcdctl --write-out=table --endpoints=$ENDPOINTS endpoint status
输出示例:
+-----------------+------------------+---------+---------+-----------+-----------+------------+
| ENDPOINT | ID | VERSION | DB SIZE | IS LEADER | RAFT TERM | RAFT INDEX |
+-----------------+------------------+---------+---------+-----------+-----------+------------+
| 10.24.57.10:2379 | d11825e0fdf39ac4 | 3.3.25 | 20 kB | false | 2 | 18 |
| 10.24.57.11:2379 | 9260cfdb7100411a | 3.3.25 | 20 kB | false | 2 | 18 |
| 10.24.57.12:2379 | 399c570414ca40e7 | 3.3.25 | 20 kB | true | 2 | 18 |
| 10.24.57.13:2379 | e5390a5792c85baa | 3.3.25 | 20 kB | false | 2 | 18 |
| 10.24.57.14:2379 | 5d50533ae476fa9c | 3.3.25 | 20 kB | false | 2 | 18 |
+-----------------+------------------+---------+---------+-----------+-----------+------------+
检查etcd集群健康状态:
etcdctl --write-out=table --endpoints=$ENDPOINTS endpoint health
输出示例:
+-----------------+--------+------------+-------+
| ENDPOINT | HEALTH | TOOK | ERROR |
+-----------------+--------+------------+-------+
| 10.24.57.12:2379 | true | 1.979749ms | |
| 10.24.57.10:2379 | true | 2.187282ms | |
| 10.24.57.13:2379 | true | 1.988338ms | |
| 10.24.57.11:2379 | true | 2.013949ms | |
| 10.24.57.14:2379 | true | 2.143365ms | |
+-----------------+--------+------------+-------+
5.8 Patroni服务启动
在PostgreSQL高可用集群中,Patroni
负责管理PostgreSQL数据库服务的生命周期。一般情况下,不使用pg_ctl
直接操作PostgreSQL服务,而是通过启动或停止Patroni
服务来间接控制数据库服务的启停。
Patroni服务启动原则
- 集群初始化阶段:
- 节点应按顺序启动,一个节点启动成功后再启动其他节点。
- 启动顺序:
primary
->sync standby
->replica
- 停止顺序:
replica
->sync standby
->primary
Patroni服务管理命令
启动Patroni服务
systemctl start patroni
检查Patroni服务状态
systemctl status patroni
输出示例:
● patroni.service - Runners to orchestrate a high-availability PostgreSQL
Loaded: loaded (/etc/systemd/system/patroni.service; enabled; vendor preset: disabled)
Active: active (running) since Thu 2024-09-19 12:38:39 CST; 1min ago
Main PID: 12345 (patroni)
Tasks: 5 (limit: 4915)
Memory: 30.0M
CPU: 3.5s
CGroup: /system.slice/patroni.service
├─12345 /usr/bin/python3 /usr/local/bin/patroni /etc/patroni.yml
└─12346 postgres -D /var/lib/pgsql/13/data --config-file=/var/lib/pgsql/13/data/postgresql.conf --listen_addresses=*
停止Patroni服务
systemctl stop patroni
Patroni端口访问测试
在启动Patroni服务后,可以通过以下命令测试节点的master
和replica
角色是否正常工作。
测试Replica角色
curl http://10.24.57.11:8008/replica -I
输出示例(HTTP状态码200表示成功):
HTTP/1.0 200 OK
Content-Type: text/html; charset=UTF-8
Content-Length: 0
Date: Thu, 24 Apr 2025 16:09:00 GMT
测试Master角色
curl http://10.24.57.11:8008/master -I
输出示例(HTTP状态码200表示成功):
HTTP/1.0 200 OK
Content-Type: text/html; charset=UTF-8
Content-Length: 0
Date: Thu, 24 Apr 2025 16:09:00 GMT
注意事项:
- 如果返回的状态码不是
200
,请检查Patroni服务日志以排查问题:journalctl -u patroni
6 集群管理
在PostgreSQL高可用集群中,Patroni
提供了丰富的集群管理功能。通过patronictl
命令,可以实现以下功能:
- 检查集群状态
- 集群部分节点启动、停止
- 修改集群参数配置
- 集群主节点切换
注意事项:
- 所有操作需以
postgres
用户执行。patronictl
命令依赖配置文件(如/etc/patroni/pg.yml
)。
6.1 检查集群状态
使用以下命令查看集群状态:
patronictl -c /etc/patroni/pg.yml list
输出示例:
+ Cluster: PGCluster (7415171211622209103) ------+----+-----------+
| Member | Host | Role | State | TL | Lag in MB |
+--------+------------+--------------+-----------+----+-----------+
| pg01 | 10.24.57.20 | Leader | running | 4 | |
| pg02 | 10.24.57.21 | Sync Standby | streaming | 4 | 0 |
| pg03 | 10.24.57.22 | Replica | streaming | 4 | 0 |
+--------+------------+--------------+-----------+----+-----------+
说明:
Role
字段显示节点角色(Leader、Sync Standby、Replica)。State
字段显示节点状态(running、streaming等)。Lag in MB
字段显示从节点与主节点之间的延迟。
6.2 主备切换
Patroni
支持手动切换主库。一般情况下,建议指定Sync Standby
节点提升为主库。
切换步骤
执行以下命令进行主备切换:
patronictl -c /etc/patroni/pg.yml switchover
交互式提示示例:
Current cluster topology
+ Cluster: PGCluster (7415116788883109348) ------+----+-----------+-----------------+-------------------------------------+
| Member | Host | Role | State | TL | Lag in MB | Pending restart | Pending restart reason |
+--------+------------+--------------+-----------+----+-----------+-----------------+-------------------------------------+
| pg01 | 10.24.57.10 | Replica | streaming | 3 | 0 | | |
| pg02 | 10.24.57.11 | Leader | running | 3 | | * | max_connections: 1000->3000 |
| | | | | | | | max_locks_per_transaction: 64->1024 |
| | | | | | | | max_prepared_transactions: 0->1024 |
| | | | | | | | wal_level: replica->logical |
| pg03 | 10.24.57.12 | Replica | streaming | 3 | 0 | | |
| pg04 | 10.24.57.13 | Sync Standby | streaming | 3 | 0 | | |
| pg05 | 10.24.57.14 | Replica | streaming | 3 | 0 | | |
+--------+------------+--------------+-----------+----+-----------+-----------------+-------------------------------------+
Primary [pg02]:
Candidate ['pg01', 'pg03', 'pg04', 'pg05'] []: pg04
When should the switchover take place (e.g. 2024-09-17T10:59 ) [now]:
Are you sure you want to switchover cluster PGCluster, demoting current leader pg02? [y/N]: y
切换成功后,输出如下:
2024-09-17 09:59:36.19760 Successfully switched over to "pg04"
+ Cluster: PGCluster (7415116788883109348) -+----+-----------+
| Member | Host | Role | State | TL | Lag in MB |
+--------+------------+---------+-----------+----+-----------+
| pg01 | 10.24.57.10 | Replica | streaming | 4 | 0 |
| pg02 | 10.24.57.11 | Replica | streaming | 4 | 0 |
| pg03 | 10.24.57.12 | Replica | streaming | 4 | 0 |
| pg04 | 10.24.57.13 | Leader | running | 4 | |
| pg05 | 10.24.57.14 | Replica | streaming | 4 | 0 |
+--------+------------+---------+-----------+----+-----------+
注意事项:
- 切换完成后,建议再次检查集群状态以确认切换成功。
6.3 修改集群配置
Patroni
支持通过edit-config
命令修改集群配置,包括Patroni
自身参数和数据库参数。
修改配置
执行以下命令进入配置编辑界面:
patronictl -c /etc/patroni/pg.yml edit-config
配置文件内容示例:
loop_wait: 10
master_start_timeout: 300
maximum_lag_on_failover: 1048576
postgresql:
parameters:
hot_standby: 'on'
listen_addresses: 0.0.0.0
max_connections: 3000
max_locks_per_transaction: 1024
max_prepared_transactions: 1024
max_replication_slots: '10'
max_wal_senders: '10'
max_worker_processes: '8'
port: 5432
track_commit_timestamp: 'off'
wal_keep_size: 10240MB
wal_level: logical
use_pg_rewind: true
use_slots: true
retry_timeout: 10
synchronous_mode: true
ttl: 30
编辑操作说明:
- 编辑界面类似于
vi
编辑器,保存并退出时输入:wq
,放弃修改时输入:q
。- 部分参数修改后需要重启数据库节点才能生效。
检查配置是否生效
执行以下命令检查配置是否生效:
patronictl -c /etc/patroni/pg.yml list
如果某些参数需要重启节点,会在Pending restart
列中显示相关信息。例如:
+ Cluster: PGCluster (7415116788883109348) ------+----+-----------+-----------------+-------------------------------------+
| Member | Host | Role | State | TL | Lag in MB | Pending restart | Pending restart reason |
+--------+------------+---------+-----------+----+-----------+-----------------+-------------------------------------+
| pg01 | 10.24.57.10 | Replica | streaming | 4 | 0 | * | max_connections: 1000->3000 |
| pg02 | 10.24.57.11 | Replica | streaming | 4 | 0 | * | max_wal_senders: 10->20 |
+--------+------------+---------+-----------+----+-----------+-----------------+-------------------------------------+
注意事项:
- 如果有节点需要重启,可以通过以下命令重启:
patronictl -c /etc/patroni/pg.yml restart <member_name>
6.4 重启集群部分节点
在某些场景下,可能需要重启集群中的部分节点(如Replica或Sync Standby)。Patroni
提供了便捷的命令来完成这一操作。
重启Replica节点
执行以下命令重启所有Replica
角色的节点:
patronictl -c /etc/patroni/pg.yml restart PGCluster -r replica --force
输出示例:
+ Cluster: PGCluster (7415116788883109348) ------+----+-----------+-----------------+-------------------------------------+
| Member | Host | Role | State | TL | Lag in MB | Pending restart | Pending restart reason |
+--------+------------+--------------+-----------+----+-----------+-----------------+-------------------------------------+
| pg01 | 10.24.57.10 | Replica | streaming | 3 | 0 | | |
| pg02 | 10.24.57.11 | Leader | running | 3 | | * | max_connections: 1000->3000 |
| pg03 | 10.24.57.12 | Replica | streaming | 3 | 0 | * | max_connections: 1000->3000 |
| pg04 | 10.24.57.13 | Sync Standby | streaming | 3 | 0 | * | max_connections: 1000->3000 |
| pg05 | 10.24.57.14 | Replica | streaming | 3 | 0 | * | max_connections: 1000->3000 |
+--------+------------+--------------+-----------+----+-----------+-----------------+-------------------------------------+
Success: restart on member pg03
Success: restart on member pg04
Success: restart on member pg05
Success: restart on member pg01
注意事项:
--force
选项会强制重启节点,请谨慎使用。- 如果节点有
Pending restart
标记,重启后配置才会生效。
6.5 故障切换
在PostgreSQL高可用集群中,当某个节点发生故障时,Patroni
会自动进行故障切换,确保服务的连续性。
6.5.1 Primary节点重启
查看当前集群状态
patronictl -c /etc/patroni/pg.yml list
输出示例:
+ Cluster: PGCluster (7415116788883109348) ------+----+-----------+
| Member | Host | Role | State | TL | Lag in MB |
+--------+------------+--------------+-----------+----+-----------+
| pg01 | 10.24.57.10 | Replica | streaming | 6 | 0 |
| pg02 | 10.24.57.11 | Leader | running | 6 | |
| pg03 | 10.24.57.12 | Replica | streaming | 6 | 0 |
| pg04 | 10.24.57.13 | Sync Standby | streaming | 6 | 0 |
| pg05 | 10.24.57.14 | Replica | streaming | 6 | 0 |
+--------+------------+--------------+-----------+----+-----------+
模拟Primary节点故障
对Leader
节点(如pg02
)执行重启操作:
reboot
再次查看集群状态:
patronictl -c /etc/patroni/pg.yml list
输出示例:
+ Cluster: PGCluster (7415116788883109348) ------+----+-----------+
| Member | Host | Role | State | TL | Lag in MB |
+--------+------------+--------------+-----------+----+-----------+
| pg01 | 10.24.57.10 | Replica | streaming | 7 | 0 |
| pg02 | 10.24.57.11 | Replica | streaming | 7 | 0 |
| pg03 | 10.24.57.12 | Sync Standby | streaming | 7 | 0 |
| pg04 | 10.24.57.13 | Leader | running | 7 | |
| pg05 | 10.24.57.14 | Replica | streaming | 7 | 0 |
+--------+------------+--------------+-----------+----+-----------+
说明:
- 原
Leader
节点pg02
降级为Replica
。- 新
Leader
节点为pg04
。
6.5.2 同步Standby节点重启
查看当前集群状态
patronictl -c /etc/patroni/pg.yml list
输出示例:
+ Cluster: PGCluster (7415116788883109348) ------+----+-----------+
| Member | Host | Role | State | TL | Lag in MB |
+--------+------------+--------------+-----------+----+-----------+
| pg01 | 10.24.57.10 | Replica | streaming | 7 | 0 |
| pg02 | 10.24.57.11 | Replica | streaming | 7 | 0 |
| pg03 | 10.24.57.12 | Sync Standby | streaming | 7 | 0 |
| pg04 | 10.24.57.13 | Leader | running | 7 | |
| pg05 | 10.24.57.14 | Replica | streaming | 7 | 0 |
+--------+------------+--------------+-----------+----+-----------+
模拟Sync Standby节点故障
对Sync Standby
节点(如pg03
)执行重启操作:
reboot
再次查看集群状态:
patronictl -c /etc/patroni/pg.yml list
输出示例:
+ Cluster: PGCluster (7415116788883109348) ------+----+-----------+
| Member | Host | Role | State | TL | Lag in MB |
+--------+------------+--------------+-----------+----+-----------+
| pg01 | 10.24.57.10 | Sync Standby | streaming | 7 | 0 |
| pg02 | 10.24.57.11 | Replica | streaming | 7 | 0 |
| pg03 | 10.24.57.12 | Replica | streaming | 7 | 0 |
| pg04 | 10.24.57.13 | Leader | running | 7 | |
| pg05 | 10.24.57.14 | Replica | streaming | 7 | 0 |
+--------+------------+--------------+-----------+----+-----------+
说明:
- 原
Sync Standby
节点pg03
降级为普通Replica
。- 新
Sync Standby
节点为pg01
。
6.6 重新加载集群参数
当修改了集群配置后,可以通过reload
命令让所有节点重新加载配置。
重新加载集群配置
执行以下命令重新加载配置:
patronictl -c /etc/patroni/pg.yml reload PGCluster
交互式提示示例:
+ Cluster: PGCluster (7377658010534254086) ----+-----------+
| Member | Host | Role | State | TL | Lag in MB |
+--------+------------+---------+---------+----+-----------+
| pg01 | 10.24.57.20 | Leader | running | 2 | |
| pg02 | 10.24.57.21 | Replica | running | 2 | 0 |
| pg03 | 10.24.57.22 | Replica | running | 2 | 0 |
+--------+------------+---------+---------+----+-----------+
Are you sure you want to reload members pg01, pg02, pg03? [y/N]: y
Reload request received for member pg01 and will be processed within 10 seconds
Reload request received for member pg02 and will be processed within 10 seconds
Reload request received for member pg03 and will be processed within 10 seconds
说明:
reload
操作不会中断数据库服务。- 部分参数可能仍需重启节点才能生效。
6.7 清理集群元数据
在某些特殊场景下(如重建集群或恢复不同数据库ID的集群),需要清理etcd
中存储的集群元数据。
清理步骤
- 查看
etcd
中存储的集群信息:
etcdctl ls /
输出示例:
/pgsql
- 删除
pgsql
目录下的所有信息:
etcdctl rm -r /pgsql
- 再次确认是否删除成功:
etcdctl ls /
注意事项:
- 清理元数据会导致集群信息丢失,请确保已备份重要数据。
- 清理完成后,可以重新初始化集群(如执行
initdb
操作)。