我没有成功让Spring Data向NOWAIT发送一个FOR更新的帖子。
我在存储库中试过这个:
@Lock(value = LockModeType.PESSIMISTIC_WRITE)
MyObject findByUuid(String uuid);
配置(摘录)
@Configuration
@EnableTransactionManagement
@EnableJpaRepositories(
entityManagerFactoryRef = "docsEntityManagerFactory",
transactionManagerRef = "docsTransactionManager",
@Bean(name = "docsEntityManagerFactory")
public EntityManagerFactory docsEntityManagerFactory(DataSource docsDataSource) {
props.setProperty("javax.persistence.lock.timeout", "0");
...
我甚至在我的服务中注入了EntityManager,这返回0:
logger.info(em.getProperties()得到(" javax.persistence.lock.timeout&#34));
但是上面的内容只能让我获得" FOR UPDATE",NOWAIT部分没有被设置。我是否设置正确的东西(从另一个帖子看起来它应该可以工作)。
这让我更接近,虽然我不想使用原始的SQL
@Lock(value = LockModeType.PESSIMISTIC_WRITE)
@Query(value = "SELECT * FROM the_table WHERE uuid = :uuid FOR UPDATE NOWAIT", nativeQuery = true)
MyObject findByUuid(@Param("uuid") String uuid);
这确实给了我一个Lock异常,但是Spring装饰服务(代理)会在返回时抛出一个Transaction / Rollback异常,这意味着我不能给出我需要的方法的返回值。
问题: 1)如何让Spring Data添加NOWAIT? 2)有没有办法返回价值?我怀疑我需要自己处理事务,还是改变逻辑流程?如果Spring表现不同,不确定Spring是否处理NOWAIT。
我意识到有类似的问题,但这有点不同。 我正在使用hibernate 4.2.15,spring-data-jpa 1.7.1,postgres sql 9.3。
答案 0 :(得分:0)
javax.persistence.lock.timeout也不对我有用
@QueryHints({@QueryHint(name = "javax.persistence.lock.timeout",value = "15000")})
但是后来我尝试了其他可行的方法。现在,我使用实体管理器配置休眠,而不是使用@Repository和CrudRepository。与锁定和设置锁定超时一起使用了createQuery。并且此配置按预期工作。我有两个并行运行的事务,并试图锁定数据库中完全相同的行。第一个事务能够获取WRITE锁定,并在释放锁定之前将其保持约10秒钟。同时,第二个事务尝试获取同一行上的锁,但是由于javax.persistence.lock.timeout设置为15秒,因此它等待释放锁,然后获取自己的锁。因此,使流程序列化。
@Component
public class Repository {
@PersistenceContext
private EntityManager em;
public Optional<Cache> getById(int id){
List<Cache> list = em.createQuery("select c from Cache c where c.id = ?1")
.setParameter(1, id)
.setHint("javax.persistence.lock.timeout", 15000)
.setLockMode(LockModeType.PESSIMISTIC_WRITE)
.getResultList();
return Optional.ofNullable(list.get(0));
}
public void save(Cache cache) {
cache = em.find(Cache.class, cache.getId());
em.merge(cache);
}
}
确保此锁定机制在事务内部,因为在提交或回滚事务时将释放锁定。
答案 1 :(得分:-1)
使用PESSIMISTIC_FORCE_INCREMENT