标签:因此 存在 _for user 下载 l数据库 更新 主备 unix
目录原理
经过抓包分析,tcpdump -n -i eth0 -A -s0 -v host 218.24.23.253。当从与主处于正常连接状态时(而不是slave第一次启动时),主发生sql操作时,是将binlog主动推送给从服务器。
当正常同步之后,如果Slave mysql 停止,如服务停止了,或者设备故障了。那么在slave重新正常后,在这期间的主的变化都会正常同步到slave。
一 MySQL 复制的基本过程如下:(各部分学习自Google,谢谢)
主从同步配置
安装:
yum install mysql mysql-server #安装
cp /usr/share/mysql/my-medium.cnf /etc/my.cnf #复制配置文件
service mysql start #启动
chkconfig mysql on #设置开机自动启动
mysql_secure_installatio n #初始化数据库,删除test库;禁止root远程登录;
mysql root密码:anhuilgl@86253744!@#
218.24.44.80;218.24.23.253 的mysql密码修改为 root/Aanhuilgl@86253744
同步用的账号和密码:ZHUOMING_backup/ZHU0MING@135!#%
修改mysql的服务端口
vim /etc/my.cnf
主服务器同步用户授权
CREATE DATABASE backup
DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci; 建库
#CREATE USER ‘ZHUOMING_backup‘@‘218.24.44.80‘ IDENTIFIED BY ‘ZHU0MING@135!#%‘; 建备份用的用户和密码(建用户时填写允许用户备份操作的IP;在给此用户赋权时的IP必须与此相同,否则赋不上权限)
#建用户并授权
GRANT FILE,REPLICATION SLAVE ON . TO ‘ZHUOMING_backup‘@‘218.24.44.80‘ IDENTIFIED BY ‘ZHU0MING@135!#%‘; #给备份用户相应的权限,
REVOKE FILE,REPLICATION SLAVE ON . FROM ‘ZHUOMING_backup‘@‘218.24.23.232‘; #收回授权
如果中间还通过防火墙做的静态地址映射还需要增加防火墙外网口的地址和映射用的地址,否则连不上
GRANT FILE,REPLICATION SLAVE ON . TO ‘ZHUOMING_backup‘@‘223.100.7.151‘ IDENTIFIED BY ‘ZHU0MING@135!#%‘;
GRANT FILE,REPLICATION SLAVE ON . TO ‘ZHUOMING_backup‘@‘223.100.7.155‘ IDENTIFIED BY ‘ZHU0MING@135!#%‘;
GRANT ALL PRIVILEGES ON . TO ‘ZHUOMING_backup‘@‘223.100.7.155‘ IDENTIFIED BY ‘ZHU0MING@135!#%‘;
flush privileges; 每次赋权后必须刷新
三、把MySQL主服务器中的数据库osyunweidb导入到MySQL从服务器中
1、导出数据库osyunweidb
备注:在导出之前可以先进入MySQL控制台执行下面命令
flush tables with read lock; #生产环境必须先锁定。数据库只读锁定命令,防止导出数据库的时候有数据写入。这个命令是全局读锁定,执行了命令之后所有库所有表都被锁定只读。一般都是用在数据库联机备份,这个时候数据库的写操作将被阻塞,读操作顺利进行。解锁的语句也是unlock tables。
mysqldump -u root -p osyunweidb > /home/osyunweidbbak.sql #在MySQL主服务器进行操作,导出数据库osyunweidb到/home/osyunweidbbak.sql
unlock tables; #解除锁定
2、导入数据库到MySQL从服务器
mysql -u root -p #进入从服务器MySQL控制台
create database osyunweidb; #创建数据库
use osyunweidb #进入数据库
source /home/osyunweidbbak.sql #导入备份文件到数据库
mysql -u osyunweidbbak -h 192.168.21.169 -p #测试在从服务器上登录到主服务器
MySQL主服务器配置
use backup; 将backup库设置为当前库
create table mytest (username varchar(20),password varchar(20)); 创建一个测试用表
vi /etc/my.cnf #编辑配置文件,在[mysqld]部分添加下面内容
server-id=1 #设置服务器id,为1表示主服务器,注意:如果原来的配置文件中已经有这一行,就不用再添加了。
log-bin=mysql-bin #启动MySQL二进制日志系统,注意:如果原来的配置文件中已经有这一行,就不用再添加了。
binlog_format = MIXED #建议使用MIXED格式。使用show variables like ‘binlog_format‘查看;
expire_logs_days = 10 #binlog过期清理时间,根据每日生成的日志量,磁盘空间等设置过期时间。
max_binlog_size = 100M #每个日志文件大小的最大值
binlog-do-db=backup #需要同步的数据库名,如果有多个数据库,可重复此参数,每个数据库一行
binlog-ignore-db=mysql #不同步mysql数据库
binlog-ignore-db=information_schema
binlog-ignore-db=performance_schema
service mysql restart #重启MySQL
mysql -u root -p #进入mysql控制台
查看主服务器,出现以下类似信息
mysql> show master status;
+------------------+----------+--------------+------------------+
| File | Position | Binlog_Do_DB | Binlog_Ignore_DB |
+------------------+----------+--------------+------------------+
| mysql-bin.000001 | 106 | backup | |
+------------------+----------+--------------+------------------+
1 row in set (0.00 sec)
查看server-id:
mysql> show variables like ‘server_id‘;
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| server_id | 1 |
+---------------+-------+
1 row in set (0.00 sec)
Mysql从服务器配置
vi /etc/my.cnf #编辑配置文件,在[mysqld]部分添加下面内容
server-id=2 #配置文件中已经有一行server-id=1,修改其值为2,主从不能相同
log-bin=mysql-bin #启动MySQL二进制日志系统,如果只做从数据库则不起也可以,建议开启。
binlog_format = MIXED #建议使用MIXED格式。使用show variables like ‘binlog_format‘查看;
expire_logs_days = 10 #binlog过期清理时间,根据每日生成的日志量,磁盘空间等设置过期时间。
max_binlog_size = 100M #每个日志文件大小的最大值
read-only = 1 #设置为只读,以免被误写入而导致主从不同步,对非root用户有效。
replicate-do-db=backup #需要同步的数据库名,如果有多个数据库,可重复此参数,每个数据库一行
replicate-ignore-db=mysql #不同步mysql系统数据库
:wq! #保存退出
service mysql restart #重启MySQL
注意:MySQL 5.1.7版本之后,已经不支持把master配置属性写入my.cnf配置文件中了,配置文件中只需要把同步的数据库和要忽略的数据库写入即可。
mysql -u root -p #进入MySQL控制台
slave stop; #停止slave同步进程
进入主库,锁定主库表:
flush tables with read lock; #生产环境必须先锁定。
#执行同步语句(执行同步必须在mysql> stop slave; 的状态下进行)
change master to master_host=‘223.100.7.155‘, MASTER_PORT=3306,master_user=‘ZHUOMING_backup‘,master_password=‘ZHU0MING@135!#%‘,master_log_file=‘mysql-bin.000001‘ ,master_log_pos=106;
start slave; #开启slave同步进程
进入主库,解锁主库标:
unlock tables;#解锁。
SHOW SLAVE STATUS\G #查看slave同步信息,出现以下内容
1. row
Slave_IO_State: Waiting for master to send event
Master_Host: 192.168.21.169
Master_User: osyunweidbbak
Master_Port: 3306
Connect_Retry: 60
Master_Log_File: mysql-bin.000019
Read_Master_Log_Pos: 7131
Relay_Log_File: MySQLSlave-relay-bin.000002
Relay_Log_Pos: 253
Relay_Master_Log_File: mysql-bin.000019
Slave_IO_Running: Yes
Slave_SQL_Running: Yes
Replicate_Do_DB: osyunweidb
Replicate_Ignore_DB: mysql
Replicate_Do_Table:
Replicate_Ignore_Table:
1 row in set (0.00 sec)
测试:
在主备数据库服务器上:
CREATE DATABASE backup
DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci; 建库
create table cc(id int auto_increment,name varchar(20),primary key(id)); 建表
insert into cc (name) values(‘Mr.chai‘); 插数据
在备数据库服务器上查看是否有新建的表和数据。
常用命令:
1、用户创建完,赋完权限之后在备服务器上用此命令进行测试。如果能进行登录则表明权限和连通性没问题。
mysql -u osyunweidbbak -h 192.168.21.169 -p #测试在从服务器上登录到主服务器
1、查看用户及权限
SELECT DISTINCT CONCAT(‘User: ‘‘‘,user,‘‘‘@‘‘‘,host,‘‘‘;‘) AS query FROM mysql.user;
Show grants for ‘ZHUOMING_backup‘@‘10.34.34.232‘;
允许root用户从218.24.23.253访问
mysql>GRANT ALL PRIVILEGES ON . TO ‘root‘@‘218.24.23.253‘ IDENTIFIED BY ‘Aanhuilgl@86253744‘;
mysql> flush privileges; 修改权限之后需要执行此句以使之生效。
1、手动同步主数据库;必须在slave stop的状态下;
mysql>change master to master_host=‘223.100.7.155‘,master_user=‘ZHUOMING_backup‘,master_password=‘ZHU0MING@135!#%‘,master_log_file=‘mysql-bin.000002‘ ,master_log_pos=2394;
2、查看slave状态
mysql> show slave status\G;
3、手动从主数据库下载
mysql> load data from master;
4、在主备上可以查看各自的进程状态,主上一个BinlogDump,从上两个一个是I/O一个是SQL进程,I/O进程负责接收更新,SQL负责写入本地库。
show processlist;
5、查看参数配置
show variables like ‘slave%‘;
6、查看某用户权限
Show grants for ‘ZHUOMING_backup‘@‘218.24.23.232‘;
7、修改配置文件my.cnf,在[mysqld]下添加slave_net_timeout = 600;此参数的默认值是3600(秒,1小时),是指 slave 端(备数据库)的 I/O 线程处于 “waiting for master to send event”状态,如果这个等待状态超过 slave_net_timeout 时间,就会触发重连 master 的动作。
slave_net_timeout = 600 此参数的合理值需要在实际环境中进行一下测试,时间太长,容易导致同步不及时,时间太短,则备机会频繁连接主机。
在一个已经建立主从复制关系的系统里面,正常情况下,由从库向主库发送一个 COM_BINLOG_DUMP 命令后,主库有新的binlog event,会向备库发送binlog。但是由于网络故障或者其他原因(如主从数据库之间跨防火墙)导致主库与从库的连接断开或者主库长时间没有向从库发送binlog。例如该例子中数据库集群 10s 左右还没有写入的情况,超过slave_net_timeout设置的值,从库会向主库发起重连请求。5.6 版本slave 发起重连请求时,MySQL都会判断有没有用明文的用户名密码,如果有则发出上述信息到error.log。
8、--logs-slave-updates 参数
这个是在my.cnf文件配置的
通常情况,从服务器从主服务器接收到的更新不记入它的二进制日志。该选项告诉从服务器将其SQL线程执行的更新记入到从服务器自己的二进制日志。为了使该 选项生效,还必须用--logs-bin选项启动从服务器以启用二进制日志。如果想要应用链式复制服务器,应使用--logs-slave- updates。例如,可能你想要这样设置:
A -> B -> C
也就是说,A为从服务器B的主服务器,B为从服务器C的主服务器。为了能工作,B必须既为主服务器又为从服务器。你必须用--logs-bin启动A和B以启用二进制日志,并且用--logs-slave-updates选项启动B。
在my.cnf文件设置此选项
log_slave_updates=1
当然在这种机制下可能有的同学会存在这么个问题:
如果a->b b->a 这样的双master架构下,a,b都打开log_slave_updates选项会不会出现无限循环的状态。
mysql已经考滤到了这个问题,每条bin-log都会记录执行语句的源server_id.当slave读到语句的server_id等于本身的ID的时候,不会执行,所以我们不用担心a,b会不会无限循环下去。
基于以上这种情况,mysql的replication集群将更加灵活,你如果需要可以做成各种各样的链式复制。比如 a->b b->a b中设置log_slave_updates后还可以b->c. 这样a,c中的数据也是一致的。
双主配置my.cnf
结果创建的表,Slave上一个都没有,导致杯具发生。
到底是什么原因引起的呢?那就是没有使用use 库名导致的,如果使用了,就可以记录binlog,如图:
所以,如果想在Slave上忽略一个库的复制,最好不要用binlog_ignore_db这个参数,使用replicate-ignore-db = yourdb,取代之。
MySQL binlog_format (Mixed,Statement,Row)
MySQL 5.5 中对于二进制日志 (binlog) 有 3 种不同的格式可选:Mixed,Statement,Row,默认格式是 Statement。总结一下这三种格式日志的优缺点。
MySQL Replication 复制可以是基于一条语句 (Statement Level) ,也可以是基于一条记录 (Row Level),可以在 MySQL 的配置参数中设定这个复制级别,不同复制级别的设置会影响到 Master 端的 bin-log 日志格式。
常见错误
mysql主从复制,经常会遇到错误而导致slave端复制中断,这个时候一般就需要人工干预,跳过错误才能继续
跳过错误有两种方式:
1.跳过指定数量的事务:
mysql>slave stop;
mysql>SET GLOBAL SQL_SLAVE_SKIP_COUNTER = 1; #跳过一个事务
mysql>slave start;
2.修改mysql的配置文件,通过slave_skip_errors参数来跳所有错误或指定类型的错误
vi /etc/my.cnf
[mysqld]
#slave-skip-errors=1062,1053,1146 #跳过指定error no类型的错误
#slave-skip-errors=all #跳过所有错误
Mysql Binlog三种格式介绍及分析
一.Mysql Binlog格式介绍
Mysql binlog日志有三种格式,分别为Statement,MiXED,以及ROW!
1.Statement:每一条会修改数据的sql都会记录在binlog中。
优点:不需要记录每一行的变化,减少了binlog日志量,节约了IO,提高性能。(相比row能节约多少性能与日志量,这个取决于应用的SQL情况,正常同一条记录修改或者插入row格式所产生的日志量还小于Statement产生的日志量,但是考虑到如果带条件的update操作,以及整表删除,alter表等操作,ROW格式会产生大量日志,因此在考虑是否使用ROW格式日志时应该跟据应用的实际情况,其所产生的日志量会增加多少,以及带来的IO性能问题。)
缺点:由于记录的只是执行语句,为了这些语句能在slave上正确运行,因此还必须记录每条语句在执行的时候的一些相关信息,以保证所有语句能在slave得到和在master端执行时候相同 的结果。另外mysql 的复制,像一些特定函数功能,slave可与master上要保持一致会有很多相关问题(如sleep()函数, last_insert_id(),以及user-defined functions(udf)会出现问题).
使用以下函数的语句也无法被复制:
二.Binlog基本配制与格式设定
1.基本配制
Mysql BInlog日志格式可以通过mysql的my.cnf文件的属性binlog_format指定。如以下:
binlog_format = MIXED //binlog日志格式
log_bin =目录/mysql-bin.log //binlog日志名
expire_logs_days = 7 //binlog过期清理时间
max_binlog_size 100m //binlog每个日志文件大小
2.Binlog日志格式选择
Mysql默认是使用Statement日志格式,推荐使用MIXED.
由于一些特殊使用,可以考虑使用ROWED,如自己通过binlog日志来同步数据的修改,这样会节省很多相关操作。对于binlog数据处理会变得非常轻松,相对mixed,解析也会很轻松(当然前提是增加的日志量所带来的IO开销在容忍的范围内即可)。
3.mysqlbinlog格式选择
mysql对于日志格式的选定原则:如果是采用 INSERT,UPDATE,DELETE 等直接操作表的情况,则日志格式根据 binlog_format 的设定而记录,如果是采用 GRANT,REVOKE,SET PASSWORD 等管理语句来做的话,那么无论如何 都采用 SBR 模式记录
三.Mysql Binlog日志分析
通过MysqlBinlog指令查看具体的mysql日志,如下:
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
SET TIMESTAMP=1350355892/!/;
BEGIN
/!/;
#121016 10:51:32 server id 1 end_log_pos 1643885 Query thread_id=272571 exec_time=0 error_code=0
SET TIMESTAMP=1350355892/!/;
Insert into T_test….)
/!/;
#121016 10:51:32 server id 1 end_log_pos 1643912 Xid = 0
COMMIT/!/;
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
1.开始事物的时间:
SET TIMESTAMP=1350355892/!/;
BEGIN
2.sqlevent起点
#at 1643330 :为事件的起点,是以1643330字节开始。
3.sqlevent 发生的时间点
#121016 10:51:32:是事件发生的时间,
4.serverId
server id 1 :为master 的serverId
5.sqlevent终点及花费时间,错误码
end_log_pos 1643885:为事件的终点,是以1643885 字节结束。
execTime 0: 花费的时间
error_code=0:错误码
Xid:事件指示提交的XA事务
Mixed日志说明:
在slave日志同步过程中,对于使用now这样的时间函数,MIXED日志格式,会在日志中产生对应的unix_timestamp()*1000的时间字符串,slave在完成同步时,取用的是sqlEvent发生的时间来保证数据的准确性。另外对于一些功能性函数slave能完成相应的数据同步,而对于上面指定的一些类似于UDF函数,导致Slave无法知晓的情况,则会采用ROW格式存储这些Binlog,以保证产生的Binlog可以供Slave完成数据同步。
标签:因此 存在 _for user 下载 l数据库 更新 主备 unix
原文地址:http://blog.51cto.com/207698/2130785