如何解决Spring Boot JPA save() 方法尝试插入现有行
我有一个简单的 kafka 消费者,它收集事件,并根据其中的数据插入或更新数据库中的记录 - 表在 ID 列和实体字段中都有唯一的 ID 约束。
当表预先填充并且插入时不时发生时,一切正常。但是,当我截断表并发送几千个 ID 数量有限的事件(我在 3k 个事件中执行 50 个唯一 ID)时,会同时处理事件,并且 save() 方法随机失败并出现唯一约束冲突异常。我调试了它,结果很简单。
event1={id = 1 ... //somedata} 被拾取,服务方法 saveOrUpdateRecord() 通过 ID=1 查找记录,没有找到,插入新记录。
event2={id = 1 ... //somedata} 几乎同时被拾取,服务方法 saveOrUpdateRecord() 查找 ID=1 的记录,没有找到(上一个一个是中间插入),尝试插入并因违反约束异常而失败 - 应该找到此记录并将其与基于我的条件的事件输入合并。
我怎样才能让 saveOrUpdateRecord() 只有在前一个完全执行时才运行以防止这种行为?我真的不想通过轮询大小等来减慢 kafka 消费者的速度,我只想让我的服务一次执行一项事务。
服务方式:
public void saveOrUpdateRecord(Object input) {
Object output = repository.findById(input.getId));
if (output == null) {
repository.save(input);
} else {
mergeRecord(input,output);
repository.save(output);
}
}
@Transactional 对方法的注解会起作用吗?
解决方法
使您的服务线程安全。 使用这个:
public synchronized void saveOrUpdateRecord(Object input) {
Object output = repository.findById(input.getId));
if (output == null) {
repository.save(input);
} else {
mergeRecord(input,output);
repository.save(output);
}
}
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。