Chinaunix首页 | 论坛 | 博客
  • 博客访问: 1451920
  • 博文数量: 263
  • 博客积分: 10851
  • 博客等级: 上将
  • 技术积分: 2627
  • 用 户 组: 普通用户
  • 注册时间: 2008-11-26 22:40
文章分类

全部博文(263)

文章存档

2013年(4)

2012年(25)

2011年(33)

2010年(50)

2009年(138)

2008年(13)

分类: LINUX

2012-04-22 23:19:51

线上遇到的错误:
主库5.1版本执行下面类似的语句

mysql> update test set age=greatest(0,age-1) where id=1;
从库5.5版本复制出错:
mysql> update test set age=greatest(0,age-1) where id=1;

原因:
Mysql5.5下sql_mode为空时,两个数想减,当其中一个为unsigned时,如果结果为负数,则会出现error;sql_mode修改为NO_UNSIGNED_SUBTRACTION,则不会出现error,如下所示:

mysql> SET sql_mode = '';
Query OK, 0 rows affected (0.00 sec)

mysql> SELECT CAST(0 AS UNSIGNED) - 1;
ERROR 1690 (22003): BIGINT UNSIGNED value is out of range in '(cast(0 as unsigned) - 1)'
If the NO_UNSIGNED_SUBTRACTION SQL mode is enabled, the result is negative:

mysql> SET sql_mode = 'NO_UNSIGNED_SUBTRACTION';
mysql> SELECT CAST(0 AS UNSIGNED) - 1;
+-------------------------+
| CAST(0 AS UNSIGNED) - 1 |
+-------------------------+
| -1 |
+-------------------------+

目前从测试的结果看,sql_mode不会对replication的sql_thread产生影响(使用NO_ZERO_IN_DATE、STRICT_ALL_TABLES、NO_UNSIGNED_SUBTRACTION进行测试),5.1->5.5时,当遇到这个错误的时候,通过修改从库的sql_mode无法解决这个问题。

测试5.5->5.5,当主库的sql_mode设置成NO_UNSIGNED_SUBTRACTION时,主库可以插入,从库也不会报错。
从目前调查的结论看,这个应该是一个bug。

解决方法:
1, 主库和从库版本保持一致(主库升级或者从库降级)。如果主库升级的话,主库需要设置sql_mode=” NO_UNSIGNED_SUBTRACTION”。
2, 将原来的greatest函数修改为控制流函数if,建议使用这种方法。

mysql> update test set age=greatest(0,age-1) where id=1;
Query OK, 0 rows affected (0.00 sec)
Rows matched: 1 Changed: 0 Warnings: 0
mysql> update test set age=if(age>1,age-1,0) where id=1;
Query OK, 1 row affected (0.00 sec)
Rows matched: 1 Changed: 1 Warnings: 0

本文转自:

阅读(10250) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~