最近踩到一个说大不大,说小不小的坑,在此分享出来给各位同学。事情是这样的,线上有2台服务器,1主1从。A -> B,B服务器从A服务器同步数据。每天使用xtrabackup在B服务器上面进行全备。某天A服务器挂了,后来由于某种原因无法进入系统了,只有重装了系统,那么此时要恢复A服务器的步骤就是在A服务器部署mysql实例,从B服务器上面拿备份恢复到A,再根据POS点change到B服务器,让A服务器从B服务器同步。此时是B -> A。相信熟悉MySQL的人都知道步骤是没有问题的。

但在这过程中还是出问题了,在A服务器从新从B服务器同步完成以后,确认没有延时以后,此时把A重新恢复成了原来的角色,也就是主库,架构又变回了A -> B。恢复完成以后询问开发说没有异常。到第二天的时候有玩家反馈数据不正确。此时进行数据差异的查找。最后发现A的数据比B的数据少。在经过几番查找以及回忆操作步骤以后,发现踩了大坑。那就是我们安装mysql实例的时候,server-id是根据服务器ip地址的后2位生成的,比如ip地址是:192.168.5.6,那么server-id就是56。

有同学会问了,和server-id有毛关系啊。大家仔细想想mysql的双主是怎样确定binlog是否需要应用的?没错,那就是server-id,如果server-id是自己的就不再应用binlog,那么我踩的坑就是当A再次重新向B同步的时候,A的server-id还是老的,没有修改,B服务器的binlog里面记录的server-id就是A服务器的server-id,最后导致有一部分binlog没有应用。原理已经说明了,那么接下来进行简单的实验就可以论证了。

环境:

自己搭建一个测试环境,简单的1主1从。

我主库的server-id是

mysql> show variables like '%server_id%';+---------------+-------+

| Variable_name | Value |

+---------------+-------+

| server_id | 25152 |

+---------------+-------+

1 row in set (0.00 sec)

从库的server-id是

mysql> show variables like '%server_id%';+---------------+-------+

| Variable_name | Value |

+---------------+-------+

| server_id | 25250 |

+---------------+-------+

1 row in set (0.00 sec)

主库建库,建表,插入数据:

mysql> create databaseyayun;

Query OK,1 row affected (0.00sec)

mysql> create table yayun.tb1 ( id int, age int, name char(20), primary key(id) );

Query OK,0 rows affected (0.07sec)

mysql> useyayunDatabasechanged

mysql> insert into tb1 (id,age,name)values(1,18,'aa');

Query OK,1 row affected (0.00sec)

mysql> insert into tb1 (id,age,name)values(2,18,'bb');

Query OK,1 row affected (0.00sec)

mysql> select * fromtb1;+----+------+------+

| id | age | name |

+----+------+------+

| 1 | 18 | aa |

| 2 | 18 | bb |

+----+------+------+

2 rows in set (0.00sec)

mysql>

从库查询:

mysql> select * fromtb1;+----+------+------+

| id | age | name |

+----+------+------+

| 1 | 18 | aa |

| 2 | 18 | bb |

+----+------+------+

2 rows in set (0.00sec)

mysql>

此时数据是一致的。

接下来在从库备份数据,并且记录pos点。(这里模拟的是从库每天进行的备份)

mysqldump -uroot -p --master-data=2 yayun > /tmp/backup_yayun.sql

下面在主库继续进行insert,update操作。

mysql> insert into tb1 (id,age,name)values(3,19,'cc');

Query OK,1 row affected (0.00sec)

mysql> update tb1 set name='yayun' where id=1;

Query OK,1 row affected (0.00sec)

Rows matched:1 Changed: 1 Warnings: 0mysql> select * fromtb1;+----+------+-------+

| id | age | name |

+----+------+-------+

| 1 | 18 | yayun |

| 2 | 18 | bb |

| 3 | 19 | cc |

+----+------+-------+

3 rows in set (0.00sec)

mysql>

查询从库记录:

mysql> select * fromtb1;+----+------+-------+

| id | age | name |

+----+------+-------+

| 1 | 18 | yayun |

| 2 | 18 | bb |

| 3 | 19 | cc |

+----+------+-------+

3 rows in set (0.00sec)

mysql>

可以看到此时主从数据是一致的。接下来我们就当主库挂了。重新需要拉取备份,然后向从库同步数据。

1. 把备份文件backup_yayun.sql拉到主库。

2. 把从库的同步断掉,清掉同步信息。

从库操作:

mysql> stop slave;reset slave all;

Query OK,0 rows affected (0.03sec)

Query OK,0 rows affected (0.05sec)

mysql>

主库操作:

mysql -uroot -p yayun < backup_yayun.sql

查看pos点:

[root@mdw ~]# grep -i change backup_yayun.sql-- CHANGE MASTER TO MASTER_LOG_FILE='mysql-bin.000004', MASTER_LOG_POS=4070;

[root@mdw~]#

主库change到原来的从库

mysql> CHANGE MASTER TO MASTER_HOST='10.36.25.250',MASTER_USER='repl',MASTER_PASSWORD='123',MASTER_LOG_FILE='mysql-bin.000004',MASTER_LOG_POS=4070;

Query OK,0 rows affected (0.10sec)

mysql>start slave;

Query OK,0 rows affected (0.00 sec)

查询数据:

如果查询出来的数据是下面的数据,那么就是正确的:

+----+------+-------+

| id | age | name |

+----+------+-------+

| 1 | 18 | yayun |

| 2 | 18 | bb |

| 3 | 19 | cc |

+----+------+-------+

我们实际查询一下:

mysql> select * fromtb1;+----+------+------+

| id | age | name |

+----+------+------+

| 1 | 18 | aa |

| 2 | 18 | bb |

+----+------+------+

2 rows in set (0.00sec)

mysql>

卧槽,发生了什么,怎么数据少了,而且id等于1的name字段结果也不一样?

下面我们看看原来老的从库的binlog

#160908 13:45:57 server id 25152 end_log_pos 4239 Query thread_id=16 exec_time=0 error_code=0SET TIMESTAMP=1473313557/*!*/;

insert into tb1 (id,age,name)values(3,19,'cc')/*!*/;

# at4239#160908 13:45:57 server id 25152 end_log_pos 4266 Xid = 160COMMIT/*!*/;

# at4266#160908 13:46:20 server id 25152 end_log_pos 4325 Query thread_id=16 exec_time=0 error_code=0SET TIMESTAMP=1473313580/*!*/;

BEGIN/*!*/;

# at4325#160908 13:46:20 server id 25152 end_log_pos 4427 Query thread_id=16 exec_time=0 error_code=0SET TIMESTAMP=1473313580/*!*/;

update tb1 set name='yayun' where id=1

/*!*/;

# at4427#160908 13:46:20 server id 25152 end_log_pos 4454 Xid = 162COMMIT/*!*/;

DELIMITER ;

可以看见有insert,update,但是server id都是25152,也就是主库的。这也就是为什么少了数据的原因。开头也提到过了。

如果我们在新的主库上面进行update,如果这条记录在从库没有存在,而且主从的binlog是row模式,那么就会触发1032错误,复制将中断,由于我的是mixed模式,同步一直没有报错,没有早发现问题。我update语句加limit就会触发row模式,下面我们试试。

主库:

mysql> update tb1 set name='abcd' where id=3 limit 1;

Query OK,1 row affected (0.00sec)

Rows matched:1 Changed: 1 Warnings: 0mysql>

从库:

mysql>show slave status\G*************************** 1. row ***************************Slave_IO_State: Waitingfor master tosend event

Master_Host:10.36.25.250Master_User: repl

Master_Port:3306Connect_Retry:60Master_Log_File: mysql-bin.000004Read_Master_Log_Pos:4653Relay_Log_File: relaylog.000002Relay_Log_Pos:253Relay_Master_Log_File: mysql-bin.000004Slave_IO_Running: Yes

Slave_SQL_Running: No

Replicate_Do_DB:

Replicate_Ignore_DB:

Replicate_Do_Table:

Replicate_Ignore_Table:

Replicate_Wild_Do_Table:

Replicate_Wild_Ignore_Table:

Last_Errno:1032Last_Error: Couldnot execute Update_rows event on table yayun.tb1; Can't find record in'tb1', Error_code: 1032; handler error HA_ERR_KEY_NOT_FOUND; the event's master log mysql-bin.000004, end_log_pos 4626Skip_Counter:0Exec_Master_Log_Pos:4454Relay_Log_Space:601Until_Condition: None

Until_Log_File:

Until_Log_Pos:0Master_SSL_Allowed: No

Master_SSL_CA_File:

Master_SSL_CA_Path:

Master_SSL_Cert:

Master_SSL_Cipher:

Master_SSL_Key:

Seconds_Behind_Master:NULLMaster_SSL_Verify_Server_Cert: No

Last_IO_Errno:0Last_IO_Error:

Last_SQL_Errno:1032Last_SQL_Error: Couldnot execute Update_rows event on table yayun.tb1; Can't find record in'tb1', Error_code: 1032; handler error HA_ERR_KEY_NOT_FOUND; the event's master log mysql-bin.000004, end_log_pos 4626Replicate_Ignore_Server_Ids:

Master_Server_Id:25250

1 row in set (0.00 sec)

可以看见抛1032错误,主库有这条记录,从库没有,同时触发了row模式,就会导致复制中断。

结论:

1. 在重新搭建复制关系的时候一定注意server-id。

2. 线上对数据一致性要求比较高的一定要使用row模式。

mysql的server_id怎么设置_MySQL Server-id踩到的坑相关推荐

  1. mysql字符集在哪设置_MySQL字符集设置

    最近,在项目组使用的mysql数据库中,插入数据出现乱码,关于这个问题做了下总结,我们从最基本的地方说起,到错误产生的深层次原因和解决办法. 基本概念 • 字符(Character)是指人类语言中最小 ...

  2. mysql有热备设置_Mysql数据热备配置与操作方法

    Server: 1.grant all on *.* to postfix@'192.168.128.174' identified by 'postfix'; --新建授权用户 2.# cd /va ...

  3. mysql安装的密码设置_MySql之安装以及设置密码等

    1.MySQL的下载安装.简单应用及目录介绍 1.下载安装 linux下的mysql安装和使用(参考博客): 如果Mac本安装完mysql之后,登陆以后,不管运行什么指令,总是提示这个:mac mys ...

  4. mysql 慢查询时间设置_Mysql 慢查询设置

    Mysql慢查询设置 分析MySQL语句查询性能的方法除了使用 EXPLAIN 输出执行计划,还可以让MySQL记录下查询超过指定时间的语句,我们将超过指定时间的SQL语句查询称为"慢查询& ...

  5. mysql数据库的字符集设置_mysql数据库字符集设置

    1. mysql UTF8设置 1)vi /etc/my.cnf [client] port = 3306 socket = mysql default-character-set=utf8 [mys ...

  6. mysql数据库表类型设置_mysql数据库表的类型介绍

    目录 前言 之前我们讲了下载安装数据库,还有如何卸载(虽然直接重装系统就好) 那么现在让我们来讲讲 """ 1.数据库与表的剩余操作 编码配置.引擎介绍 2.数据库字段的 ...

  7. mysql最大并行用户设置_mysql 优化配置

    1.目的: 通过根据服务器目前状况,修改Mysql的系统参数,达到合理利用服务器现有资源,最大合理的提高MySQL性能. 2.服务器参数: 32G内存.4个CPU,每个CPU 8核. 3.MySQL目 ...

  8. mysql 从服务器同步设置_mysql主从同步配置

    1.为什么要主从同步? 在Web应用系统中,数据库性能是导致系统性能瓶颈最主要的原因之一.尤其是在大规模系统中,数据库集群已经成为必备的配置之一.集群的好处主要有:查询负载.数据库复制备份等.其中Ma ...

  9. mysql怎么查看字符集设置_mysql 设置查看字符集

    一.查看字符集 1.查看MYSQL数据库服务器和数据库字符集 方法一:show variables like '%character%'; 方法二:show variables like 'colla ...

  10. mysql数据库的字符集设置_mysql数据库的字符集设置

    原文链接:http://blog.csdn.net/sin90lzc/article/details/7648439 作者:开浪裤 Notice:文章基于ubuntu系统而写 1.关于MySQL字符集 ...

最新文章

  1. WordPress数据库优化技巧
  2. android 获取图片
  3. python填写excel-Python|读、写Excel文件(三种模块三种方式)
  4. 视觉设计师跟平面设计_使设计具有视觉吸引力
  5. HDU 2296 Ring AC自动机 + DP
  6. Grunt上手指南(转)
  7. java 内存溢出分析_用一段时间后java内存溢出问题分析(转)
  8. 【NLP】蓦然回首:谈谈学习模型的评估系列文章(一)
  9. LitePal 数据库使用方法(最新2.0LitePal数据库适用)
  10. Linux基础(八)服务器RAID及配置
  11. 数据时代建设医疗数据,主要有哪些意义?
  12. 法国电子与计算机信息工程学校排名,法国工程学院的十大排名情况
  13. 抽35块树莓派新品单片机送给可爱的你们
  14. Kubernetes pod的生命周期
  15. Java利用itchat4j插件实现个人微信自动化
  16. 笔记本光驱拆解——让整个世界变得安静
  17. 学习指针后对int main(int argc, char *argv[]),“()“内部参数的详解(初学者不要怕,浅浅学过指针的就可以看懂)
  18. 锂矿降龙十八掌之时乘六龙:盛新锂能
  19. python京东预约抢购_京东抢购脚本js教程
  20. 谁在痛打“诺顿”落水狗

热门文章

  1. 【工业控制】基于matlab多变量动态矩阵预测控制(DMC)【含Matlab源码 1499期】
  2. 【图像隐写】基于matlab GUI DWT+SVD数字水印 【含Matlab源码 939期】
  3. 【锂电池健康状态预测】基于matlab BP神经网络锂电池健康状态预测【含Matlab源码 688期】
  4. oracle 表或视图不存在_sqlalchemy反射不存在主键的表引发的问题
  5. dev c++调试怎么看变量的值_DevC++ 安装教程
  6. c语言中x的n次方怎么表示_为什么一定要慎用C语言标准库中的pow函数,你知道吗?...
  7. 一、K3 Wise 实施指导《K3 Wise实施手册》
  8. 《BGP设计与实现》一2.10 案例研究:BGP内存的使用评估
  9. [Asp.Net web api]基于自定义Filter的安全认证
  10. Android 打开WIFI并快速获取WIFI的信息