暂无图片
暂无图片
暂无图片
暂无图片
暂无图片

Oracle ORA-12899: 当插入具有不同字符集的DB链接时,值太大

askTom 2017-11-06
1460

问题描述

嗨,汤姆,
我们正在使用两个具有两个不同字符集的数据库
11.2.0.1.0-64位 = AR8MSWIN1256
12.1.0.2.0-64位 = AL32UTF8

尝试通过DBLINK将数据从11.2版本插入到12.1,但它给出了 “ORA-12899: value too large” 错误的许多记录,而当检查字段的长度时仅给出12个字符,但在插入时说 “(实际: 13,最大值: 12)'用于项目“ OR_ITEMS_TEMP ”。“ ITEMTYPE ”;

我们已经尝试过直接插入数据,例如: 下面给出了脚本

------- 创建表 --------------
create table or_items_temp (id number, bu varchar2(12), brand varchar2(12), family varchar2(12), catgory varchar2(12), subcatgory varchar2(12),
grp varchar2(12), sgrp varchar2(12), saletype varchar2(12), itmodel varchar2(12), itemtype varchar2(12), uom varchar2(12),
rsp number(15,3), currency varchar2(12), itmobapp varchar2(12), status number(2))
-----End Create Table------------
-------Row details--------------
insert into or_items_temp(id, bu, brand, family, catgory, subcatgory, grp, sgrp, saletype, itmodel, itemtype, uom, rsp, currency, itmobapp,status)
VALUES(1, 'BU80', 'MR LIGHT', 'ELECTRONICS', 'LIGHTING', 'REC. LIGHT', 'COMBO', 'TORCH+TORCH', '01.TRADING', 'MR 670-2 CO', '24+24  EMERG', 'PCS', 104, 'QAR', NULL, 2);
-------End Row details--------------
复制


但是当取物品的长度时

select length('24+24  EMERG') from dual; 
复制


它给出了12个

我们已经将 “OR_ITEMS_TEMP”。“ITEMTYPE” 长度更改为14并插入值,它成功地通过了。之后,我们再次取了字段的长度,该字段的长度也与12相同。

为什么会有这样的行为?我们如何纠正这一点?请帮忙

致以最诚挚的问候,
斯雷朱

专家解答

这个问题很可能是由于以下事实: 在不同的字符集中,字符可以是不同长度的字节。

例如,如果您比较AL32UTF8和AR8MSWIN1256中变音符号的字节大小,您会看到:

select lengthb(CONVERT('Ä', 'AL32UTF8')) bytes from dual;

BYTES   
      2 

select lengthb(CONVERT('Ä', 'AR8MSWIN1256')) bytes from dual;

BYTES   
      1 
复制


那为什么这是个问题?

您可以使用字符或字节语义声明列长度。这决定了长度是以字节为单位还是以字符为单位。您不能在1字节列中插入单个两个字节的字符:

create table t (
  str_bytes varchar2(1 byte),
  str_chars varchar2(1 char)
);

insert into t values (CONVERT('Ä', 'AL32UTF8'), CONVERT('Ä', 'AL32UTF8'));

ORA-12899: value too large for column "CHRIS"."T"."STR_BYTES" (actual: 2, maximum: 1)

insert into t values (CONVERT('Ä', 'AR8MSWIN1256'), CONVERT('Ä', 'AR8MSWIN1256'));

1 row inserted.

select * from t;

STR_BYTES   STR_CHARS   
?           ? 
复制


所以我猜:

-“OR_ITEMS_TEMP”。“ITEMTYPE” 是目标上的varchar2(12字节)
-您在此列中有一些字符在AR8MSWIN1256中是一个字节,而在AL32UTF8中是两个字符

您可以检查user_tab_cols中的char (C) 或byte (B) 设置:

select column_name, char_used 
from   user_tab_cols
where  table_name = 'T';

COLUMN_NAME   CHAR_USED   
STR_BYTES     B           
STR_CHARS     C 
复制


您可以通过将长度修改为字符而不是字节来解决此问题:

alter table t modify ( str_bytes varchar2( 1 char ) );

insert into t ( str_bytes ) values (CONVERT('Ä', 'AL32UTF8'));

1 row inserted.

select * from t;

STR_BYTES   STR_CHARS   
?           ?           
�
复制

「喜欢这篇文章,您的关注和赞赏是给作者最好的鼓励」
关注作者
【版权声明】本文为墨天轮用户原创内容,转载时必须标注文章的来源(墨天轮),文章链接,文章作者等基本信息,否则作者和墨天轮有权追究责任。如果您发现墨天轮中有涉嫌抄袭或者侵权的内容,欢迎发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论