Mybatis之基于XML的调用存储过程与手动回滚事务
一、调用存储过程
一、返回单个值
1、存储过程准备
这里先创建一个存储过程,传入参数为age,传出参数为count。然后先测试一下是否正确。

CREATE DEFINER=`root`@`localhost` PROCEDURE `pro_get_usercountbyage`(in age int,out user_count int) BEGIN select count(1) into user_count from user a where a.age=age; END

DELIMITER ; SET @user_count = 0; CALL mybatis.pro_get_usercountbyage(27, @user_count); SELECT @user_count;
2、XML配置
这里配置传入参数的映射parameterMap,statementType,在parameterMap中设置参数的方向。

<select id="getUserCount" parameterMap="getUserCountMap" statementType="CALLABLE"> CALL pro_get_usercountbyage(?,?) </select> <parameterMap type="java.util.Map" id="getUserCountMap"> <parameter property="age" mode="IN" jdbcType="INTEGER"/> <parameter property="usercount" mode="OUT" jdbcType="INTEGER"/> </parameterMap>
3、测试
这里传入参数age=27,然后获取返回的结果值。

String statement="Cuiyw.MyBatis.DBMapping.UserMapper.getUserCount"; Map<String,Integer > map=new HashMap<String,Integer>(); map.put("age", 27); session.selectOne(statement, map); int result = map.get("usercount"); System.out.println(result);
二、返回列表
1.返回列表的和返回多个值的基本没太大区别,只是有一个地方需要注意,就是在存储过程select的列名要和resultMap的一致,我就踩到坑了在这个地方。存储过程还是在上面存储过程上改的。返回table。

DELIMITER ; CALL mybatis.pro_get_usercountbyage(27); DELIMITER $$ CREATE DEFINER=`root`@`localhost` PROCEDURE `pro_get_usercountbyage`(in age int) BEGIN select * from user a where a.age=age; END$$ DELIMITER ;
2.xml配置
这个只是增加了resultMap

<select id="getUserCount" parameterMap="getUserCountMap" statementType="CALLABLE" resultMap="userResult"> CALL pro_get_usercountbyage(?) </select> <parameterMap type="java.util.Map" id="getUserCountMap"> <parameter property="age" mode="IN" jdbcType="INTEGER"/> </parameterMap>
3.测试

String statement="Cuiyw.MyBatis.DBMapping.UserMapper.getUserCount"; Map<String,Integer > map=new HashMap<String,Integer>(); map.put("age", 27); List<User>users= session.selectList(statement, map); for(int i=0;i<users.size();i++) { System.out.println(users.get(i).toString()); }
二、手动回滚事务
前面的demo中都是openSession()传的都是true,表示自动开启事务,这里演示下不是自动的情况。

String resource = "Config.xml"; //使用MyBatis提供的Resources类加载mybatis的配置文件(它也加载关联的映射文件) Reader reader = Resources.getResourceAsReader(resource); //构建sqlSession的工厂 SqlSessionFactory sessionFactory = new SqlSessionFactoryBuilder().build(reader); //创建能执行映射文件中sql的sqlSession SqlSession session = sessionFactory.openSession(false); // System.out.println("新增"); String statement="Cuiyw.MyBatis.DBMapping.UserMapper.addUser"; try{ User user1=new User(); user1.setName("Cuiyw"); user1.setAge(27); user1.setStatus(UserState.AVAILABLE); int result=session.insert(statement, user1); User user2=new User(); user2.setName("Cuiyw"); user2.setAge(1/0); user2.setStatus(UserState.AVAILABLE); result=session.insert(statement, user2); session.commit(); System.out.println("OK"); } catch(Exception e){ System.out.println("出错------------"); e.printStackTrace(); session.rollback(); } finally { session.close(); }
上面实现User的新增,增加了两个user,第一个正常的,第二个会报错,当openSession()参数为false时执行上面的代码,会自动回滚,一条数据都没保存,如果是true时,会增加了第一条。
---------------我是有底线的--------------------
作者:社会主义接班人
出处:http://www.cnblogs.com/5ishare/
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。
如果文中有什么错误,欢迎指出。以免更多的人被误导。
作者:社会主义接班人
出处:http://www.cnblogs.com/5ishare/
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。
如果文中有什么错误,欢迎指出。以免更多的人被误导。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 分享 3 个 .NET 开源的文件压缩处理库,助力快速实现文件压缩解压功能!
· Ollama——大语言模型本地部署的极速利器
· DeepSeek如何颠覆传统软件测试?测试工程师会被淘汰吗?