使用虚拟IP和Keepalived搭建高可用Web集群
应用场景
虚拟IP(Virtual IP Address)是从VPC子网网段中划分的一个内网IP地址,通常搭配高可用软件(比如Keepalived)使用,主要用来搭建高可用的主备集群。多个云服务器形成主备集群,当主云服务器发生故障无法对外提供服务时,系统动态将虚拟IP切换到备云服务器,通过备云服务器继续对外提供服务。本文档为您详细介绍使用虚拟IP和Keepalived搭建高可用Web集群的方法。
方案架构
- ECS-HA1作为主云服务器,通过与虚拟IP绑定的EIP对外提供服务,ECS-HA2作为备云服务器不承载实际业务。
- 当ECS-HA1发生故障时,此时会自动启用ECS-HA2,ECS-HA2将会接管业务并对外提供服务,实现业务不中断的高可用需求。
方案优势
基于虚拟IP和Keepalived能力,采用“一主一备”或“一主多备”的方法组合使用云服务器,这些云服务器对外呈现为一个虚拟IP。当主云服务器故障时,备云服务器可以转为主云服务器并继续对外提供服务,以此达到高可用性HA(High Availability)的目的,可以解决用户由于云服务器故障导致的对外服务中断问题。
约束与限制
使用虚拟IP搭建的高可用集群,所有服务器必须位于同一个虚拟私有云的子网内。
资源规划说明
本示例中,虚拟私有云VPC和子网、虚拟IP、弹性公网IP以及弹性云服务器ECS等资源只要位于同一个区域内即可,可用区可以任意选择,无需保持一致。
以下资源规划详情仅为示例,您可以根据需要自行修改。
资源类型 |
资源数量 |
说明 |
---|---|---|
虚拟私有云VPC和子网 |
1 |
|
弹性云服务器ECS |
2 |
本示例中,需要两个ECS作为主备倒换,配置说明如下:
|
虚拟IP |
1 |
在子网Subnet-A01中申请虚拟IP地址:
|
弹性公网IP |
1 |
|
步骤一:创建云服务资源
- 创建1个VPC和1个子网。
具体方法请参见创建虚拟私有云和子网。
- 创建2个ECS,分别作为主ECS和备ECS。
具体方法请参见自定义购买ECS。
本示例中,ECS的网络配置详情如下:- 网络:选择已创建的虚拟私有云和子网,VPC-A和Subnet-A01。
- 安全组:新建一个安全组Sg-A,并添加入方向和出方向规则。您在创建安全组的时候,系统会自动添加部分规则,您需要根据实际情况进行检查修改。
本示例中,ECS-HA1和ECS-HA2属于同一个安全组,您需要确保表2中的规则均已正确添加。
表2 安全组Sg-A规则说明 方向
策略
类型
协议端口
源地址/目的地址
描述
入方向
允许
IPv4
TCP: 22
源地址:0.0.0.0/0
放通安全组内ECS的SSH(22)端口,用于远程登录Linux ECS。
入方向
允许
IPv4
TCP: 3389
源地址:0.0.0.0/0
放通安全组内ECS的RDP(3389)端口,用于远程登录Windows ECS。
入方向
允许
IPv4
TCP: 80
源地址:0.0.0.0/0
放通安全组内ECS的HTTP(80)端口,用于外部通过HTTP协议访问ECS上部署的网站。
入方向
允许
IPv4
全部
源地址:当前安全组Sg-A
针对IPv4,用于安全组内ECS之间网络互通。
入方向
允许
IPv6
全部
源地址:当前安全组Sg-A
针对IPv6,用于安全组内ECS之间网络互通。
出方向
允许
IPv4
全部
目的地址:0.0.0.0/0
针对IPv4,用于安全组内ECS访问外部,允许流量从安全组内ECS流出。
出方向
允许
IPv6
全部
目的地址:::/0
针对IPv6,用于安全组内ECS访问外部,允许流量从安全组内ECS流出。
本示例中,源地址设置为0.0.0.0/0表示允许所有外部IP远程登录云服务器,为了确保安全,建议您遵循最小原则,根据实际情况将源IP设置为特定的IP地址,比如,源地址设置为您的本地PC地址。
如果您的ECS位于不同的安全组,比如ECS-HA1属于Sg-A,ECS-HA2属于Sg-B,则除了在两个安全组中分别配置表2中的规则,您还需要添加表3中的规则,放通两个安全组之间的内网网络流量。
- 弹性公网IP:选择“暂不购买”。
- 在子网Subnet-A01内,申请虚拟IP地址。
具体方法请参见申请虚拟IP地址。
- 申请弹性公网IP。
具体方法请参见购买弹性公网IP。
步骤二:为主备ECS配置Keepalived
- 执行以下操作,为ECS-HA1配置Keepalived。
- 将EIP绑定至ECS-HA1。
具体方法请参见绑定弹性公网IP。
- 远程登录ECS-HA1。
ECS有多种登录方法,具体请参见登录弹性云服务器。
- 执行以下命令,安装Nginx、Keepalived软件包及相关依赖包。
yum install nginx keepalived -y
回显类似如下信息,表示安装完成。[root@ecs-ha1 ~]# yum install nginx keepalived -y Loaded plugins: fastestmirror Determining fastest mirrors base | 3.6 kB 00:00:00 epel | 4.3 kB 00:00:00 extras | 2.9 kB 00:00:00 updates | 2.9 kB 00:00:00 (1/7): epel/x86_64/group | 399 kB 00:00:00 (2/7): epel/x86_64/updateinfo | 1.0 MB 00:00:00 (3/7): base/7/x86_64/primary_db | 6.1 MB 00:00:00 (4/7): base/7/x86_64/group_gz | 153 kB 00:00:00 (5/7): epel/x86_64/primary_db | 8.7 MB 00:00:00 (6/7): extras/7/x86_64/primary_db | 253 kB 00:00:00 (7/7): updates/7/x86_64/primary_db ..... Dependency Installed: centos-indexhtml.noarch 0:7-9.el7.centos gperftools-libs.x86_64 0:2.6.1-1.el7 lm_sensors-libs.x86_64 0:3.4.0-8.20160601gitf9185e5.el7_9.1 net-snmp-agent-libs.x86_64 1:5.7.2-49.el7_9.4 net-snmp-libs.x86_64 1:5.7.2-49.el7_9.4 nginx-filesystem.noarch 1:1.20.1-10.el7 openssl11-libs.x86_64 1:1.1.1k-7.el7 Complete!
- 执行以下操作,修改Nginx配置文件,添加80端口相关配置。
- 执行以下命令,打开“/etc/nginx/nginx.conf”文件。
vim /etc/nginx/nginx.conf
- 按i进入编辑模式。
- 将文件中原有的内容,全部替换成以下内容。
user root; worker_processes 1; #error_log logs/error.log; #error_log logs/error.log notice; #error_log logs/error.log info; #pid logs/nginx.pid; events { worker_connections 1024; } http { include mime.types; default_type application/octet-stream; #log_format main '$remote_addr - $remote_user [$time_local] "$request" ' # '$status $body_bytes_sent "$http_referer" ' # '"$http_user_agent" "$http_x_forwarded_for"'; #access_log logs/access.log main; sendfile on; #tcp_nopush on; #keepalive_timeout 0; keepalive_timeout 65; #gzip on; server { listen 80; server_name localhost; #charset koi8-r; #access_log logs/host.access.log main; location / { root html; index index.html index.htm; } #error_page 404 /404.html; # redirect server error pages to the static page /50x.html error_page 500 502 503 504 /50x.html; location = /50x.html { root html; } } }
- 按ESC退出,并输入:wq!保存配置。
- 执行以下命令,打开“/etc/nginx/nginx.conf”文件。
- 执行以下操作,修改index.html文件内容,用来验证网站的访问情况。
- 执行以下命令,打开“/usr/share/nginx/html/index.html”文件。
vim /usr/share/nginx/html/index.html
- 按i进入编辑模式。
- 将文件中原有的内容,全部替换成以下内容。
Welcome to ECS-HA1
- 按ESC退出,并输入:wq!保存配置。
- 执行以下命令,打开“/usr/share/nginx/html/index.html”文件。
- 执行以下命令,设置Nginx服务开机自启动,并启动Nginx服务。
systemctl start nginx.service
回显类似如下信息:[root@ecs-ha1 ~]# systemctl enable nginx Created symlink from /etc/systemd/system/multi-user.target.wants/nginx.service to /usr/lib/systemd/system/nginx.service. [root@ecs-ha1 ~]# systemctl start nginx.service
- 打开浏览器,并输入EIP地址(124.X.X.187),验证Nginx单节点的访问情况。
- 执行以下操作,修改Keepalived配置文件。
- 执行以下命令,打开“/etc/keepalived/keepalived.conf”文件。
vim /etc/keepalived/keepalived.conf
- 按i进入编辑模式。
- 根据实际情况,替换配置文件中的IP参数,并将文件中原有的内容,全部替换成以下内容。
- mcast_src_ip和unicast_src_ip:替换为ECS-HA1的私有IP地址,本示例为192.168.0.195。
- virtual_ipaddress:替换为虚拟IP地址,本示例为192.168.0.177。
! Configuration File for keepalived global_defs { router_id master-node } vrrp_script chk_http_port { script "/etc/keepalived/chk_nginx.sh" interval 2 weight -5 fall 2 rise 1 } vrrp_instance VI_1 { state BACKUP interface eth0 mcast_src_ip 192.168.0.195 virtual_router_id 51 priority 100 advert_int 1 authentication { auth_type PASS auth_pass 1111 } unicast_src_ip 192.168.0.195 virtual_ipaddress { 192.168.0.177 } track_script { chk_http_port } }
- 按ESC退出,并输入:wq!保存配置。
- 执行以下命令,打开“/etc/keepalived/keepalived.conf”文件。
- 执行以下操作,配置Nginx监控脚本。
- 执行以下命令,打开“/etc/keepalived/chk_nginx.sh”文件。
vim /etc/keepalived/chk_nginx.sh
- 按i进入编辑模式。
- 将文件中原有的内容,全部替换成以下内容。
#!/bin/bash counter=$(ps -C nginx --no-heading|wc -l) if [ "${counter}" = "0" ]; then systemctl start nginx.service sleep 2 counter=$(ps -C nginx --no-heading|wc -l) if [ "${counter}" = "0" ]; then systemctl stop keepalived.service fi fi
- 按ESC退出,并输入:wq!保存配置。
- 执行以下命令,打开“/etc/keepalived/chk_nginx.sh”文件。
- 执行以下命令,为“chk_nginx.sh”文件添加执行权限。
chmod +x /etc/keepalived/chk_nginx.sh
- 执行以下命令,设置Keepalived服务开机自启动,并启动Keepalived服务。
systemctl start keepalived.service
- 将EIP和ECS-HA1解绑定。
具体方法请参见解绑弹性公网IP。
- 将EIP绑定至ECS-HA1。
- 执行以下操作,为ECS-HA2配置Keepalived。
- 将EIP绑定至ECS-HA2。
具体方法请参见绑定弹性公网IP。
- 远程登录ECS-HA2。
ECS有多种登录方法,具体请参见登录弹性云服务器。
- 执行以下命令,安装Nginx、Keepalived软件包及相关依赖包。
yum install nginx keepalived -y
回显类似如下信息,表示安装完成。[root@ecs-ha2 ~]# yum install nginx keepalived -y Loaded plugins: fastestmirror Determining fastest mirrors base | 3.6 kB 00:00:00 epel | 4.3 kB 00:00:00 extras | 2.9 kB 00:00:00 updates | 2.9 kB 00:00:00 (1/7): epel/x86_64/group | 399 kB 00:00:00 (2/7): epel/x86_64/updateinfo | 1.0 MB 00:00:00 (3/7): base/7/x86_64/primary_db | 6.1 MB 00:00:00 (4/7): base/7/x86_64/group_gz | 153 kB 00:00:00 (5/7): epel/x86_64/primary_db | 8.7 MB 00:00:00 (6/7): extras/7/x86_64/primary_db | 253 kB 00:00:00 (7/7): updates/7/x86_64/primary_db ..... Dependency Installed: centos-indexhtml.noarch 0:7-9.el7.centos gperftools-libs.x86_64 0:2.6.1-1.el7 lm_sensors-libs.x86_64 0:3.4.0-8.20160601gitf9185e5.el7_9.1 net-snmp-agent-libs.x86_64 1:5.7.2-49.el7_9.4 net-snmp-libs.x86_64 1:5.7.2-49.el7_9.4 nginx-filesystem.noarch 1:1.20.1-10.el7 openssl11-libs.x86_64 1:1.1.1k-7.el7 Complete!
- 执行以下操作,修改Nginx配置文件,添加80端口相关配置。
- 执行以下命令,打开“/etc/nginx/nginx.conf”文件。
vim /etc/nginx/nginx.conf
- 按i进入编辑模式。
- 将文件中原有的内容,全部替换成以下内容。
user root; worker_processes 1; #error_log logs/error.log; #error_log logs/error.log notice; #error_log logs/error.log info; #pid logs/nginx.pid; events { worker_connections 1024; } http { include mime.types; default_type application/octet-stream; #log_format main '$remote_addr - $remote_user [$time_local] "$request" ' # '$status $body_bytes_sent "$http_referer" ' # '"$http_user_agent" "$http_x_forwarded_for"'; #access_log logs/access.log main; sendfile on; #tcp_nopush on; #keepalive_timeout 0; keepalive_timeout 65; #gzip on; server { listen 80; server_name localhost; #charset koi8-r; #access_log logs/host.access.log main; location / { root html; index index.html index.htm; } #error_page 404 /404.html; # redirect server error pages to the static page /50x.html error_page 500 502 503 504 /50x.html; location = /50x.html { root html; } } }
- 按ESC退出,并输入:wq!保存配置。
- 执行以下命令,打开“/etc/nginx/nginx.conf”文件。
- 执行以下操作,修改index.html文件内容,用来验证网站的访问情况。
- 执行以下命令,打开“/usr/share/nginx/html/index.html”文件。
vim /usr/share/nginx/html/index.html
- 按i进入编辑模式。
- 将文件中原有的内容,全部替换成以下内容。
Welcome to ECS-HA2
- 按ESC退出,并输入:wq!保存配置。
- 执行以下命令,打开“/usr/share/nginx/html/index.html”文件。
- 执行以下命令,设置Nginx服务开机自启动,并启动Nginx服务。
systemctl start nginx.service
回显类似如下信息:[root@ecs-ha2 ~]# systemctl enable nginx Created symlink from /etc/systemd/system/multi-user.target.wants/nginx.service to /usr/lib/systemd/system/nginx.service. [root@ecs-ha2 ~]# systemctl start nginx.service
- 打开浏览器,并输入EIP地址(124.X.X.187),验证Nginx单节点的访问情况。
- 执行以下操作,修改Keepalived配置文件。
- 执行以下命令,打开“/etc/keepalived/keepalived.conf”文件。
vim /etc/keepalived/keepalived.conf
- 按i进入编辑模式。
- 根据实际情况,替换配置文件中的IP参数,并将文件中原有的内容,全部替换成以下内容。
- mcast_src_ip和unicast_src_ip:替换为ECS-HA2的私有IP地址,本示例为192.168.0.233。
- virtual_ipaddress:替换为虚拟IP地址,本示例为192.168.0.177。
! Configuration File for keepalived global_defs { router_id master-node } vrrp_script chk_http_port { script "/etc/keepalived/chk_nginx.sh" interval 2 weight -5 fall 2 rise 1 } vrrp_instance VI_1 { state BACKUP interface eth0 mcast_src_ip 192.168.0.233 virtual_router_id 51 priority 100 advert_int 1 authentication { auth_type PASS auth_pass 1111 } unicast_src_ip 192.168.0.233 virtual_ipaddress { 192.168.0.177 } track_script { chk_http_port } }
- 按ESC退出,并输入:wq!保存配置。
- 执行以下命令,打开“/etc/keepalived/keepalived.conf”文件。
- 执行以下操作,配置Nginx监控脚本。
- 执行以下命令,打开“/etc/keepalived/chk_nginx.sh”文件。
vim /etc/keepalived/chk_nginx.sh
- 按i进入编辑模式。
- 将文件中原有的内容,全部替换成以下内容。
#!/bin/bash counter=$(ps -C nginx --no-heading|wc -l) if [ "${counter}" = "0" ]; then systemctl start nginx.service sleep 2 counter=$(ps -C nginx --no-heading|wc -l) if [ "${counter}" = "0" ]; then systemctl stop keepalived.service fi fi
- 按ESC退出,并输入:wq!保存配置。
- 执行以下命令,打开“/etc/keepalived/chk_nginx.sh”文件。
- 执行以下命令,为“chk_nginx.sh”文件添加执行权限。
chmod +x /etc/keepalived/chk_nginx.sh
- 执行以下命令,设置Keepalived服务开机自启动,并启动Keepalived服务。
systemctl start keepalived.service
- 将EIP和ECS-HA2解绑定。
具体方法请参见解绑弹性公网IP。
- 将EIP绑定至ECS-HA2。
步骤三:将虚拟IP绑定至主备ECS及EIP
- 将虚拟IP分别绑定至主备ECS上,本示例中需要绑定ECS-HA1和ECS-HA2。
具体操作请参见将虚拟IP地址绑定至实例或EIP。
- 关闭主备ECS网卡的“源/目的检查”功能。
将虚拟IP绑定至ECS时,系统会自动关闭ECS网卡的“源/目的检查”功能,您需要参考以下操作检查关闭情况。如果未关闭,则请关闭该功能。
- 在ECS列表中,单击目标ECS的名称。
- 选择“弹性网卡”页签,并单击展开ECS的网卡详情区域,可以查看“源/目的检查”功能。
如图5所示,表示“源/目的检查”功能已关闭。
- 将虚拟IP绑定至EIP上,本示例中需要绑定EIP-A。
具体操作请参见将虚拟IP地址绑定至实例或EIP。
步骤四:关闭备ECS的IP转发功能
使用虚拟IP构建主备场景的高可用集群时,需要关闭备ECS的IP转发功能,当主备ECS切换后,则需要确保新的备ECS也关闭IP转发功能。
为了避免ECS主备切换后遗漏配置,建议您将主备ECS的IP转发功能全都关闭。
- 打开浏览器,并输入EIP地址(124.X.X.187),通过网页确认主ECS。
- 远程登录备ECS,本示例是ECS-HA2。
ECS有多种登录方法,具体请参见登录弹性云服务器。
- 请根据ECS的操作系统,在表4中选择关闭IP转发功能的操作,本示例ECS为Linux操作系统。
步骤五:验证主备ECS的自动切换功能
- 执行以下操作,分别重启主备ECS。
- 执行以下操作,验证主ECS的网页访问情况。
- 打开浏览器,并输入EIP地址(124.X.X.187),验证主ECS的网页访问情况。
- 远程登录ECS-HA1,并执行以下命令,查看虚拟IP是否已绑定到ECS-HA1的eth0网卡上。
回显类似如下信息,可以看到虚拟IP(192.168.0.177)已绑定至eth0网卡上,再次确认ECS-HA1为主ECS。
[root@ecs-ha1 ~]# ip addr show 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000 link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00 inet 127.0.0.1/8 scope host lo valid_lft forever preferred_lft forever inet6 ::1/128 scope host valid_lft forever preferred_lft forever 2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP group default qlen 1000 link/ether fa:16:3e:fe:56:19 brd ff:ff:ff:ff:ff:ff inet 192.168.0.195/24 brd 192.168.0.255 scope global noprefixroute dynamic eth0 valid_lft 107898685sec preferred_lft 107898685sec inet 192.168.0.177/32 scope global eth0 valid_lft forever preferred_lft forever inet6 fe80::f816:3eff:fefe:5619/64 scope link valid_lft forever preferred_lft forever
- 执行以下命令,停止主ECS的Keepalived服务,本示例中主ECS为ECS-HA1。
- 执行以下命令,验证主ECS是否切换成ECS-HA2。
- 远程登录ECS-HA2,并执行以下命令,查看虚拟IP是否已绑定到ECS-HA2的eth0网卡上。
回显类似如下信息,可以看到虚拟IP(192.168.0.177)已绑定至eth0网卡上,此时确认ECS-HA2为主ECS。
[root@ecs-ha2 ~]# ip addr show 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000 link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00 inet 127.0.0.1/8 scope host lo valid_lft forever preferred_lft forever inet6 ::1/128 scope host valid_lft forever preferred_lft forever 2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP group default qlen 1000 link/ether fa:16:3e:fe:56:3f brd ff:ff:ff:ff:ff:ff inet 192.168.0.233/24 brd 192.168.0.255 scope global noprefixroute dynamic eth0 valid_lft 107898091sec preferred_lft 107898091sec inet 192.168.0.177/32 scope global eth0 valid_lft forever preferred_lft forever inet6 fe80::f816:3eff:fefe:563f/64 scope link valid_lft forever preferred_lft forever
- 打开浏览器,并输入EIP地址(124.X.X.187),验证ECS-HA2作为主ECS时的网页访问情况。
- 远程登录ECS-HA2,并执行以下命令,查看虚拟IP是否已绑定到ECS-HA2的eth0网卡上。