在两个MySQL事务中,如果都开启了事务后使用版本乐观锁,是可以避免并发写入问题的。
关键在于update语句执行时,会加排他锁;以及在执行update前,会检查version版本是否被其他事务修改过。
具体流程是:
- 事务1启动,读取数据(无锁)
- 事务2启动,读取同一行数据(无锁)
- 事务1执行update要修改这行数据,加排他锁
- 事务2此时执行update会被阻塞,因为被事务1的排他锁锁住
- 事务1在执行update前检查version,确认无其他事务修改
- 事务1提交更新,释放排他锁
- 事务2阻塞解除,可以执行update,但会检查到version已被更新,需要回滚并重试
所以通过行锁+版本检查,可以有效防止并发写入问题。
需要注意的是,读取数据时没有加任何锁,所以事务隔离级别还可能会导致其他并发问题,比如脏读、不可重复读。但写入并发是避免了。