南大通用GBase 8a执行Insert,update,delete报错 The returned information between nodes is not consistent的原因和解决方法

GBase 8a数据库集群,采用主副本机制实现高可用,如果由于意外原因,出现主副本数据不一致,比如行数不同,当做DML操作时,比如insert update delete等,主副本返回的影响行数不同,就会报这个错误:The returned information between nodes is not consistent。本文介绍该报错的解决方法。

故障原因

主副本的数据不一致导致,一般发生在GBase 8.5版本里较多,在V8.6和V9版本,则都是由于环境故障导致,包括宕机,死机,磁盘空间满等导致,导致数据虽然不一致,但无法写入event记录信息,或者写入的event信息丢失了。 还一种可能是手工清理event时,误清除了不该删掉的event。

如果是表结构不一致,请参考如下文章:

GBase 8a数据库集群执行报错GBA-02AD-0005 Failed to query in gnode :source table and destination are not same src… dst…

报错样例

如下是我构造的一个报错环境,方便后面模拟分析和处理过程。

节点环境

两节点集群,1个管理调度,2个计算。注意主备策略里,n1分片,202是主。

[gbase@rh6-1 ~]$ gcadmin
CLUSTER STATE:  ACTIVE
CLUSTER MODE:   NORMAL

=================================================================
|             GBASE COORDINATOR CLUSTER INFORMATION             |
=================================================================
|   NodeName   |     IpAddress     |gcware |gcluster |DataState |
-----------------------------------------------------------------
| coordinator1 |    10.0.2.201     | OPEN  |  OPEN   |    0     |
-----------------------------------------------------------------
=============================================================
|              GBASE DATA CLUSTER INFORMATION               |
=============================================================
|NodeName |     IpAddress     |gnode |syncserver |DataState |
-------------------------------------------------------------
|  node1  |    10.0.2.201     | OPEN |   OPEN    |    0     |
-------------------------------------------------------------
|  node2  |    10.0.2.202     | OPEN |   OPEN    |    0     |
-------------------------------------------------------------
[gbase@rh6-1 ~]$ gcadmin showdistribution

              Distribution ID: 2 | State: new | Total segment num: 2

     Primary Segment Node IP                           Segment ID         Duplicate Segment node IP
========================================================================================================================
|    10.0.2.202                                  |       1          |    10.0.2.201                                    |
------------------------------------------------------------------------------------------------------------------------
|    10.0.2.201                                  |       2          |    10.0.2.202                                    |
========================================================================================================================

集群版本

gbase> select version();
+----------------------+
| version()            |
+----------------------+
| 8.6.2.43-R28 .125499 |
+----------------------+
1 row in set (Elapsed: 00:00:00.00)

报错信息

gbase> select * from tt1;
+------+-------+
| id   | name  |
+------+-------+
|    1 | First |
|    2 |       |
|    3 | NULL  |
+------+-------+
3 rows in set (Elapsed: 00:00:00.38)

gbase> insert into tt1 values(5,'Five');
ERROR 1705 (HY000): gcluster DML error: testdb.tt1: the returned information between nodes is not consistent.
GBase 8a 报错 The returned information between nodes is not consistent
The returned information between nodes is not consistent

排查

先排查主副本数据行数是否一致,如果行数一样,再排查数据内容是否一致。

数据行数不一致

如果是复制表,通过gncli连接每个计算节点,执行对应的count语句,查询行数

select count(*) from MY_TABLE_NAME

如果是分布表,则需要增加分片号, 通过gncli连接每个计算节点,执行对应的count语句,查询【分片】行数。

select count(*) from MY_TABLE_NAME_nX

其中X是分片号,分别在主备2个节点执行,看是否一致。

查看主副本的方法,请参考 GBase8a MPP Cluster 查看集群主副本状态showdistribution

我这个集群

[gbase@rh6-1 ~]$ gncli -h10.0.2.201 -e"select count(*) from testdb.tt1_n1";
+----------+
| count(*) |
+----------+
|        1 |
+----------+
[gbase@rh6-1 ~]$ gncli -h10.0.2.202 -e"select count(*) from testdb.tt1_n1";
+----------+
| count(*) |
+----------+
|        3 |
+----------+
[gbase@rh6-1 ~]$
[gbase@rh6-1 ~]$ gncli -h10.0.2.201 -e"select count(*) from testdb.tt1_n2";
+----------+
| count(*) |
+----------+
|        0 |
+----------+
[gbase@rh6-1 ~]$ gncli -h10.0.2.202 -e"select count(*) from testdb.tt1_n2";
+----------+
| count(*) |
+----------+
|        0 |
+----------+

可以看到,n1分片不一致,再201上是1行,202是3行,主副本不一致。

数据内容不一致

如果出现数据行数一致,也报错时,那就是数据内容不一致了。这个在V85出现过,是数据库BUG,在新的V85和V95版本里,除非手工制造,否则不会出现这个情况。

排查方法,需要用户自行根据业务进行,因为只有用户才清楚哪个副本的数据是正确的。

比如update 时条件时 where id=1, 那就分别在主副本查询 where id=1的数据,然后人工确认哪个是对的。同样的这个id多了一行,肯定有另外一个id少了一行。

解决方案

手工从挑选的正确的分片,这个需要根据业务判断,如果不确定,那建议以多的为准。

同步到有问题的分片。具体步骤和命令,请参考

GBase 8a集群通过gc_sync_client手工同步分片数据

数据同步完成后,验证数据一致。

[gbase@rh6-1 ~]$ gc_sync_client  10.0.2.202 testdb tt1_n1 10.0.2.201 5258
[gbase@rh6-1 ~]$ gncli -h10.0.2.201 -e"refresh table testdb.tt1_n1;select count(*) from testdb.tt1_n1";
+----------+
| count(*) |
+----------+
|        3 |
+----------+
[gbase@rh6-1 ~]$ 

再执行DML操作,结果正确。

gbase> insert into tt1 values(5,'Five');
Query OK, 1 row affected (Elapsed: 00:00:01.50)

gbase> select * from tt1;
+------+-------+
| id   | name  |
+------+-------+
|    1 | First |
|    2 |       |
|    3 | NULL  |
|    5 | Five  |
+------+-------+
4 rows in set (Elapsed: 00:00:00.56)