1.事务失效-自身调用(通过REQUIRES、REQUIRES_NEW传播属性):自身调用即调该类自己的方法。
同类OrderServiceImpl 中 doSomeThing()方法 不存在事务,该方法去调用本类中的存在事务注解的 insertAndUpdateOrderInfo() 方法。但是insertAndUpdateOrderInfo() 其实是无法保证预想的事务性。
示列验证:
OrderServiceImpl.insertAndUpdateOrderInfo方法中upateData(updateParam) 发生异常时,insertData(insertParam) 未发生回滚
说明:自身调用时候,无论是以下哪种传播属性均是无效的,因为自身调用时的子方法压根就不会被AOP 代理拦截到以下的这两种方式均经过验证,无法保证子方法事务的有效性
@Transactional(propagation = Propagation.REQUIRES)
@Transactional(propagation = Propagation.REQUIRES_NEW)
@Controller @RequestMapping("/trans") public class TransactionalController { @Autowired OrderService orderService; @RequestMapping("/test.do") @ResponseBody public void getIndex(HttpServletRequest request, HttpServletResponse response, Model model) { orderService.doSomeThing(); } } @Service public interface OrderService { /* *添加订单和修改其他订单信息 * */ public void doSomeThing(); } @Service public class OrderServiceImpl implements OrderService { @Autowired TransBusiness transBusiness; @Override public void doSomeThing() { insertAndUpdateOrderInfo(); } @Transactional(propagation = Propagation.REQUIRED) public void insertAndUpdateOrderInfo(){ Date date = new Date(); SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); String updateTime = dateFormat.format(date); //步骤1:插入订单记录信息 String[] insertParam = {"555555555", "977723233", updateTime, updateTime}; transBusiness.insertData(insertParam); //步骤2:修改订单记录信息 String[] updateParam = {"1111111111", updateTime, "1"}; transBusiness.upateData(updateParam); } } @Service public class TransBusiness { @Autowired JdbcTemplate dalClient; public void insertData(String[] param) { Map<String, Object> resultMap = new HashMap<>(); String sql = "INSERT INTO test_order (`order_no`, `cust_no`,create_time,update_time) VALUES (?, ?,?,?)"; int i = dalClient.update(sql, param); System.out.println("TransBusiness>>>insertData" + i); resultMap.put("插入的记录数", i); } public void upateData(String[] param) { Map<String, Object> resultMap = new HashMap<>(); String sql<strong>本文来源gaodai#ma#com搞@@代~&码*网2</strong> = "update test_order set order_no =?,update_time=? ? where id= ?"; int i = dalClient.update(sql, param); System.out.println("TransBusiness>>>upateData" + i); resultMap.put("修改的记录数", i); } }
2.1自身调用事务失效解决方法1—在父方法中添加事务
通过doSomeThing()方法中添加事务性,可以解决1中事务自身调用失效的问题。
示列验证:
OrderServiceImpl.insertAndUpdateOrderInfo方法中当步骤1执行完成后,数据库中并不会存在该订单记录。当执行步骤2时发生了异常,整个事务发生了回滚。说明才方法解决了1自身调用事务失效的问题。
说明:此处的@Transactional等同于 @Transactional(propagation = Propagation.REQUIRED) 表示支持当前事务,如果没有事务就新建一个事务,这是常见的选择,也是spring默认的事务传播
@Override @Transactional(propagation = Propagation.REQUIRED,rollbackFor = Exception.class) public void doSomeThing1() { insertAndUpdateOrderInfo(); } public void insertAndUpdateOrderInfo(){ Date date = new Date(); SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); String updateTime = dateFormat.format(date); //步骤1:插入订单记录信息 String[] insertParam = {"8888888888", "977723233", updateTime, updateTime}; transBusiness.insertData(insertParam); //步骤2:修改订单记录信息 String[] updateParam = {"1111111112", updateTime, "1"}; transBusiness.upateData(updateParam); }