Java Spring引导和Hibernate事务未按预期工作

Java Spring引导和Hibernate事务未按预期工作,java,spring,hibernate,Java,Spring,Hibernate,我有一个MySql上带有Hibernate的Spring启动应用程序,我需要对一些服务使用一些悲观的锁定逻辑 我有一个计划好的作业,它应该更新一些对象,但是接下来的迭代没有考虑前一个,所以我想对服务使用悲观的逻辑 所以,这是预定的任务 @Scheduled(fixedDelay=3000, initialDelay=5000) public void checkSwitchToShutDown(){ // logger.debug("scheduled partito :"+ date

我有一个MySql上带有Hibernate的Spring启动应用程序,我需要对一些服务使用一些悲观的锁定逻辑

我有一个计划好的作业,它应该更新一些对象,但是接下来的迭代没有考虑前一个,所以我想对服务使用悲观的逻辑

所以,这是预定的任务

@Scheduled(fixedDelay=3000, initialDelay=5000)
public void checkSwitchToShutDown(){ 
    // logger.debug("scheduled partito :"+ dateFormat.format(new Date()));
    List<Interruttore> interruttori = interruttoreService.findAllSwitches();

    for (int i = 0; i < interruttori.size(); i++){
        Interruttore interruttore = interruttori.get(i);

        interruttoreService.toggleSwitchNew(interruttore);
    }   
}
updateInterruttore

@Override
@Transactional(readOnly = false, isolation = Isolation.SERIALIZABLE)
public void updateInterruttore(Interruttore interruttore) {
    try {
        Interruttore entity = dao.findById(interruttore.getIdInterruttore());

        if (entity != null) {
            entity.setStato(interruttore.isStato());
            entity.setDateTime(interruttore.getDateTime());
            entity.setTimeoutDate(interruttore.getTimeoutDate());
        }

    } catch (Throwable t) {
        logger.debug("Error: ",t);
    }
}
现在,计划任务的两个连续步骤进入
toggleSwitchNew
,即使第一个步骤将开关的状态更改为true,第二个步骤也会将该值设置为false,因为事务未被锁定

例如,这是一个发生了什么的日志:

2016-11-08 13:03:03 DEBUG InterruttoreServiceImpl:173 [pool-2-thread-1] - status at the beginning false
2016-11-08 13:03:03 DEBUG InterruttoreServiceImpl:177 [pool-2-thread-1] - updated status true
2016-11-08 13:03:03 DEBUG InterruttoreServiceImpl:183 [pool-2-thread-1] - L'interruttore si deve accendere: Zona -4B
2016-11-08 13:03:07 DEBUG InterruttoreServiceImpl:173 [pool-2-thread-1] - status at the beginning false
2016-11-08 13:03:07 DEBUG InterruttoreServiceImpl:177 [pool-2-thread-1] - updated status true
2016-11-08 13:03:07 DEBUG InterruttoreServiceImpl:183 [pool-2-thread-1] - L'interruttore si deve accendere: Zona -4B

为什么会有所不同呢?您在
updateInterruttore
上的
@Transactional
非常无用,因为它是一个内部方法调用,因为Spring使用代理来应用AOP,没有任何事务应用。实际上,当您在分离的实体上操作时,任何东西都不会被持久化。如果你真的想修复它,事务性方法实际上应该是你的
@Scheduled
方法,而不是单独的方法调用。你在数据库上的具体操作位置是什么?我在服务层下有一个DAO,它与数据库一起运行,但更新只在服务中,因为我以为Hibernate会用transaction@M.Deinum为什么你说什么都不会坚持?如果我没有2个并发请求,那么当您没有显示所有内容时,数据库将正确更新。然而,您的事务划分仍然是错误的,您的整个计划方法应该是事务性的。问题是,您正在读取内容,然后在单个事务中重新读取,因此序列化的数据很短,旧线程仍然具有旧的读取数据(使用find all)。为什么会有所不同?您在
updateInterruttore
上的
@Transactional
非常无用,因为它是一个内部方法调用,因为Spring使用代理来应用AOP,没有任何事务应用。实际上,当您在分离的实体上操作时,任何东西都不会被持久化。如果你真的想修复它,事务性方法实际上应该是你的
@Scheduled
方法,而不是单独的方法调用。你在数据库上的具体操作位置是什么?我在服务层下有一个DAO,它与数据库一起运行,但更新只在服务中,因为我以为Hibernate会用transaction@M.Deinum为什么你说什么都不会坚持?如果我没有2个并发请求,那么当您没有显示所有内容时,数据库将正确更新。然而,您的事务划分仍然是错误的,您的整个计划方法应该是事务性的。问题是,您正在读取内容,然后在单个事务中重新读取,因此序列化的数据很短,旧线程仍然具有旧的读取数据(使用find all)。
2016-11-08 13:03:03 DEBUG InterruttoreServiceImpl:173 [pool-2-thread-1] - status at the beginning false
2016-11-08 13:03:03 DEBUG InterruttoreServiceImpl:177 [pool-2-thread-1] - updated status true
2016-11-08 13:03:03 DEBUG InterruttoreServiceImpl:183 [pool-2-thread-1] - L'interruttore si deve accendere: Zona -4B
2016-11-08 13:03:07 DEBUG InterruttoreServiceImpl:173 [pool-2-thread-1] - status at the beginning false
2016-11-08 13:03:07 DEBUG InterruttoreServiceImpl:177 [pool-2-thread-1] - updated status true
2016-11-08 13:03:07 DEBUG InterruttoreServiceImpl:183 [pool-2-thread-1] - L'interruttore si deve accendere: Zona -4B