部署zrlog-HAProxy-Keepalived双主双从
本文档详细记录了ZrLog博客系统的高可用部署方案,采用双主双从架构实现负载均衡与故障自动切换。主要内容包括:1)服务器架构说明,包含数据库服务器、应用服务器及HAProxy/Keepalived的IP分配;2)基础环境配置,涉及YUM源替换和依赖安装;3)MariaDB数据库部署流程;4)ZrLog应用服务器的完整部署步骤,涵盖JDK/Maven环境搭建、源码编译和Tomcat部署;5)HAPr
一、架构说明(兼容原双主双从)
| 角色 | IP | |
| 数据库服务器 | 192.168.223.22 | |
| 应用服务器1 | 192.168.223.21 | |
| 应用服务器2 | 192.168.223.24 | |
| HAProxy Master1 | 192.168.223.20 | |
| HAPRoxy Master2 | 192.168.223.23 | |
| VIP1 | 192.168.223.100 | |
| VIP2 | 192.168.223.101 |
二,基础环境配置
2.1 替换阿里云 YUM 源(替代本地光盘,更通用)

2.2 安装基础依赖(所有机器)

三、部署 MariaDB(192.168.223.22)
3.1安装MariaDB(阿里云源)并启动并设置开机自启

启动并设置开机自启且初始化数据库并配置ZrLog权限

四、部署 ZrLog 应用服务器
下载好需要的安装包

4.1 安装 JDK + Maven(配置阿里云镜像)
安装JDK 11 配置全局环境变量(永久生效) 生效并验证

下载 Maven 3.9.6(适配JDK 11)或者解压安装包
wget https://archive.apache.org/dist/maven/maven-3/3.9.6/binaries/apache-maven-3.9.6-bin.tar.gz
配置全局环境变量

编辑镜像源配置文件

4.2下载 ZrLog 源码并通过 Maven 编译
解压到指定目录,避免文件混乱

配置阿里云镜像(解决依赖下载慢/失败)写入全新的独立pom.xml(无需父POM,直接构建War包
cat > /root/zrlog-src/META-INF/maven/com.hibegin/package/pom.xml << 'EOF'
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<!-- 手动定义项目基本信息(替代父POM) -->
<groupId>com.hibegin</groupId>
<artifactId>zrlog-web</artifactId>
<version>3.3.0</version>
<packaging>war</packaging>
<name>ZrLog Web</name>
<description>ZrLog Blog System</description>
<!-- 核心依赖(覆盖父POM的关键依赖) -->
<dependencies>
<!-- Servlet & JSP 核心 -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>4.0.1</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
<version>2.2</version>
<scope>provided</scope>
</dependency>
<!-- Java EE 基础 -->
<dependency>
<groupId>javax</groupId>
<artifactId>javaee-api</artifactId>
<version>8.0.1</version>
<scope>provided</scope>
</dependency>
<!-- 数据库驱动(ZrLog核心依赖) -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.33</version>
</dependency>
<!-- 日志依赖 -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.36</version>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.2.13</version>
</dependency>
</dependencies>
<!-- 构建配置(确保能打出可运行的War包) -->
<build>
<finalName>zrlog</finalName>
<plugins>
<!-- 编译插件(适配JDK11) -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.8.1</version>
<configuration>
<source>11</source>
<target>11</target>
<encoding>UTF-8</encoding>
</configuration>
</plugin>
<!-- War包插件(忽略缺失web.xml) -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>3.3.2</version>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
<!-- 指向ZrLog的源码/资源目录(关键) -->
<webResources>
<resource>
<directory>/root/zrlog-src</directory>
<includes>
<include>WEB-INF/**/*</include>
<include>META-INF/**/*</include>
<include>**/*.jsp</include>
<include>**/*.html</include>
<include>**/*.css</include>
<include>**/*.js</include>
</includes>
</resource>
</webResources>
</configuration>
</plugin>
</plugins>
</build>
</project>
EOF
# 在 /root/zrlog-src/META-INF/maven/com.hibegin/package/目录下执行Maven打包(-DskipTests跳过测试,加快构建速度)


4.3复制 War 包并清理旧数据
解压Tomcat包


复制War包到Tomcat webapps目录,重命名为ROOT.war(直接访问根路径) 清理Tomcat旧解压文件(避免冲突)

4.4 启动 Tomcat 并验证
启动Tomcat 并查看启动日志(确认War包解压、服务无报错)

访问zrlog


五、HAProxy + Keepalived 适配调整(20/23 服务器)
5.1 调整 HAProxy 配置
下载HAProxy

调整配置
cat > /etc/haproxy/haproxy.cfg << 'EOF'
# global 段:全局配置(进程级参数)
global
log 127.0.0.1 local2
chroot /var/lib/haproxy
pidfile /var/run/haproxy.pid
maxconn 4000
user haproxy
group haproxy
daemon
stats socket /var/lib/haproxy/stats
# defaults 段:为后续的 frontend/backend 设置默认参数,避免重复配置。
defaults
mode http
log global
option httplog
option dontlognull
option http-server-close
option forwardfor except 127.0.0.0/8
option redispatch
retries 3
timeout http-request 10s
timeout queue 1m
timeout connect 10s
timeout client 1m
timeout server 1m
timeout http-keep-alive 10s
timeout check 10s
maxconn 3000
# listen stats 段:监控页面(可选)
# 提供可视化监控界面,查看后端节点健康状态、连接数等。
listen stats
bind *:8080
mode http
stats enable
stats uri /haproxy-stats
stats auth admin:admin123
#frontend http-in 段:定义 HAProxy 接收请求的端口和转发规则。
frontend http-in
bind *:80 # 监听80端口(客户端访问的入口)
default_backend zrlog_servers # 所有请求默认转发到zrlog_servers后端
#backend zrlog_servers 段:定义后端服务器列表、负载均衡算法、健康检查规则。
#check:启用健康检查;inter 2000:每 2 秒检查一次;rise 2:连续 2 次健康则标记为可用;fall 3:连续 3 次失败则标记为不可用。
backend zrlog_servers
balance roundrobin # 负载均衡策略
# 关键1:调整健康检查规则,匹配后端实际响应
option httpchk GET / HTTP/1.1\r\nHost:\ zrlog.example.com # 模拟带Host的请求(替换为你的ZrLog域名/IP)
http-check expect status 200 # 若后端返回302,改为 http-check expect status 302
# 关键2:放宽健康检查参数,避免误判
server zrlog1 192.168.223.21:8080 check inter 5s fall 3 rise 2 # 检查间隔5s,3次失败才标记DOWN
server zrlog2 192.168.223.24:8080 check inter 5s fall 3 rise 2
# 关键3:转发关键请求头(ZrLog可能依赖)
http-request set-header X-Real-IP %[src]
http-request set-header X-Forwarded-For %[src]
EOF
重启HAProxy

5.2 Keepalived 配置(无变更,复用原双主配置)
创建 Shell 邮件发送脚本
下载

赋权 编辑邮箱的主配置文件


发送测试文件进行测试


5.3 配置keepalived
192.168.223.20 配置(同原文档)
下载keepaliveed

配置主配置文件
cat > /etc/keepalived/keepalived.conf << 'EOF'
global_defs {
router_id LVS_20 # 全局标识:当前Keepalived节点的唯一名称(自定义,建议含IP/主机名)
}
vrrp_instance VI_1 { # 定义第一个VRRP实例(对应VIP1:192.168.223.100)
state MASTER # 初始状态:MASTER(主节点),但最终由priority决定实际角色
interface ens160 # 绑定的网卡(必须和服务器实际网卡名一致,如ens33/eth0)
virtual_router_id 51 # VRRP组ID(范围1-255):同一VIP的实例ID必须相同(20和23节点的VI_1都为51)
priority 100 # 优先级(0-255):数值越高越优先成为Master,20节点VI_1优先级100 > 23节点的90
advert_int 1 # VRRP通告间隔:1秒(节点间每秒发送一次心跳,确认对方存活)
authentication { # 认证配置:防止非法节点加入VRRP组
auth_type PASS # 认证类型:PASS(密码认证,另一种是AH,较少用)
auth_pass 1111 # 认证密码:同一VRRP组(VI_1)的节点密码必须相同(20和23节点都为1111)
}
virtual_ipaddress { # 该实例对应的VIP列表(可配置多个,空格分隔)
192.168.223.100 # 核心:虚拟IP,客户端访问的入口
}
# 状态变化触发的脚本(自定义告警脚本,路径需存在且可执行)
notify_master "/usr/local/bin/keepalived_notify.sh master" # 成为Master时执行
notify_backup "/usr/local/bin/keepalived_notify.sh backup" # 成为Backup时执行
notify_fault "/usr/local/bin/keepalived_notify.sh fault" # 故障(如网卡宕机)时执行
}
vrrp_instance VI_2 { # 定义第二个VRRP实例(对应VIP2:192.168.223.101)
state BACKUP # 初始状态:BACKUP(备节点)
interface ens160 # 绑定同一块网卡(和VI_1一致)
virtual_router_id 52 # VRRP组ID:VI_2的ID为52(和VI_1不同,避免冲突)
priority 90 # 优先级:90 < 23节点VI_2的100,因此23节点是VI_2的Master
advert_int 1 # 心跳间隔:1秒(和VI_1一致即可)
authentication {
auth_type PASS
auth_pass 2222 # VI_2的认证密码(和VI_1不同,也可相同,建议区分)
}
virtual_ipaddress {
192.168.223.101 # 第二个VIP
}
# 状态变化脚本(和VI_1共用同一个脚本,通过参数区分状态)
notify_master "/usr/local/bin/keepalived_notify.sh master"
notify_backup "/usr/local/bin/keepalived_notify.sh backup"
notify_fault "/usr/local/bin/keepalived_notify.sh fault"
}
EOF
在192.168.223.23主配置文件中配置
192.168.223.23 配置(同原文档)
cat > /etc/keepalived/keepalived.conf << 'EOF'
global_defs {
router_id LVS_23 # 节点唯一标识(和20节点区分,如LVS_23)
}
vrrp_instance VI_1 { # 对应20节点的VI_1(VIP1:100)
state BACKUP # 初始状态:BACKUP(备节点)
interface ens160 # 网卡名必须和20节点一致
virtual_router_id 51 # VRRP组ID:必须和20节点VI_1的51一致,否则无法组成同一组
priority 90 # 优先级:90 < 20节点的100,因此20节点是VI_1的Master
advert_int 1 # 心跳间隔:和20节点一致(1秒)
authentication {
auth_type PASS
auth_pass 1111 # 认证密码:必须和20节点VI_1的1111一致,否则认证失败
}
virtual_ipaddress {
192.168.223.100 # 同一VIP:100(和20节点VI_1一致)
}
# 状态脚本(和20节点路径一致,需确保脚本在23节点也存在)
notify_master "/usr/local/bin/keepalived_notify.sh master"
notify_backup "/usr/local/bin/keepalived_notify.sh backup"
notify_fault "/usr/local/bin/keepalived_notify.sh fault"
}
vrrp_instance VI_2 { # 对应20节点的VI_2(VIP2:101)
state MASTER # 初始状态:MASTER(主节点)
interface ens160
virtual_router_id 52 # VRRP组ID:必须和20节点VI_2的52一致
priority 100 # 优先级:100 > 20节点的90,因此23节点是VI_2的Master
advert_int 1
authentication {
auth_type PASS
auth_pass 2222 # 认证密码:必须和20节点VI_2的2222一致
}
virtual_ipaddress {
192.168.223.101 # 同一VIP:101
}
# 状态脚本
notify_master "/usr/local/bin/keepalived_notify.sh master"
notify_backup "/usr/local/bin/keepalived_notify.sh backup"
notify_fault "/usr/local/bin/keepalived_notify.sh fault"
}
EOF
重启Keepalived

5.4创建 Keepalived 通知脚本
cat > /usr/local/bin/keepalived_notify.sh << 'EOF'
#!/bin/bash
# Keepalived 状态变更邮件通知脚本
# 参数:$1 = 状态(master/backup/fault)
# 配置参数
VIP="192.168.223.100" # 你的 VIP 地址
TO_EMAIL="1341101176@qq.com" # 收件邮箱
SUBJECT="【Keepalived 告警】节点状态变更"
# 拼接邮件内容
MESSAGE="
=====================================
Keepalived 节点状态变更通知
=====================================
节点状态:$1
VIP 地址:${VIP}
发生时间:$(date +'%Y-%m-%d %H:%M:%S')
=====================================
"
# 用 mailx 发送邮件
echo "${MESSAGE}" | mailx -s "${SUBJECT}" ${TO_EMAIL}
# 记录日志(可选,便于排查)
echo "$(date +'%Y-%m-%d %H:%M:%S') - 发送 Keepalived 状态邮件,状态:$1" >> /var/log/keepalived_mail.log
EOF
赋予执行权限
chmod +x /usr/local/bin/keepalived_notify.sh
查看两台主机的IP

六、验证与访问
6.1 基础验证
检查HAProxy后端健康状态

访问192.168.223.100和192.138.223.101


6.2模拟故障
20号机器故障
预期结果:23 节点同时显示192.168.223.100/32和192.168.223.101/32(两个 VIP 均漂移到 23 节点)

23号机器故障
预期结果:20 节点同时显示192.168.223.100/32和192.168.223.101/32(两个 VIP 均漂移到 20 节点)

openEuler 是由开放原子开源基金会孵化的全场景开源操作系统项目,面向数字基础设施四大核心场景(服务器、云计算、边缘计算、嵌入式),全面支持 ARM、x86、RISC-V、loongArch、PowerPC、SW-64 等多样性计算架构
更多推荐
所有评论(0)