我正在运行带有MySQL数据库和kafka作为消息传递服务的Spring Boot应用程序(使用用于kafka和mysql的chainedKafkaTransactionManager进行了事务同步)以进行一些异步操作。
当多条消息有时会发送给kafka侦听器时,旧数据来自数据库,而不是先前提交的数据。
我正在使用Crud存储库,这种情况也只会在同时出现在多条消息上
示例: 更新一个具有名称和ID的对象PERSON;
第一条消息将通过id获取对象,并将名称更新为SAM。
第二条消息将获取对象并将名称更新为REGO
第三个消息将获取对象,然后如果我检查它包含名称作为SAM但在数据库中具有REGO的数据。
我尝试添加隔离属性,因为在事务中提交了读取但没有运气
// listeners
@Autowired
private PersonRepository personRepository;
@Autowired
private AddressRepository addressRepository;
@KafkaListener(id = "update_name", topics = "update_name")
@Transactional(readOnly = false)
public void updateName(PersonModel personModel) {
Person person = personRepository.findById(personModel.getId());
log.info("before -> name which is in database : " + person.getName());
person.setName(personModel.getName());
person = personRepository.save(person);
log.info("after-> name which is in database : " + person.getName());
}
@KafkaListener(id = "update_name_and_address", topics = "update_name_and_address")
@Transactional(readOnly = false)
public void updateNameAndAddress(PersonModel personModel) {
Address addr= addressRepository.findById(personModel.getAddresId);
addr.setPlace(personModel.getPlace());
addressRepository.save(addr);
updateName(personModel);
}
// repository
public interface PersonRepository extends CrudRepository<Person , Integer> {
}
我需要数据库中的最新数据
答案 0 :(得分:1)
这种情况发生在第三笔交易在第二笔交易提交之前开始的时候。 效果变得更加明显,因为一旦在会话中加载了JPA,JPA不会重新加载它。
为了最小化此问题,请使您的交易越短越好。 还要确保您可以通过在新事务中重试来处理乐观的锁定异常。