1. server id 重复
这个在我们刚接触主从复制的时候可能会犯的错误,也就是主从的 server_id 配置成相等的了,show slave status\G 会报如下错误:
报错中也提示了:主和从有相等的 server id。
解决办法:
修改主从的 server_id,建议改成IP后两段的组合。
比如 IP 是192.168.11.11。
那 server_id 就定义为 1111,通常情况同一架构中的 server_id 重复的概率就小很多了。
2. 端口不通
主从端口不通,通常 show slave status\G 报错如下:
其中:
Slave_IO_State 显示为:Connection to master;
Slave_IO_Running 显示为:Connection;
Seconds_Behind_Master 显示为:NULL。
解决办法:
将主从端口调通,保证能互相 telnet 通对方的 3306 端口。
3. 主库要新增的内容在从库已经有了
可以先模拟出这种报错(注意!只能在自己的测试环境操作)。
在从库上新建一个库:
1 | create database martin_test; |
再到主库执行同样的建库语句:
1 | create database martin_test; |
再去从库执行 show slave status\G:
Last_Error 中提示了,不能再创建 martin_test 库,因为已经存在了。
解决办法:
从库跳过这条记录。
如果是 GTID 模式:
假如 Executed_Gtid_set 为:
1 | 65c07f5e-1e37-11ed-b657-fa163e0d61f4:1-10139 |
则恢复操作为:
1 | mysql> stop slave; |
session.gtid_next 后面接的是 Executed_Gtid_set 下一个值。
如果是位点模式:
1 | stop slave; |
4. 主要更新的记录,从库没有
可以先模拟出这种报错(注意!只能在自己的测试环境操作)。
创建测试表并写入数据:
1 | CREATE TABLE test_repl ( |
在从库删除一条记录
1 | delete from test_repl where id=1; |
再到主库更新 id =1 的记录
1 | update test_repl set a=2 where id=1; |
从库执行 show slave status\G
提示要更新的记录不存在。
解决办法:
我们可以根据上图的 Relay_Log_File 和 Relay_Log_Pos(分表对应的是:mysql-relay-bin.000014 和 1112 )来解析出报错的 SQL 语句。
1 | mysqlbinlog mysql-relay-bin.000014 --start-position=1112 --base64-output=decode-rows -v >/tmp/1110.sql |
可以看到如下内容:
可以找到原记录,原记录就是 WHERE 后面对应的值,然后在MySQL中执行
1 | insert into test_repl select 1,1;stop slave;start slave; |
这样主从同步就恢复了。