zoukankan      html  css  js  c++  java
  • ThreadLocal与事务

    ThreadLocal中放置connection, 保证事务中的DAO类获取的都是同一个connection,这样才保证事务。

    下面是网上找到的一个具体的例子http://www.pin5i.com/showtopic-26854.html

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

    通常我们会把事务处理放在业务层。

    [1]引子

    比如:
    业务逻辑方法

    1. public A bussinessMethod(){
    2.   DaoA  a = new DaoA();
    3.   a.udpate();
    4.   DaoB  b = new DaoB();
    5.   b.update;
    6. }
    复制代码

    假设,上面的事务是自动提交的。

    那么,我们就可以什么不考虑。但是有一个问题,创建DAO对象的时候两个对象用的是不同的Connection对象。

    再假定我们的取得连接的代码是

    1.     public Connection getConnection(String username, String password)
    2.             throws SQLException {
    3.         Connection con = DriverManager
    4.                 .getConnection(conStr, username, password);
    5.         return con;
    6.     }
    复制代码

    这个方法的一个调用。

    那么如果,我们需要自己控制事务的开始和结束。

    如何控制呢。

    也许又有了新的方法

    1. public A bussinessMethod(){
    2.   DaoA  a = new DaoA();
    3.   a.beginTx();
    4.   a.udpate();
    5.   a.endTx();
    6.   a.close();
    7.   DaoB  b = new DaoB();
    8.   b.beginTx();
    9.   b.update;
    10.   b.endTx();
    11.   b.close();
    12. }
    复制代码

    这样我们就控制了事务,并且我们也只有这样才能实现,因为,不同的DAO取得的是不同的Connection对象。

    [2]问题

    那么怎么才能实现两个或多个DAO用同一个事务来控制呢?

    首先就要解决一个根本问题,我们在一个事务中,不同的DAO取得的是同一个Connection,这个要怎么实现呢。我们想到了TheadLocal.

    [3]方案

    因为当一个业务逻辑要对多个DAO进行处理的时候,此操作属于同一个线程内。所以,我们希望能把此Connection放在线程内,或者和线程有关联。

    第一个方案,可以用Map来使现。

    就是Map<Thread,Connection>

    但是这个map维护起来比较麻烦,如果一直put的话,那么这个map随着系统的运行就会越来越大。

    第二个方案,就是用ThreadLocal

    在任何一个线程内都可以用ThreadLocal来保存一个变量的copy,这样,如果此对象存在,就可以直接取用。

    如果把Connection存在ThreadLocal也一样。

    所以,在同一个线程内,就可以保证取得到的是同一个Connection.

    [4]实现

    1.     private static ThreadLocal<Connection> localCon = new ThreadLocal<Connection>();
    2.     public final static Connection getConnection() throws SQLException {
    3.      
    4.         Connection con = localCon.get();
    5.      
    6.         if(con==null||con.isClosed()){
    7.             con = new OracleJdbcDatasource().getConnection();
    8.          
    9.             localCon.set(con);
    10.         }
    11.      
    12.         return con;
    13.     }
    复制代码

    这样就实现了上面的问题。

    [5]新的事务管理

    1. public A bussinessMethod(){
    2.   DaoA  a = new DaoA();
    3.   DaoB  b = new DaoB();
    4.   a.beginTx();
    5.   a.udpate();
    6.   b.beginTx();
    7.   b.update;
    8.   a.endTx();
    9.   a.close();
    10. //  b.endTx();
    11. //  b.close();
    12. 能实现一样的效果
    13.  
    14. }
    复制代码

    上面的黑体部分,就可以实现对事务的统一管理。

  • 相关阅读:
    2009年信息技术十大趋势
    转:ASP.NET MVC 第五个预览版和表单提交场景
    终于在博客园开通了
    与虚拟机Oracle连接出现ora12154问题的解决
    Frame框架页面加载中进度条的实现
    WordPress安装部署
    Xmarks不会关闭了,太好了!
    抠出淘宝的菜单树
    asp.net实现类似MaskTextBox功能
    win2003 64位系统下ODBC连接使用
  • 原文地址:https://www.cnblogs.com/highriver/p/2129594.html
Copyright © 2011-2022 走看看