MySQL通过ODBC 5.2插入到位(1)列

时间:2013-05-27 17:11:41

标签: mysql oracle odbc

我已经搜索过,似乎无法找到我正在寻找的东西。 我在Oracle中运行PL / SQL脚本,并尝试使用MySQL ODBC 5.2 Unicode驱动程序通过数据库链接将记录插入MySQL中的表。

链接工作正常,我可以在Oracle中使用它进行复杂查询,并在那里对记录进行各种插入和更新。

失败的地方是尝试将记录插入到具有bit(1)类型列的MySQL表中。

它基本上是一个循环游标,insert语句类似于:

INSERT INTO "app_user"@mobileapi (USERNAME, VERSION, ACCOUNT_EXPIRED, ACCOUNT_LOCKED, PASSWD, PASSWORD_EXPIRED)
VALUES  (CU_rec.USERNAME, CU_rec.VERSION, CU_rec.ACCOUNT_EXPIRED, CU_rec.ACCOUNT_LOCKED, CU_rec.PASSWD, CU_rec.PASSWORD_EXPIRED)

某些目标列(如ACCOUNT_EXPIREDACCOUNT_LOCKED等)是MySQL中的bit(1)列。鉴于我可以将游标CU_rec中的数据类型转换为Oracle中我想要的任何内容,如何将它们插入到目标中?我已经尝试了所有我能想到的东西,而且我一直在努力:

错误报告:

ORA-28500: connection from ORACLE to a non-Oracle system returned this message:
[MySQL][ODBC 5.2(w) Driver][mysqld-5.6.10]Data too long for column 'ACCOUNT_EXPIRED' at row 1 {HY000,NativeErr = 1406}
ORA-02063: preceding 2 lines from MOBILEAPI
ORA-06512: at line 44
28500. 00000 -  "connection from ORACLE to a non-Oracle system returned this message:"
*Cause:    The cause is explained in the forwarded message.
*Action:   See the non-Oracle system's documentation of the forwarded
           message.

非常感谢任何帮助。

2 个答案:

答案 0 :(得分:0)

你的问题是Oracle的default datatype conversion而不是ODBC;根据他们自己的文档,他们将SQL_BINARY转换为raw。虽然没有直接关系,Oracle's comparison of MySQL and Oracle within SQL Developer也暗示了从MySQL位自动转换为Oracle raw。

非常容易混淆,MySQL's documentation表示某个位转换为SQL_BIT或SQL_CHAR,这意味着可能在另一个方向 1 工作。

根据Microsoft's ODBC docs,理论上你应该能够使用CONVERT()函数将其转换为一个字符,从理论上讲,它应该可以被MySQL翻译。

insert into some_table@some_db (bit_col)
values( {fn convert(some_col, SQL_CHAR)} );

如果没有另外两个选项,但它确实取决于您尝试从Oracle插入MySQL数据库的内容以及Oracle中的数据类型。例如,您可以使用Oracle CAST()函数在数据类型之间进行转换。例如,以下内容将整数转换为二进制double。

select cast(1 as binary_double) from dual

不幸的是,你不能将整数转换为raw,只能转换为raw或rowid,所以为了转换为raw,你必须执行以下操作:

select cast(to_char(1) as raw(1)) from dual

我不知道MySQL是否会接受这个,但通过一些测试你应该能够解决它。

<子> 1。为清楚起见,我从未尝试过任何方向。

答案 1 :(得分:0)

哈!我找到了解决方案。把它放在这里,以防它帮助别人。它不漂亮,但它有效。

我使用了旧的EXECUTE IMMEDIATE技巧。

基本上,我创建了一个变量sql_stmt varchar2(4000)并编写了如下代码:

sql_stmt := 'insert into "app_user"@mobileapi (USERNAME, VERSION, ACCOUNT_EXPIRED, ACCOUNT_LOCKED, CIPHER_PASSPHRASE, ENABLED, PASSWD, PASSWORD_EXPIRED) 
values ('''||CU_rec.USERNAME||'','||CU_rec.VERSION||', '||CU_rec.ACCOUNT_EXPIRED||', '||CU_rec.ACCOUNT_LOCKED||', '''||CU_rec.CIPHER_PASSPHRASE||''', '|| 
           CU_rec.ENABLED||', '''||CU_rec.PASSWD||''', '||CU_rec.PASSWORD_EXPIRED||')';
EXECUTE IMMEDIATE sql_stmt;

无论如何都是这样的(引号可能不会排成一行,因为我从实际代码中删了一点)。看一下sql_stmt的内容,我得到:

insert into "app_user"@mobileapi (USERNAME, VERSION, ACCOUNT_EXPIRED, ACCOUNT_LOCKED, CIPHER_PASSPHRASE, ENABLED, PASSWD,PASSWORD_EXPIRED) 
values ('user@email.com', 0, 0, 0, 'asdfastrwaebawavgansdhnsgjsjsh', 1, 'awercbcakwjerhcawuerawieubkahbewvkruh', 0)

EXECUTE IMMEDIATE完成,并检查目标表,值就在那里。

可能是一个糟糕的解决方案,但总比没有好。