#################################################################
#################################################################
开篇引题

直接上图,有图有真相啊!此图是MFS网络组成和运行原理,先不说图中每种角色的作用(下文会有详细说明),直观信息告诉我们客户端无论是读写请求都需要与MasterServer通信,而图中MasterServer角色只有一个,因此单点故障的因素就显而易见了。解决MFS的单点故障正是本文的初衷,接下来就介绍如何利用多种技术解决MFS的单点故障,实现MasterServer的高可用。
Distributed Replicated Block Device

分布式复制块设备是Linux内核的存储层中的一个分布式存储系统,可利用DRBD在两台Linux服务器之间共享块设备、文件系统和数据,类似于一个网络RAID1的功能,内核中的DRBD模块监听特定套接字上,复制系统调用产生的写数据为副本并通过TCP协议发送至DRBD从节点,因为节点间磁盘设备每一个数据位都是相同的,所以DRBD可以实现廉价块级别的数据共享。
DRBD工作模型
主从模型(primary/secondary),同一时刻只能有一个节点提供服务(否则会产生脑裂),从节点无法使用磁盘分区(挂载也不可以)。
主主模型(primary/primary),需要借助于集群文件系统并启用分布式文件锁功能,而且写性能不会有提升.
DRBD管理
内核模块:drbd用户空间
管理工具:drbdadm,drbdsetup,drbdmeta
工作流程(默认模型是Sync)
Async:副本交于本地TCP/IP协议栈就返回(性能最高)
SemiSync:副本交对方TCP/IP协议栈就返回(折中方案)
Sync:副本被secondary存储到磁盘中就返回(性能差)
安装配置DRBD(drbd内核模块必须和内核版本完全匹配)
1
|
rpm -ivh drbd-8.4.3-33.el6.x86_64.rpm drbd-kmdl-2.6.32-358.el6-8.4.3-33.el6.x86_64.rpm
|
主配置文件
1
2
3
4
|
[root@one packages]
include "drbd.d/global_common.conf" ;
include "drbd.d/*.res" ;
|
全局配置文件
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
|
cat /etc/drbd .d /global_common .conf
global {
usage-count yes ;
}
common {
handlers {
pri-on-incon-degr "/usr/lib/drbd/notify-pri-on-incon-degr.sh; /usr/lib/drbd/notify-emergency-reboot.sh; echo b > /proc/sysrq-trigger ; reboot -f" ;
pri-lost-after-sb "/usr/lib/drbd/notify-pri-lost-after-sb.sh; /usr/lib/drbd/notify-emergency-reboot.sh; echo b > /proc/sysrq-trigger ; reboot -f" ;
local -io-error "/usr/lib/drbd/notify-io-error.sh; /usr/lib/drbd/notify-emergency-shutdown.sh; echo o > /proc/sysrq-trigger ; halt -f" ;
}
startup {
}
options {
}
disk {
on-io-error detach;
}
net {
cram-hmac-alg "sha1" ;
shared-secret "soulboy" ;
}
syncer {
rate 1000M;
}
}
|
定义资源mfs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
|
[root@one packages]
resource mydata {
on one.soulboy.com {
device /dev/drbd0 ;
disk /dev/sdb2 ;
address 192.168.1.61:7789;
meta-disk internal;
}
on two.soulboy.com {
device /dev/drbd0 ;
disk /dev/sdb1 ;
address 192.168.1.62:7789;
meta-disk internal;
}
}
resource mfs {
on one.soulboy.com {
device /dev/drbd1 ;
disk /dev/sdb3 ;
address 192.168.1.61:7788;
meta-disk internal;
}
on two.soulboy.com {
device /dev/drbd1 ;
disk /dev/sdb2 ;
address 192.168.1.62:7788;
meta-disk internal;
}
}
|
同步配置文件到从节点
1
|
scp /etc/drbd .d/* two.soulboy.com: /etc/drbd .d/
|
初始化资源(分别在两个节点上执行)
启动资源(分别在两个节点上执行)
将某节点变为主节点(192.168.1.61为主节点)
1
|
drbdadm primary --force mydata
|
查看状态确定同步完毕
1
2
|
[root@one packages]
1:mfs Connected Primary /Secondary UpToDate /UpToDate C /mfs ext4
|
格式化文件系统(在主节点)
1
|
mke2fs -t ext4 /dev/drbd1
|
允许对方抢占(分别在两节点上执行)
开机不要自动启动
部署MFS
MFS工作原理
MFS文件系统能够实现RAID功能,节约成本,不逊色于专业的存储系统,可以实现在线扩容。
MFS的四种角色
MasterServer(元数据服务器):负责管理各个ChunkServer及调度文件读写,回收文件空间及恢复多节点拷贝。
Metalogger(元数据日志服务器):负责备份管理服务器的变化日志文件。
ChunkServer(数据存储服务器):真正存储用户数据的服务器,将文件切块相互同步,听从MasterServer的调度为Client提供数据传输,Chunk节点数量越多,可靠性和MFS可用的磁盘空间就会越大。
Client(客户端):客户端通过fuse内核接口远程管理服务器上所管理的数据存储服务器,和使用本地文件系统一样。
安装配置元数据服务
1
2
3
4
5
6
7
8
9
10
11
12
|
mount /dev/drbd1 /mfs
groupadd -g 1000 mfs
useradd -u 1000 -g mfs -s /sbin/nologin mfs
mkdir -pv /mfs
chown -R mfs.mfs /mfs
tar xf mfs-1.6.26. tar .gz
cd mfs-1.6.26
. /configure --prefix= /mfs --with-default-user=mfs --with-default-group=mfs
make && make install
cp /mfs/etc/mfsmaster .cfg.dist /mfs/etc/mfsmaster .cfg
cp /mfs/etc/mfsexports .cfg.dist /mfs/etc/mfsexports .cfg
cp /mfs/var/mfs/metadata .mfs.empty /mfs/var/mfs/metadata .mfs
|
主配置文件
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
|
vim /mfs/etc/mfsmaster .cfg
|
目录挂载控制文件
1
2
3
4
|
vim /mfs/etc/mfsexports .cfg
* . rw
* / rw,alldirs,maproot=0
客户端IP 被挂载目录 客户端拥有的权限
|
为MasterServer提供lsb格式启动脚本
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
|
cat /etc/init .d /mfsmaster
. /etc/rc .d /init .d /functions
. /etc/sysconfig/network
path= "/mfs/sbin"
[ "${NETWORKING}" = "no" ] && exit 0
start() {
$path /mfsmaster start
$path /mfscgiserv start
}
stop() {
$path /mfsmaster stop
$path /mfscgiserv start
}
restart() {
$path /mfsmaster restart
$path /mfscgiserv restart
}
status() {
$path /mfsmaster test
$path /mfscgiserv test
}
case "$1" in
start)
start
;;
stop)
stop
;;
restart)
restart
;;
status)
status
;;
*)
echo $ "Usage: $0 start|stop|restart|status"
exit 1
esac
exit 0
|
修改权限
1
|
chmod 755 /etc/init .d /mfsmaster
|
导出命令
1
2
|
echo 'export PATH=$PATH:/mfs/sbin' > /etc/profile .d /mfs .sh
. /etc/profile .d /mfs .sh
|
同步启动脚本至从节点
1
|
scp -p /etc/init .d /mfsmaster two: /etc/init .d/
|
关闭服务卸载drbd设备
1
2
|
service mfsmaster stop
umount /dev/drbd1
|
部署Corosync+Pacemaker

Corosync是集群管理套件的一部分,它在传递信息的时候可以通过一个简单的配置文件来定义信息传递的方式和协议等,RHCS集群套件就是基于corosync实现。但corosync只提供了message layer的能力。集群的资源管理则需要Pacemaker,其管理接口有两个分别是crmsh和pcs。
环境准备
service NetworkManager stop
时间同
主机名称解析的结果等于uname -n
安装(pacemaker作为corosync的插件运行)
1
|
yum install -y corosync pacemaker
|
资源管理器配置接口基于crmsh
1
|
yum install -y crmsh-1.2.6-4.el6.x86_64.rpm pssh-2.3.1-2.el6.x86_64.rpm
|
生成密钥
1
2
|
corosync-keygen
cp /etc/corosync/corosync .conf.example /etc/corosync/corosync .conf
|
配置文件
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
|
vim /etc/corosync/corosync .conf
compatibility: whitetank
totem {
version: 2
secauth: on
threads: 0
interface {
ringnumber: 0
bindnetaddr: 192.168.2.0
mcastaddr: 226.194.61.21
mcastport: 5405
ttl: 1
}
}
logging {
fileline: off
to_stderr: no
to_logfile: yes
to_syslog: no
logfile: /var/log/cluster/corosync .log
debug: off
timestamp: on
logger_subsys {
subsys: AMF
debug: off
}
}
amf {
mode: disabled
}
service {
ver: 0
name: pacemaker
}
aisexec {
user: root
group: root
}
|
复制配置文件到其他节点
1
|
scp -p /etc/corosync/corosync .conf /etc/corosync/authkey two.soulboy.com: /etc/corosync/
|
分别在两节点启动corosync服务
使用crmsh接口定义drbd资源(忽略法定票数、禁用stonith设备)
1
2
|
crm(live)configure
crm(live)configure
|
定义原始资源
1
2
3
4
5
|
crm(live)configure
crm(live)configure
crm(live)configure
crm(live)configure
crm(live)configure
|
定义colocation约束(资源运行在同一个节点上的偏好)
1
2
3
|
crm(live)configure
crm(live)configure
crm(live)configure
|
定义资源组(如果定义了资源组就没有必要定义colocation约束了)
定义order约束(资源启动和关闭的次序)
1
2
3
|
crm(live)configure
crm(live)configure
crm(live)configure
|
定义location约束(资源对节点的倾向性)
1
|
location mfsservice_prefer_one ha_mfsservice 500: one.soulboy.com
|
检查语法并保存
1
2
|
crm(live)configure
crm(live)configure
|
查看集群状态(发现资源都运行在主节点上)
1
2
3
4
5
6
7
8
9
|
[root@one packages]
crm(live)
Online: [ one.soulboy.com two.soulboy.com ]
Master /Slave Set: ms_mfs_drbd [mfs_drbd]
Masters: [ one.soulboy.com ]
Slaves: [ two.soulboy.com ]
mfsstore (ocf::heartbeat:Filesystem): Started one.soulboy.com
mfsserver (lsb:mfsmaster): Started one.soulboy.com
mfsip (ocf::heartbeat:IPaddr): Started one.soulboy.com
|
查看验证
1
2
3
4
5
6
7
8
9
|
[root@one ~]
1:mfs /0 Connected Primary /Secondary UpToDate /UpToDate C r----- /mfs ext4 5.0G 142M 4.6G 3%
[root@one ~]
mfsmaster pid: 13966
mfscgiserv pid:14158
[root@one ~]
inet 192.168.1.40 /24 brd 192.168.1.255 scope global secondary eth0
[root@one ~]
etc lost+found sbin share var
|
故障模拟测试
安装ChunkServer
1
2
3
4
5
6
7
|
useradd mfs -s /sbin/nologin
tar xf mfs-1.6.26. tar .gz
cd mfs-1.6.26
. /configure --prefix= /usr/local/mfs --with-default-user=mfs --with-default-group=mfs
make && make install
cp /usr/local/mfs/etc/mfschunkserver .cfg.dist /usr/local/mfs/etc/mfschunkserver .cfg
cp /usr/local/mfs/etc/mfshdd .cfg.dist /usr/local/mfs/etc/mfshdd .cfg
|
主配置文件
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
|
vim /usr/local/mfs/etc/mfschunkserver .cfg
MASTER_HOST = 192.168.1.40
MASTER_PORT = 9420
|
磁盘空间配置文件
1
2
|
vim /usr/local/mfs/etc/mfshdd .cfg
/data
|
修改权限并启动服务
1
2
|
chown -R mfs:mfs /data
mfschunkserver start
|
Client编译安装
MFS客户端依赖于fuse
1
2
3
4
5
6
7
8
|
tar xf fuse-2.9.2. tar .gz
cd fuse-2.9.2
. /configure
make && make install
vim /etc/profile
export PKG_CONFIG_PATH= /usr/local/lib/pkgconfig :$PKG_CONFIG_PATH
source /etc/profile
export PKG_CONFIG_PATH= /usr/local/lib/pkgconfig :$PKG_CONFIG_PATH
|
安装MFS客户端
1
2
3
4
5
6
|
useradd mfs -s /sbin/nologin
tar xf mfs-1.6.26. tar .gz
cd mfs-1.6.26
. /configure --prefix= /usr/local/mfs --with-default-user=mfs --with-default-group=mfs -- enable -mfsmount
make && make install
modprobe fuse
|
挂载MFS文件系统
1
2
|
mkdir /webdata
/usr/local/mfs/bin/mfsmount /webdata -H 192.168.1.40
|
挂载MFSMeta文件系统
1
2
|
mkdir /webdatameta
/usr/local/mfs/bin/mfsmount -m /webdatameta -H 192.168.1.40
|
client创建文件并查看信息(正常)
1
2
3
4
5
6
|
[root@five /]
[root@five /]
/webdata/one :
chunk 0: 0000000000000006_00000001 / ( id :6 ver:1)
copy 1: 192.168.1.50:9422
copy 2: 192.168.1.64:9422
|
登录web管理控制台(正常)

模拟主节点故障
1
2
3
4
5
6
7
8
9
10
11
|
crm(live)node
crm(live)node
crm(live)node
crm(live)
Online: [ one.soulboy.com two.soulboy.com ]
Master /Slave Set: ms_mfs_drbd [mfs_drbd]
Masters: [ two.soulboy.com ]
Slaves: [ one.soulboy.com ]
mfsstore (ocf::heartbeat:Filesystem): Started two.soulboy.com
mfsserver (lsb:mfsmaster): Started two.soulboy.com
mfsip (ocf::heartbeat:IPaddr): Started two.soulboy.com
|
client再次创建文件并查看副本数(正常)
1
2
3
4
5
6
|
[root@five /]
[root@five /]
/webdata/two :
chunk 0: 0000000000000007_00000001 / ( id :7 ver:1)
copy 1: 192.168.1.50:9422
copy 2: 192.168.1.64:9422
|
再次登录web管理控制台(正常)

补充和总结
解决MFS单点故障的主要思路是将MasterServer安装在drbd设备目录中,通过corosync+pacemaker将drbd、vip、mount、mfsmaster资源粘合在一起,并通过colocation和order的约束保证了资源间依赖关系和启动次序,此外mfsmaster的启动在pacemaker中定义为lsb风格RA,也就是形如/etc/init.d/目录下的sysv风格的脚本。值得一提的是pacemaker的管理接口,本文中使用的是crmsh,而pcs接口有着比crmsh更强大的功能,可以实现管理集群整个生命周期,支持节点的添加、移除、启动、关闭等操作。
实现mysql的高可用也可以通过本文这种思路实现,具体步骤可参考本文,这里补充下pcs接口的用法,方便读者做对比。
1
2
3
4
5
6
7
8
9
|
pcs resource create myvip ocf:heartbeat:IPaddr params ip=192.168.1.70 op monitor interval=20 timeout=20 on-fail=restart
pcs resource create mystore ocf:heartbeat:Filesystem params device= "192.168.1.50:/mysqldata" directory= "/mydata" fstype= "nfs" op monitor interval=40 timeout=40 on-fail=restart op start timeout=60 op stop timeout=60
pcs resource create mysqlserver lsb:mysqld op monitor interval=20 timeout=20 on-fail=restart
pcs resource group add mysqlservice myvip mystore mysqlserver
pcs constraint location mysqlservice prefers two.soulboy.com=500
pcs constraint order start myvip then start mystore
pcs constraint order start mystore then start mysqlserver
pcs constraint colocation add myvip mystore
pcs constraint colocation add mystore mysqlserver
|
实现mfs的高可用也可以通过heartbeat+drbd来实现,思路和本文类似,已经大牛撰写,文章内容优质,请参考: qzhijun的BLOG
本文转自 ftmoonfans 51CTO博客,原文链接:http://blog.51cto.com/soulboy/1393114