Spring框架深入浅出

Spring 的事务传播类型、事务隔离级别

2018-09-29  本文已影响0人  锕123

事务传播类型

spring 的7种事务传播类型

注意:
内部方法直接调用,传播性失效

@Service("studentImpl")
public class StudentImpl implements Student {
 
    @Autowired
    StudentDao studentDao;
    
    @Autowired
    UserService userService;
 
    @Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.DEFAULT, rollbackFor = Exception.class)
    public String doA() throws Exception {
        Student student = new Student();
        student.setSex("F");
        student.setUsername("唐玄奘");
        studentDao.insertStudent(student);
        
        
        userService.addUser();
        int i = 1 / 0; // 模拟异常,事务回滚
        return "ok!";
    }
 
}
@Service("userServiceImpl")
public class UserServiceImpl implements UserService {
  
    @Autowired
    UserDao userDao;
    
    @Transactional(propagation = Propagation.REQUIRES_NEW,isolation=Isolation.DEFAULT,rollbackFor=Exception.class)  
    public String addUser() throws Exception {
        User user = new User();
        user.setUsername("观世音菩萨");
        userDao.insert(user);
        return "ok!";
    }
     
}

结果:只会是 user 插入成功, 因为 addUser方法使用了事务传播行为:Propagation.REQUIRES_NEW,当前存在事务1,则新建了一个自己的事务,并挂起了事务1. 事务2提交后,事务1由于抛出了异常回滚。

如果以上例子改为在一个方法中调用另一个事务方法,另一个方法的传播行为会失效:

@Service("studentImpl")
public class StudentImpl implements Student {
 
    @Autowired
    StudentDao studentDao;
    
    @Autowired
    UserDao userDao;
 
    @Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.DEFAULT, rollbackFor = Exception.class)
    public String doA() throws Exception {
        Student student = new Student();
        student.setSex("F");
        student.setUsername("唐玄奘");
        studentDao.insertStudent(student);
        
        
        userService.addUser();
        int i = 1 / 0; // 模拟异常,事务回滚
        return "ok!";
    }
    
    @Transactional(propagation = Propagation.REQUIRES_NEW,isolation=Isolation.DEFAULT,rollbackFor=Exception.class)  
    public String addUser() throws Exception {
        User user = new User();
        user.setUsername("观世音菩萨");
        userDao.insert(user);
        return "ok!";
    }
 
}


结果:addUser 的事务传播性会失效,事务1回滚后,数据库不会插入任何记录。

spring 的5种隔离级别

关键词:

幻读: 事务1 读取记录时,事务2 增加了记录并提交, 事务1 再次读取时可以看到事务2 新增的记录。 指一个事务读取了一个未提交事务的数据。

不可重复读取: 事务1 读取记录时, 事务2 更新了记录并提交, 事务1 再次读取时可以看到 事务2 修改后的记录。 在一个事务内读取表中的某一行数据,多次读取结果不同,一个事务读取到了另一个事务提交后的数据。

脏读: 事务1 更新了记录, 但是没有提交,事务2 读取了更新后的行, 然后事务1 回滚,现在事务2 读取无效。 在一个事务内读取了别的事务插入的数据,导致前后读取不一致。

上一篇 下一篇

猜你喜欢

热点阅读