javax.transaction包是Java事务API(JTA)的核心部分,提供了分布式事务管理的接口和类。它允许应用程序在多个资源管理器(如数据库、消息队列等)之间执行原子性操作。
1、UserTransaction - 应用程序级事务控制接口
2、TransactionManager - 事务管理器接口
3、Transaction - 代表单个事务
4、Status - 事务状态常量
5、Synchronization - 事务同步回调接口
import javax.transaction.*;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
public class BasicTransactionExample {
public void transferMoney(Connection conn1, Connection conn2,
String fromAccount, String toAccount, double amount) {
UserTransaction ut = null;
try {
// 获取UserTransaction实例
ut = (UserTransaction) new InitialContext().lookup("java:comp/UserTransaction");
// 开始事务
ut.begin();
// 执行第一个数据库操作 - 扣款
String sql1 = "UPDATE accounts SET balance = balance - ? WHERE account_id = ?";
PreparedStatement ps1 = conn1.prepareStatement(sql1);
ps1.setDouble(1, amount);
ps1.setString(2, fromAccount);
ps1.executeUpdate();
// 执行第二个数据库操作 - 存款
String sql2 = "UPDATE accounts SET balance = balance + ? WHERE account_id = ?";
PreparedStatement ps2 = conn2.prepareStatement(sql2);
ps2.setDouble(1, amount);
ps2.setString(2, toAccount);
ps2.executeUpdate();
// 提交事务
ut.commit();
System.out.println("转账成功");
} catch (Exception e) {
try {
if (ut != null) {
ut.rollback();
}
System.out.println("转账失败,已回滚");
} catch (SystemException se) {
se.printStackTrace();
}
e.printStackTrace();
}
}
}import javax.transaction.*;
import javax.naming.InitialContext;
public class TransactionManagerExample {
private TransactionManager tm;
public TransactionManagerExample() {
try {
tm = (TransactionManager) new InitialContext().lookup("java:comp/TransactionManager");
} catch (Exception e) {
e.printStackTrace();
}
}
public void performTransactionalOperation(Runnable operation) {
try {
// 开始事务
tm.begin();
// 获取当前事务
Transaction transaction = tm.getTransaction();
// 注册同步回调
transaction.registerSynchronization(new CustomSynchronization());
// 执行业务操作
operation.run();
// 提交事务
tm.commit();
} catch (Exception e) {
try {
tm.rollback();
} catch (SystemException se) {
se.printStackTrace();
}
e.printStackTrace();
}
}
// 自定义同步回调
private static class CustomSynchronization implements Synchronization {
@Override
public void beforeCompletion() {
System.out.println("事务即将完成,准备提交前的清理工作");
}
@Override
public void afterCompletion(int status) {
if (status == Status.STATUS_COMMITTED) {
System.out.println("事务已提交,执行后续操作");
} else if (status == Status.STATUS_ROLLEDBACK) {
System.out.println("事务已回滚,执行补偿操作");
}
}
}
}import javax.transaction.*;
public class TransactionStatusChecker {
public void checkTransactionStatus(UserTransaction ut) {
try {
int status = ut.getStatus();
switch (status) {
case Status.STATUS_ACTIVE:
System.out.println("事务正在进行中");
break;
case Status.STATUS_COMMITTED:
System.out.println("事务已提交");
break;
case Status.STATUS_ROLLEDBACK:
System.out.println("事务已回滚");
break;
case Status.STATUS_NO_TRANSACTION:
System.out.println("没有活动的事务");
break;
case Status.STATUS_PREPARING:
System.out.println("事务正在准备");
break;
case Status.STATUS_PREPARED:
System.out.println("事务已准备就绪");
break;
case Status.STATUS_COMMITTING:
System.out.println("事务正在提交");
break;
case Status.STATUS_ROLLING_BACK:
System.out.println("事务正在回滚");
break;
case Status.STATUS_MARKED_ROLLBACK:
System.out.println("事务已标记为回滚");
break;
default:
System.out.println("未知事务状态: " + status);
}
} catch (SystemException e) {
e.printStackTrace();
}
}
public void setRollbackOnly(UserTransaction ut) {
try {
ut.setRollbackOnly();
System.out.println("事务已标记为仅回滚");
} catch (SystemException e) {
e.printStackTrace();
}
}
}import javax.transaction.*;
import javax.sql.DataSource;
import javax.naming.InitialContext;
import java.sql.Connection;
import java.sql.PreparedStatement;
public class BankTransferService {
private DataSource dataSource;
private UserTransaction userTransaction;
public BankTransferService() {
try {
InitialContext ctx = new InitialContext();
dataSource = (DataSource) ctx.lookup("java:comp/env/jdbc/BankDB");
userTransaction = (UserTransaction) ctx.lookup("java:comp/UserTransaction");
} catch (Exception e) {
throw new RuntimeException("初始化失败", e);
}
}
public boolean transfer(String fromAccount, String toAccount, double amount) {
Connection conn = null;
try {
// 开始事务
userTransaction.begin();
conn = dataSource.getConnection();
// 检查余额是否足够
if (!hasSufficientBalance(conn, fromAccount, amount)) {
userTransaction.rollback();
return false;
}
// 执行转账操作
withdraw(conn, fromAccount, amount);
deposit(conn, toAccount, amount);
// 记录交易
logTransaction(conn, fromAccount, toAccount, amount);
// 提交事务
userTransaction.commit();
return true;
} catch (Exception e) {
try {
userTransaction.rollback();
} catch (SystemException se) {
se.printStackTrace();
}
e.printStackTrace();
return false;
} finally {
if (conn != null) {
try {
conn.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
private boolean hasSufficientBalance(Connection conn, String account, double amount)
throws Exception {
String sql = "SELECT balance FROM accounts WHERE account_id = ?";
try (PreparedStatement ps = conn.prepareStatement(sql)) {
ps.setString(1, account);
var rs = ps.executeQuery();
if (rs.next()) {
return rs.getDouble("balance") >= amount;
}
return false;
}
}
private void withdraw(Connection conn, String account, double amount) throws Exception {
String sql = "UPDATE accounts SET balance = balance - ? WHERE account_id = ?";
try (PreparedStatement ps = conn.prepareStatement(sql)) {
ps.setDouble(1, amount);
ps.setString(2, account);
ps.executeUpdate();
}
}
private void deposit(Connection conn, String account, double amount) throws Exception {
String sql = "UPDATE accounts SET balance = balance + ? WHERE account_id = ?";
try (PreparedStatement ps = conn.prepareStatement(sql)) {
ps.setDouble(1, amount);
ps.setString(2, account);
ps.executeUpdate();
}
}
private void logTransaction(Connection conn, String fromAccount,
String toAccount, double amount) throws Exception {
String sql = "INSERT INTO transactions (from_account, to_account, amount, timestamp) " +
"VALUES (?, ?, ?, CURRENT_TIMESTAMP)";
try (PreparedStatement ps = conn.prepareStatement(sql)) {
ps.setString(1, fromAccount);
ps.setString(2, toAccount);
ps.setDouble(3, amount);
ps.executeUpdate();
}
}
}1、环境依赖: JTA通常需要Java EE应用服务器支持,如WebLogic、WebSphere或JBoss
2、资源查找: 事务管理器通常通过JNDI查找获取
3、异常处理: 必须妥善处理事务回滚
4、超时设置: 可以通过setTransactionTimeout方法设置事务超时时间
在现代Java应用中,通常使用Spring框架的声明式事务管理,它提供了更简洁的事务管理方式:
@Transactional
public void transferMoney(String fromAccount, String toAccount, double amount) {
// 业务逻辑
}javax.transaction包为分布式事务提供了标准API,但在实际开发中,建议使用框架提供的高级抽象来简化事务管理。