MySQL 高可用实战:PXC + HAProxy + Keepalived 完整版笔记

一、PXC 基础讲解

1. 什么是 PXC

PXC(Percona XtraDB Cluster)是基于 Galera 库 实现的 MySQL 多主同步高可用集群 。核心特点:强一致性、实时同步、任意节点可写、事务全局原子提交

官方文档:

2. PXC 特点

  • 完全兼容 MySQL
  • 同步复制,事务要么所有节点提交,要么全部不提交
  • 多主架构,任意节点都可写入
  • 并行复制,真正实时同步
  • 自动节点克隆、自动补数据
  • 故障切换简单

3. PXC 优点

  • 服务高可用
  • 数据几乎无延迟同步
  • 多节点同时读写,可扩展写
  • 自动部署新节点
  • 数据强一致,适合电商
  • 完全兼容 MySQL

4. PXC 缺点

  • 只支持 InnoDB
  • 写入效率取决于最慢节点
  • 所有表必须有主键
  • 不支持 LOCK TABLE
  • 锁冲突、死锁更多
  • 节点越多,同步越慢

5. PXC 常用端口

  • 3306:MySQL 服务
  • 4444:SST 全量同步
  • 4567:集群通信
  • 4568:IST 增量同步

二、环境规划

角色 主机名 IP 地址
PXC 节点 1 pxc1 192.168.24.140
PXC 节点 2 pxc2 192.168.24.141
PXC 节点 3 pxc3 192.168.24.142
HAProxy 主,keepalived lb01 192.168.24.143
HAProxy 备,keepalived lb02 192.168.24.144
浮动 VIP --- 192.168.24.145

三、3 节点 PXC 集群搭建

1. 所有节点配置 hosts 解析(不然配置一台dns)

复制代码
cat >> /etc/hosts <<EOF
192.168.24.140 pxc1
192.168.24.141 pxc2
192.168.24.142 pxc3
192.168.24.143 lb01
192.168.24.144 lb02
EOF

解释

  • cat >>:向文件末尾追加内容
  • /etc/hosts:系统主机名映射文件
  • 作用:让所有机器用主机名互相访问,无需依赖 DNS

2. 所有节点卸载 mariadb(避免冲突,作为失败参考点)

复制代码
yum -y remove mari*

解释

  • 系统自带 mariadb 与 PXC 冲突,卸载干净

3. 安装 PXC(所有节点)

离线安装

上传 rpm 包后执行:

复制代码
yum localinstall *.rpm -y

解释

正常下载:

复制代码
下载仓库后启动源下载
yum install -y https://repo.percona.com/yum/percona-release-latest.noarch.rpm
percona-release setup pxc-84-lts
yum install percona-xtradb-cluster

4. 启动 MySQL 并获取临时密码

复制代码
systemctl start mysqld

解释:启动 MySQL 服务

复制代码
tmp_pass=$(awk '/temporary password/ {print $NF}' /var/log/mysqld.log)

也可以:
[root@pxc1 ~]# cat /var/log/mysqld.log | grep -i 'temporary password'
2026-04-13T09:44:10.472868Z 6 [Note] [MY-010454] [Server] A temporary password is generated for root@localhost: n2;5tF+ah3cg

解释

  • 从 MySQL 日志提取临时 root 密码

  • $NF 表示取每行最后一列

    mysql -uroot -p${tmp_pass}

解释:用临时密码登录数据库

5. 修改密码并创建远程账号(MySQL 内执行,3台都要,这个时候还没有同步)

复制代码
ALTER USER 'root'@'localhost' IDENTIFIED BY 'MySQL@123';

解释:修改本地 root 密码,一般第一次以临时密码登录都必须改一次密码

复制代码
CREATE USER 'admin'@'%' IDENTIFIED WITH caching_sha2_password BY 'Abc_123456';
GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, ALTER, DROP, INDEX ON *.* TO 'admin'@'%';
FLUSH PRIVILEGES;

解释

  • 创建远程账号 admin
  • % 允许任意 IP 连接
  • 授予相对应权限,供集群与 HAProxy 使用

6. 停止 MySQL,准备配置集群

复制代码
systemctl stop mysqld

7. 生成并分发 SSL 证书(pxc1 执行)

没有openssl要先下载

复制代码
dnf install -y openssl

openssl req -newkey rsa:2048 -nodes -keyout /etc/server-key.pem -x509 -days 365 -out /etc/server-cert.pem

1. openssl
作用:开源安全工具包,用于生成证书、加密、解密
必须先安装:dnf install -y openssl
2. req
作用:请求证书(request)
表示我们要生成一个证书请求 / 自签名证书
3. -newkey rsa:2048
-newkey:生成新的密钥对
rsa:2048:使用 RSA 2048 位 加密算法(目前最安全、最通用)
4. -nodes
作用:私钥不加密,不需要密码
如果不加,启动 PXC 时每次都要输证书密码,集群无法自动启动
5. -keyout /etc/server-key.pem
-keyout:把私钥输出到哪个文件
/etc/server-key.pem:私钥保存路径
6. -x509
作用:生成自签名证书(不需要第三方 CA 认证)
我们自己给自己签发证书,内网 / 测试 / 生产都能用
7. -days 365
作用:证书有效期 365 天
过期后需要重新生成
8. -out /etc/server-cert.pem
-out:把公钥证书输出到哪个文件
/etc/server-cert.pem:证书保存路径

执行后会出现什么?
执行命令后会让你输入:
Country Name (2 letter code) [XX]:
State or Province Name (full name) []:
Locality Name (eg, city) [Default City]:
Organization Name (eg, company) [Default Company Ltd]:
Organizational Unit Name (eg, section) []:
Common Name (eg, your name or your server's hostname) []:
Email Address []:
✔ 正确做法:一路回车即可!
这些信息不影响 PXC 使用,不需要认真填写。

解释:生成 PXC 集群加密通信证书

复制代码
scp /etc/server-* pxc2:/etc/
scp /etc/server-* pxc3:/etc/

解释:把证书分发到所有节点,保证加密一致

8. 配置 /etc/my.cnf(所有节点)

pxc1 完整配置

复制代码
# Template my.cnf for PXC
# Edit to your requirements.

[client]
socket=/var/lib/mysql/mysql.sock

[mysqld]
server-id=140     #这里id不要一样的就行,我是按照ip改的
datadir=/var/lib/mysql
socket=/var/lib/mysql/mysql.sock
log-error=/var/log/mysqld.log
pid-file=/var/run/mysqld/mysqld.pid

# Binary log expiration period is 604800 seconds, which equals 7 days
binlog_expire_logs_seconds=604800

######## wsrep ###############
# Path to Galera library
wsrep_provider=/usr/lib64/galera4/libgalera_smm.so

# Cluster connection URL contains IPs of nodes
#If no IP is found, this implies that a new cluster needs to be created,
#in order to do that you need to bootstrap this node
wsrep_cluster_address=gcomm://  # 【已修改】替换为下方集群IP列表,本行保留注释

# In order for Galera to work correctly binlog format should be ROW
binlog_format=ROW

# Slave thread to use
wsrep_slave_threads=8

wsrep_log_conflicts

# This changes how InnoDB autoincrement locks are managed and is a requirement for Galera
innodb_autoinc_lock_mode=2

# Node IP address
#wsrep_node_address=192.168.70.63  

# Cluster name
wsrep_cluster_name=pxc-cluster

#If wsrep_node_name is not specified,  then system hostname will be used
wsrep_node_name=pxc-cluster-node-1  

#pxc_strict_mode allowed values: DISABLED,PERMISSIVE,ENFORCING,MASTER
pxc_strict_mode=ENFORCING

# SST method
wsrep_sst_method=xtrabackup-v2

# ===================== 以下为【新增/修改】内容 =====================
# 集群所有节点IP(必须写3个节点)
wsrep_cluster_address=gcomm://192.168.24.140,192.168.24.141,192.168.24.142  # 【新增】集群地址

wsrep_node_name=pxc1  # 【新增】当前节点名称(覆盖原有)
wsrep_node_address=192.168.24.140  # 【新增】当前节点IP

wsrep_applier_threads=8  # 【新增】同步线程数

# 【新增】SSL 加密通信(集群节点安全认证)
wsrep_provider_options="socket.ssl_key=/etc/server-key.pem;socket.ssl_cert=/etc/server-cert.pem"

# ===================== 【SST 全量同步加密】 =====================
[sst]
encrypt=4  # 【新增】开启SSL加密传输
ssl-key=/etc/server-key.pem  # 【新增】私钥
ssl-cert=/etc/server-cert.pem  # 【新增】证书

逐行解释

  • server-id:MySQL 唯一 ID,不能重复
  • wsrep_cluster_name:集群名称,所有节点必须相同
  • wsrep_cluster_address:集群所有节点地址
  • wsrep_node_name:本节点主机名
  • wsrep_node_address:本节点 IP
  • pxc_strict_mode=ENFORCING:PXC 严格模式
  • innodb_autoinc_lock_mode=2:集群强制要求
  • wsrep_sst_method=xtrabackup-v2:全量同步方式

pxc2 修改或添加

复制代码
server-id=141
wsrep_node_name=pxc2
wsrep_node_address=192.168.24.141
wsrep_cluster_address=gcomm://192.168.24.140
wsrep_provider_options="socket.ssl_key=/etc/server-key.pem;socket.ssl_cert=/etc/server-cert.pem"

[sst]
encrypt=4
ssl-key=/etc/server-key.pem
ssl-cert=/etc/server-cert.pem

pxc3修改或者添加

复制代码
server-id=142
wsrep_node_name=pxc3
wsrep_node_address=192.168.24.142
wsrep_cluster_address=gcomm://192.168.24.140
wsrep_provider_options="socket.ssl_key=/etc/server-key.pem;socket.ssl_cert=/etc/server-cert.pem"

[sst]
encrypt=4
ssl-key=/etc/server-key.pem
ssl-cert=/etc/server-cert.pem

9. 启动 PXC 集群(顺序绝对不能错)

pxc1 引导启动(第一个节点)

复制代码
systemctl start mysql@bootstrap.service

mysql@bootstrap.service
这是 PXC 专属的特殊服务单元,不是普通 MySQL!
mysql:PXC 数据库服务名
@:systemd 模板服务标记
bootstrap:引导模式 / 集群初始化模式
.service:服务文件后缀

这条命令到底做了什么?
以 "集群初始化模式" 启动 MySQL
创建全新的 PXC 集群
生成集群 UUID
打开节点接收其他机器加入
不依赖任何其他节点,自己成为集群第一个节点,其他节点不能用

解释:以引导模式启动,初始化集群

出现启动失败

复制代码
[root@pxc1 ~]# systemctl start mysql@bootstrap.service
Job for mysql@bootstrap.service failed because the control process exited with error code.
See "systemctl status mysql@bootstrap.service" and "journalctl -xeu mysql@bootstrap.service" for details.

解决方法
systemctl stop mysqld
systemctl stop mysql@bootstrap.service
pkill -9 mysqld
rm -rf /var/lib/mysql/grastate.dat
rm -rf /var/lib/mysql/gvwstate.datPXC 
规定:一个节点一旦加入过集群,就不允许再创建集群!
里面记录了:
我属于哪个集群
我的 seqno(同步位置)
最重要:safe_to_bootstrap(是否允许重新创建集群)

rm -rf /var/lib/mysql/*.pid
rm -rf /var/lib/mysql/*.lock
作用:清理残留标记,避免启动报错。

pxc2、pxc3 正常启动

复制代码
systemctl start mysql
systemctl enable mysql

10. PXC 集群完整验证

验证 1:查看集群节点数

复制代码
mysql -uroot -p'MySQL@123' -e "show status like 'wsrep_cluster_size';"

预期结果wsrep_cluster_size = 3

验证 2:查看关键状态汇总

复制代码
mysql -uroot -p'MySQL@123' -e "show status where Variable_name in ('wsrep_cluster_size','wsrep_cluster_status','wsrep_connected','wsrep_ready');"

预期:全部为 ON / Primary

验证 3:查看节点同步视图

复制代码
select * from performance_schema.pxc_cluster_view;

预期:所有节点 STATUS 为 SYNCED

验证 4:跨节点数据同步测试(文档标准验证)

  1. pxc2 创建库

    CREATE DATABASE percona;

  2. pxc3 创建表

    CREATE TABLE percona.example (node_id INT PRIMARY KEY, node_name VARCHAR(30));

  3. pxc1 插入数据

    INSERT INTO percona.example VALUES (1,'percona1');

  4. pxc2 查询

    SELECT * FROM percona.example;

预期:能查到数据,证明同步正常


四、HAProxy 负载均衡搭建

官方文档:https://docs.percona.com/percona-xtradb-cluster/8.4/haproxy.htmlhttps://docs.percona.com/percona-xtradb-cluster/8.4/haproxy.html

1. 安装 HAProxy(lb01、lb02 都执行)

复制代码
dnf install haproxy -y

2. 配置 /etc/haproxy/haproxy.cfg

复制代码
#---------------------------------------------------------------------
# Example configuration for a possible web application.  See the
# full configuration options online.
#
#   https://www.haproxy.org/download/1.8/doc/configuration.txt
#
#---------------------------------------------------------------------

#---------------------------------------------------------------------
# Global settings
#---------------------------------------------------------------------
global
    # 日志配置:输出到本地syslog
    log         127.0.0.1 local2

    # 运行路径、进程ID
    chroot      /var/lib/haproxy
    pidfile     /var/run/haproxy.pid

    # 最大连接数(调高支持更高并发)
    maxconn     4096

    # 运行用户和用户组
    user        haproxy
    group       haproxy

    # 后台守护进程模式运行
    daemon

    # 统计socket(用于管理)
    stats socket /var/lib/haproxy/stats

    # 系统加密策略
    ssl-default-bind-ciphers PROFILE=SYSTEM
    ssl-default-server-ciphers PROFILE=SYSTEM

#---------------------------------------------------------------------
# common defaults that all the 'listen' and 'backend' sections will
# use if not designated in their block
#---------------------------------------------------------------------
defaults
    # 日志继承全局配置
    log                     global

    # 【重要】MySQL 必须使用 TCP 模式(不能用HTTP)
    mode                    tcp

    # 记录TCP日志
    option                  tcplog

    # 不记录空连接日志
    option                  dontlognull

    # 连接失败重试3次
    retries                 3

    # 各种超时时间(保证MySQL长连接稳定)
    timeout http-request    10s
    timeout queue           1m
    timeout connect         5000
    timeout client          50000
    timeout server          50000
    timeout http-keep-alive 10s
    timeout check           10s

    # 单进程最大连接数
    maxconn                 3000

#---------------------------------------------------------------------
# HAProxy 监控页面(网页查看状态)
# 访问:http://LB_IP:8088/haproxy/stats
# 账号:admin   密码:admin
#---------------------------------------------------------------------
frontend stats-front
    bind *:8088
    mode http
    default_backend stats-back

backend stats-back
    mode http
    # 监控页面URL
    stats uri /haproxy/stats
    # 监控页面账号密码
    stats auth admin:admin

#---------------------------------------------------------------------
# MySQL-PXC 负载均衡入口
# 监听 3306 端口,应用通过此端口连接数据库
#---------------------------------------------------------------------
frontend pxc-front
    bind *:3306
    mode tcp
    default_backend pxc-cluster

#---------------------------------------------------------------------
# PXC 集群后端节点配置
# 负载策略:leastconn(优先给连接少的节点分发)
# 健康检查:使用 9200 端口(PXC 集群状态检查端口)
#---------------------------------------------------------------------
backend pxc-cluster
    mode tcp
    balance leastconn

    # PXC 节点1  健康检查端口9200
    server pxc1 192.168.24.140:3306 check port 9200 inter 12000 rise 3 fall 3

    # PXC 节点2
    server pxc2 192.168.24.141:3306 check port 9200 inter 12000 rise 3 fall 3

    # PXC 节点3
    server pxc3 192.168.24.142:3306 check port 9200 inter 12000 rise 3 fall 3

#---------------------------------------------------------------------
# 原来的 Web 配置(已保留,不影响PXC)
#---------------------------------------------------------------------
# main frontend which proxys to the backends
frontend main
    bind *:5000
    acl url_static       path_beg       -i /static /images /javascript /stylesheets
    acl url_static       path_end       -i .jpg .gif .png .css .js

    use_backend static          if url_static
    default_backend             app

# static backend for serving up images, stylesheets and such
backend static
    balance     roundrobin
    server      static 127.0.0.1:4331 check

# round robin balancing between the various backends
backend app
    balance     roundrobin
    server  app1 127.0.0.1:5001 check
    server  app2 127.0.0.1:5002 check
    server  app3 127.0.0.1:5003 check
    server  app4 127.0.0.1:5004 check


检查语法
haproxy -c -f /etc/haproxy/hapro.cfg
-c check -f file

关键解释

  • mode tcp:MySQL 必须用 TCP 模式
  • balance leastconn:最少连接调度,数据库最稳定
  • check port 9200:健康检查端口
  • 8088:HAProxy 监控页面

3. 配置 PXC 健康检查(所有 PXC 节点),xinted

注意:rhel10、rocky10没办法用xinetd

复制代码
echo 'mysqlchk 9200/tcp' >> /etc/services
dnf install -y xinetd
systemctl enable --now xinetd

给 9200 端口起一个服务名字叫 mysqlchk,写入系统端口配置文件 /etc/services
作用:
让系统认识 9200 端口 = MySQL 集群健康检查
HAProxy 就是靠 9200 端口 检查 PXC 节点是否正常
不配置这行,HAProxy 不知道检查什么端口

安装 xinetd 超级服务(一个用来管理其他小服务的监听服务)
作用:
PXC 的 9200 健康检查服务 必须依靠 xinetd 才能启动
xinetd 会监听 9200 端口,用来回答 HAProxy 的检查请求
没有 xinetd,9200 端口不会开启

理解:9200 只是个健康检查脚本,不是独立服务,靠 xinetd 帮它监听端口。

第二种方法:

3.所有 PXC 节点都要执行(pxc1、pxc2、pxc3),systemd

1. 创建健康检查脚本(真正检查 PXC 状态)

复制代码
# 创建脚本文件,并将以下内容写入 /usr/local/bin/pxc_check.sh
cat > /usr/local/bin/pxc_check.sh <<'EOF'
#!/bin/bash

# ===================== 检查1:MySQL 进程是否存在 =====================
# pgrep mysqld  = 查找系统中是否有 mysqld 进程
# if ! ...     = 如果找不到进程(条件不成立),执行下面内容
if ! pgrep mysqld > /dev/null; then
    # 返回 HTTP 503 状态码,表示服务不可用
    echo "HTTP/1.1 503 Service Unavailable\r\n"
    # 退出脚本,返回错误码 1(异常)
    exit 1
fi

# ===================== 检查2:PXC 集群是否准备就绪 =====================
# 执行 MySQL 命令,查看 wsrep_ready 状态(只返回值,不要表头)
#-N = 去掉表头(列名)
STATUS=$(mysql -N -e "SHOW STATUS LIKE 'wsrep_ready';" | awk '{print $2}')

# 如果状态不是 ON,说明 PXC 集群未准备好,不能提供服务
if [ "$STATUS" != "ON" ]; then
    echo "HTTP/1.1 503 Service Unavailable\r\n"
    exit 1
fi

# ===================== 检查3:PXC 集群是否处于正常主状态 =====================
# 查看集群状态,确保没有脑裂、没有分区
CLUSTER_STATUS=$(mysql -N -e "SHOW STATUS LIKE 'wsrep_cluster_status';" | awk '{print $2}')

# 如果不是 Primary,表示集群异常(可能脑裂/分区)
if [ "$CLUSTER_STATUS" != "Primary" ]; then
    echo "HTTP/1.1 503 Service Unavailable\r\n"
    exit 1
fi

# ===================== 所有检查都通过 =====================
# 返回 HTTP 200,表示节点健康
echo "HTTP/1.1 200 OK\r\n"
# 退出脚本,返回 0(正常)
exit 0
EOF

只有 Primary 状态,PXC 节点才能正常读写。

不是 Primary → 节点已经脱离集群、脑裂、不可用 → 必须踢出业务流量!

2. 给执行权限

复制代码
chmod +x /usr/local/bin/pxc_check.sh
chown mysql:mysql /usr/local/bin/pxc_check.sh

3. 创建 systemd 监听服务(替代 xinetd!)

复制代码
# 创建 systemd socket 配置文件,作用:监听 9200 端口
cat > /etc/systemd/system/pxc_check.socket <<'EOF'
[Unit]
# 描述信息:随便写,方便自己看懂
Description=PXC Health Check Socket

[Socket]
# 核心配置:监听 9200 端口(TCP)
# 相当于 xinetd 里的 port = 9200
ListenStream=9200

# 允许外部连接进来(必须写 yes)
# 有人访问 9200 就触发脚本
Accept=yes

[Install]
# 开机启动相关:让这个端口监听跟着系统启动
WantedBy=sockets.target
EOF

# 创建 systemd 服务配置文件(@ 代表:由 socket 触发启动)
cat > /etc/systemd/system/pxc_check@.service <<'EOF'
[Unit]
# 服务描述(给人看的,随便写)
Description=PXC Health Check Service

[Service]
# ================= 核心:启动脚本 =================
# 有人访问 9200 端口时,执行这个健康检查脚本
ExecStart=/usr/local/bin/pxc_check.sh

# ================= 必须项:和 socket 对接 =================
# 告诉 systemd:这个服务的输入来自 socket(端口连接)
StandardInput=socket

# ================= 安全项:以什么用户运行 =================
# 使用 mysql 用户启动脚本(最小权限,更安全)
User=mysql
# 使用 mysql 组
Group=mysql
EOF

4. 启动监听(9200 端口!)

复制代码
systemctl daemon-reload
systemctl enable --now pxc_check.socket

5. 防火墙放行 9200

复制代码
firewall-cmd --permanent --add-port=9200/tcp
firewall-cmd --reload

MySQL 内创建检查用户

pxc1,pxc2,pxc3执行(如果pxc架构还在只需pxc1执行就行)

复制代码
CREATE USER 'clustercheckuser'@'localhost' IDENTIFIED BY 'clustercheckpassword!';
GRANT PROCESS ON *.* TO 'clustercheckuser'@'localhost';
FLUSH PRIVILEGES;

4. 启动 HAProxy

复制代码
systemctl start haproxy
systemctl enable haproxy

启动不了:
1.防火墙或者selinux
[root@lb02 yum.repos.d]# setsebool -P haproxy_connect_any 1 处理selinux
2.访问端口被占用
3.配置文件错误

5. HAProxy 验证

复制代码
curl -I 192.168.24.140:9200
[root@lb01 ~]# curl -I 192.168.24.140:9200
HTTP/1.1 200 OK\r\n
curl: (56) Recv failure: Connection reset by peer
第二行不影响,说明脚本正常退出
主要是因为\r\n的问题
脚本echo加-e参数就行
[root@lb01 ~]# curl -I 192.168.24.140:9200
HTTP/1.1 200 OK

[root@lb01 ~]# 


不通,经常是防火墙原因
pxc1,2,3执行
1. 放行 3306(MySQL)和 9200(健康检查)
firewall-cmd --permanent --add-port=3306/tcp
firewall-cmd --permanent --add-port=9200/tcp
firewall-cmd --reload
2. 确认放行成功
firewall-cmd --list-ports
应该看到:
3306/tcp 9200/tcp
3. 再确保健康检查服务在运行(lb执行)
systemctl daemon-reload
systemctl enable --now pxc_check.socket
systemctl status pxc_check.socket
4. 回到 lb01 测试连通性
curl -I 192.168.24.140:9200
curl -I 192.168.24.141:9200
curl -I 192.168.24.142:9200
能返回 200 或 503 就说明通了,HAProxy 马上变 UP。

预期:HTTP/1.1 200 OK

浏览器访问监控:http://192.168.24.143:8088/haproxy/stats账号:admin密码:admin

访问网页不通就是8080端口没放行

复制代码
firewall-cmd --permanent --add-port=8080/tcp
firewall-cmd --reload

五、Keepalived 高可用搭建

1. 安装 Keepalived(lb01、lb02)

复制代码
dnf install keepalived -y

2. 主节点 lb01 配置

关键点待解决:

vrrp_strict在生产模式下是要开的,但是虚拟环境下可能会出现别的机器无法访问的问题,根据官方文档,优先级要255的才行,priority = 255(地址所有者),当vip在优先级为255的keepalived机器上时才能被ping通。

除非 strict_mode(即 vrrp_strict)被设置,相当于这个实例关闭严格模式。

复制代码
举例子
vrrp_instance VI_1 {
    state MASTER
    interface eth0
    virtual_router_id 51
    priority 100      # 不用 255!
    advert_int 1

    strict_mode off   # 关键:关闭当前实例的严格模式
    accept            # 关键:允许响应 VIP(ping 能通)

    virtual_ipaddress {
        192.168.1.100/24
    }
}

注意:单独写strict_mode off 也不行,加accept这样就能够正常被访问了

复制代码
可能会出现脑裂问题
只需要在两台 LB 都执行这一条命令:放通 VRRP 协议
firewall-cmd --add-protocol=vrrp --permanent
firewall-cmd --reload

或者 iptables 模式:
iptables -A INPUT -p vrrp -j ACCEPT

总体配置:

复制代码
! 全局配置区(必须保留,精简无用邮件功能)
global_defs {
   ! 关闭邮件通知(生产环境可自己开启)
   ! notification_email {
   !   acassen@firewall.loc
   ! }
   ! notification_email_from Alexandre.Cassen@firewall.loc
   ! smtp_server 192.168.200.1
   ! smtp_connect_timeout 30

   ! 路由器ID(唯一标识,随便写,不重复即可)
   router_id HAPROXY_LB

   ! VRRP 基础参数
   vrrp_skip_check_adv_addr
   vrrp_garp_interval 0
   vrrp_gna_interval 0
   #vrrp_strict
}

! ---------------------- 关键:HAProxy 健康检查脚本 ----------------------
! 作用:每隔2秒检查 haproxy 是否存活
! 如果挂了,自动降低优先级,让备机抢占VIP
vrrp_script chk_haproxy {
    script "/etc/keepalived/check_haproxy.sh"   ! 检查脚本路径
    interval 2                                  ! 每2秒检查一次
    weight -10                                  ! 检查失败:优先级-10
    rise 2
    fall 2
}

! ---------------------- VRRP 实例(核心) ----------------------
vrrp_instance VI_HAPROXY {
    ! 状态:MASTER / BACKUP
    ! 主LB写 MASTER
    ! 备LB写 BACKUP
    state BACKUP

    ! 网卡名称(你用的是 ens160,必须正确)
    interface ens160

    ! 虚拟路由ID(主备必须一样,同一集群唯一)
    virtual_router_id 51

    ! 优先级(主100,备90,数字越大越优先)
    priority 100

    ! 通告间隔(1秒心跳)
    advert_int 1

    ! 不抢占模式(主挂了恢复后,不抢回VIP,更稳定)
    nopreempt

    ! 认证密码(主备必须一样)
    authentication {
        auth_type PASS
        auth_pass 1111
    }

    ! 虚拟IP(VIP),你的 PXC 对外访问IP
    virtual_ipaddress {
        192.168.24.145
    }

    ! 绑定上面的检查脚本
    track_script {
        chk_haproxy
    }
}

! ---------------------- 以下全部删除!你是 HAProxy 不是 LVS!----------------------
! 你原来的 virtual_server 配置是 LVS 用的
! 我们现在用的是 HAProxy + Keepalived 模式
! 所以下面所有 virtual_server 配置 全部 删掉!
! ---------------------- 已清理 ----------------------

3. 备节点 lb02 配置(只改两行)

复制代码
state BACKUP
priority 90

4. 健康检查脚本

复制代码
vim /etc/keepalived/check_haproxy.sh

#!/bin/bash
stat=$(ps -C haproxy --no-header | wc -l)
#-C 按 命令名称(command name) 筛选 wc = word count    -l = line
if [ $stat -eq 0 ]; then
    systemctl start haproxy
    sleep 3
    if [ $(ps -C haproxy --no-header | wc -l) -eq 0 ]; then
        systemctl stop keepalived
    fi
fi

以上会重启,导致验证时ip不会漂移

#!/bin/bash
if pgrep haproxy >/dev/null; then
    exit 0
else
    exit 1
fi

chmod +x /etc/keepalived/check_haproxy.sh

5. 启动 Keepalived

复制代码
systemctl start keepalived
systemctl enable keepalived

六、整套架构最终完整验证

1. 使用 VIP 登录 MySQL(统一入口)

复制代码
mysql -uadmin -p'Abc_123456' -h 192.168.24.145 -P 3306

使用用户 admin,密码 Abc_123456
连接到 192.168.24.145 这台机器的 3306 端口(MySQL)
这个账号在一开始的时候创建,用来管理业务,'admin'@'%',有%相当与可以远程连接

流程:
你 → VIP(145) → HAProxy → PXC 集群

2. 查看集群状态

复制代码
show status like 'wsrep_cluster_size';

3. 查看 VIP 所在节点

复制代码
ip a

4. 高可用切换测试

  • 停掉主 lb01 的 haproxy
  • 查看 VIP 是否自动漂移到 lb02
  • 业务依然可用

七、全套官方网址(你文档里全部网址)

  1. PXC 官方文档:https://docs.percona.com/percona-xtradb-cluster/8.4/
  2. PXC 安装指南:https://docs.percona.com/percona-xtradb-cluster/8.4/yum.html
  3. PXC 下载地址:http://repo.percona.com/pxc-84-lts/yum/release/10/RPMS/x86_64/
  4. HAProxy 集成文档:https://docs.percona.com/percona-xtradb-cluster/8.4/haproxy.html
相关推荐
2301_764150562 小时前
Redis如何控制只读从库的安全_配置replica-read-only防止从节点数据被意外篡改
jvm·数据库·python
Once_day2 小时前
Linux之(31)Shell的set命令
linux·运维·bash
DaqunChen2 小时前
SQL如何检测分组内是否存在满足条件的数据_EXISTS结合分组
jvm·数据库·python
脑子加油站2 小时前
OpenEuler24.03 分布式配置redis 集群
数据库·redis·分布式·php·nginx代理
wanhengidc2 小时前
云手机能够实现哪些功能?
大数据·运维·安全·智能手机
2301_803538952 小时前
Bootstrap 5栅格系统的五列等分布局方案
jvm·数据库·python
Hello.Reader2 小时前
算法是什么
linux·运维·算法
cui_ruicheng2 小时前
Linux IO入门(二):重定向与缓冲区机制
linux·运维·服务器
粉嘟小飞妹儿2 小时前
如何用 error 事件全局捕获页面图片或脚本加载失败状态
jvm·数据库·python