博客
关于我
Java事务处理全解析(四)—— 成功的案例(自己实现一个线程安全的TransactionManager)
阅读量:195 次
发布时间:2019-02-28

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

ConnectionHolder与事务管理的实现

在本文中,我们将探讨如何在事务处理中实现Connection对象的共享,并解决线程安全问题。

ConnectionHolder的设计

为了共享Connection对象,我们引入了ConnectionHolder类。其核心思想是将Connection对象存储在一个全局可用的地方,并在需要时从该处获取。ConnectionHolder维护了一个键为DataSource、值为Connection的Map,用于支持多个DataSource的访问。

getConnection逻辑

当调用getConnection方法时:

  • 从Map中获取对应的Connection。
  • 如果Connection不存在或已关闭,获取新的Connection。
  • 将新的Connection存储到Map中。
  • 返回该Connection。
  • 这种方式确保了在同一个事务中,所有操作使用相同的Connection对象。

    线程安全问题

    尽管ConnectionHolder提供了共享机制,但默认情况下并非线程安全。例如,一个线程可能在另一个线程关闭Connection后继续使用,导致资源泄漏或错误。

    线程安全的解决方案

    为了确保线程安全,我们引入了SingleThreadConnectionHolder类。该类利用ThreadLocal确保每个线程都有自己的ConnectionHolder实例,避免了共享状态带来的问题。

    ThreadLocal的作用

    ThreadLocal保证了每个线程在访问类变量时,都能获得其自己的独立拷贝。SingleThreadConnectionHolder使用ThreadLocal存储ConnectionHolder实例,确保线程安全。

    TransactionManager的角色

    为了更好地管理事务,我们设计了TransactionManager类。其职责包括:

  • 获取并管理Connection。
  • 处理事务的开始、提交和回滚。
  • 确保Connection的正确关闭。
  • TransactionManager的实现

    TransactionManager维护一个DataSource,并通过SingleThreadConnectionHolder获取Connection。其方法包括:

    • start(): 开始事务,获取并设置自动提交为false。
    • commit(): 提交事务。
    • rollback(): 回滚事务。
    • close(): 关闭Connection,并恢复数据源。

    在Service层的应用

    在实际应用中,Service类通常会使用TransactionManager来管理事务。例如,BankService和InsuranceService可能会继承自ConnectionHolderBankService类,这类确保了所有操作都在同一个事务中进行。

    代码示例

    public class ConnectionHolderBankService implements BankService {    private TransactionManager transactionManager;    private ConnectionHolderBankDao connectionHolderBankDao;        public ConnectionHolderBankService(DataSource dataSource) {        transactionManager = new TransactionManager(dataSource);        connectionHolderBankDao = new ConnectionHolderBankDao(dataSource);    }        public void transfer(int fromId, int toId, int amount) {        try {            transactionManager.start();            connectionHolderBankDao.withdraw(fromId, amount);            connectionHolderInsuranceDao.deposit(toId, amount);            transactionManager.commit();        } catch (Exception e) {            transactionManager.rollback();        } finally {            transactionManager.close();        }    }}

    总结

    通过ConnectionHolder和SingleThreadConnectionHolder,我们实现了Connection对象的共享和线程安全。TransactionManager类则集中管理了事务处理,确保了数据的完整性和一致性。在实际应用中,Service层使用TransactionManager进行事务管理,避免了API污染和线程安全问题。

    这种设计模式不仅简化了Service层代码,还提高了代码的可维护性和扩展性。

    转载地址:http://svbi.baihongyu.com/

    你可能感兴趣的文章
    R&Python Data Science系列:数据处理(5)--字符串函数基于R(一)
    查看>>
    PHP设计模式:观察者模式
    查看>>
    php详细学习1
    查看>>
    php语言优劣
    查看>>
    PHP语言最优雅的支付SDK扩展包
    查看>>
    PHP请求https域名发生segment fault段错误
    查看>>
    PHP读写XML文件
    查看>>
    PHP读写XML文件
    查看>>
    R&Python Data Science 系列:数据处理(3)
    查看>>
    php读取xml 数据库字段超长处理
    查看>>
    php课程 12-40 抽象类的作用是什么
    查看>>
    php课程 4-16 数组自定义函数(php数组->桶)
    查看>>
    php转化IP为整形
    查看>>
    php输出数据到csv文件
    查看>>
    php进程通信
    查看>>
    R&Python Data Science 系列:数据处理(2)
    查看>>
    php递归算法总结
    查看>>
    php错误日志文件
    查看>>
    PHP错误解决:Array and string offset access syntax with curly braces is deprecated
    查看>>
    php隐藏手机号中间4位方法总结
    查看>>