免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
楼主: byrcc
打印 上一主题 下一主题

【讨论中】【更新】求教:binlog中字段值是十六进制 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2012-08-15 13:44 |显示全部楼层 |倒序浏览
本帖最后由 byrcc 于 2012-09-07 18:32 编辑

前些时间很忙,没有继续分析这个问题。今天再研究了一下,有些眉头了,基本定位到prepare statement的问题,并且可以重现,脚本附后面。在这里有个类似的问题http://bugs.mysql.com/bug.php?id=54791,不过粗看一下还是没发现问题根源和解决办法。求各位大牛帮分析分析!
重现条件:1,表gbk编码。2,使用prepare方式插入数据。
我在5.0.77-log和5.1.61-log版本的mysql上都测试都有这问题,php版本5.1.6
插入数据可以成功,并在表中能查到数据,值都正确,但是使用mysqlbinlog查看到的sql中的数值是十六进制的,而general query log也显示是十六进制的,如下
mysqlbinlog查看结果:
insert into tbl_test_pdo values(0x30,0x313030373736363032,0xB2E2)
general log:
  1. Time                 Id Command    Argument
  2. 120907 18:24:20     1 Connect   root@127.0.0.1 on cc
  3.                     1 Query     set names gbk
  4.                     1 Prepare   insert into tbl_test_pdo values(?,?,?)
  5.                     1 Execute   insert into tbl_test_pdo values(0x30,0x313030373736363032,0xB2E2)
  6.                     1 Close stmt
复制代码
我测试使用的脚本
建表:
  1. CREATE TABLE `tbl_test_pdo` (
  2.   `id` int(11) NOT NULL AUTO_INCREMENT,
  3.   `num` decimal(18,0) DEFAULT NULL,
  4.   `dsc` varchar(32) DEFAULT NULL,
  5.   PRIMARY KEY (`id`)
  6. ) ENGINE=InnoDB AUTO_INCREMENT=56 DEFAULT CHARSET=gbk
复制代码
php脚本:
  1. $dbms='mysql';
  2. $host='127.0.0.1';
  3. $dbname='test';
  4. $dbuser='root';
  5. $dbpass='pass';
  6. $dsn="$dbms:host=$host;dbname=$dbname";
  7. try {
  8.         $dbh = new PDO($dsn, $dbuser, $dbpass);
  9.         $sql2 = "insert into tbl_test_pdo values(:_1,:_2,:_3)";
  10.         $dbh->exec('set names gbk');
  11.         $stmt = $dbh->prepare($sql2,array(PDO::ATTR_CURSOR => PDO::CURSOR_FWDONLY));
  12.         $rlt = $stmt->execute(array(':_1'=>0,':_2'=>100776602,':_3'=>'测'));
  13. } catch (PDOException $e) {  die ("Error!: " . $e->getMessage()); }
复制代码
===================上次发贴内容=====================
新手求教大家一个问题
mysql版本:5.1.61-log
使用这个版本自带mysqlbinlog查看一个binlog文件,发现有下面的sql。它的特点是,values列表的值全是十六进制的,开发反应也没有直接使用十六进制操作数据库。为啥查看出来的binlog结果是这样的呢?
表的id定义为decimal(18,0) primary key,而这个sql中的id值0x313030373736383436转成十进制后,已经超过decimal(18,0)的范围。当前mysql的sql_mode为默认设置。这条数据,依据开发的log,id的值大概在100776703这个值大小。而100776703这个id在表中也能够查到那条数据。
这问题导致的结果是,在从库上,这个表的更新报错了,错误描述是tbl_xxxxxxxxxx这个表id主键冲突,冲突的值是999999999999999999,这个值恰好是十六进制id值0x313030373736383436截断到精度decimal(18,0)后的值。

不知道大家是否遇到过同样的问题?

insert into tbl_xxxxxxxxxx (id,version,createtime,updatetime,...在此省略部分字段列表...) values (0x313030373736383436,0x31,0x323031322D30382D31342031363A31313A3132,0x323031322D30382D31342031363A31313A3132,"","",0x313932307831323030,"","","","",0x736F676F752E636F6D,0xBAA3D4F4CDF5382E6A7067,0x373532,"","","","","","","",0x2F75706C6F6164496D6167652F323031322F30382F31342F313334343933313837325F352E6A7067,0x2F75706C6F6164496D6167652F323031322F30382F31342F313334343933313837325F352E6A70675F73,0x31,0x33,0x2D31,0x3530,0x30,0x2D31,0x2D31,0x30,0x31,"")

论坛徽章:
0
2 [报告]
发表于 2012-08-15 17:33 |显示全部楼层
就直接是mysqlbinlog logfile_name,并且在slave库上,报错时,show slave status 看到的错误信息中sql里的值也是十六进制的,同样在从库的errorlog中显示得结果也如此
回复 3# cenalulu


   

论坛徽章:
0
3 [报告]
发表于 2012-08-15 17:45 |显示全部楼层
本帖最后由 byrcc 于 2012-08-15 17:46 编辑

回复 5# cenalulu


这个sql是在master上的binlog中看到的。

mysql 5.1.61版本,刚从5.0版本升级完成,没有修改mysql的默认复制模式,所以应该是statement format,不过不知道跟升级是否有关。只是升级之前从库一直打开着slave-skip-errors=1062,升级以后特意把它关闭了。

ps:开发说这个表操作有点特殊,使用了pdo连接,执行sql前运行了PDO:: perpare。这东西没见过,也没研究,但应该跟它无关吧

论坛徽章:
0
4 [报告]
发表于 2012-08-16 19:59 |显示全部楼层
搜到这个帖子,也遇到了同样的问题。不过我还在跟开发沟通
http://www.itpub.net/forum.php?m ... ble&tid=1402633

论坛徽章:
0
5 [报告]
发表于 2012-09-07 18:36 |显示全部楼层
up一下。更新了主贴
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP