离职后的交接是一件有意思的事,被交接的时候有多头大,交接给别人的时候就有多爽,哈哈哈哈哈,不多说了,接手工作的同事要来打我了(手动狗头保命.jpg)。
不过话说回来,交接工作本身真的是学习和提升的好机会,在之前一次次接手同事工作的时候,自己也得到了快速的成长,虽然痛苦,但也学到了很多之前没接触过的技能;而当自己辞职把工作交接给同事的时候,也是回顾总结、反省自我和共同提升的好机会。
回想工作的 5 年里,一个人前前后后接下了系统的后端代码、架构、部署,从对后端一知半解到能够独立设计开发功能,到经验慢慢丰富可以给别人建议,再到掌握底层原理,一路走来,也感谢自己的坚持和不放弃。
目前对系统中使用的架构和部署方面还不够熟练,正好借着整理这篇博客的机会好好学习下 HAProxy + Keepalived 架构,也希望能给小伙伴们带来一些收获。
首先,先来了解一下 HAProxy 是什么。
HAProxy 是一个使用 C 语言编写的自由开源软件,提供了高性能的负载均衡能力,是一个基于 TCP 和 HTTP 的反向代理服务器。
它支持双机热备,支持虚拟主机,配置简单,拥有非常不错的服务器健康检查功能。当其代理的后端服务器出现故障,HAProxy会自动将该服务器摘除,故障恢复后再自动将该服务器加入。
那么我们的系统又为什么偏偏要用 HAProxy?Nginx 也可以用于负载均衡,难道它不香么?
这就要结合具体的应用场景来说了,系统当年的场景和开发要求如下:
而 HAProxy 的特点如下:
这么一看,HAProxy 略胜一筹,猜测这大概是当年选择它的原因吧。
如上图所示,系统中使用了 虚拟 IP + Haproxy + Keepalived + 服务节点 的服务方式。
我们的系统对高可用的要求是非常高的,如果有一台 Haproxy 无法正常提供服务,那系统访问就会出现问题。所以我们需要对 Haproxy 进行实时检测和故障转移处理,这时,Keepalived 就派上用场了。
这个 Keepalived 是什么?具体是怎么工作的?
Keepalived 软件起初是专为 LVS 负载均衡软件设计的,用来管理并监控 LVS 集群系统中各个服务节点的状态,是一种有效的高可用解决方案。
一般来说,会有 2 台服务器运行 Keepalived,一台为主服务器,一台为备份服务器,对外表现为一个虚拟 IP。
Keepalived 一旦检测到 Haproxy 进程停止,会尝试重启 Haproxy,如果重启失败,Keepalived 就会自杀,另一台 Keepalived 节点检测到对方消失,则会自动接管服务,此时的虚拟 IP 就漂移至另一台 Keepalived 节点上,由另一台 Haproxy 分发请求。
那 Keepalived 之间又是如何实现相互检测的呢?
Keepalived 服务正常工作时,主节点会以多播的方式不断地向备节点发送心跳消息,告诉备节点自己还活着,当主节点发生故障无法发送心跳消息时,备节点无法继续检测到来自主节点的心跳,就会调用自身的接管程序,接管主节点的 IP 资源及服务。
而当主节点恢复时,备节点又会释放主节点故障时自身接管的 IP 资源及服务,恢复到原来的备用角色。
1. 安装
yum install -y haproxy rsyslog
2. 编辑配置文件
vim /etc/haproxy/haproxy.cfg
配置文件内容如下:
#---------------------------------------------------------------------
# Global settings
#---------------------------------------------------------------------
global
log 127.0.0.1 local2
chroot /var/lib/haproxy
pidfile /var/run/haproxy.pid
maxconn 40000
user haproxy
group haproxy
daemon
# turn on stats unix socket
stats socket /var/lib/haproxy/stats
#---------------------------------------------------------------------
# common defaults that all the 'listen' and 'backend' sections will
# use if not designated in their block
#---------------------------------------------------------------------
defaults
log global
option dontlognull
option http-server-close
option redispatch
retries 3
timeout http-request 10s
timeout queue 1m
timeout connect 10s
timeout http-keep-alive 10s
timeout check 10s
maxconn 30000
#---------------------------------------------------------------------
# frontend
#---------------------------------------------------------------------
frontend main *:9007
mode http
option httplog
option forwardfor header x-real-ip
timeout client 10m
timeout client-fin 10m
default_backend main-servers
frontend db *:3306
mode tcp
option tcplog
timeout client 470m
timeout client-fin 470m
default_backend db-servers
frontend db-slave *:3307
mode tcp
option tcplog
timeout client 470m
timeout client-fin 470m
default_backend db-slave-servers
backend main-servers
mode http
balance roundrobin
timeout server 10m
server main-ip1:9000 ip1:9000 check
server main-ip2:9000 ip2:9000 check
server main-ip3:9000 ip3:9000 check
server main-ip4:9000 ip4:9000 check
# 两台主DB
backend db-servers
mode tcp
balance roundrobin
option tcplog
timeout server 470m
timeout server-fin 470m
timeout tunnel 470m
server db-ip5:3306 ip5:3306 maxconn 16000 check
server db-ip6:3306 ip6:3306 maxconn 16000 check backup
# 两台从DB
backend db-slave-servers
mode tcp
balance roundrobin
option tcplog
timeout server 470m
timeout server-fin 470m
timeout tunnel 470m
server db-ip7:3306 ip7:3306 maxconn 16000 check
server db-ip8:3306 ip8:3306 maxconn 16000 check
listen admin_stats
stats enable
bind *:8000 #监听的ip端口号
mode http #开关
option httplog
timeout client 1m
log global
maxconn 10
stats refresh 10s #统计页面自动刷新时间
stats uri /haproxy/status #访问的uri ip:8000/haproxy/status
stats realm haproxy
stats auth xy:superHelloKitty #认证用户名和密码
stats hide-version #隐藏HAProxy的版本号
stats admin if TRUE #管理界面,如果认证成功了,可通过webui管理节点
3.日志配置
在 /etc/rsyslog.conf 文件追加以下内容:
local2.* /var/log/haproxy.log
并将以下配置项的注释去掉:
$ModLoad imudp
$UDPServerRun 514
新建 /etc/rsyslog.d/haproxy.conf 文件,输入以下内容:
local2.* /var/log/haproxy.log
4.启动
service rsyslog start
service haproxy start
1.安装
yum install -y ipvsadm keepalived rsyslog
2.修改配置文件 /etc/keepalived/keepalived.conf
主服务的配置文件:
! Configuration File for keepalived
global_defs {
router_id LVS_DEVEL
}
vrrp_script chk_haproxy {
script "/etc/keepalived/chk_haproxy.sh" #服务探测,返回0说明服务是正常的
interval 1 #每隔1秒探测一次
weight 2 #haproxy上线,权重加2;下线,权重减2
fall 1
rise 1
}
vrrp_instance VI_1 { #双主实例1
state MASTER #主
interface eth0 #网卡
virtual_router_id 88 #实例1的VRID为88
priority 100 #主的优先级为100,从的优先级为99
advert_int 1 #检查时间为1s
authentication {
auth_type PASS
auth_pass passwd@#$?1234@
}
virtual_ipaddress {
10.136.48.65 #虚拟IP
}
track_script { #脚本追踪
chk_haproxy
}
}
从服务的配置文件:
! Configuration File for keepalived
global_defs {
router_id LVS_DEVEL
}
vrrp_script chk_haproxy {
script "/etc/keepalived/chk_haproxy.sh" #服务探测,返回0说明服务是正常的
interval 1 #每隔1秒探测一次
weight 2 #haproxy上线,权重加2;下线,权重减2
fall 1
rise 1
}
vrrp_instance VI_1 { #双主实例1
state BACKUP #从
interface eth0 #网卡
virtual_router_id 88 #实例1的VRID为88
priority 99 #主的优先级为100,从的优先级为99
advert_int 1 #检查时间为1s
authentication {
auth_type PASS
auth_pass passwd@#$?1234@
}
virtual_ipaddress {
10.136.48.65 #虚拟IP
}
track_script { #脚本追踪
chk_haproxy
}
}
Haproxy 进程状态检查脚本 chk_haproxy.sh:
#!/bin/bash
A=`ps -C haproxy --no-header |wc -l`
if [ $A -eq 0 ];then
service haproxy start
sleep 3
if [ `ps -C haproxy --no-header |wc -l` -eq 0 ];then
service keepalived stop
exit 1
fi
fi
exit 0
需要把检查脚本 chk_haproxy.sh 上传到每台机器的 /etc/keepalived 目录下。
3. 启动
service keepalived start