将国家字符插入oracle NCHAR或NVARCHAR列不起作用

在oracle数据库中插入字符串时,某些国家字符将替换为问号,即使它们插入NCHAR或NVARCHAR列中 – 应该能够处理所有Unicode字符。

使用Oracle的SQL Developer,sqlplus或使用JDBC驱动程序会发生这种情况。

数据库NLS_CHARACTERSET设置为WE8ISO8859P1(西欧iso-8859-1)。用于NCHAR列的NLS_NCHAR_CHARACTERSET设置为AL16UTF16。 (UTF-16)

任何不在NLS_CHARACTERSET中的字符似乎都被替换为反转的问号。

编辑:请注意,在Oracle上处理UTF的最佳方法是使用数据库字符集AL32UTF8创建数据库,并使用普通的varchar2列。 使用nchar列的一个问题是,当默认情况下将参数作为nchar发送时,oracle不能使用普通char / varchar2列的索引。

无论如何:如果你不能转换数据库:


首先,unicode文字需要以’n’为前缀,如下所示:

select n'Language - Språk - Język' from dual; 

*)8位编码无法处理此文本

不幸的是,这还不够。

出于某种原因,数据库客户端的默认行为是将所有字符串文字转换为数据库字符集,这意味着即使在数据库看到字符串之前,也会更改值。

客户端需要一些配置才能将unicode字符插入NCHAR或NVARCHAR列:

Unix上的SQL Plus

这些environemnet变量设置unix环境和sqlplus使用UTF-8文件,并配置sqlplus以在unicode中发送字符串文字。

 NLS_LANG=AMERICAN_AMERICA.AL32UTF8 LC_CTYPE="en_US.UTF-8" ORA_NCHAR_LITERAL_REPLACE=true 

(en_US.UTF-8适用于Solaris – Linux或其他系统可能需要不同的字符串,使用locale -a列出支持的语言环境。)

JDBC驱动程序

使用Oracles JDBC驱动程序的应用程序需要定义以下系统属性,以便在unicode中发送字符串文字。

 -Doracle.jdbc.defaultNChar=true -Doracle.jdbc.convertNcharLiterals=true 

SQL Developer

找到sqldeveloper.conf,并添加以下行:

 AddVMOption -Doracle.jdbc.defaultNChar=true AddVMOption -Doracle.jdbc.convertNcharLiterals=true 

Microsoft Windows上的SQL Plus

如果Microsoft Windows上的SQLplus或Toad完全处理utf-8,我还没试过。 Sqlplusw.exe可能会这样做,并且以下注册表设置可能会起作用。

 NLS_LANG=AMERICAN_AMERICA.AL32UTF8 ORA_NCHAR_LITERAL_REPLACE=true 

谢谢KarlP – 让我走了。 重新利用对我有用的东西。

使用linux上的sqlplus将中文(任何utf8)文本插入非unicode数据库的nvarchar列(例如:ISO8859等)。

这些db params在我的系统上,注意char的单字节编码,但nchare的多字节编码。 NLS_CHARACTERSET WE8ISO8859P1
NLS_NCHAR_CHARACTERSET AL16UTF16

例如:

 INSERT INTO tt values ( N'气前照灯' ); 

字符串前面的’N’很重要。 另外,必须在启动sqlplus之前设置env,

 # Important to tell sqldeveloper what encoding is needed. export NLS_LANG=AMERICAN_AMERICA.UTF8 # Others might find AMERICAN_AMERICA.AL32UTF8 or whatever better suits. # ** THIS MATTERS - DOES NOT WORK WITHOUT !! export ORA_NCHAR_LITERAL_REPLACE=true