将一个复杂的模型列表从Java传递给PL / SQL

时间:2014-11-14 19:07:35

标签: java oracle data-structures plsql

我正在尝试将模型列表传递给PL / SQL函数

我创建了两种类型,如此

create or replace TYPE SPECIAL_TYPE AS OBJECT(
 SPECIAL_ID NUMBER,
 NAME VARCHAR2(4000),
 IS_ACTIVE NUMBER);

create or replace TYPE SPECIAL_ARRAY 
AS TABLE OF SPECIAL_TYPE;

我已将模型定义为以下

public Class Special{

  protected long specialId;
  protected String specialName;
  protected boolean isActive;

     public long getSpecialId() {
        return specialId;
    }

    public void setSpecialId(long value) {
        this.specialId = value;
    }

    public String getSpecialName() {
        return specialName;
    }

    public void setSpecialName(String value) {
        this.specialName = value;
    }


    public boolean isIsActive() {
        return isActive;
    }

    public void setIsActive(boolean value) {
        this.isActive = value;
    }

}

在我的DAO类中,我试图将上面定义的模型列表传递给PL / SQL过程。为了实现这一点,我有以下代码

Object[] listToPass=list.toArray();

ArrayDescriptor descriptor = ArrayDescriptor.createDescriptor( "SPECIAL_ARRAY", conn );

ARRAY array_to_pass = new ARRAY( descriptor, conn, listToPass);

一旦我到达上面的行,我得到一个异常,即bean无法转换为内部表示。

Caused by: java.sql.SQLException: Fail to convert to internal representation: Special [specialId=81, specialName=CHP, isActive=true]
    at oracle.jdbc.oracore.OracleTypeADT.toDatum(OracleTypeADT.java:339)
    at oracle.jdbc.oracore.OracleTypeADT.toDatumArray(OracleTypeADT.java:372)
    at oracle.jdbc.oracore.OracleTypeUPT.toDatumArray(OracleTypeUPT.java:108)
    at oracle.sql.ArrayDescriptor.toOracleArray(ArrayDescriptor.java:1321)
    at oracle.sql.ARRAY.<init>(ARRAY.java:141)
    ... 70 more

我遗失了一些小东西,但我无法弄清楚是什么。感谢您的帮助。

1 个答案:

答案 0 :(得分:0)

执行此操作的一种方法是让Special班级实施SQLData

您的Special类中接口方法的实现如下:

    public String getSQLTypeName() { 
        return "SPECIAL_TYPE";
    }

    public void readSQL(SQLInput stream, String typeName) throws SQLException {
        this.specialId = stream.readLong();
        this.specialName = stream.readString();
        this.isActive = (stream.readInt() != 0);
    }    

    public void writeSQL(SQLOutput stream) throws SQLException {
        stream.writeLong(this.specialId);
        stream.writeString(this.specialName);
        stream.writeInt(this.isActive ? 1 : 0);
    }

您还需要将类型添加到database connection's type map。每当您获得可能使用SPECIAL_TYPE类型的数据库连接时执行此操作:

        Map<String, Class<?>> map = conn.getTypeMap();
        map.put("SPECIAL_TYPE", Special.class);
        conn.setTypeMap(map);