【问题标题】:Springboot JPA Repository not releasing Hikari DB ConnectionSpring Boot JPA Repository 未释放 Hikari DB Connection
【发布时间】:2023-10-19 01:39:01
【问题描述】:

我在 Springboot 中有一个使用 Hikari 进行连接池的休息 API。 Hikari 与默认配置一起使用(池中有 10 个连接,等待连接超时 30 秒)。 API 本身非常简单

  1. 它首先进行 JPA 存储库查询以从 PostgresDB 获取一些数据。这部分大约需要 15-20 毫秒。
  2. 然后,它会将这些数据发送到远程 REST API,该 API 速度很慢,可能需要 120 秒以上的时间。
  3. 一旦远程 API 响应,我的 API 会将结果返回给客户端。简化版如下所示。
    public ResponseEntity analyseData(int companyId) {
        Company company = companyRepository.findById(companyId);//takes 20ms
        Analysis analysis = callRemoteRestAPI(company.data) //takes 120seconds
       return ResponseEntity.status(200).body(analysis);

    }

代码没有任何@Transactional 注释。我发现 JDBC 连接在我的 API 的整个持续时间内都保持不变(即 ~ 120 秒)。因此,如果我们收到超过 10 个请求,它们会超时等待 hikari 连接池(30 秒)。但严格来说,我的 API 在 JPA 查询完成后不需要连接(上面的第 1 步)。

有没有办法让 spring 在查询后立即释放此连接,而不是保持它直到整个 API 完成处理?可以将 Spring 配置为为每个 JPA 请求获取连接吗?这样,如果我有多个 JPA 查询,其中散布着非常慢的操作,则服务器吞吐量不会受到影响,并且它可以处理超过 10 个并发 API 请求。 .

【问题讨论】:

  • 请不要描述您的代码...发布它

标签: java spring-boot connection-pool


【解决方案1】:

本质上问题是由 Spring OpenSessionInViewFilter 引起的,即“将 Hibernate Session 绑定到线程以完成请求的整个处理”这实际上是在第一个 JPA 时从池中获取连接查询被执行,然后一直保持到请求被处理。

此页面 - https://www.baeldung.com/spring-open-session-in-view 提供了有关此功能的清晰简洁的说明。它有其优点和缺点,目前的意见似乎对它的使用存在分歧。

【讨论】: