使用场景
在实际业务场景中,@Transactional(propagation = REQUIRES_NEW) 的使用可以帮助我们实现更精细的事务控制。比如在银行转账业务中,假设有一个大的业务逻辑包括账户扣款和购买理财产品两个子操作,这两个操作都必须保证事务性(即要么都成功,要么都失败)但又需要彼此独立。
1,账户扣款操作:
根据用户输入,从用户A的账户中扣除一定金额。
这是一个完整的事务,如果扣款失败(如余额不足),则整个事务需要回滚,确保资金不会丢失。
购买理财产品操作:
2,扣款成功后,将扣款金额用于购买某理财产品。
这也是一个完整的事务,如果购买理财产品过程中出现问题(如理财产品已售罄),则这个事务需要单独回滚,不影响之前的扣款操作。
在这种情况下,我们可以这样设计:
@Service
public class TransferService {
@Transactional
public void transferAndInvestMoney() {
// 扣款操作
debitAccount();
// 使用REQUIRES_NEW,确保购买理财产品的操作在一个新的、独立的事务中执行
investMoney();
}
@Transactional(propagation = Propagation.REQUIRES_NEW)
private void investMoney() {
// 购买理财产品的具体实现,如果有异常,这个事务会独立回滚,不影响扣款事务
}
@Transactional
private void debitAccount() {
// 扣款的具体实现,如果有异常,这个事务会回滚
}
}
通过这样的设计,即使购买理财产品的事务因为某种原因失败并回滚,也不会影响到前面扣款操作的成功执行,从而保证了数据的一致性和完整性。同时,每个操作都在各自的事务中得到了保障。