使用mybatis完成数据更新,为防止并发造成数据出错,采用乐观锁机制如下:
(1)使用select某id的数据,计算total再更新操作;
(2)更新操作语句利用version实现乐观锁机制;
update table
set total = #{total,jdbcType=DECIMAL},
version = version + 1
where id = #{id,jdbcType=BIGINT}
and version = #{version,jdbcType=INTEGER}
(3)如果更新失败,则重复(1)、(2)步骤,直至超过一定次数。
但因为mybatis有缓存机制,在(3)失败是,重复执行(1),查询出的结果仍为旧数据,而不是数据库最新数据,导致一直更新失败。
在(1)之前执行clearCache,不起作用
SqlSessionUtils.getSqlSession(sqlSessionFactory).clearCache();
修改mybatis配置,不起作用
<setting name="cacheEnabled" value="false"/>
<setting name="localCacheScope" value="STATEMENT"/>
不起作用。。。不起作用。。。不起作用。。。。。。
已崩溃~~~
求指教!
后来发现是因为事务的原因。
当update失败后(失败的原因一定是version不匹配),会重新查询数据最新值,然后再次重试;
因为事务级别是repeatable-read,所以查询出来的“最新”值依旧是原值,而不是真正的最新值;
所以需要修改事务级别为read-commited,问题解决。