Rebuild MySQL Slave Server

来源:互联网 发布:投屏软件 编辑:程序博客网 时间:2024/05/21 22:36

刚锻炼回来,在听‘爱似狂潮’。刚写完了C++的Signal Handler的封装。下周一我们Search Backend Offsite,而且下周轮到我Shaddow On Call了,周末要把项目的事情先做掉,整理以前的Site Issue的email,免得到时被TDO鄙视。中午和Peter出去散步,Peter是SFE的PD Manager,是一个对工作很有激情的一个人,这一点我跟他很像。Peter说了两点品质,第一点Sam以前也常跟我说,就是Passion;第二点是 坚持!激情+坚持,恩,我很有同感的。走着走着,下雨了,两个人被淋得彻头彻尾。

下午COC的阿杜给我打了个电话,说他准备做我发的那个Rebuild MySQL Salve Server的ticket,我说阿杜,你做的时候我要上楼观摩,看看到底是怎么做的。看文档和看别人操作一遍是不一样的,最好是自己动手。阿杜是很热情的一个人,是COC最早的一批Oracle DBA之一,他先给我发了一个step by step instruction,然后下班前一边做,一边给我解释了一遍。我在这里做个笔记:

前些天因为temporary table 的replication的问题把slave server搞垮了,今天我们实际上是rebuild mysql slave server.

1. 为’复制’创建专门的用户,控制好权限
#在master上创建专门的用户,赋于其对所有对象的replication salve权限。
GRANT REPLICATION SLAVE ON *.* TO ‘repluser’@'master.vip.arrowpig.com’ IDENTIFIED BY ‘repluser’;

#如果你想让我们从Slave的机器上登录Master做replication的操作,可以这样:
GRANT REPLICATION SLAVE ON *.* TO ‘repluser’@'slave.vip.arrowpig.com’ IDENTIFIED BY ‘repluser’;

2. Master的配置
查看master的my.cnf文件,是不是这样配置了:
[mysqld]
log-bin=mysql-bin      //replicating就是通过bin log来进行的,bin log会记录所有的更新操作
server-id=1              //每个server都必须有唯一的标识

server-id就像是每个mysqld的IP Address一样,slave的server-id必须和master的不一样,在有多个slave的情况下,各个slave之间的server-id也不能冲突。log-bin=mysql-bin有两个意思,一是enable binary logging,binary logging非常重要,它记录所有对数据库的更新,所以像select这样的操作是不被bin log记录的。简单来讲,replication的时候就是slave通过网络把master的binary logging拿过来在slave上重新执行一遍。这里的mysql-bin是指binary log的前缀。我们来看一看mysqld的data目录,默认情况下,bin log就放在那里:
[jianxu@master.arrowpig mysql]$ ls data
mysql-bin.002166  mysql-bin.002172   mysql-bin.002167  mysql-bin.002173   mysql-bin.002162
mysql-bin.002168  …                       …                      …                        mysql-bin.index 

有3点要注意的:a)不要enable skip-networking选项 b)在设计数据库的时候最后使用InnoDB数据引擎,因为InnoDB有很好的transaction支持 c)如果使用InnoDB数据引擎,请在[mysqld]下面再加两行:
innodb_flush_log_at_trx_commit=1
sync_binlog=1

mysql数据库要使my.cnf中的修改生效,需要重新启动数据库,注意千万不要使用kill来关闭数据库,我就吃过一次亏,结果把表都弄坏了,还要恢复,很麻烦的。
关闭mysql数据库:bin/mysqladmin -u <username> shutdown -p<password>
启动mysql数据库:bin/mysqld_safe –user=mysql &

3. Slave的配置
查看slave的my.cnf文件:
[mysqld]
server-id=2
relay-log=/usr/local/mysql/data/HOSTNAME-relay-bin
replicate-do-db=arrowpigDB   #if you only want to replicate one database
master-host=master.vip.arrowpig.com  #HOSTNAME OF MASTER
master-port=3306
master-user=repluser
master-password=repluser
report-host=slave.vip.arrowpig.com     #HOSTNAME oF SLAVE

4. Dump Master数据库

其实上面讲的3点都是replication的配置,并不是rebuild,rebuild相当于重建一个slave,往往通过mysqldump来做,mysqldump的意思是把master数据库中的内容全部以SQL语句的形式dump到一个文本文件中,然后把dump文件source进slave数据库。但是这里有一个问题,dump的过程很慢,如果dump还没有完成,master就又有更新怎么办?所以一般的做法是 在做dump前,先给master加read锁,这样Master还能响应查询请求,但是无法服务有更新需要的SQL,等dump文件生成以后解除read锁。我们在接触read锁之前一定要记住当时Master的bin log的位置,因为在master解除read锁和我们把dump文件成功source到slave之间的那段时间Master还是会被更新,这段时间需要依靠replication来完成,我们需要告诉slave从哪一点开始复制同步。

mysql>FLUSH TABLES WITH READ LOCK;              //给所有的表加Read LOCK
mysql> show master status;
+——————+———-+————–+——————+
| File                    | Position   | Binlog_Do_DB  | Binlog_Ignore_DB   |
+——————+———-+————–+——————+
| mysql-bin.002174 |  6551976 | arrowpigDB     |                         |
+——————+———-+————–+——————+
1 row in set (0.00 sec)

使用show master status我们可以看到加锁以后bin log的位置,记住这个位置。等dump完成以后开始slave replication的时候需要的。
接下来就开始dump操作:(假设用户名和密码都是root),这一步有点耗时,所以最好在master的机器上做
[jianxu@master.arrowpig mysql]$ mysqldump –databases arrowpigDB -uroot -proot  >dbdump.sql

dump完成后给Master数据库解除Read Lock:
mysql> unlock tables;

5. 将dump数据导入Slave数据库
先把刚才生成的dbdump.sql拷贝到Slave的机器上
[jianxu@master.arrowpig mysql]$scp dbdump.sql slave.vip.arrowpig.com:/var/tmp/

下面这一步在Slave的机器上操作:
[jianxu@slave.arrowpig mysql]$ mysql -uroot -proot < /var/tmp/dbdump.sql

6. 从同步点开始Replication
首先我们停掉Slave的Replication服务
mysql> stop slave;
记得我们刚才记录了Master上了Read Lock以后的bin log的位置吗?那个就是我们的同步点
mysql>CHANGE MASTER TO
   MASTER_HOST=master.vip.arrowpig.com’,
   MASTER_USER=’repluser’,
   MASTER_PASSWORD=’repluser’,
   MASTER_LOG_FILE=‘mysql-bin.002174′,    /该信息是dump之前用show master status得到的
   MASTER_LOG_POS=6551976;

然后我们就可以开始复制了:
mysql>start slave;

7. 检查Replication的进度

mysql> show slave statusG;
*************************** 1. row ***************************
Slave_IO_State: Waiting for master to send event
Master_Host: master.vip.arrowpig.com
Master_User: repluser
Master_Port: 3306
Connect_Retry: 60
Master_Log_File: mysql-bin.002174
Read_Master_Log_Pos: 69299898
Relay_Log_File: relay-bin.000071
Relay_Log_Pos: 69300035
Relay_Master_Log_File: mysql-bin.002174
Slave_IO_Running: Yes
Slave_SQL_Running: Yes
Replicate_Do_DB: arrowpigDB
Replicate_Ignore_DB:
Replicate_Do_Table:
Replicate_Ignore_Table:
Replicate_Wild_Do_Table:
Replicate_Wild_Ignore_Table: arrowpigDB.%tmp
Last_Errno: 0
Last_Error:
Skip_Counter: 0
Exec_Master_Log_Pos: 69299898
Relay_Log_Space: 69300035
Until_Condition: None
Until_Log_File:
Until_Log_Pos: 0
Master_SSL_Allowed: No
Master_SSL_CA_File:
Master_SSL_CA_Path:
Master_SSL_Cert:
Master_SSL_Cipher:
Master_SSL_Key:
Seconds_Behind_Master: 183

1 row in set (0.00 sec)

G的意思是我希望竖着打印报表,因为我的屏幕不够宽。Slave_IO_Running和Slave_SQL_Running表示复制正在进行,运行stop slave后你会看见这两处都是no。Replicate_Wild_Ignore_Table是一种复制策略,我们为了性能考虑规定编写SQL的时候所有的temporary table的表名都以tmp结尾,在复制时忽略所有的temporary表。但是这有个问题,就是不能出现使用temp表来更新非temp表的SQL,不然就会出错!最后的Second_Behind_Master是检查Replication进度时最为关心的,现在是183秒,当这个数字变成0的时候,同步就完成了。

感谢阿杜给我做了这个免费Hands On。这篇文章的前半部分是周五的时候写得,后半部分是今天补上的。

原创粉丝点击