博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Mybatis使用存储过程以及原理
阅读量:7192 次
发布时间:2019-06-29

本文共 4466 字,大约阅读时间需要 14 分钟。

hot3.png

一直在用Mybatis,身处互联网公司,对于存储过程这块一直没怎么使用,数据库设计基本上都是单表+冗余+服务划分来设计,关键部分使用缓存,因此对存储过程一直不怎么感冒。今天偶然看到一篇Mybatis操作存储过程的文章,发现了一奇妙的事情(可能是见识少了些),传入的参数在查询成功后就有了结果的值。二话不说下载源码就开干!

-------------------------------------------一个文档中的内容,未标明作者,这里就不注明版权了------------------------

首先是,数据库创建的脚本:

CREATE TABLE p_user(id INT PRIMARY KEY AUTO_INCREMENT,NAME VARCHAR(10),sex CHAR(2));INSERT INTO p_user(NAME,sex) VALUES('A',"男");INSERT INTO p_user(NAME,sex) VALUES('B',"女");INSERT INTO p_user(NAME,sex) VALUES('C',"男");#创建存储过程( 查询得到男性或女性的数量,  如果传入的是 0  就女性否则是男性)DELIMITER $CREATE PROCEDURE tssss.ges_user_count(IN sex_id INT, OUT user_count INT)BEGINIF sex_id=0 THENSELECT COUNT(*) FROM tssss.p_user WHERE p_user.sex='女' INTO user_count;ELSESELECT COUNT(*) FROM tssss.p_user WHERE p_user.sex='男' INTO user_count;END IF;END$#调用存储过程DELIMITER ;SET @user_count = 0;CALL tssss.ges_user_count(1, @user_count);SELECT @user_count;

然后新建一个Java项目,需要的jar包为Mybatis的jar和mysql连接jar,如下:

mybatis-3.2.8.jarmysql-connector-java-5.1.34.jar

新建一个Mybatis的配置文件sqlMapConfig.xml

新建一个mapper映射文件TssssMapper.xml:

新建一个测试类:

package mybatis2;import java.io.IOException;import java.io.Reader;import java.util.HashMap;import java.util.Map;import org.apache.ibatis.io.Resources;import org.apache.ibatis.session.ResultContext;import org.apache.ibatis.session.ResultHandler;import org.apache.ibatis.session.SqlSession;import org.apache.ibatis.session.SqlSessionFactory;import org.apache.ibatis.session.SqlSessionFactoryBuilder;public class A {          public static void main(String[] args) throws IOException {         String resource = "sqlMapConfig.xml";         Reader reader = Resources.getResourceAsReader(resource);       SqlSessionFactory ssf = new SqlSessionFactoryBuilder().build(reader);             SqlSession session = ssf.openSession();         Map
paramMap = new HashMap<>(); paramMap.put("sex_id", 1); try { Object returnValue = session.selectOne("getCount", paramMap); System.out.println("result="+paramMap.get("result")); System.out.println("sex_id="+paramMap.get("sex_id")); System.out.println("returnValue="+returnValue); } catch (Exception e) { e.printStackTrace(); } finally { session.close(); } System.out.println("result="+paramMap.get("result")); System.out.println("sex_id="+paramMap.get("sex_id")); } }

--------------------------------------------------------------------------------------------------------------------------------------------------

很神奇的发现,传入的paraMap参数在查询后有了存储过程的结果值 result,我决定去找找源码。通过跟踪找到了两个关键的类org.apache.ibatis.mapping.ParameterMode.java和org.apache.ibatis.executor.resultset.DefaultResultSetHandler.Java:

package org.apache.ibatis.mapping;/** * @author Clinton Begin */public enum ParameterMode {  IN, OUT, INOUT}
public void handleOutputParameters(CallableStatement cs) throws SQLException {    final Object parameterObject = parameterHandler.getParameterObject();    final MetaObject metaParam = configuration.newMetaObject(parameterObject);    final List
parameterMappings = boundSql.getParameterMappings(); for (int i = 0; i < parameterMappings.size(); i++) { final ParameterMapping parameterMapping = parameterMappings.get(i); if (parameterMapping.getMode() == ParameterMode.OUT || parameterMapping.getMode() == ParameterMode.INOUT) { if (ResultSet.class.equals(parameterMapping.getJavaType())) { handleRefCursorOutputParameter((ResultSet) cs.getObject(i + 1), parameterMapping, metaParam); } else { final TypeHandler
typeHandler = parameterMapping.getTypeHandler(); metaParam.setValue(parameterMapping.getProperty(), typeHandler.getResult(cs, i + 1)); } } } }

其中在DefaultResultSetHandler类中的handleOutputParameters(CallableStatement cs)方法中处理了传入参数和传出的参数。有兴趣的童鞋也可以试着跟一下,这里判断了当parameterMapping.getMode() == ParameterMode.OUT时候,即现在操作的为存储过程的out参数,因此这里在metaParam.setValue(parameterMapping.getProperty(), typeHandler.getResult(cs, i + 1)); 该句的时候将存储过程的result值设置给了输入的参数map。

该句执行前:

该句执行后:

到此为止,知道其内部的设置结果。其实对于使用来说这并没有什么意义,但是多看源码对自己的思路以及底层还是有好处,反正我是信了。

纯手打,欢迎拍砖~

转载请指明出处:

转载于:https://my.oschina.net/u/1991646/blog/731250

你可能感兴趣的文章
[20171107]dbms_shared_pool.pin.txt
查看>>
UIView
查看>>
mysql-distinct去重、mysql-group&nbsp;…
查看>>
Vmworkstation启用错误
查看>>
mysql中函数DISTINCT,group by,CONCAT及GROUP_CONCAT的使用
查看>>
4月5日 编码问题
查看>>
消息反射
查看>>
DVWA之brute force
查看>>
HTML DOM 第一篇
查看>>
Java 枚举类型简介
查看>>
21. Merge Two Sorted Lists (Java 合并有序链表 空间复杂度O(1))
查看>>
Visual Studio 2010 Shortcut
查看>>
一些互联网术语
查看>>
ArrayList的底层实现
查看>>
基于Cyclone II Device Hankbook 的几种电压描述(转)
查看>>
springboot单元测试通过MockMvc类调用controller接口
查看>>
[NOI2013]快餐店
查看>>
Linux 文件操作总结
查看>>
Chrome下的语音控制框架MyVoix.js使用篇(三)
查看>>
【iOS】UIKit框架 学习笔记
查看>>