Mysql 如何确定主从数据一致

Master 库上创建库和表

create database percona;
CREATE TABLE `percona`.`dsns` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`parent_id` int(11) DEFAULT NULL,
`dsn` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
);

主库上创建授权用户

grant all privileges on *.* to 'checksum'@'10.106.216.%' identified by '123456';

插入从库数据到dsn表中去

use percona;

insert into percona.dsns(dsn) values('h=10.106.216.182,P=3307,u=checksum,p=123456');

参数解释

--nocheck-replication

忽略replication-do-db规则

--no-check-binlog-format

不检查复制的binlog模式,要是binlog模式是ROW,则会报错。

--replicate

选择哪个库下创建checksums表,并将数据写入到表中

--ignore-tables

忽略某张表

--replicate-check-only

结果只显示数据不一致的表

--create-replicate-table

首次运行时需要添加,创建checksum表,若不指定需要手动创建表,

--databases=,-d

要检查的数据库,逗号分隔。用脚趾头想也知道

--databases-regex

正则匹配要检测的数据库

--ignore-databases[-regex]

忽略检查的库。Filter选项

--tables=,-t

要检查的表,逗号分隔。如果要检查的表分布在不同的db中,可以用--tables=dbname1.table1,dbnamd2.table2的形式。同理有--tables-regex,--ignore-tables,--ignore-tables-regex。

--replicate

指定的checksum表

--no-check-replication-filters

表示不需要检查 Master 配置里是否指定了 Filter。 默认会检查,如果配置了 Filter,如 replicate_do_db,replicate-wild-ignore-table,binlog_ignore_db 等,在从库checksum就与遇到表不存在而报错退出,所以官方默认是yes(--check-replication-filters)但我们实际在检测中时指定--databases=,所以就不存在这个问题,干脆不检测

recursion-method

发现从库的方式 指定复制检查的方式,默认情况下使用SHOW PROCESSLIST,如果非标准的3306端口,就使用SHOW SLAVE HOSTS的方式,推荐使用dsn方式,手动指定,比如下面使用 dsn

recursion-method=dsn=h=10.106.216.182,D=pt,t=dsns 使用 dsn来指定slave h 为ip地址 D 数据库 t 为表

recursion-method=dsn=t=percona.dsns,h=10.106.216.182,P=3307,u=checksum,p=123456

--replicate-check-only

只显示不一致的表

输出结果解释

· TS :完成检查的时间戳。

· ERRORS :检查时候发生错误和警告的数量。

· DIFFS :不一致的chunk数量。当指定 --no-replicate-check 即检查完但不立即输出结果时,会一直为0;当指定 --replicate-check-only 即不检查只从checksums表中计算crc32,且只显示不一致的信息(毕竟输出的大部分应该是一致的,容易造成干扰)。

· ROWS :比对的表行数。

· CHUNKS :被划分到表中的块的数目。

· SKIPPED :由于错误或警告或过大,则跳过块的数目。

· TIME :执行的时间。

· TABLE :被检查的表名

使用举例

1. 只检查test库

pt-table-checksum -S /data/3306/mysql.sock h='10.106.216.182',u='checksum',p='123456',P=3306 -d test --no-check-binlog-format --replicate=percona.checksumResult --recursion-method=dsn=t=percona.dsns,h=10.106.216.182,P=3307,u=checksum,p=123456




mysql 比较2张表某个字段内容 mysql对比两张表不一致_数据


SELECT * FROM percona.checksumResult;


mysql 比较2张表某个字段内容 mysql对比两张表不一致_数据_02


在从库3307上修改test.a 表

update test.a

set `name`=concat(`name`,'_g');


mysql 比较2张表某个字段内容 mysql对比两张表不一致_mysql 比较2张表某个字段内容_03


mysql 比较2张表某个字段内容 mysql对比两张表不一致_数据_04


再次检查库 看看是否能体现出差异来

pt-table-checksum -S /data/3306/mysql.sock h='10.106.216.182',u='checksum',p='123456',P=3306 -d test --no-check-binlog-format --replicate=percona.checksumResult --recursion-method=dsn=t=percona.dsns,h=10.106.216.182,P=3307,u=checksum,p=123456


mysql 比较2张表某个字段内容 mysql对比两张表不一致_mysql 比较2张表某个字段内容_05


pt-table-checksum -S /data/3306/mysql.sock h='10.106.216.182',u='checksum',p='123456',P=3306 --replicate-check-only -d test --no-check-binlog-format --replicate=percona.checksumResult --recursion-method=dsn=t=percona.dsns,h=10.106.216.182,P=3307,u=checksum,p=123456