mybatis调用存储过程

来源:互联网 发布:网络骑士作家百科 编辑:程序博客网 时间:2024/03/29 23:37

记两一下工作中用到的mybatis调用存储过程,这边用到的mybatis是3.2.2版本,oracle 10g。

一、返回一个值的存储过程,如下:

CREATE OR REPLACE PROCEDURE "SP_MF_I_IMP"          ( I_MANIFEST_I_ID    IN NUMBER ,            I_FUNCTION_CODE  IN VARCHAR2,            I_FIRM_ID        IN NUMBER,            I_OP_USER        IN VARCHAR2, --操作人ID            O_RETURN_MESSAGE OUT VARCHAR2  ) AS          --根据SEQ生成的报文头表的ID          V_HEAD_INFO_ID NUMBER(11);          --报文编号中,年月日时生成          V_YYMMDDHHMM VARCHAR2(10);          --报文编号          V_MESSAGE_ID VARCHAR2(50);          --申报人          V_SEND_ID VARCHAR2(50);          --货物运输批次号          V_TRAN_NO VARCHAR2(13);          --提运单号          V_BILL_NO VARCHAR2(35);          --异常报文          STR_L_ERRMSG VARCHAR2(3000);          --新增,修改,删除类型          V_FUNTYPE VARCHAR2(5);          --是否已经申报的标识          V_DECLARE VARCHAR(5);                    BEGIN                       --当要申报的单的状态为‘001’新单,‘008’发送海关失败时才需要发送            IF V_DECLARE = '001' OR V_DECLARE = '008' THEN                --获得SEQ_EDI_HEAD_INFO的值                SELECT EDI.SEQ_EDI_HEAD_INFO.NEXTVAL INTO V_HEAD_INFO_ID FROM DUAL;                --组装生成报文编号中的'YYMMDDHHMM'                SELECT TO_CHAR(SYSDATE,'YYMMDDHH24MI') INTO V_YYMMDDHHMM FROM DUAL;                --生成报文编号                V_MESSAGE_ID := '78921227X'|| V_YYMMDDHHMM || I_MANIFEST_I_ID;                --通过GET_SEND_ID函数获取SENDID                V_SEND_ID := GET_SEND_ID(I_FIRM_ID);                --新增报文头表信息                INSERT INTO EDI.EDI_MANIFEST_I_HEAD_INFO                  (ID,MESSAGE_ID,FUNCTION_CODE,MESSAGE_TYPE,SENDER_ID,RECEIVER_ID,VERSION,IMP_ID)                VALUES                  (V_HEAD_INFO_ID,V_MESSAGE_ID,I_FUNCTION_CODE,'MT1401',V_SEND_ID,'EPORT','1.0',I_MANIFEST_I_ID);                               O_RETURN_MESSAGE := 'success';                  --写入LOG表                  SP_TRACE_WRITE(V_FUNTYPE, V_TRAN_NO, V_BILL_NO, I_OP_USER, '004', STR_L_ERRMSG, O_RETURN_MESSAGE);                 END;              ELSE ---表示没有对应的申报类型,事物回滚,写入异常日志                O_RETURN_MESSAGE := 'error';                RAISE_APPLICATION_ERROR(-20100, 'Invalid Registration');              END IF;                COMMIT;                    --异常处理        EXCEPTION        WHEN   OTHERS   THEN            STR_L_ERRMSG := SQLCODE || ' ' || SQLERRM;            ROLLBACK ;  --异常处理,异常点上面的操作都不会被执行            O_RETURN_MESSAGE := 'error';            SP_TRACE_WRITE(V_FUNTYPE, V_TRAN_NO, V_BILL_NO, I_OP_USER, '005', STR_L_ERRMSG, O_RETURN_MESSAGE);            COMMIT;    END SP_MF_I_IMP;
中间加入了异常处理,出现异常要回滚并且写入日志表,同时返回显示是否成功的标识。

如下是在mybatis配置如下:

<parameterMap id="sendMap" type="java.util.HashMap">  <parameter property="I_MANIFEST_I_ID" jdbcType="NUMERIC" javaType="java.lang.Long" mode="IN"/>  <parameter property="I_FUNCTION_CODE" jdbcType="VARCHAR" javaType="java.lang.String" mode="IN"/>  <parameter property="I_FIRM_ID" jdbcType="NUMERIC" javaType="java.lang.Integer" mode="IN"/>  <parameter property="I_OP_USER" jdbcType="VARCHAR" javaType="java.lang.String" mode="IN"/><parameter property="O_RETURN_MESSAGE" jdbcType="VARCHAR" javaType="java.lang.String" mode="OUT"/>  </parameterMap><update id="sendManifstmanToEdi" parameterMap="sendMap" statementType="CALLABLE"><![CDATA[{call SP_MF_I_IMP(?, ?, ?, ?, ?)}  ]]></update>  

存储过程中都有IN,OUT的参数,创建一个<parameterMap>列出你要向存储过程传递的参数与获取的返回值。因为这边会有更新数据字段的设置,所以这边用的是<update>,再在后台之后代码的设值、调用、获取返回值如下:

private String sendEdi(Long id) throws Exception {String result = "";Map<String,Object> params = new HashMap<String, Object>();try {params.put("I_MANIFEST_I_ID", id); params.put("I_FUNCTION_CODE", Constants.MAINIFEST_DECLARE); params.put("I_FIRM_ID", getFirmOfLoginUser().getFirmId()); params.put("I_OP_USER", getLoginUser().getLoginName());params.put("O_RETURN_MESSAGE", "");manifestIMainService.sendManifstmanToEdi(params);result = String.valueOf(params.get("O_RETURN_MESSAGE"));} catch (Exception e) {log.error("sendEdi occurred error.", e);if(Constants.IS_TEST)setErrorMsg(e.getMessage());}return result;}

二、返回SYS_REFCURSOR,我们取出将其对应成为一个List,写在<parameterMap>里面,存储过程如下:

CREATE OR REPLACE PROCEDURE "SP_TRACE_GET"(I_DATA_TYPE IN CHAR,                                          I_TRAN_NO   IN VARCHAR2,                                          I_BILL_NO   IN VARCHAR2,                                          O_LIST      OUT SYS_REFCURSOR) AS  CURSOR_VALUE SYS_REFCURSOR;BEGIN  CASE    WHEN I_DATA_TYPE = 'I' THEN      BEGIN        OPEN CURSOR_VALUE FOR      SELECT A.*          FROM MANIFEST_I_LOG A         WHERE A.TRAN_NO = I_TRAN_NO           AND A.BILL_NO = I_BILL_NO;       EXCEPTION         WHEN no_data_found THEN              RETURN;      END;      BEGIN      OPEN CURSOR_VALUE FOR       SELECT T.* FROM(        SELECT A.*          FROM MANIFEST_I_LOG A         WHERE A.TRAN_NO = I_TRAN_NO           AND A.BILL_NO = I_BILL_NO        UNION ALL        SELECT B.*          FROM BINDING_L_LOG B         WHERE B.TRAN_NO = I_TRAN_NO        UNION ALL        SELECT C.* FROM LOADCHANG_LOG C WHERE C.TRAN_NO = I_TRAN_NO)T ORDER BY T.OP_TIME DESC;        END;    WHEN I_DATA_TYPE = 'C' THEN      OPEN CURSOR_VALUE FOR        SELECT * FROM LOADCHANG_LOG WHERE TRAN_NO = I_TRAN_NO ORDER BY OP_TIME DESC;  END CASE;  O_LIST := CURSOR_VALUE;END SP_TRACE_GET;
返回查询出来的结果,在mybatis的配置文件中可以跟上面一种不一样的方式来写,配置如下:

<!-- 结果集映射 --><resultMap id="flowLogsResultMap" type="com.hwt.glmf.log.vo.FlowLogModel"><result column="ID" property="id" /><result column="STATUS" property="status" /><result column="OP_USER" property="op_user" /><result column="OP_TIME" property="op_time" /><result column="BILL_NO" property="bill_no" /><result column="TRAN_NO" property="tran_no" /><result column="MEMO" property="memo" /><result column="DATA_TYPE" property="data_type" /></resultMap><!-- jdbcType=INTEGER  ORACLE:INT--><select id="viewFlowLog" parameterType="java.util.Map" statementType="CALLABLE"><![CDATA[{call SP_TRACE_GET(#{I_DATA_TYPE,mode=IN,jdbcType=VARCHAR},#{I_TRAN_NO,mode=IN,jdbcType=VARCHAR},#{I_BILL_NO,mode=IN,jdbcType=NUMERIC},#{O_LIST,mode=OUT,jdbcType=CURSOR,javaType=java.sql.ResultSet,resultMap=flowLogsResultMap})}]]></select>


在后台代码如下:

public List<FlowLogModel> viewFlowLog(String dataType, String tran_no,String bill_no) throws Exception {Map<String, Object> param = new HashMap<String, Object>(); param.put("I_DATA_TYPE", dataType);param.put("I_TRAN_NO", tran_no);param.put("I_BILL_NO", bill_no);param.put("O_LIST", OracleTypes.CURSOR);flowLogDao.viewFlowLog(param);return (List<FlowLogModel>)param.get("O_LIST");}

由此完成调用与取返回值,值得说的下的是在配置文件中配置<parameterMap>时对应的

 parameterType="java.util.Map"

中的值全是java中具备的基础类型,而且根据字段的长度选择对应的类型。




0 0
原创粉丝点击