【问题标题】:Spring @Transactional doesn't work with third party API callSpring @Transactional 不适用于第三方 API 调用
【发布时间】:2020-10-25 11:15:00
【问题描述】:

我正在开发 Spring-boot 应用程序,服务层有文件上传功能这里是代码 sn-p-

@Transactional(rollbackOn = AmazonServiceException.class)
@Override
public Post createPost(PostEntity postEntity, MultipartFile attachments) {
    uploadOnS3(postEntity.getPostMedia(), attachments); // push into s3 bucket
    .....
    ....
    postRespository.save(postEntity);//store into application databse
}

问题场景:

  1. 假设文件成功上传到 s3 存储桶并返回 文件地址

  2. 在下一步之后发生异常并且事务已滚动 支持

  3. 由于文件已经上传,所以应用程序不会 任何信息

到目前为止我已经尝试过什么:

  1. 我已经绑定在 s3 存储桶上传之前插入本地数据库的东西,但我没有 获取任何回调,例如本地数据库插入已经完成,现在我们应该 启动 s3 任务。

  2. 同时,我还必须向客户发送关于 状态

spring 是否提供任何机制来让我们知道本地数据库插入已经完成?或者有没有更好的方法来处理这种类型的场景?

【问题讨论】:

    标签: spring-boot amazon-s3 spring-aop spring-transactions


    【解决方案1】:

    基本上第三方 API 不能成为 Spring 事务的一部分。您可以选择以下方法之一。所有这些方法都有其优点和缺点,因此您必须根据最适合您的方法进行选择 -

    1. 使用ThreadLocal 保存 postEntity 对象(或任何其他已上传文件信息的对象)。在你的错误处理例程中,检查这个对象并用它做任何你想做的事情。如果没有错误,那么这已经在数据库中了。请确保适当地清理 threadlocal 值,以确保它可以在多个调用中安全使用。
    2. 使用Annotation-Driven Event Async Listener 并将此侦听器标记为事务性。这样,即使主事务失败,对象也将使用单独的事务保存在数据库中。您可能希望在主流程中执行此操作,或者您可以选择在错误处理例程中执行此操作(例如通过从 threadlocal 中提取实体对象)。
    3. 使用Transaction Bound Events 并将其绑定到AFTER_ROLLBACK 阶段。仅当事务已回滚时才会触发此事件。这可能会简化您的用例,因为这将避免 ThreadLocal 类型的中间存储。

    【讨论】:

      猜你喜欢
      • 2018-08-10
      • 2011-01-22
      • 2023-03-31
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-11-18
      • 1970-01-01
      • 2022-11-14
      相关资源
      最近更新 更多