首页

Java基于weblogic实现分布式事务UserTransaction实现测试工程完整源码分析

标签:UserTransaction,源码解析,demo,示例,jta,分布式,事务     发布时间:2016-08-13   

一、前言

相信大家对分布式系统多少有点接触,一个大型的互联网体系平台 往往有一系列的分布式系统构建而成,对于完成实现一个用户业务请求响应,往往伴随n个服务的重叠和n个数据库的数据状态的刷新,因此对于这种用例场景,传统单应用或关系型数据事务无法保证数据“一致性”或状态同步等等要求,这边主要通过weblogic实现JTA(Java Transaction API)接口实现容器来示例数据一致性(主流的WebLogic、websphere等都提供了JTA的实现和支持,Tomcat借助第三方的框架Jotm、Automikos等来实现,两者均支持spring事务整合),完整项目源码下载或依赖包跳转相关页面(download)。

二、实践步骤

1. 分别在weblogic配置两个独立数据源分别对应不同的用户数据库,注意在配置数据源的时候,驱动初选择对应的版本外,还需要选择支持XA协议(它是TM(事务管理器)和RM(资源管理器)之间的接口)的驱动

Java基于weblogic实现分布式事务UserTransaction实现测试工程完整源码分析

2. 在spring配置注册不同的数据源和相关配置,如下所示

<?xml version="1.0" encoding="UTF-8"?>@b@<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd">@b@<beans>@b@    <!-- JNDI数据源 -->@b@    <bean id="jndiTemplate" class="org.springframework.jndi.JndiTemplate">@b@    </bean>@b@    <bean id="dataSource"@b@        class="org.springframework.jndi.JndiObjectFactoryBean">        @b@        <property name="jndiName" value="jndi/utx" />@b@        <property name="jndiTemplate"><ref bean="jndiTemplate"/></property>@b@    </bean>@b@    <bean id="dataSource2"@b@        class="org.springframework.jndi.JndiObjectFactoryBean">        @b@        <property name="jndiName" value="jndi/utx2" />@b@        <property name="jndiTemplate"><ref bean="jndiTemplate"/></property>@b@    </bean>@b@    <bean id="jdbcTemplate"@b@        class="org.springframework.jdbc.core.JdbcTemplate">@b@        <property name="dataSource">@b@            <ref local="dataSource" />@b@        </property>@b@    </bean>@b@    <bean id="jdbcTemplate2"@b@        class="org.springframework.jdbc.core.JdbcTemplate">@b@        <property name="dataSource">@b@            <ref local="dataSource2" />@b@        </property>@b@    </bean>@b@</beans>

3. 数据操作工具类,分别删除uat1表tab_1和uat2表tab_2记录id分别为1、2的记录,工具类如下

import org.springframework.jdbc.core.JdbcTemplate;@b@import com.xwood.utx.util.SpringBeans;@b@@b@public class UtxDaoUtils {@b@    private static JdbcTemplate dbs=(JdbcTemplate)SpringBeans.getBean("jdbcTemplate");@b@    private static JdbcTemplate dbs2=(JdbcTemplate)SpringBeans.getBean("jdbcTemplate2");@b@    public static void delTab1(){@b@            String sql = "delete from tab_1 where id = ?";@b@            Object[] values = new Object[] { 1 };@b@            dbs.update(sql, values);@b@    }@b@    public static void delTab2(){@b@        String sql = "delete from tab_2 where id = ?";@b@        Object[] values = new Object[] { 2 };@b@        dbs2.update(sql, values);@b@    }@b@}

4. 获取weblogic容器分布式事务对象,调用工具类内容如下

import javax.naming.Context;@b@import javax.naming.InitialContext;@b@import javax.naming.NamingException;@b@import javax.transaction.SystemException;@b@import javax.transaction.UserTransaction;@b@@b@public class UserBeaTransaction {@b@    public static UserTransaction getUserTransaction() throws NamingException,SystemException {@b@        UserTransaction trans = null;@b@        Context ctx = new InitialContext();@b@        trans = (UserTransaction) ctx.lookup("java:comp/UserTransaction");//Bea默认注册名@b@        if (trans != null){@b@            trans.setTransactionTimeout(30*20); // 设置事务超时间@b@            return trans;@b@        }else{@b@            return null;@b@        }@b@    }@b@}

备注其他容器注册名,如下

* "java:comp/UserTransaction" for Resin 2.x, Oracle OC4J (Orion), JOnAS (JOTM), BEA WebLogic

   * "java:comp/TransactionManager" for Resin 3.x

   * "java:appserver/TransactionManager" for GlassFish

   * "java:pm/TransactionManager" for Borland Enterprise Server and Sun Application Server (Sun ONE 7 and later)

   * "java:/TransactionManager" for JBoss Application Server

5. 下面是配置一个简单的servlet的测试类,并在执行两个数据库删除操作动作之前,模拟抛出个运行异常

import java.io.IOException;@b@import javax.servlet.ServletException;@b@import javax.servlet.http.HttpServlet;@b@import javax.servlet.http.HttpServletRequest;@b@import javax.servlet.http.HttpServletResponse;@b@import javax.transaction.UserTransaction;@b@@b@import com.xwood.utx.service.UtxDaoUtils;@b@@b@public class UserActionServlet extends HttpServlet {@b@@b@    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {@b@        // TODO Auto-generated method stub@b@        doPost(request,response);@b@    }@b@    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {@b@        UserTransaction ut =null;@b@        try {@b@            ut = UserBeaTransaction.getUserTransaction();@b@            ut.begin();@b@            UtxDaoUtils.delTab1();@b@            throwException();//模拟发送异常@b@            UtxDaoUtils.delTab2();@b@            System.out.println("exception...");@b@            ut.commit();@b@        } catch (Exception e) {@b@            try {@b@                ut.rollback();@b@                System.out.println("rollback...");@b@            } catch (Exception e1) {@b@                // TODO Auto-generated catch block@b@                e1.printStackTrace();@b@            }  @b@        }@b@    }@b@    private void  throwException() throws RuntimeException{@b@        throw new RuntimeException();@b@    }@b@}

6. 浏览器执行用户请求,进行测试,结果事务成功发射回滚,保证数据同步,如下图

Java基于weblogic实现分布式事务UserTransaction实现测试工程完整源码分析

7. 项目完整的源码或依赖包跳转到下载页