服务器维护,服务器代维,安全设置,漏洞扫描,入侵检测服务

运维之家

 找回密码
 注册
搜索
查看: 4968|回复: 0

MySQL双机互备热备自动切换

[复制链接]
dirtysea 发表于 2010-4-22 14:30:04 | 显示全部楼层 |阅读模式
本方案致力于数据库实时备份,并且在故障发生后以最短的时间恢复和修复。
  在mysql数据库的备份应用中,主从复制结构是应用的比较广泛,数据同步和实时性都很高,基本上能满足大部分的需求。
  本方案基于主从复制结构的基础上,当主库出现故障时,从库能自动接管主库的功能,向外提供服务,且将自身设置为主库,将这个故障时间和影响缩短至最小,5秒内可切换完成。待原主库修复后,会自动**从库的备份角色,如此循环。
  在本方案的实现中,有两种方法且均基于mysql的主从结构中:
  1、 高可用(High Availability)HA集群,用heartbeat实现及增加了故障后的恢复功能。
  2 、同样是高可用,只是是自己编写脚本程序来监控,切换,恢复。
  在方法1中,使用稳定的heartbeat开源软件实现,但此方法,需要多一个IP对外访问,同时在监控上,是监控机器的状态而不是mysql,有些情况下,机器是好的但mysql服务挂了,这种情况下就不准确了。不过可以修改监控方式或增加对mysql服务的监控。
  方法2中,可以不用增加一个对外IP,同时在监控上,可以直接监控mysql的服务,至于稳定性,有待测试。此方法中还有一个问题,就是提供给客户端的数据库连接IP,因为切换后,IP也就变了。如果说更改程序,那不现实。所以,这里可以用域名,不过仍然需要修改域名的IP指向或是修改客户机的hosts文件。本文使用的是修改DNS的方法,因为DNS是自己配置的,可以灵活操作。
  本文分两部分进行说明
  第一部分 用 heartbeat 实现的高可用
  1环境条件
  两个虚拟机(IP:192.168.1.91/92/93),
  CentOS5.4,mysql-5.1.37,heartbeat-2.1.3-3
  2 安装前的准备
  Heartbeat 的工作原理:heartbeat最核心的包括两个部分,心跳监测部分和资源接管部分,心跳监测可以通过网络链路和串口进行,而且支持冗余链路,它们之间相互发送报文来告诉对方自己当前的状态,如果在指定的时间内未受到对方发送的报文,那么就认为对方失效,这时需启动资源接管模块来接管运行在对方主机上的资源或者服务。更多请看官网 http://linux-ha.org/HomePage
  基础系统的安装,mysql的安装(略)
  软件下载
  http://linux-ha.org/DownloadSoftware
  Http://www.packetfactory.net/libnet
  http://dev.mysql.com/downloads/mysql/5.1.html
  3 安装过程(heartbeat)
  一般的软件源码安装是./configure –prefix=path;make;make install,本文使用yum安装。
  yum install heartbeat
  yum install heartbeat-ldirectord
  有一点要注意:heartbeat的监测,可以是网络或串口,本文使用网络也就是网卡
  4 配置文档及脚本
  1) Heartbeat的三个配置文件ha.cf,authkeys,haresources
Cat Ha.cf
debugfile
/var/log/ha-
debug
logfile
/var/log/ha-
log
logfacility local0
keepalive
2

deadtime
5
warntime
10
initdead
10
udpport
694
bcast eth0
auto_failback off
node mysqlm
node mysqls
respawn hacluster
/usr/lib/heartbeat/ipfail
apiauth ipfail gid
=haclient uid=
hacluster

Cat authkeys
auth
1

1 crc

Cat haresources
mysqlm mysql_start1.sh IPaddr::
192.168.1.93/32/eth0


  2) mysql_start1.sh脚本  3) 同保证和记录当主机由slave到master转变时记录当前master的文件和位置,需要建一个数据库和表来记录
#!/bin/sh
# author:wdlinux
# url:http:
//
www.wdlinux.cn
# description: mysql start
local_ip
=192.168.1.91

mip
=192.168.1.92
vip
=192.168.1.93
mysql_in
=/usr/local/mysqlm
mysql_bin
=${mysql_in}/bin/
mysql
mysql_user
=
root
mysql_port
=3306

mysql_pass
=12345
mysqld_start
=/etc/rc.d/init.d/mysqldm
.
/etc/rc.d/init.d/
functions
function
slave_to_master() {
        echo "mysql
to master from
slave..."
        $mysql_bin
-u"${mysql_user}" -p"${mysql_pass}" -
e "slave stop;"                                                                  
log_file
=$(${mysql_bin} -u"${mysql_user}" -p"${mysql_pass}" -P"${mysql_port}" -e"show master status\G" | grep "File:" |
a
wk
-F ': '
'{printf $2}'
)                                                                                                               
log_id
=$(${mysql_bin} -u"${mysql_user}" -p"${mysql_pass}" -P"${mysql_port}" -e"show master status\G" | grep "Position:" |

awk
-F ': '
'{printf $2}'
)                                                                                                               
$mysql_bin
-u"${mysql_user}" -p"${mysql_pass}" -P"${mysql_port}" -e "use ms_state;update ms_log set mlf='${log_file}'
,mlp
='${log_id}'
"
        echo "mysql server
is
master"
}
function
master_to_slave {
        echo "mysql
to slave from
master..."
        
if (${mysql_bin} -h"${vip}" -u"${mysql_user}" -p"${mysql_pass}" -P"${mysql_port}" -e"show slave status" >
/dev/null
2>&1
)
        
then
                                                                                                                                    
log_file
=$(${mysql_bin} -h"${vip}" -u"${mysql_user}" -p"${mysql_pass}" -P"${mysql_port}" -e"use ms_state;select
m
lf
from ms_log\G" | grep "mlf:" | awk -F': '
'{printf $2}'
)                                                                                      
log_id
=$(${mysql_bin} -h"${vip}" -u"${mysql_user}" -p"${mysql_pass}" -P"${mysql_port}" -e"use ms_state;select
mlp
from ms_log\G" | grep "mlp:" | awk -F': '
'{printf $2}'
)                                                                                       
$mysql_bin
-u"${mysql_user}" -p"${mysql_pass}" -P"${mysql_port}" -e "slave stop;CHANGE MASTER TO
MASTER_LOG_FILE
=
'${log_file}',MASTER_LOG_POS =
${log_id};slave start";
                echo "mysql server
is
slave"
        fi
}
case "$1" in

     start)
        slave_to_master
        ;;
     stop)
        master_to_slave
        ;;
     
*)
        echo "Usage: mysql_start.sh {start
|
stop}"
        echo "start
is slave to
master"
        echo "stop
is master to
slave"
        
exit
1

esac


  3) 同保证和记录当主机由slave到master转变时记录当前master的文件和位置,需要建一个数据库和表来记录
create
database
ms_state;
use
ms_state;
create
table
ms_log(
id
tinyint (1) unsigned not
null
auto_increment,
mlf
varchar (20) not
null
default
''
,
mlp
varchar (20) not
null
default
''
,
primary
key
(id)
);
insert
into ms_log values (NULL,"test","123");


  4) mysql的配置
log-bin=mysql-bin
binlog_format
=
mixed
server
-id       =
1

master
-host     =
192.168.1.92

master
-user
=
msdata
master
-password =
pass
slave
-skip-errors=all

replicate-do-db=test
replicate-ignore-db=
mysql
replicate-ignore-db=ms_state


  其它配置略
  经测试,91,92重起关机都能自动切换,接管93的IP,且故障机恢复后都能自动**备份状态,且数据同步及时和一致。

第二部分 自己编写脚本实现的高可用
  一 监控实现原理
  自己编写脚本,实现的功能和heartbeat差不多,都是监控,切换等。
  对于监控,可以监控系统的状态如ping,也可以监控mysql服务状态(本文使用的方法)。
  二 实现脚本
  除了用此脚本替换heartbeat外,其它的实现和配置同上。
  1 监控脚本 mysql_monitor.sh
#!/bin/bash
# author:wdlinux
# url:http:
//www.wdlinux.cn
# description:monitor shell of mysql
local_ip
=192.168.1.92
rip
=192.168.1.91
mysql_in
=/usr/local/mysqlm
mysql_bin
=${mysql_in}/bin/mysql
mysql_user
=root
mysql_pass
=12345
mysql_port
=3306

st
=0
while
true;do
if (${mysql_bin} -h"${rip}"
-u"${mysql_user}"
-p"${mysql_pass}"
-P"${mysql_port}"
-e "show master status"
--connect_timeout=1
>
/
dev
/null
2>&1)
then
if (($st==0));then
/etc/rc.d/init.d/mysql_start1.sh stop
let st
=$st+1
fi
else
for ((i=0;i<=3;i++));do
sleep
3
if (${mysql_bin} -h"${rip}"
-u"${mysql_user}"
-p"${mysql_pass}"
-P"${mysql_port}"
-e "show master status"
--conne
ct_timeout
=1
>
/dev/null
2>&1)
then
break
else
if (($i==3));then
echo
"slave to master"
/etc/rc.d/init.d/mysql_start1.sh start
###modify dns prg
exit
fi
fi
done
fi
sleep
3
done
将local_ip,rip作相应的修改,local_ip代表本机IP,rip为另一台机的IP


  2 将监控脚本加入自启动,随系统启动,如
Echo “/etc/rc.d/init.d/mysql_monitor.sh &>>
/etc/rc.d/rc.local

  此方法也可以增加一个对外服务IP,如ha实现的一样,这样就省去了修改域名IP等问题。
  但在脚本里,需要增加监控,添加,删除IP的实现和功能。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

QQ|小黑屋|手机版|Archiver|运维之家

GMT+8, 2024-4-26 18:11 , Processed in 0.212990 second(s), 14 queries .

Powered by Dirtysea

© 2008-2020 Dirtysea.com.

快速回复 返回顶部 返回列表