2012-05-03 17 views
2

SQL文字列配列をプリペアドステートメントにバインドしようとしていますが、一部のデータベースのcharsetでは配列の値がnullになります。単純な文字列(配列ではない)をバインドすると、機能します。Jdbc配列バインド:文字セットエンコーディング

文字セット(v $ nls_parametersのNLS_CHARACTERSET)がAL32UTF8の場合、正常に動作します。 WE8ISO8859P15の場合、文字列をバインドできますが、文字列はバインドできません。違いは、Oracle JDBCには変換がサポートされているspecific list of character setがあり、ISO-8859-15はその一部ではないということです。

DBの中ですべての文字列をnullに変換すると、問題の一部が説明されます。しかし、文字列が配列に含まれていない場合は変換が機能します...だから私は混乱します。

私の全体的なテストは以下の通りです。私は私が宣言し、私の​​配列をバインド方法で、何か間違ったことをやっていると思われる

Connection connection; 

@Before 
public void setup() throws SQLException { 
    OracleDataSource ds = new OracleDataSource(); 
    ds.setUser("aaa"); 
    ds.setPassword("a"); 
    ds.setURL("jdbc:oracle:thin:@server:1521:orcl"); 
    connection = ds.getConnection(); 
} 

@Test 
// works with both AL32UTF8 and WE8ISO8859P15 
public void testScalar() throws SQLException { 
    CallableStatement stmt = connection.prepareCall("declare a varchar2(4000) := ?; " 
      + "begin if a is null then raise_application_error(-20000,'null'); end if; end;"); 
    stmt.setString(1, "a"); 
    stmt.execute(); 
} 

@Test 
// works only with AL32UTF8 
public void testArray() throws SQLException { 
    ArrayDescriptor descriptor = ArrayDescriptor.createDescriptor("T_V4000_TABLE", connection); 
    String[] array = new String[] {"a"}; 
    Array sqlArray = new ARRAY(descriptor, connection, array); 
    CallableStatement stmt = connection.prepareCall("declare a t_v4000_table := ?; " + 
      "begin if a(1) is null then raise_application_error(-20000,'null'); end if; end;"); 
    stmt.setArray(1, sqlArray); 
    stmt.execute(); 
} 

create type t_v4000_table as table of varchar2(4000);として私が使用しているテーブル型が定義されていますが、私は何かを見つけることができません。何か案が?

+0

のように動作します: 'VARCHAR2(4000)のテーブルとして型t_v4000_tableを作成;' – Xavier

+0

私はそれをテーブルに変更した場合nvarchar2(4000)のテスト・パスですが、NLS_NCHAR_CHARACTERSETはOracle JDBCでサポートされているインスタンスのAL16UTF16であるためです。だから私は他のところで問題を動かすだけだ... – Xavier

答えて

3

ソリューションだけでなく、実際のオブジェクト/コレクション内の文字列の区別か、is well documented、:

基本的なJavaアーカイブ(JAR)のojdbc5.jarファイル、およびojdbc6.jarは、すべて含まれていOracleオブジェクトまたはコレクション型のデータ・メンバーとして取得または挿入されないCHAR、VARCHAR、LONGVARCHAR、またはCLOBデータ用

  • Oracleキャラクタ・セット:のための完全なグローバリゼーション・サポートを提供するために必要なクラス。
  • キャラクタ・セットUS7ASCII、WE8DEC、WE8ISO8859P1、WE8MSWIN1252およびUTF8のオブジェクトおよびコレクションのCHARまたはVARCHARデータ・メンバー。

オブジェクトまたはコレクションのCHARまたはVARCHARデータ・メンバーに他の文字セットを使用するには、アプリケーションのCLASSPATH環境変数にorai18n.jarを含める必要があります。

CLASSPATHにorai18n.jarをを追加した後、それはそれは問題ではすでにの魅力