admin 管理员组

文章数量: 887021


2023年12月25日发(作者:weigh的动词和名词)

【未完】对nginx做负载均衡实现双机热备

首先:

使用nginx做为负载均衡器时,通讯模型类似于LVS-NAT,在某些情况下,随着集群节点数量的增长,nginx将会成为网络通讯的瓶颈,因为所有应答数据包都必须通过nginx,一颗400MHz的处理器能够容纳100Mbps的连接,因此,在一般情况下,网络更可能比LVS Director更可能成为瓶颈。在这种情况下,使用LVS-DR比使用nginx做负载均衡器上更可靠一些。

使用nginx+keepalived的可行性:

Keepalived是Linux下面实现VRRP 备份路由的高可靠性运行件。基于Keepalived设计的服务模式能够真正做到主服务器和备份服务器故障时IP瞬间无缝交接。在新浪动态应用平台上,Keepalived配合LVS在线上服务中有着很好的稳定性。

Nginx是基于Linux 2.6内核中epoll模型http服务器,与Apache进程派生模式不同的是Nginx进程基于于Master+Slave多进程模型,自身具有非常 稳定的子进程管理功能。在Master进程分配模式下,Master进程永远不进行业务处理,只是进行任务分发,从而达到Master进程的存活高可靠 性,Slave进程所有的业务信号都由主进程发出,Slave进程所有的超时任务都会被Master中止,属于非阻塞式任务模型。在新浪博客应用平台上, 经过将近8个月的运行,没有因为主进程退出或者子进程僵死导致服务中致的故障存在。

在生产环境中,任何的机器宕机导致的损失都需要被 降到最低,传统的生产环境中,都是将服务器直接放置在4/7层交换机后面以避免因为服务器或者服务器软件故障导致的服务中止。当前的业务模式下,有许多高 并发的服务需求,Js小文件、高速动态接口、Nginx七层业务,都希望所有的Socket操作能够尽快完成,减少用户的时间等待。4/7层交换机由于负 责了新浪全站多个产品的服务,经常会成为高并发服务应用的一个制约条件。于是,就孕育出了使用Keepalived+Nginx实现双机交叉热备使用公网 ip进行DNS轮询服务的想法,这个方案可以运用于需要高并发服务的所有应用环境。越少的Socket通讯层,数据到达用户桌面的速度越快。

1、服务器IP存活检测:

服务器IP存活检测是由Keepalived自己本身完成的,将2台服务器配置成Keepalived互为主辅关系,任意一方机器故障对方都能够将IP接管过去。

2、服务器应用服务存活检测:

一个正常的业务服务,除了保证服务器的状态存活之外,还需要应用业务的存活。之前之所以有Apache服务器因为进程僵死导致HTTP不响应从而影响服 务是因为Apache的进程模式导致的。在Nginx的进程模型下,可以认为只要Nginx进程存活状态,服务就是正常的,于是只需要做到检测进程存活就 能够做到检测服务的存活。Slave进程的健康状态由Nginx自身的Master进程去完成,Master进程的存活可以通过服务器上的专用脚本进行监 测,一旦发现Nginx Master进程异常退出,则立即重新启动Nginx进程,该方案已经在新浪博客系统上运行近半年。

3、服务器在线维护:

Keepalived的服务IP通过其配置文件进行管理,依靠其自身的进程去确定服务器的存活状态,如果在需要对服务器进程在线维护的情况下,只需要停掉被维护机器的Keepalived服务进程,另外一台服务器就能够接管该台服务器的所有应用。

上面的可行性的文章转自其他blog,以下是根据上面的方案做的配置笔记,另外,我还没有搞明白keepalived如何防止脑

裂,因此,现在,个人觉得,用heartbeat做双机的热备更可靠一些,文章的后面有使用heartbeat做双机热备的配置。

方案 一 使用keepalived做nginx负载均衡器的双机热备

Keepalived为LVS群集提供强劲的健康检查机制。它实现了一个多层L3、L4、L5/7容错健康检查框架,当有Server Pool宕机后通过socket通知***内核***将其从Server Pools中剔除,进一步提高Linux Virtual Server project项目的High Availability。同时提供了独立的VRRPv2栈来及时处理 director failover ,及时为LVS集群节点健康检查及LVS directors failover。

在这里我们只使用keepalived的vrrp的功能,使主服务器和备份服务器故障时IP瞬间无缝交接。

1 安装

./configure --prefix=/usr/local/keepalived

make

make install

2 配置文件

vi /usr/local/keepalived/etc/keepalived/

Master的配置文件

vrrp_instance VI_INET1 {

state MASTER #(主机为MASTER,备用机为BACKUP)

interface eth0

#(HA监测网络接口)

mcast_src_ip 192.168.7.191 #(VRRP Multicast广播源地址,分别取主、备机地址,不能取与virtual_ipaddress相同)

track_interface { #其他要监测状态的接口

eth1

}

virtual_router_id 53 #(主、备机的virtual_router_id必须相同)

priority 200

#(主、备机取不同的优先级,主机值较大,备份机值较小,值越大优先级越高)

advert_int 5

#(VRRP Multicast广播周期秒数)

authentication {

auth_type pass #(VRRP认证方式)

auth_pass yourpass #(VRRP口令字)

}

virtual_ipaddress {

192.168.7.100 #(VRRP HA虚拟地址)

}

}

Slave的配置文件

vrrp_instance VI_INET1 {

state BACKUP

interface eth0

track_interface {

eth1

}

virtual_router_id 53

priority 100

advert_int 5

authentication {

auth_type pass

auth_pass yourpass

}

virtual_ipaddress {

192.168.7.100

}

}

track_interface的意思是将Linux中你想监控的网络接口卡监控起来,当其中的一块出现故障是keepalived都将视为路由器出现故障。

启动

在启动前先查看IP地址。注:不能使用ifconfig查看

[root@real1 ~]# ip addr show

1: lo: mtu 16436 qdisc noqueue

link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00

inet 127.0.0.1/8 scope host lo

2: eth0: mtu 1500 qdisc pfifo_fast qlen 1000

link/ether 00:0c:29:c8:9b:3c brd ff:ff:ff:ff:ff:ff

inet 192.168.7.191/24 brd 192.168.7.255 scope global eth0

/usr/local/keepalived/sbin/keepalived -D -f /usr/local/keepalived/etc/keepalived/

启动后

[root@real1 ~]# ip addr show

1: lo: mtu 16436 qdisc noqueue

link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00

inet 127.0.0.1/8 scope host lo

2: eth0: mtu 1500 qdisc pfifo_fast qlen 1000

link/ether 00:0c:29:c8:9b:3c brd ff:ff:ff:ff:ff:ff

inet 192.168.7.191/24 brd 192.168.7.255 scope global eth0

inet 192.168.7.100/32 scope global eth0

当Master失效时,Backup就会通过MultiCast地址:224.0.0.18(vrrp的默认地址)这个组播地址,获得这个消息,并将192.168.7.100这个地址接管过来。

别忘记在iptables配置当中增加:

-I INPUT -s <主/备服务器ip> -d 224.0.0.18 -j ACCEPT

老外的HA配置:

Using keepalived to failover routers

vrrpd is a router failover demon protocol. While keepalived uses it to failover LVS, vrrpd can be used independantly of LVS

to failover a pair of routers.

Graeme Fowler graeme (at) graemef (dot) net 11 Sep 2007

config for the ACTIVE router looks like:

# for HA "routers"

global_defs {

notification_email {

********************* }

***********************************.machine smtp_server 1.2.3.4

smtp_connect_timeout 60

router_id router_1

}

vrrp_script check_running {

script "/usr/local/bin/check_running"

interval 10

weight 10

}

vrrp_script always_succeed {

script "/bin/date"

interval 10

weight 10

}

vrrp_script always_fail {

script "/usr/local/bin/always_fail"

interval 10

weight 10

}

vrrp_instance ROUTER_1 {

state MASTER

smtp_alert

interface eth0

virtual_router_id 101

priority 100

advert_int 3

authentication {

auth_type PASS

auth_pass whatever

}

virtual_ipaddress {

1.1.1.1

}

track_script {

check_running weight 20

}

}

...the corresponding config for the BACKUP looks like:

# for HA "routers"

global_defs {

notification_email {

********************* }

***********************************.machine smtp_server 1.2.3.4

smtp_connect_timeout 60

router_id router_2

}

vrrp_script check_running {

script "/usr/local/bin/check_running"

interval 10

weight 10

}

vrrp_script always_succeed {

script "/bin/date"

interval 10

weight 10

}

vrrp_script always_fail {

script "/usr/local/bin/always_fail"

interval 10

weight 10

}

vrrp_instance ROUTER_1 {

state BACKUP

smtp_alert

interface eth0

virtual_router_id 101

priority 90

advert_int 3

authentication {

auth_type PASS

auth_pass whatever

}

virtual_ipaddress {

1.1.1.1

}

track_script {

check_running weight 20

}

}

i.e. it differs in the "weight" stanza for the VRRP definition (90 instead of 100) and there are cosmetic differences to the

name.

The "check_running" script is simply a wrapper round:

KILLALL -0 procname

if the result code ($?) is 0, it exits with 0. If not, it exits with 1.

If it exits with 1, the weight of the VRRP announcement is pulled down by 20 - this makes sure that the critical process on

this machine is up, and if it isn't then we play a smaller part in the VRRP adverts (these are derived from a pair of

frontend mail servers).

关于检查nginx状态的脚本,使用写好的启动脚本,运行时判断状态是否running就可以了,crontab,定时运行。

nginx启动脚本,放于/etc/init.d/nginxd

#!/bin/bash

# nginx Startup script for the Nginx HTTP Server

# this script create it by jackbillow at 2007.10.15.

# it is v.0.0.2 version.

# if you find any errors on this scripts,please contact jackbillow.

# and send mail to jackbillow at gmail dot com.

#

# chkconfig: - 85 15

# description: Nginx is a high-performance web and proxy server.

# It has a lot of features, but it's not for everyone.

# processname: nginx

# pidfile: /usr/local/nginx/logs/

# config: /usr/local/nginx/conf/

nginxd=/usr/local/nginx/sbin/nginx

nginx_config=/usr/local/nginx/conf/

nginx_pid=/var/run/

RETVAL=0

prog="nginx"

# Source function library.

. /etc/rc.d/init.d/functions

# Source networking configuration.

. /etc/sysconfig/network

# Check that networking is up.

[ ${NETWORKING} = "no" ] && exit 0

[ -x $nginxd ] || exit 0

# Start nginx daemons functions.

start() {

if [ -e $nginx_pid ];then

echo "nginx "

exit 1

fi

echo -n $"Starting $prog: "

daemon $nginxd -c ${nginx_config}

RETVAL=$?

echo

[ $RETVAL = 0 ] && touch /var/lock/subsys/nginx

return $RETVAL

}

# Stop nginx daemons functions.

stop() {

echo -n $"Stopping $prog: "

killproc $nginxd

RETVAL=$?

echo

[ $RETVAL = 0 ] && rm -f /var/lock/subsys/nginx /var/run/

}

# reload nginx service functions.

reload() {

echo -n $"Reloading $prog: "

#kill -HUP `cat ${nginx_pid}`

killproc $nginxd -HUP

RETVAL=$?

echo

}

# See how we were called.

case "$1" in

start)

start

;;

stop)

stop

;;

reload)

reload

;;

restart)

stop

start

;;

status)

status $prog

RETVAL=$?

;;

*)

echo $"Usage: $prog {start|stop|restart|reload|status|help}"

exit 1

esac

exit $RETVAL

方案二 使用heartbeat做双机热备

1、原理

heartbeat的工作原理:heartbeat最核心的包括两个部分,心跳监测部分和资源接管部分,心跳监测可以通过网络链路和串口进行,而且支持冗余链路,它们之间相互发送报文来告诉对方自己

当前的状态,如果在指定的时间内未受到对方发送的报文,那么就认为对方失效,这时需启动资源接管模块来接管运行在对方主机上的资源或者服务。

heartbeat的主从机通过定时交换信号来确认对方依然存活,实现方式有3种:串口、单播(ucast)和多播(mcast)。如果在一段时间内获取不到对方的信号,就认为对方已经down掉了。

HeartBeat用于搭建双机热备环境,可以通过专门的心跳线来连接双机,也可以通过普通的网线来连接。

2、准备

heartbeat、libnet软件包可以到如下网址下载:

heartbeat:

/download/

/lha-2.1/archive/2 will give you the 2.1.4 release.

libnet

/libnet/dist/ 版本 1.1.2.1

/unix/privat/

libnet包可以在/linux/rpm2html/ rpm包

3.安装

3.1. 准备

本试验环境共有2个主机,其IP分别为:

IP地址 主机名

192.168.7.100 (虚拟浮动ip)

192.168.7.191

real1

192.168.7.192

real2

10.10.10.1

real1

(用于做心跳)

10.10.10.2

real2

(用于做心跳)

如果/etc/hosts中没有配置的话, 需要配置/etc/hosts文件,添加:

192.168.7.191

real1

192.168.7.192

real2

10.10.10.1

real1

10.10.10.2

real2

3.2 创建用户和用户组

heartbeat需要haclient用户组和hacluster用户。

两个节点做同样的操作,并保证haclient和hacluster的ID一样。

groupadd haclient -g 600

useradd -g haclient hacluster -u 600

3.3. 安装

可以直接下载rpm包,或者自己下载源码包进行编译,在这里,我采用自己编译源码的方式。安装heartbeat前,需要先安装libnet包。

tar -xvzf

cd libnet

./configure

make

make install

tar -xvf

cd Heartbeat-STABLE-2-1-STABLE-2.1.4

./ConfigureMe configure

make

make install

同样地,在另一台主机上也是这么安装。

4、 配置

cat /etc/ha.d/

You need three configuration files to make heartbeat happy,

and they all go in this directory.

They are:

Main configuration file

haresources Resource configuration file

authkeys Authentication information

These first two may be readable by everyone, but the authkeys file must not be.

这些文件除有一处区别外,另外两个文件在每台机器都要保持一致.

cp /usr/share/doc/heartbeat-2.1.4/ /etc/ha.d

cp /usr/share/doc/heartbeat-2.1.4/haresources /etc/ha.d

cp /usr/share/doc/heartbeat-2.1.4/authkeys /etc/ha.d

4.1 编辑hertbeat主配置文件。

以下是需要打开的配置,里面有详细说明。

vi /etc/ha.d/

#logfile /var/log/ha-log #File to write other messages to

logfacility local0

#这个是设置heartbeat的日志,这里是用的系统日志,如禁止写入系统日志,应设置为none

keepalive 2

#设定心跳(监测)时间时间为2秒

warntime 10

#连续多长时间联系不上后开始警告提示

deadtime 20

#连续多长时间联系不上后,立即切换服务

initdead 120

#这里主要是给重启后预留的一段忽略时间段(比如:重启后,网络还没通,keepalive检测肯定通不过,但这时候并不切换)bcast eth1

#心跳所使用的网络接口,采用eth0的udp广播用来发送心跳信息。

ucast eth1 10.10.10.2

#采用网卡eth0的udp单播来通知心跳,ip应为对方IP。

udpport 694

#使用udp端口694 进行心跳监测

auto_failback on

#恢复正常后是否需要再自动切换回来。

node real1 real2

ping

#通过ping google来监测心跳是否正常,note: don't use a cluster node as ping node 。ping指令以及下面的ping_group指令是用于建立伪集群成员,它们必须与下述#的ipfail指令一起使用,它们的作用是监测物理链路,也就是说如果集群节点与上述伪设备不相通,那么该节点也将无权接管资源或服务,它将释放掉资源。

#是否采用v2 style模式,在三节点以上时一定要打开,CRM, Cluster Resouce Manager, 用于在cluster计算管理资源。开启了它,就开启了2.0的新功能

#crm yes

4.2 编辑双机互联验证文件:authkeys

authkeys决定了您的认证密钥。共有三种认证方式:crc,md5,和sha1。 如果您的Heartbeat运行于安全网络之上,如本例中的交叉线(串口),可以使用crc,从资源的角度来看,这是代价最低的方法。如果网络并不安全,但您也希望降低CPU使用,则使用md5。最后,如果您想得到最好的认证,而不考虑CPU使用情况,则使用sha1,它在三者之中最难破解。

文件格式如下:

auth

[]

vi /etc/ha.d/authkeys

auth 1

1 crc

chmod 600 /etc/ha.d/authkeys

注意authkeys的权限一定要是600.

4.3 编辑集群资源文件:haresources

该文件列出集群所提供的服务以及服务的默认所有者。 注意:两个集群节点上的该文件必须相同。集群的IP地址是该选项是必须配置的,不能在haresources文件以外配置该地址, haresources文件用于指定双机系统的主节点、集群IP、子网掩码、广播地址以及启动的服务等。其配置语句格式如下:

node-name network-config

其中node-name指定双机系统的主节点,取值必须匹配文件中node选项设置的主机名中的一个,node选项设置的另一个主机名成为从节点。network-config用于网络设置,包括指定集群IP、子网掩码、广播地址等。resource-group用于设置heartbeat启动的服务,该服务最终由双机系统通过集群IP对外提供。

vi /etc/ha.d/haresources

real1 IPaddr::192.168.7.100/24/eth0 nginx

如果包含挂载共享存储,可以用类似下面的资源

real1 IPaddr::192.168.7.100/24/eth0 Filesystem::192.168.7.121:/home/www::/var/www/html/::nfs nginx

这句话意思是 主服务器的主机名 虚拟服务器的浮动ip地址 存储服务器NFS的源到挂载的目的 启动heartbeat顺便还要启动的服务。

有几个注意事项:

1).资源组的第一列是我们在配置文件中的node之一,而且应该是当前准备作为primary节点的那一个node。

2).每一行代表一个资源组,如果一行写不下可以用" "换行

3).资源组启动顺序是从左往右,关闭的顺序是从右往左

4).脚本的参数通过::来分隔和传递

5).一个资源组里面不同资源之间以空格分隔

6).不同的资源组之间没有必然关系

7).每个资源都是一个脚本,可以是在/etc/init.d目录下面的,也可以是/etc/ha.d/resource.d目录下面的角本。这些脚本必须要支持xxx start;xxx stop;模式。

8).关于service IP的资源设置格式详见haresources文件。

9).如果mysql是编译安装的话, 则需要修改/etc/init.d/mysql文件中的basedir和datadir两个参数

后面的资源组resource1 resource2 …resourceN中每一个资源都是一个shell脚本,它们的搜索路径为/etc/init.d/和/usr/local/etc/ha.d/resource.d(该路径根据你所安装heartbeat的路径有所不同),heartbeat为我们提供了一个非常好的资源扩展框架,如果我们需要控制一种自己的资源,只需要实现一个支持start和stop参数的shell脚本就可以了,目前heartbeat所支持的资源脚本可以在我提供的上述路径中去查看。

4.4 资源角本例子---drbd

下面是drbd的资源管理角本的例子:

vi /etc/ha.d/resource.d/drbd

#!/bin/sh

case "$1" in

start)

#声明为drbd的primary节点

drbdadm primary db

#挂载文件系统

mount /dev/drbd0 /data

#启动相关服务

service mysql start

;;

stop)

#上面操作的反向

service mysql stop

umount /dev/drbd0 /data

drbdadm secondary db

;;esac

exit 0

4.5 传送配置文件到另一台主机

scp -r /etc/ha.d/ 192.168.7.192:

注意:传送成功后需要修改 ucast eth0 10.10.10.2。

5. 测试

测试切换不外乎以下几种:1).手工调用heartbeat的节点切换脚本

2).拔掉网线,测试在primary节点的网络断开后的切换情况,通过测试,在拔掉网线后,当主节点发现无法和standby节点无法通信后,会在log中记录warn信息,如果延续时间达到在中设定的时长后,会开始释放资源,standby节点发现无法和主节点通信一段时间(设定)后,开始尝试启动资源并将自己active成primary节点。切换过程除中设定的时长之外的时间段同样非常短。这里容易出现custer脑分裂的问题。如果采用双master的话,就不存在这个问题。

3). shutdown primary主机,测试是否能够正常切换。4). 主节点机器掉电,是否能够正常切换。

第一种和第三种测试方法一定要测一下。

6.管理

启动和关闭:

/etc/init.d/hearbeat start

/etc/init.d/hearbeat stop

手工切换:

[root@real1 sbin]# /usr/share/heartbeat/hb_standby

2008/11/10_15:21:15 Going standby [all]

[root@real1 sbin]# service heartbeat status

heartbeat OK [pid 27224 et al] is running on real1 [real1]..

手工接管

[root@real2 logs]# /usr/share/heartbeat/hb_takeover

查看heartbeat状态

[root@real2 logs]# service heartbeat status

heartbeat OK [pid 22600 et al] is running on real2 [real2]....

另 关于CRM 及heartbeat 2的新特性,有时间再研究

ipfail已经在2以上的版本上不用了

pingd is a replacement for ipfail that like the rest of version 2 allows for connectivity (and resource placement based on

relative connectivity) to work in clusters with any number of nodes.

2.1) Heartbeat 1.x的特性

Heartbeat1.x允许集群节点和资源通过/etc/ha.d目录下面的两个文件来配置

:定义集群节点,失效检测和切换时间间隔,集群时间日志机制和节点Fence方法

haresources: 定义集群资源组,每一行定义可以一起进行失效切换的一个默认的节点和一组资源,资源包括IP地址,文件系统,服务或者应

2.2) Heartbeat 2.0的特性

Heartbeat 2.0 即支持基于Heartbeat1.x 的配置(仅限于2个节点)又支持模块结构的配置方法-集群资源管理器(Cluster Rescource

Manager-CRM).

CRM模型可以支持最多16个节点,这个模型使用基于XML的集群信息(Cluster Information Base-CIB)配置。CIB文件

(/var/lib/heartbeat/crm/)会在各个节点间自动复制,它定义了下面的对象和动作:

*集群节点

*集群资源,包括属性,优先级,组和依赖性

*日志,监控,仲裁和fence标准

*当服务失败或者其中设定的标准满足时,需要执行的动作

现在ip也是服务的一种,可以start, stop,所以和其他服务一样处理,比较方便。

一) 前言:

网上关于heartbeat的文章很多,但大部分是基于1.x style的,

我把我配置的2.x style的heartbeat 过程发出来,

希望对大家能有一点用,

2.x和1.x最主要的区别在于,

1) 2.x支持CRM管理,资源文件由原来的haresources变为,

2) 支持OCF格式的resource agent,

3) 可以对多资源组进行独立监控(这点我不确定在1.x里是否可以,没试过)

4)支持多节点

二) 配置

本文假设原有的heartbeat 已经配置好且能正常工作,

如和配置heartbeat不属于本文讨论范围.

我这里以两节点为例:

node1 和node2,

有两个资源作HA,apache和jboss,

其中apache使用vip :192.168.1.205,

jboss无vip,

1)在里面增加

crm yes

apiauth cibmon uid=hacluster

respawn hacluster /usr/local/lib/heartbeat/cibmon -d

2)将haresources资源文件转换成,2.x里编译好后自带有转换脚本,很方便.

假设haresources文件如下,

node1 192.168.1.205

node2

每一行表示一个资源组,

node1,node2表示prefered node,即该资源组优先在该node上运行,

192.168.1.205与一起属于第一个资源组,为提供http服务的vip,

启动的时候从左到右依次运行脚本,关闭的时候从右到左依次关闭.

转换命令

/usr/lib/heartbeat/

输出文件在/var/lib/heartbeat/crm/

ocf格式的启动角本在/usr/lib/ocf/resource.d/heartbeat(也许你的机器上目录不是这个,可以搜索ocf来查找)

lsb格式的启动角本在/usr/lib/lsb/resource.d/heartbeat目录下。

3)

修改heartbeat目录权限,可以用以下命令:

find / -type d -name "heartbeat" -exec chown -R hacluster {} ;

find / -type d -name "heartbeat" -exec chgrp -R haclient {} ;

chown -R nt

/var/run/heartbeat

/var/lib/heartbeat

/usr/share/heartbeat

/usr/include/heartbeat

/usr/lib/heartbeat

/usr/lib/ocf/resource.d/heartbeat

4 )LSB格式的resource agent script中必须支持status功能所谓的resource agent就是服务的启动脚本,这我这里叫,runjboss等,必须能接收start,stop,status,三个参数,如果是OCF格式agent,则必须支持start,stop,monitor三个参数.其中status和monitor参数是用来监控资源的,非常重要.

例如LSB风格的脚本,运行./ status时候,

返回值包含OK或则running则表示资源正常

返回值包含stopped或者No则表示资源不正常。

假如是OCF风格的脚本,运行./ monitor时候,

返回0表示资源是正常的,

返回7表示资源出现问题.


本文标签: 资源 服务 节点