|
1.方案簡(jiǎn)介 本方案采用Heartbeat雙機(jī)熱備軟件來(lái)保證數(shù)據(jù)庫(kù)的高穩(wěn)定性和連續(xù)性,數(shù)據(jù)的一致性由DRBD這個(gè)工具來(lái)保證。默認(rèn)情況下只有一臺(tái)mysql在工作,當(dāng)主mysql服務(wù)器出現(xiàn)問(wèn)題后,系統(tǒng)將自動(dòng)切換到備機(jī)上繼續(xù)提供服務(wù),當(dāng)主數(shù)據(jù)庫(kù)修復(fù)完畢,又將服務(wù)切回繼續(xù)由主mysql提供服務(wù)。 2.方案優(yōu)缺點(diǎn) 優(yōu)點(diǎn):安全性高、穩(wěn)定性高、可用性高,出現(xiàn)故障自動(dòng)切換。 缺點(diǎn):只有一臺(tái)服務(wù)器提供服務(wù),成本相對(duì)較高,不方便擴(kuò)展,可能會(huì)發(fā)生腦裂。 3.軟件介紹 Heartbeat介紹 官方站點(diǎn):http:///wiki/Main_Page heartbeat可以資源(VIP地址及程序服務(wù))從一臺(tái)有故障的服務(wù)器快速的轉(zhuǎn)移到另一臺(tái)正常的服務(wù)器提供服務(wù),heartbeat和keepalived相似,heartbeat可以實(shí)現(xiàn)failover功能,但不能實(shí)現(xiàn)對(duì)后端的健康檢查 DRBD介紹 官方站點(diǎn):http://www./ DRBD(DistributedReplicatedBlockDevice)是一個(gè)基于塊設(shè)備級(jí)別在遠(yuǎn)程服務(wù)器直接同步和鏡像數(shù)據(jù)的軟件,用軟件實(shí)現(xiàn)的、無(wú)共享的、服務(wù)器之間鏡像塊設(shè)備內(nèi)容的存儲(chǔ)復(fù)制解決方案。它可以實(shí)現(xiàn)在網(wǎng)絡(luò)中兩臺(tái)服務(wù)器之間基于塊設(shè)備級(jí)別的實(shí)時(shí)鏡像或同步復(fù)制(兩臺(tái)服務(wù)器都寫入成功)/異步復(fù)制(本地服務(wù)器寫入成功),相當(dāng)于網(wǎng)絡(luò)的RAID1,由于是基于塊設(shè)備(磁盤,LVM邏輯卷),在文件系統(tǒng)的底層,所以數(shù)據(jù)復(fù)制要比cp命令更快。DRBD已經(jīng)被MySQL官方寫入文檔手冊(cè)作為推薦的高可用的方案之一 4.方案拓?fù)?/strong>
5.方案適用場(chǎng)景: 適用于數(shù)據(jù)庫(kù)訪問(wèn)量不太大,短期內(nèi)訪問(wèn)量增長(zhǎng)不會(huì)太快,對(duì)數(shù)據(jù)庫(kù)可用性要求非常高的場(chǎng)景。 6.測(cè)試環(huán)境介紹(如下所示,均已關(guān)閉防火墻及selinux,生產(chǎn)環(huán)境自行開放端口) 主機(jī)名 ip 系統(tǒng) DRBD磁盤 heartbeat版本 db-server-01 192.168.0.10 centos6.2 64bit /dev/sda5 3.0.4 db-server-02 192.168.0.20 centos6.2 64bit /dev/sda5 3.0.4 7.軟件安裝以及環(huán)境配置 (1)安裝drbd依賴組件(兩臺(tái)機(jī)器,安裝以后重啟系統(tǒng),因?yàn)闀?huì)升級(jí)內(nèi)核版本,不重啟會(huì)對(duì)不上內(nèi)核版本,有知道不用重啟的童鞋請(qǐng)給我留言^_^): yum install -y kernel kernel-devel kernel-headers flex (2)下載軟件安裝(兩臺(tái)機(jī)器操作一樣) wget http://oss.linbit.com/drbd/8.4/drbd-8.4.2.tar.gz tar xf drbd-8.4.2.tar.gz cd drbd-8.4.2 ./configure --prefix=/usr/local/drbd --with-km make KDIR=/usr/src/kernels/2.6.32-431.11.2.el6.x86_64/ #很多童鞋無(wú)法加載drbd模塊,多半是正在運(yùn)行的內(nèi)核版本和新安裝的不相符 make install mkdir -p /usr/local/drbd/var/run/drbd cp /usr/local/drbd/etc/rc.d/init.d/drbd /etc/rc.d/init.d chmod 755 /etc/init.d/drbd cd drbd make clean make KDIR=/usr/src/kernels/2.6.32-431.11.2.el6.x86_64/ cp drbd.ko /lib/modules/`uname -r`/kernel/lib/ modprobe drbd 檢查是否加載了drbd模塊 [root@192.168.0.10 ~]# lsmod | grep drbd drbd 314246 0 libcrc32c 1246 1 drbd [root@192.168.0.10 ~]# (3)DRBD配置(配置之前需要先使用fdisk對(duì) /dev/sda進(jìn)行分區(qū)) [root@192.168.0.10 ~]# df -HT Filesystem Type Size Used Avail Use% Mounted on /dev/sda2 ext4 19G 2.6G 16G 15% / tmpfs tmpfs 121M 0 121M 0% /dev/shm /dev/sda1 ext4 204M 52M 141M 27% /boot /dev/sda5 ext4 34G 185M 32G 1% /data [root@192.168.0.10 ~]# 我這里兩臺(tái)機(jī)器之前都已經(jīng)分區(qū)了,由于是自己筆記本上的虛擬機(jī),所以懶得加磁盤了,我直接把 /data/卸載,然后格式化/dev/sda5,我兩臺(tái)機(jī)器都這樣操作,如果你有空的磁盤,照樣需要進(jìn)行分區(qū),比如可以將一個(gè)1T的盤分一個(gè)區(qū)就行了。 [root@192.168.0.10 ~]# umount /data/ [root@192.168.0.10 ~]# mkfs.ext4 /dev/sda5 mke2fs 1.41.12 (17-May-2010) Filesystem label= OS type: Linux Block size=4096 (log=2) Fragment size=4096 (log=2) Stride=0 blocks, Stripe width=0 blocks 2048000 inodes, 8185344 blocks 409267 blocks (5.00%) reserved for the super user First data block=0 Maximum filesystem blocks=4294967296 250 block groups 32768 blocks per group, 32768 fragments per group 8192 inodes per group Superblock backups stored on blocks: 32768, 98304, 163840, 229376, 294912, 819200, 884736, 1605632, 2654208, 4096000, 7962624 Writing inode tables: done Creating journal (32768 blocks): done Writing superblocks and filesystem accounting information: done This filesystem will be automatically checked every 28 mounts or 180 days, whichever comes first. Use tune2fs -c or -i to override. [root@192.168.0.10 ~]# [root@192.168.0.10 ~]# fdisk -l Disk /dev/sda: 53.7 GB, 53687091200 bytes 255 heads, 63 sectors/track, 6527 cylinders Units = cylinders of 16065 * 512 = 8225280 bytes Sector size (logical/physical): 512 bytes / 512 bytes I/O size (minimum/optimal): 512 bytes / 512 bytes Disk identifier: 0x000eb0ff Device Boot Start End Blocks Id System /dev/sda1 * 1 26 204800 83 Linux Partition 1 does not end on cylinder boundary. /dev/sda2 26 2321 18432000 83 Linux /dev/sda3 2321 2451 1048576 82 Linux swap / Solaris /dev/sda4 2451 6528 32742400 5 Extended /dev/sda5 2451 6528 32741376 83 Linux [root@192.168.0.10 ~]# 我這里還要在/etc/fstab里面注釋一項(xiàng): #UUID=33958004-e8a7-4135-844f-707a5537e86a /data ext4 defaults 1 2 否則重啟機(jī)器的時(shí)候提示無(wú)法掛載,會(huì)無(wú)法啟動(dòng)的。 修改/etc/hosts文件,兩臺(tái)服務(wù)器操作一樣。 192.168.0.10 db-server-01 192.168.0.20 db-server-02 drbd配置只需要修改/usr/local/drbd/etc/drbd.d/global_common.conf配置文件即可,修改后如下(兩臺(tái)服務(wù)器配置一樣): [root@192.168.0.10 ~]# cat /usr/local/drbd/etc/drbd.d/global_common.conf global { usage-count yes; } common { syncer { rate 30M; } } #同步速率,視帶寬而定 resource r0 { #創(chuàng)建一個(gè)資源,名字叫"r0" protocol C; #選擇的是drbd的C 協(xié)議(數(shù)據(jù)同步協(xié)議,C為收到數(shù)據(jù)并寫入后返回,確認(rèn)成功) startup { } disk { on-io-error detach; } net { } on db-server-01 { #設(shè)定一個(gè)節(jié)點(diǎn),分別以各自的主機(jī)名命名 device /dev/drbd0; #設(shè)定資源設(shè)備/dev/drbd0 指向?qū)嶋H的物理分區(qū) /dev/sda5 disk /dev/sda5; address 192.168.0.10:7888; #設(shè)定監(jiān)聽地址以及端口 meta-disk internal; } on db-server-02 { device /dev/drbd0; disk /dev/sda5; address 192.168.0.20:7888; meta-disk internal; #internal表示是在同一個(gè)局域網(wǎng)內(nèi) } } [root@192.168.0.10 ~]# (4)DRBD的管理與維護(hù): 創(chuàng)建DRBD資源 配置好drbd以后,就需要使用命令創(chuàng)建配置的drbd資源,使用如下命令(兩臺(tái)服務(wù)器操作一樣): [root@192.168.0.10 ~]# dd if=/dev/zero of=/dev/sda5 bs=1M count=100 #不這樣做的話,在創(chuàng)建資源的時(shí)候報(bào)錯(cuò) 100+0 records in 100+0 records out 104857600 bytes (105 MB) copied, 3.34339 s, 31.4 MB/s [root@192.168.0.10 ~]# [root@192.168.0.10 ~]# drbdadm create-md r0 Writing meta data... initializing activity log NOT initializing bitmap New drbd meta data block successfully created. success [root@192.168.0.10 ~]# (5)DRBD的啟動(dòng)與狀態(tài)查看(分別在兩臺(tái)服務(wù)器啟動(dòng)) [root@192.168.0.10 ~]# /etc/init.d/drbd start Starting DRBD resources: [ create res: r0 prepare disk: r0 adjust disk: r0 adjust net: r0 ] ..... [root@192.168.0.10 ~]# [root@192.168.0.20 ~]# /etc/init.d/drbd start Starting DRBD resources: [ create res: r0 prepare disk: r0 adjust disk: r0 adjust net: r0 ] . [root@192.168.0.20 ~]# 查看drbd的狀態(tài): [root@192.168.0.10 ~]# /etc/init.d/drbd status drbd driver loaded OK; device status: version: 8.4.2 (api:1/proto:86-101) GIT-hash: 7ad5f850d711223713d6dcadc3dd48860321070c build by root@db-server-01, 2014-04-18 21:15:57 m:res cs ro ds p mounted fstype 0:r0 Connected Secondary/Secondary Inconsistent/Inconsistent C [root@192.168.0.10 ~]# 可以看見都還沒有主節(jié)點(diǎn)。設(shè)置當(dāng)前節(jié)點(diǎn)(192.168.0.10)為主節(jié)點(diǎn),并進(jìn)行格式化和掛載 。 drbdadm -- --overwrite-data-of-peer primary all mkfs.ext4 /dev/drbd0 mkdir /data mount /dev/drbd0 /data/ 在另外一臺(tái)服務(wù)器創(chuàng)建掛載目錄,也創(chuàng)建/data [root@192.168.0.20 ~]# mkdir /data 查看一下drbd的狀態(tài)(可以看見還在同步): [root@192.168.0.10 ~]# /etc/init.d/drbd status drbd driver loaded OK; device status: version: 8.4.2 (api:1/proto:86-101) GIT-hash: 7ad5f850d711223713d6dcadc3dd48860321070c build by root@db-server-01, 2014-04-18 21:15:57 m:res cs ro ds p mounted fstype ... sync'ed: 13.7% (27596/31972)M 0:r0 SyncSource Primary/Secondary UpToDate/Inconsistent C /data ext4 [root@192.168.0.10 ~]# (6)mysql安裝,我這里為了簡(jiǎn)單直接安裝編譯好的二進(jìn)制軟件包(兩臺(tái)服務(wù)器都需要安裝,操作一樣,只是第二臺(tái)mysql不需要初始化數(shù)據(jù)) 注意:兩臺(tái)服務(wù)器上的mysql用戶的uid和gid要一樣。不然切換后會(huì)導(dǎo)致mysql數(shù)據(jù)目錄的屬主不正確而啟動(dòng)失敗。 [root@192.168.0.10 ~]# wget http://cdn.mysql.com/Downloads/MySQL-5.5/mysql-5.5.37-linux2.6-x86_64.tar.gz [root@192.168.0.10 ~]# tar xf mysql-5.5.37-linux2.6-x86_64.tar.gz -C /usr/local/ [root@192.168.0.10 ~]# cd /usr/local/ [root@192.168.0.10 local]# ln -s mysql-5.5.37-linux2.6-x86_64/ mysql [root@192.168.0.10 local]# groupadd mysql [root@192.168.0.10 local]# useradd -r -g mysql mysql [root@192.168.0.10 local]# cd mysql [root@192.168.0.10 mysql]# chown -R mysql . [root@192.168.0.10 mysql]# chgrp -R mysql . [root@192.168.0.10 mysql]# mkdir /data/mysql [root@192.168.0.10 mysql]# chown -R mysql.mysql /data/mysql/ [root@192.168.0.10 mysql]# /usr/local/mysql/scripts/mysql_install_db --user=mysql --datadir=/data/mysql/ --basedir=/usr/local/mysql [root@192.168.0.10 mysql]# chown -R root . [root@192.168.0.10 mysql]# cp support-files/my-medium.cnf /etc/my.cnf [root@192.168.0.10 mysql]# cp support-files/mysql.server /etc/init.d/mysqld [root@192.168.0.10 mysql]# chmod 755 /etc/init.d/mysqld [root@192.168.0.10 mysql]# egrep 'datadir|basedir' /etc/my.cnf #兩臺(tái)服務(wù)器上的mysql配置文件都加入這里的配置 datadir=/data/mysql basedir=/usr/local/mysql [root@192.168.0.10 mysql]# (7)手動(dòng)切換drbd的主從??戳硗庖慌_(tái)服務(wù)器是否有數(shù)據(jù)(自動(dòng)切換需要使用heartbeat,后面介紹): [root@192.168.0.10 ~]# ll /data/ total 20 drwx------ 2 root root 16384 Apr 18 22:16 lost+found drwxr-xr-x 5 mysql mysql 4096 Apr 18 23:01 mysql [root@192.168.0.10 ~]# [root@192.168.0.20 ~]# ll /data/ total 0 [root@192.168.0.20 ~]# [root@192.168.0.10 ~]# /etc/init.d/drbd status drbd driver loaded OK; device status: version: 8.4.2 (api:1/proto:86-101) GIT-hash: 7ad5f850d711223713d6dcadc3dd48860321070c build by root@db-server-01, 2014-04-18 21:15:57 m:res cs ro ds p mounted fstype 0:r0 Connected Primary/Secondary UpToDate/UpToDate C /data ext4 [root@192.168.0.10 ~]# 可以看見當(dāng)前服務(wù)器是主,也就是數(shù)據(jù)在這臺(tái)服務(wù)器上,另外一臺(tái)服務(wù)器是沒有數(shù)據(jù)的。下面進(jìn)行手動(dòng)切換 主切換成從,需要先卸載文件系統(tǒng),再執(zhí)行降級(jí)為從的命令: [root@192.168.0.10 ~]# umount /data/ [root@192.168.0.10 ~]# drbdadm secondary all 從切換成主,要先執(zhí)行升級(jí)成主的命令然后掛在文件系統(tǒng): [root@192.168.0.20 ~]# drbdadm primary all [root@192.168.0.20 ~]# mount /dev/drbd0 /data/ [root@192.168.0.20 ~]# ll /data/ total 20 drwx------ 2 root root 16384 Apr 18 22:16 lost+found drwxr-xr-x 5 mysql mysql 4096 Apr 18 23:01 mysql [root@192.168.0.20 ~]# /etc/init.d/drbd status drbd driver loaded OK; device status: version: 8.4.2 (api:1/proto:86-101) GIT-hash: 7ad5f850d711223713d6dcadc3dd48860321070c build by root@db-server-02, 2014-04-18 21:22:55 m:res cs ro ds p mounted fstype 0:r0 Connected Primary/Secondary UpToDate/UpToDate C /data ext4 [root@192.168.0.20 ~]# 可以看見已經(jīng)成功切換成主,并且mysql初始化數(shù)據(jù)也存在了。 DRBD腦裂后的處理 當(dāng)DRBD出現(xiàn)腦裂后,會(huì)導(dǎo)致drbd兩邊的磁盤數(shù)據(jù)不一致,在確定要作為從的節(jié)點(diǎn)上切換成secondary,并放棄該資源的數(shù)據(jù): drbdadm secondary r0 drbdadm -- --discard-my-data connect r0 在要作為primary的節(jié)點(diǎn)重新連接secondary(如果這個(gè)節(jié)點(diǎn)當(dāng)前的連接狀態(tài)為WFConnection的話,可以省略),使用如下命令連接: drbdadm connect r0 (8)Heartbeat安裝(兩臺(tái)服務(wù)器) 需要添加epel源,centos默認(rèn)自己沒有該軟件包,當(dāng)然你可以自己源碼編譯。 rpm -ivh http://dl.fedoraproject.org/pub/epel/6/x86_64/epel-release-6-8.noarch.rpm yum install heartbeat -y 創(chuàng)建DRBD腳本文件drbddisk:(兩臺(tái)服務(wù)器) 注意: 此處是一個(gè)大坑,因?yàn)槟J(rèn)yum安裝Heartbeat,不會(huì)在/etc/ha.d/resource.d/創(chuàng)建drbddisk腳本,估計(jì)是版本太新了吧。記得前兩年都不會(huì)這樣的。囧。而且也無(wú)法在安裝后從本地其他路徑找到該文件。此處也是因?yàn)閱?dòng)Heartbeat后無(wú)法PING通虛IP,最后通過(guò)查看/var/log/ha-log日志,找到一行ERROR: Cannot locate resource script drbddisk,然后進(jìn)而到/etc/ha.d/resource.d/路徑下發(fā)現(xiàn)竟然沒有drbddisk腳本,最后在google上找到該代碼,創(chuàng)建該腳本,終于測(cè)試通過(guò): [root@192.168.0.20 ~]# chmod 755 /etc/ha.d/resource.d/drbddisk [root@192.168.0.20 ~]# cat /etc/ha.d/resource.d/drbddisk #!/bin/bash # # This script is inteded to be used as resource script by heartbeat # # Copright 2003-2008 LINBIT Information Technologies # Philipp Reisner, Lars Ellenberg # ### DEFAULTFILE="/etc/default/drbd" DRBDADM="/sbin/drbdadm" if [ -f $DEFAULTFILE ]; then . $DEFAULTFILE fi if [ "$#" -eq 2 ]; then RES="$1" CMD="$2" else RES="all" CMD="$1" fi ## EXIT CODES # since this is a "legacy heartbeat R1 resource agent" script, # exit codes actually do not matter that much as long as we conform to # http://wiki./HeartbeatResourceAgent # but it does not hurt to conform to lsb init-script exit codes, # where we can. # http://refspecs.linux-foundation.org/LSB_3.1.0/ #LSB-Core-generic/LSB-Core-generic/iniscrptact.html #### drbd_set_role_from_proc_drbd() { local out if ! test -e /proc/drbd; then ROLE="Unconfigured" return fi dev=$( $DRBDADM sh-dev $RES ) minor=${dev#/dev/drbd} if [[ $minor = *[!0-9]* ]] ; then # sh-minor is only supported since drbd 8.3.1 minor=$( $DRBDADM sh-minor $RES ) fi if [[ -z $minor ]] || [[ $minor = *[!0-9]* ]] ; then ROLE=Unknown return fi if out=$(sed -ne "/^ *$minor: cs:/ { s/:/ /g; p; q; }" /proc/drbd); then set -- $out ROLE=${5%/**} : ${ROLE:=Unconfigured} # if it does not show up else ROLE=Unknown fi } case "$CMD" in start) # try several times, in case heartbeat deadtime # was smaller than drbd ping time try=6 while true; do $DRBDADM primary $RES && break let "--try" || exit 1 # LSB generic error sleep 1 done ;; stop) # heartbeat (haresources mode) will retry failed stop # for a number of times in addition to this internal retry. try=3 while true; do $DRBDADM secondary $RES && break # We used to lie here, and pretend success for anything != 11, # to avoid the reboot on failed stop recovery for "simple # config errors" and such. But that is incorrect. # Don't lie to your cluster manager. # And don't do config errors... let --try || exit 1 # LSB generic error sleep 1 done ;; status) if [ "$RES" = "all" ]; then echo "A resource name is required for status inquiries." exit 10 fi ST=$( $DRBDADM role $RES ) ROLE=${ST%/**} case $ROLE in Primary|Secondary|Unconfigured) # expected ;; *) # unexpected. whatever... # If we are unsure about the state of a resource, we need to # report it as possibly running, so heartbeat can, after failed # stop, do a recovery by reboot. # drbdsetup may fail for obscure reasons, e.g. if /var/lock/ is # suddenly readonly. So we retry by parsing /proc/drbd. drbd_set_role_from_proc_drbd esac case $ROLE in Primary) echo "running (Primary)" exit 0 # LSB status "service is OK" ;; Secondary|Unconfigured) echo "stopped ($ROLE)" exit 3 # LSB status "service is not running" ;; *) # NOTE the "running" in below message. # this is a "heartbeat" resource script, # the exit code is _ignored_. echo "cannot determine status, may be running ($ROLE)" exit 4 # LSB status "service status is unknown" ;; esac ;; *) echo "Usage: drbddisk [resource] {start|stop|status}" exit 1 ;; esac exit 0 [root@192.168.0.20 ~]# (9)heartbeat配置 Hearbeat的配置主要包括三個(gè)配置文件,authkeys,ha.cf和haresources的配置,下面就分別來(lái)看看: Authkerys的配置(兩臺(tái)服務(wù)器配置一樣) 這個(gè)文件用來(lái)配置密碼認(rèn)證方式,支持3種認(rèn)證方式,crc,md5和sha1,從左到右安全性越來(lái)越高,消耗的資源也越多。因此如果heartbeat運(yùn)行在安全的網(wǎng)路之上,比如私網(wǎng),那么可以將驗(yàn)證方式設(shè)置成crc,master和backup的authkeys配置一樣。我的authkeys文件配置如下: [root@192.168.0.10 ~]# cat /etc/ha.d/authkeys auth 1 1 crc [root@192.168.0.10 ~]# chmod 600 /etc/ha.d/authkeys 注意:該文件權(quán)限必須是600 ha.cf的配置(兩臺(tái)機(jī)器稍微有點(diǎn)區(qū)別),Primary(192.168.0.10)如下: [root@192.168.0.10 ~]# cat /etc/ha.d/ha.cf logfile /var/log/ha-log #定義Heartbeat的日志名字及位置 logfacility local0 keepalive 2 #設(shè)定心跳(監(jiān)測(cè))時(shí)間為2秒 deadtime 15 #設(shè)定死亡時(shí)間為15秒 ucast eth1 192.168.0.20 #采用單播的方式,IP地址指定為對(duì)方IP auto_failback off #當(dāng)Primary機(jī)器發(fā)生故障切換到Secondary機(jī)器后Primary恢復(fù)后是否進(jìn)行切回操作 (最好是我們有需求手動(dòng)進(jìn)行切換) node db-server-01 node db-server-02 [root@192.168.0.10 ~]# Secondary(192.168.0.20)如下: [root@192.168.0.20 ~]# cat /etc/ha.d/ha.cf logfile /var/log/ha-log #定義Heartbeat的日志名字及位置 logfacility local0 keepalive 2 #設(shè)定心跳(監(jiān)測(cè))時(shí)間為2秒 deadtime 15 #設(shè)定死亡時(shí)間為15秒 ucast eth1 192.168.0.10 #采用單播的方式,IP地址指定為對(duì)方IP auto_failback off #當(dāng)Primary機(jī)器發(fā)生故障切換到Secondary機(jī)器后Primary恢復(fù)后是否進(jìn)行切回操作(一般我們可以看需求,否則不用自動(dòng)切換) node db-server-01 node db-server-02 [root@192.168.0.20 ~]# haresources的配置(兩臺(tái)機(jī)器配置一樣): [root@192.168.0.10 ~]# cat /etc/ha.d/haresources db-server-01 IPaddr::192.168.0.88/24/eth1 drbddisk::r0 Filesystem::/dev/drbd0::/data::ext4 mysqld [root@192.168.0.10 ~]# 注:該文件內(nèi)IPaddr,Filesystem等腳本存放路徑在/etc/ha.d/resource.d/下,也可在該目錄下存放服務(wù)啟動(dòng)腳本(例如:mysqld),將相同腳本名稱添到/etc/ha.d/haresources內(nèi)容中,從而跟隨heartbeat啟動(dòng)而啟動(dòng)該腳本。 IPaddr::192.168.0.88/24/eth1:用IPaddr腳本配置浮動(dòng)VIP drbddisk::r0:用drbddisk腳本實(shí)現(xiàn)DRBD主從節(jié)點(diǎn)資源組的掛載和卸載 Filesystem::/dev/drbd0::/data::ext4:用Filesystem腳本實(shí)現(xiàn)磁盤掛載和卸載 (10)heartbeat的管理 配置好heartbeat之后,需要將mysql從自啟動(dòng)服務(wù)器中去掉,因?yàn)橹?span lang="EN-US">heartbeat啟動(dòng)的時(shí)候會(huì)掛載drdb文件系統(tǒng)以及啟動(dòng)mysql,切換的時(shí)候會(huì)將主上的mysql停止并卸載文件系統(tǒng),從上會(huì)掛載文件系統(tǒng),并啟動(dòng)mysql。因此需要做如下操作(兩臺(tái)服務(wù)器): [root@192.168.0.10 ~]# chkconfig mysqld off [root@192.168.0.10 ~]# chkconfig heartbeat off [root@192.168.0.10 ~]# chkconfig drbd off [root@192.168.0.10 ~]# cat /etc/rc.local #!/bin/sh # # This script will be executed *after* all the other init scripts. # You can put your own initialization stuff in here if you don't # want to do the full Sys V style init stuff. touch /var/lock/subsys/local modprobe drbd #必須先加載模塊,這也是因?yàn)閷?dòng)命令放在這里的原因 /etc/init.d/drbd start /etc/init.d/heartbeat start [root@192.168.0.10 ~]# 到這里heartbeat+drbd+mysql高可用環(huán)境就搭建結(jié)束了。接下來(lái)進(jìn)行測(cè)試。 高可用測(cè)試 (1)在第一臺(tái)服務(wù)器上面啟動(dòng)mysql服務(wù)。(192.168.0.10) [root@192.168.0.10 ~]# /etc/init.d/mysqld start Starting MySQL.The server quit without updating PID file (/[FAILED]ql/db-server-01.pid). [root@192.168.0.10 ~]# ll /data/ total 0 [root@192.168.0.10 ~]# 怎么回事?/data/下面為空。這里是因?yàn)槲覀冊(cè)谇懊嬉呀?jīng)把這個(gè)節(jié)點(diǎn)變?yōu)镾econdary [root@192.168.0.10 ~]# /etc/init.d/drbd status drbd driver loaded OK; device status: version: 8.4.2 (api:1/proto:86-101) GIT-hash: 7ad5f850d711223713d6dcadc3dd48860321070c build by root@db-server-01, 2014-04-18 21:15:57 m:res cs ro ds p mounted fstype 0:r0 Connected Secondary/Primary UpToDate/UpToDate C [root@192.168.0.10 ~]# 我們現(xiàn)在需要手動(dòng)切換回來(lái)。才能啟動(dòng)mysql [root@192.168.0.20 ~]# umount /data/ [root@192.168.0.20 ~]# drbdadm secondary all [root@192.168.0.20 ~]# [root@192.168.0.10 ~]# drbdadm primary all [root@192.168.0.10 ~]# mount /dev/drbd0 /data/ [root@192.168.0.10 ~]# ll /data/ total 20 drwx------ 2 root root 16384 Apr 18 22:16 lost+found drwxr-xr-x 5 mysql mysql 4096 Apr 18 23:01 mysql [root@192.168.0.10 ~]# /etc/init.d/drbd status drbd driver loaded OK; device status: version: 8.4.2 (api:1/proto:86-101) GIT-hash: 7ad5f850d711223713d6dcadc3dd48860321070c build by root@db-server-01, 2014-04-18 21:15:57 m:res cs ro ds p mounted fstype 0:r0 Connected Primary/Secondary UpToDate/UpToDate C /data ext4 [root@192.168.0.10 ~]# 可以看見已經(jīng)切換回來(lái)了,我們現(xiàn)在可以啟動(dòng)mysql了。 [root@192.168.0.10 ~]# /etc/init.d/mysqld start Starting MySQL....... [ OK ] [root@192.168.0.10 ~]# mysql Welcome to the MySQL monitor. Commands end with ; or \g. Your MySQL connection id is 1 Server version: 5.5.37-log MySQL Community Server (GPL) Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved. Oracle is a registered trademark of Oracle Corporation and/or its affiliates. Other names may be trademarks of their respective owners. Type 'help;' or '\h' for help. Type '\c' to clear the current input statement. mysql> (2)在兩臺(tái)服務(wù)器上面啟動(dòng)heartbeat [root@192.168.0.10 ~]# /etc/init.d/heartbeat start Starting High-Availability services: INFO: Resource is stopped Done. [root@192.168.0.10 ~]# [root@192.168.0.20 ~]# /etc/init.d/heartbeat start Starting High-Availability services: INFO: Resource is stopped Done. [root@192.168.0.20 ~]# [root@192.168.0.10 ~]# ip addr | grep eth1 3: eth1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000 inet 192.168.0.10/24 brd 192.168.0.255 scope global eth1 inet 192.168.0.88/24 brd 192.168.0.255 scope global secondary eth1 [root@192.168.0.10 ~]# 可以看見虛擬ip192.168.0.88已經(jīng)存在了。說(shuō)明成功了。我們看看heartbeat的日志就能發(fā)現(xiàn)。 [root@192.168.0.10 ~]# tail -n 20 /var/log/ha-log harc(default)[5598]: 2014/04/19_00:25:21 info: Running /etc/ha.d//rc.d/status status Apr 19 00:25:22 db-server-01 heartbeat: [5591]: info: Comm_now_up(): updating status to active Apr 19 00:25:22 db-server-01 heartbeat: [5591]: info: Local status now set to: 'active' Apr 19 00:25:22 db-server-01 heartbeat: [5591]: info: Status update for node db-server-02: status active harc(default)[5618]: 2014/04/19_00:25:22 info: Running /etc/ha.d//rc.d/status status Apr 19 00:25:33 db-server-01 heartbeat: [5591]: info: remote resource transition completed. Apr 19 00:25:33 db-server-01 heartbeat: [5591]: info: remote resource transition completed. Apr 19 00:25:33 db-server-01 heartbeat: [5591]: info: Initial resource acquisition complete (T_RESOURCES(us)) /usr/lib/ocf/resource.d//heartbeat/IPaddr(IPaddr_192.168.0.88)[5671]: 2014/04/19_00:25:33 INFO: Resource is stopped Apr 19 00:25:33 db-server-01 heartbeat: [5635]: info: Local Resource acquisition completed. harc(default)[5752]: 2014/04/19_00:25:33 info: Running /etc/ha.d//rc.d/ip-request-resp ip-request-resp ip-request-resp(default)[5752]: 2014/04/19_00:25:33 received ip-request-resp IPaddr::192.168.0.88/24/eth1 OK yes ResourceManager(default)[5775]: 2014/04/19_00:25:33 info: Acquiring resource group: db-server-01 IPaddr::192.168.0.88/24/eth1 drbddisk::r0 Filesystem::/dev/drbd0::/data::ext4 mysqld /usr/lib/ocf/resource.d//heartbeat/IPaddr(IPaddr_192.168.0.88)[5803]: 2014/04/19_00:25:33 INFO: Resource is stopped ResourceManager(default)[5775]: 2014/04/19_00:25:33 info: Running /etc/ha.d/resource.d/IPaddr 192.168.0.88/24/eth1 start IPaddr(IPaddr_192.168.0.88)[5926]: 2014/04/19_00:25:34 INFO: Adding inet address 192.168.0.88/24 with broadcast address 192.168.0.255 to device eth1 IPaddr(IPaddr_192.168.0.88)[5926]: 2014/04/19_00:25:34 INFO: Bringing device eth1 up IPaddr(IPaddr_192.168.0.88)[5926]: 2014/04/19_00:25:34 INFO: /usr/libexec/heartbeat/send_arp -i 200 -r 5 -p /var/run/resource-agents/send_arp-192.168.0.88 eth1 192.168.0.88 auto not_used not_used /usr/lib/ocf/resource.d//heartbeat/IPaddr(IPaddr_192.168.0.88)[5900]: 2014/04/19_00:25:34 INFO: Success /usr/lib/ocf/resource.d//heartbeat/Filesystem(Filesystem_/dev/drbd0)[6030]: 2014/04/19_00:25:34 INFO: Running OK [root@192.168.0.10 ~]# 激動(dòng)的時(shí)刻到了,我們測(cè)試一下自動(dòng)切換。我們先看看兩臺(tái)服務(wù)器的狀態(tài): [root@192.168.0.10 ~]# df -HT Filesystem Type Size Used Avail Use% Mounted on /dev/sda2 ext4 19G 3.5G 15G 20% / tmpfs tmpfs 121M 0 121M 0% /dev/shm /dev/sda1 ext4 204M 52M 141M 27% /boot /dev/drbd0 ext4 33G 216M 32G 1% /data [root@192.168.0.10 ~]# [root@192.168.0.20 ~]# df -HT Filesystem Type Size Used Avail Use% Mounted on /dev/sda2 ext4 19G 4.9G 13G 28% / tmpfs tmpfs 121M 0 121M 0% /dev/shm /dev/sda1 ext4 204M 52M 141M 27% /boot [root@192.168.0.20 ~]# 可以看見掛載在第一臺(tái)服務(wù)器。 測(cè)試方法: 1.停掉master上的mysqld,看看是否切換(因?yàn)閔eartheat不檢查服務(wù)的可用性,因此需要通過(guò)而外的腳本來(lái)實(shí)現(xiàn))。 我就停止master(192.168.0.10)上的heartbeat來(lái)測(cè)試是否會(huì)自動(dòng)切換,這里除了第一條無(wú)法實(shí)現(xiàn),其他的都可以切換: [root@192.168.0.10 ~]# /etc/init.d/heartbeat stop Stopping High-Availability services: Done. [root@192.168.0.10 ~]# df -HT Filesystem Type Size Used Avail Use% Mounted on /dev/sda2 ext4 19G 3.5G 15G 20% / tmpfs tmpfs 121M 0 121M 0% /dev/shm /dev/sda1 ext4 204M 52M 141M 27% /boot [root@192.168.0.10 ~]# /etc/init.d/drbd status drbd driver loaded OK; device status: version: 8.4.2 (api:1/proto:86-101) GIT-hash: 7ad5f850d711223713d6dcadc3dd48860321070c build by root@db-server-01, 2014-04-18 21:15:57 m:res cs ro ds p mounted fstype 0:r0 Connected Secondary/Primary UpToDate/UpToDate C [root@192.168.0.10 ~]# 可以看見已經(jīng)切換了,我們看另外一臺(tái)機(jī)器的情況: [root@192.168.0.20 ~]# df -HT Filesystem Type Size Used Avail Use% Mounted on /dev/sda2 ext4 19G 4.9G 13G 28% / tmpfs tmpfs 121M 0 121M 0% /dev/shm /dev/sda1 ext4 204M 52M 141M 27% /boot /dev/drbd0 ext4 33G 216M 32G 1% /data [root@192.168.0.20 ~]# netstat -nltp | grep 3306 | grep -v grep tcp 0 0 0.0.0.0:3306 0.0.0.0:* LISTEN 5542/mysqld [root@192.168.0.20 ~]# 可以發(fā)現(xiàn)已經(jīng)切換過(guò)來(lái),mysql也自動(dòng)啟動(dòng)了。之前是沒有啟動(dòng)的。 [root@192.168.0.20 ~]# ip addr | grep eth1 3: eth1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000 inet 192.168.0.20/24 brd 192.168.0.255 scope global eth1 inet 192.168.0.88/24 brd 192.168.0.255 scope global secondary eth1 [root@192.168.0.20 ~]# mysql Welcome to the MySQL monitor. Commands end with ; or \g. Your MySQL connection id is 1 Server version: 5.5.37-log MySQL Community Server (GPL) Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved. Oracle is a registered trademark of Oracle Corporation and/or its affiliates. Other names may be trademarks of their respective owners. Type 'help;' or '\h' for help. Type '\c' to clear the current input statement. mysql> 可以看見,一切正常呢。如果我們查看日志,就可以看見到底發(fā)生了什么。 [root@192.168.0.20 ~]# tail -n 10 /var/log/ha-log ResourceManager(default)[4768]: 2014/04/19_00:36:42 info: Running /etc/ha.d/resource.d/Filesystem /dev/drbd0 /data ext4 start Filesystem(Filesystem_/dev/drbd0)[5131]: 2014/04/19_00:36:42 INFO: Running start for /dev/drbd0 on /data /usr/lib/ocf/resource.d//heartbeat/Filesystem(Filesystem_/dev/drbd0)[5122]: 2014/04/19_00:36:42 INFO: Success ResourceManager(default)[4768]: 2014/04/19_00:36:43 info: Running /etc/init.d/mysqld start mach_down(default)[4741]: 2014/04/19_00:36:46 info: /usr/share/heartbeat/mach_down: nice_failback: foreign resources acquired mach_down(default)[4741]: 2014/04/19_00:36:46 info: mach_down takeover complete for node db-server-01. Apr 19 00:36:46 db-server-02 heartbeat: [4637]: info: mach_down takeover complete. Apr 19 00:36:58 db-server-02 heartbeat: [4637]: WARN: node db-server-01: is dead Apr 19 00:36:58 db-server-02 heartbeat: [4637]: info: Dead node db-server-01 gave up resources. Apr 19 00:36:58 db-server-02 heartbeat: [4637]: info: Link db-server-01:eth1 dead. [root@192.168.0.20 ~]# 對(duì)于mysqld服務(wù)掛掉的情況無(wú)法實(shí)現(xiàn)自動(dòng)切換,所以需要一個(gè)腳本來(lái)幫助我們完成,我這里有個(gè)簡(jiǎn)單的腳本,能實(shí)現(xiàn)當(dāng)mysqld服務(wù)不可用時(shí)進(jìn)行自動(dòng)切換,當(dāng)進(jìn)行切換時(shí)發(fā)送郵件等。該腳本放在主服務(wù)器執(zhí)行,也就是運(yùn)行mysqld服務(wù)的服務(wù)器上執(zhí)行。 [root@192.168.0.20 ~]# cat mysqlmon.sh #!/bin/bash trap 'echo PROGRAM INTERRUPTED; exit 1' INT username=root password=123456 n=0 log='/var/log/mysqlmon.log' while true do if /usr/local/mysql/bin/mysql -u${username} -p${password} -e "use test" >&/dev/null then echo `date +"%Y-%m-%d %H:%M:%S"` mysqld is alive! >> ${log} n=0 else echo "`date +"%Y-%m-%d %H:%M:%S"` mysqld cannot be connected!" >> ${log} n=$[n + 1] if [ $n -eq 3 ] then /etc/init.d/heartbeat stop echo "`date +"%Y-%m-%d %H:%M:%S"` mysqld switched to backup!" >> ${log} echo "`date +"%Y-%m-%d %H:%M:%S"` mysqld switched to backup" | mutt -s "mysqld switched to backup" saltstack@163.com break fi fi sleep 10 done [root@192.168.0.20 ~]# 掛在后臺(tái)執(zhí)行: [root@192.168.0.10 ~]# nohup mysqlmon.sh & 停止mysqld服務(wù),看是否進(jìn)行切換以及發(fā)送郵件: [root@192.168.0.10 ~]# /etc/init.d/mysqld stop Shutting down MySQL. [ OK ] [root@192.168.0.10 ~]#
[root@192.168.0.20 ~]# df -HT Filesystem Type Size Used Avail Use% Mounted on /dev/sda2 ext4 19G 4.9G 13G 28% / tmpfs tmpfs 121M 0 121M 0% /dev/shm /dev/sda1 ext4 204M 52M 141M 27% /boot /dev/drbd0 ext4 33G 216M 32G 1% /data [root@192.168.0.20 ~]# netstat -nltp | grep 3306 tcp 0 0 0.0.0.0:3306 0.0.0.0:* LISTEN 13771/mysqld [root@192.168.0.20 ~]#
總結(jié): 搭建還不算復(fù)雜,但是也踩了不少坑,比如yum安裝的heartbeat沒有drbddisk腳本。該方案的優(yōu)點(diǎn)是安全性高、穩(wěn)定性高、可用性高,出現(xiàn)故障自動(dòng)切換,但是缺點(diǎn)也很明顯,只有一臺(tái)服務(wù)器提供服務(wù),成本相對(duì)較高。不方便擴(kuò)展??赡軙?huì)發(fā)生腦裂。當(dāng)mysql服務(wù)掛掉或者不可用的情況下不能進(jìn)行自動(dòng)切換,需要通過(guò)crm模式實(shí)現(xiàn)或者額外的腳本實(shí)現(xiàn)(比如shell腳本監(jiān)測(cè)到master的mysql不可用就將主上的heartbeat停掉,這樣就會(huì)切換到backup中去)。監(jiān)控也特別重要,可以使用nagios或者zabbix監(jiān)控。
參考資料: |
|
|
來(lái)自: 瓜瓜2uuq7332fe > 《Mysql》