在我的服务中,在调用DataIntegrityViolationException
处理并发持久(插入)请求时已处理myCrudRepository.saveAndFlush
。它有效,我可以捕捉异常。在此之后,我更愿意确定异常是否完全是因为实体已经存在,而不是由于任何其他可能的未知问题。所以,我致电myCrudRepository.exists(entity.getId())
,但DataIntegrityViolationException
再次被抛出。
这是我的简单代码:
private void save(final Employee entity) throws MyAppException {
try{
this.myCrudRepository.saveAndFlush(entity);
}catch (org.springframework.dao.DataIntegrityViolationException e){
// check if the error is really because the entity already exists
// entity.getId() is already generated before any save. it's like National ID
boolean exists = this.myCrudRepository.exists(entity.getId()); // DataIntegrityViolationException is thrown here again!
if (exists)
throw new MyAppException(HttpStatus.CONFLICT, "Entity already exists.");
else
throw e;
}
}
但如果我使用findOne
代替exists
,则可以正常使用。这有点奇怪,但当然它有一个技术原因,我不够好猜测。
有什么想法吗?提前谢谢。
答案 0 :(得分:0)
问题是当你使用Transactional方法并且在方法返回之后,事务将自动提交,而hibernate将异常包装到另一个中。实际上,当事务提交并且那时你已经超出了那个方法时发生异常。要从方法内部捕获异常,您只需在em.flush()
之后使用this.myCrudRepository.saveAndFlush(entity);
。