pt-table-checksum是检查MySQL数据一致性的神器,配合pt-table-sync工具,简直是堪称完美,网上有很多关于这方面的文章,故这里不做过多的介绍, 只列出具体操作步骤,以备使用时参考:

1.创建用于pt-table-checksum的用户: grant select,super,process,reload,show databases,replication client,replication slave on . to 'ptchecksum'@'%' identified by 'passtchecksum'; GRANT all on percona.* to 'ptchecksum'@'%' identified by 'passtchecksum';

2.创建pt-table-checksum使用的一些表信息: CREATE DATABASE IF NOT EXISTS percona; CREATE TABLE IF NOT EXISTS percona.checksums ( db CHAR(64) NOT NULL, tbl CHAR(64) NOT NULL, chunk INT NOT NULL, chunk_time FLOAT NULL, chunk_index VARCHAR(200) NULL, lower_boundary TEXT NULL, upper_boundary TEXT NULL, this_crc CHAR(40) NOT NULL, this_cnt INT NOT NULL, master_crc CHAR(40) NULL, master_cnt INT NULL, ts TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, PRIMARY KEY (db,tbl,chunk), INDEX ts_db_tbl(ts,db,tbl) ) ENGINE=InnoDB;

CREATE DATABASE IF NOT EXISTS 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) );

3.如果环境为一主多从并且多个从库时只想验证指定从库的一致时、主库不能自动发现从库、主从检测连接用户信息不一样,都可以使用dsns指定备库: 配置从库的dsn信息: insert into percona.dsns(dsn) values('h=192.168.56.102,P=3306,u=ptchecksum,p=passtchecksum');

其中第一个主机h=192.168.56.101为主库的数据库信息,第二个主机dsn=h=192.168.56.102为备库的数据库信息,多个数据库使用逗号分开: pt-table-checksum --replicate=percona.checksums --nocheck-replication-filters --no-check-binlog-format h=192.168.56.101,u=ptchecksum,p='passtchecksum',P=3306 --databases=app,app1 --recursion-method dsn=h=192.168.56.102,u=ptchecksum,p='passtchecksum',P=3306,D=percona,t=dsns

不指定dsn,默认检查所有能发现的slave备库: pt-table-checksum --replicate=percona.checksums --nocheck-replication-filters --no-check-binlog-format h=192.168.56.101,u=ptchecksum,p='passtchecksum',P=3306 --databases=app,app1

只输出不一致的表,添加--replicate-check-only 选项: pt-table-checksum --replicate=percona.checksums --nocheck-replication-filters --replicate-check-only --no-check-binlog-format h=192.168.56.101,u=ptchecksum,p='passtchecksum',P=3306 --databases=app,app1 --recursion-method dsn=h=192.168.56.102,u=ptchecksum,p='passtchecksum',P=3306,D=percona,t=dsns

Checking if all tables can be checksummed ... Starting checksum ... Differences on my2.ml.com TABLE CHUNK CNT_DIFF CRC_DIFF CHUNK_INDEX LOWER_BOUNDARY UPPER_BOUNDARY app.name 1 2 1
app.t_name 1 0 1

输出信息: Checking if all tables can be checksummed ... Starting checksum ... TS ERRORS DIFFS ROWS CHUNKS SKIPPED TIME TABLE 12-24T10:15:30 0 1 3 1 0 0.033 app.name 12-24T10:15:30 0 1 1 1 0 0.044 app.t_name 12-24T10:15:33 0 0 426294 7 0 2.628 app1.t 12-24T10:15:34 0 0 199998 1 0 1.311 app1.t_adress 12-24T10:15:34 0 0 2965 1 0 0.364 app1.t_pd_sto_sku

说明: TS:完成检查的时间戳。 ERRORS:检查时候发生错误和警告的数量。 DIFFS:不一致的chunk数量。当指定 --no-replicate-check 即检查完但不立即输出结果时,会一直为0;当指定 --replicate-check-only 即不检查只从checksums表中计算crc32,且只显示不一致的信息(毕竟输出的大部分应该是一致的,容易造成干扰)。 ROWS:比对的表行数; CHUNKS:被划分到表中的块的数目,详细的CHUNKS信息可以用表percona.checksums中查询到; SKIPPED:由于错误或警告或过大,则跳过块的数目; TIME:执行的时间; TABLE:被检查的表名;

如果不指定dsn时,默认会根据主库的processlist中找到从库复制进程,从而识别出有哪些从库,然后进行pt-table-checksum,但是如果是多个slave库是,其中一个slave数据不一致, 检查不会给出具体的slave信息,加上--replicate-check-only可以显示是那个slave数据不一致,因此此时可以使用dsn方式进行指定具体的slave库进行检查。另外如果数据库使用的是非标准3306端口,会导致找不到从库信息, 此时也建议使用dsn,dsn指定的是某个表,本例中使用percona.dsns,表行记录是主库的多个从库的连接信息。