欢迎访问 生活随笔!

生活随笔

当前位置: 首页 > 前端技术 > javascript >内容正文

javascript

iBatis整理——iBatis批处理实现(Spring环境)

发布时间:2025/7/14 javascript 34 豆豆
生活随笔 收集整理的这篇文章主要介绍了 iBatis整理——iBatis批处理实现(Spring环境) 小编觉得挺不错的,现在分享给大家,帮大家做个参考.
最近做一个小项目,用到Spring+iBatis。突然遇到一个很久远,却很实在的问题:在Spring下怎么使用iBatis的批处理实现? 

大概是太久没有写Dao了,这部分真的忘得太干净了。 

从4个层面分析这部分实现: 
  • iBatis的基本实现
  • 基于事务的iBatis的基本实现
  • 基于事务的Spring+iBatis实现
  • 基于回调方式的Spring+iBatis实现


  • 1.iBatis的基本实现 
    iBatis通过SqlMapClient提供了一组方法用于批处理实现: 
  • startBatch() 开始批处理
  • executeBatch() 执行批处理

  • 代码如下: 
    Java代码 
  • public void create(List<Reply> replyList) {  
  •   
  •     try {  
  •         // 开始批处理  
  •         sqlMapClient.startBatch();  
  •   
  •         for (Reply reply: replyList) {  
  •             // 插入操作  
  •             sqlMapClient.insert("Reply.create", reply);  
  •         }  
  •         // 执行批处理  
  •         sqlMapClient.executeBatch();  
  •   
  •     } catch (Exception e) {  
  •         e.printStackTrace();  
  •     }  
  • }  

  • 这是基于iBatis的最基本实现,如果你一步一步debug,你会发现:其实,数据库已经执行了插入操作! 
    因此,除了这两个核心方法外,你还需要开启事务支持。否则,上述代码只不过是个空架子! 

    2.基于事务的iBatis的基本实现 
    事务处理: 
  • startTransaction() 开始事务
  • commitTransaction() 提交事务
  • endTransaction() 结束事务


  • 我们以insert操作为例,把它们结合到一起: 
    Java代码 
  • public void create(List<Reply> replyList) {  
  •   
  •     try {  
  •         // 开始事务  
  •         sqlMapClient.startTransaction();  
  •         // 开始批处理  
  •         sqlMapClient.startBatch();  
  •   
  •         for (Reply reply: replyList) {  
  •             // 插入操作  
  •             sqlMapClient.insert("Reply.create", reply);  
  •         }  
  •         // 执行批处理  
  •         sqlMapClient.executeBatch();  
  •   
  •         // 提交事务  
  •         sqlMapClient.commitTransaction();  
  •   
  •     } catch (Exception e) {  
  •         e.printStackTrace();  
  •     } finally {    
  •              try {  
  •             // 结束事务  
  •             sqlMapClient.endTransaction();  
  •                 } catch (SQLException e) {  
  •                          e.printStackTrace();  
  •                      }  
  •     }    
  • }  

  • replyList是一个List,要把这个List插入到数据库,就需要经过这三个步骤: 
  • 开始批处理 startBatch()
  • 插入      insert()
  • 执行批处理 executeBatch()

  • 如果要在Spring+iBatis中进行批处理实现,需要注意使用同一个sqlMapClient!同时,将提交事务的工作交给Spring统一处理! 

    3.基于事务的Spring+iBatis实现 
    Java代码 
  • public void create(List<Reply> replyList) {  
  •     if (!CollectionUtils.isEmpty(replyList)) {  
  •         // 注意使用同一个SqlMapClient会话  
  •         SqlMapClient sqlMapClient = sqlMapClientTemplate.getSqlMapClient();  
  •   
  •         try {  
  •             // 开始事务  
  •             sqlMapClient.startTransaction();  
  •             // 开始批处理  
  •             sqlMapClient.startBatch();  
  •             for (Reply reply : replyList) {  
  •                 // 插入操作  
  •                 sqlMapClient.insert("Reply.create", reply);  
  •             }  
  •   
  •             // 执行批处理  
  •             sqlMapClient.executeBatch();  
  •             // 提交事务 交给Spring统一控制  
  •             // sqlMapClient.commitTransaction();  
  •   
  •         } catch (Exception e) {  
  •             e.printStackTrace();  
  •         } finally {    
  •                  try {  
  •                 // 结束事务  
  •                 sqlMapClient.endTransaction();  
  •                     } catch (SQLException e) {  
  •                              e.printStackTrace();  
  •                          }  
  •         }    
  •     }  
  • }  

  • 注意使用同一个sqlMapClient: 
    SqlMapClient sqlMapClient = sqlMapClientTemplate.getSqlMapClient(); 
    如果直接sqlMapClientTemplate执行insert()方法,将会造成异常! 

    想想,还有什么问题?其实问题很明显,虽然解决了批处理实现的问题,却造成了事务代码入侵的新问题。 这么做,有点恶心! 
    除此之外,异常的处理也很恶心,不能够简单的包装为 DataAccessException 就无法被Spring当作统一的数据库操作异常做处理。 


    4.基于回调方式的Spring+iBatis实现 
    如果观察过Spring的源代码,你一定知道,Spring为了保持事务统一控制,在实现ORM框架时通常都采用了回调模式,从而避免了事务代码入侵的可能! 
    修改后的代码如下: 
    Java代码 
  • @SuppressWarnings("unchecked")  
  • public void create(final List<Reply> replyList) {  
  •     // 执行回调  
  •     sqlMapClientTemplate.execute(new SqlMapClientCallback() {  
  •         // 实现回调接口  
  •         public Object doInSqlMapClient(SqlMapExecutor executor)  
  •                 throws SQLException {  
  •             // 开始批处理  
  •             executor.startBatch();  
  •             for (Reply reply : replyList) {  
  •                 // 插入操作  
  •                 executor.insert("Reply.create", reply);  
  •   
  •             }  
  •             // 执行批处理  
  •             executor.executeBatch();  
  •   
  •             return null;  
  •   
  •         }  
  •     });  
  •   
  • }  

  • 注意,待遍历的参数replyList需要加入final标识!即,待遍历对象不能修改! 
    引用public void create(final List<Reply> replyList)
    这样做,就将事务处理的控制权完全交给了Spring! 
    简述: 
  • SqlMapClientCallback 回调接口
  • doInSqlMapClient(SqlMapExecutor executor) 回调实现方法
  • DataAccessException 最终可能抛出的异常

  • 通过上述修改,最终能够解决第三种实现方式中的种种不足! 

    Spring对iBatis提供的支持还是不够完善,即便是现在最新的Spring3.0.4。最开始,本打算用Spring3.0+iBatis3.0,结果Spring报错,说找不到“com.ibatis.xxxxx”完全是iBatis2.x的包路径!汗颜~ 还是Hibernate比较得宠! 

    转载于:https://www.cnblogs.com/sunwei2012/archive/2010/11/26/1888497.html

    总结

    以上是生活随笔为你收集整理的iBatis整理——iBatis批处理实现(Spring环境)的全部内容,希望文章能够帮你解决所遇到的问题。

    如果觉得生活随笔网站内容还不错,欢迎将生活随笔推荐给好友。