I have an issue with entities not being saved by Spring Data. The application logic goes like this:
@Scheduled(fixedDelay = 10_000)
public void scheduled() {
Pageable pageable = PageRequest.of(0, pageSize);
List<EntityClass> entities = entityService.getAllByStatusOrderByIdDesc(NEW_STATUS, pageable);
while (!entities.isEmpty()) {
entities.forEach(entity -> {
entity.setStatus(PROCESSING_STATUS);
process(entity);
});
entityService.saveAll(entities);
loggers = entityService.getAllByStatusOrderByIdDesc(NEW_STATUS, pageable);
}
private void process(Entity entity) {
threadPool.execute(
() -> processor.execute(
TaskBuilder.entity(entity).build()
)
);
}
...
log.info("[SaveStep] [execute] status before {}", entity.getStatus());
Entity entity = entityService.save(entity);
log.info("[SaveStep] [execute] status after {}", entity.getStatus());
Both log methods are showing correct status ('OK' or 'ERROR'), but database row keeps containing a 'PROCESSING' status. I've tried to redo an entityService.save() with multiple variations (entityRepository is a regular JPARepository):
public Entity save(Entity entity) {
return repository.save(logger);
}
@Transactional
public Entity save(Entity entity) {
Entity saved = repository.getFirstById(entity.getId());
saved.setStatus(entity.getStatus());
return repository.save(saved);
}
@Transactional
public Entity save(Entity entity) {
Entity saved = repository.getFirstById(entity.getId());
log.info("[Service] [save] status before {}", saved.getStatus());
saved.setStatus(entity.getStatus());
log.info("[Service] [save] status after {}", saved.getStatus());
return repository.save(saved);
}
@Modifying
@Transactional
@Query(value = "UPDATE entity_table_name set status = :status where id = :id", nativeQuery = true)
void updateStatus(@Param("id") Long id, @Param("status") String status);
At the moment I'm out of ideas to try. The main insulting thing is that most of the entities are finally digested correctly by a database, and only about 20% are ignored by a save() without any thrown exceptions.
Thanks for Taylor as he absolutely correctly pointed to my issue. List of entities has been processed in parallel and saved with correct status fast enough even before scheduler hit his saveAll('PROCESSING') line, which causes status rewriting.
You're setting the message to "processing" after it's submitted to the pool, meaning the pool may get to it first, and the "processing" update could happen after. Not sure if this is your problem, but it's a possibility with what you're doing. Try setting and saving/committing the "processing" update prior to submitting to the pool.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.