CREATE OR REPLACE TYPE EMP_SALARY_REC AS OBJECT (
EMP_ID NUMBER(5),
EMP_NAME VARCHAR2(255),
START_DATE DATE,
SALARY NUMBER
);
/
CREATE OR REPLACE Type EMP_SALARY_TAB AS TABLE OF EMP_SALARY_REC;
/
next we will create a small package with one single test procedure
CREATE OR REPLACE PACKAGE EMP_SALARY_PKG IS
PROCEDURE GET_EMP_SALARIES(i_array IN EMP_SALARY_TAB,o_array OUT
EMP_SALARY_TAB);
End EMP_SALARY_PKG;
/
用ibatis就不能配置调用吗?
问题补充
<parameterMap id="swapParameters" class="map" >
<parameter property="email1" jdbcType="VARCHAR" javaType="java.lang.String" mode="INOUT"/>
<parameter property="email2" jdbcType="VARCHAR" javaType="java.lang.String" mode="INOUT"/>
</parameterMap>
<procedure id="swapEmailAddresses" parameterMap="swapParameters" >
{call swap_email_address (?, ?)}
</procedure>
调用上面的存储过程将同时互换两个字段(数据库表)和参数对象(Map)中的两个email
地址。如果参数的mode属性设为INOUT或OUT,则参数对象的值被修改。否则保持不变。
参数是自定义的type类型(EMP_SALARY_TAB):
CREATE OR REPLACE TYPE EMP_SALARY_REC AS OBJECT (
EMP_ID NUMBER(5),
EMP_NAME VARCHAR2(255),
START_DATE DATE,
SALARY NUMBER
);
CREATE OR REPLACE Type EMP_SALARY_TAB AS TABLE OF EMP_SALARY_REC;
问题补充
中
小 订阅
最近项目里经常需要配置用Ibatis访问存储过程(或函数),多次摸索,发现配置的难点是在于如何配置输入输出参数。现以访问Oracle的存储过程(或函数)举例说明。
一般基本的配置要点如下:
(1)、访问存储过程(或函数)一般以procedure标签来定义statement。
(2)、输入输出的参数需要用parameterMap标签单独定义。
(3)、区分输入输出参数用parameter标签的mode属性来定义,分别为”OUT”和”IN”。
按照是否有返回值,是否使用游标分类说明如下:
第一类,没有返回结果,有输出参数以out标识的过程访问配置样式:
<parameterMap id=”functionPramsMap” class=”map”>
<parameter property=”p1″ jdbcType=”VARCHAR” javaType=”string” mode=”IN”/>
<parameter property=”p2″ jdbcType=”INTEGER” javaType=”int” mode=”IN”/>
<parameter property=”p3″ jdbcType=”INTEGER” javaType=”int” mode=”OUT” />
</parameterMap>
<procedure id=”statementId” parameterMap=”functionPramsMap”>
{call packageName.functionName(?,?,?)}
</procedure>
第二类,有返回结果,有输出参数以out标识的过程访问配置样式:
<parameterMap id=”functionParamsMap” class=”map”>
<parameter property=”p0″ jdbcType=” INTEGER” javaType=”string” mode=”OUT”/>
<parameter property=”p1″ jdbcType=”VARCHAR” javaType=”string” mode=”IN”/>
<parameter property=”p2″ jdbcType=”INTEGER” javaType=”int” mode=”IN”/>
<parameter property=”p3″ jdbcType=”INTEGER” javaType=”int” mode=”OUT” />
</parameterMap>
<procedure id=”statementId” parameterMap=” functionParamsMap”>
{?=call packageName.functionName(?,?,?)}
</procedure>
这里参数p0标识调用过程的返回结果。
第三类,有使用游标的的过程访问配置样式:
<resultMap id=”resultMap” class=”package.ClassA”>
<result property=”property0″ column=”field0″ />
<result property=”property1″ column=”field2″ />
<result property=”property2″ column=”field3″ />
</resultMap>
<parameterMap id=”functionParamsMap” class=”map”>
<parameter property=”p0″ jdbcType=” INTEGER” javaType=”string” mode=”OUT”/>
<parameter property=”p1″ jdbcType=”VARCHAR” javaType=”string” mode=”IN”/>
<parameter property=”p2″ jdbcType=”INTEGER” javaType=”int” mode=”IN”/>
<parameter property=”p3″ jdbcType=”ORACLECURSOR”
javaType=”java.sql.ResultSet” mode=”OUT” resultMap=”resultMap” />
</parameterMap>
<procedure id=”statementId” parameterMap=”functionPramsMap”>
{?=call packageName.functionName(?,?,?)}
</procedure>
这里,关键注意的是p3参数,由于使用的是oracle数据库驱动,所以用jdbcType=”ORACLECURSOR”表示oracle游标,同时由于是游标,所以javaType=”java.sql.ResultSet”。最后必须要给参数p3配置好resultMap属性,以说明游标返回的结果集映射方式,不配置此属性,在代码里来访问结果集是不行的。此时,在Java代码里调用的样式如下:
HashMap<String, Object> params = new HashMap<String, Object>();
params.put(”p1″, p1);
params.put(”p2″, p2);
sqlMapClient.queryForObject(”statementId”, params);
List<ClassA> list = (List<ClassA>) params.get(”p3″);
if (list != null && list.size() > 0) {
return userList.get(0);
}
return null;
第四类,有复杂的参数类型的存储过程:
(1)、对于BLOB或者CLOB,在POJO里的属性都定义为byte[]类型,iBatis配置里跟普通类型参数一样处理;
(2)、实现TypeHandler来自定义类型处理器用户处理复杂的字段;
(3)、对于数据库自定义的数据类型,首先要定义实现了java.sql.SQLData的类Class TypeA。实现getSQLTypeName方法,返回值为数据库的自定义类型名。配置文件里parameter标签的属性如:jdbcType=”TypeB” JavaType=”TypeA”,同时还要写TypeHandlerCallback用于处理jdbcType=”TypeB”的类型。
我现在需要第四类的例子,如何构建ARRAY