You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Boot多数据源场景下Hikari连接池抛出Connection is closed异常排查

应用运行数小时后抛出Connection is closed异常

应用正常运行数小时后,开始抛出以下SQL异常:

java.sql.SQLException: Connection is closed
at com.zaxxer.hikari.pool.ProxyConnection$ClosedConnection.lambda$getClosedConnection$0(ProxyConnection.java:515)
at com.sun.proxy.$Proxy171.prepareStatement(Unknown Source)
at com.zaxxer.hikari.pool.ProxyConnection.prepareStatement(ProxyConnection.java:337)
at com.zaxxer.hikari.pool.HikariProxyConnection.prepareStatement(HikariProxyConnection.java)
at org.hibernate.engine.jdbc.internal.StatementPreparerImpl$5.doPrepare(StatementPreparerImpl.java:149)
at org.hibernate.engine.jdbc.internal.StatementPreparerImpl$StatementPreparationTemplate.prepareStatement(StatementPreparerImpl.java:176)
at org.hibernate.engine.jdbc.internal.StatementPreparerImpl.prepareQueryStatement(StatementPreparerImpl.java:151)
at org.hibernate.loader.Loader.prepareQueryStatement(Loader.java:2104)
at org.hibernate.loader.Loader.executeQueryStatement(Loader.java:2034)
at org.hibernate.loader.Loader.executeQueryStatement(Loader.java:2012)
at org.hibernate.loader.Loader.doQuery(Loader.java:953)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:354)
at org.hibernate.loader.Loader.doList(Loader.java:2838)
at org.hibernate.loader.Loader.doList(Loader.java:2820)
at org.hibernate.loader.Loader.listIgnoreQueryCache(Loader.java:2652)
at org.hibernate.loader.Loader.list(Loader.java:2647)
at org.hibernate.loader.custom.CustomLoader.list(CustomLoader.java:338)
at org.hibernate.internal.SessionImpl.listCustomQuery(SessionImpl.java:2131)
at org.hibernate.internal.AbstractSharedSessionContract.list(AbstractSharedSessionContract.java:1163)
at org.hibernate.query.internal.NativeQueryImpl.doList(NativeQueryImpl.java:173)
at org.hibernate.query.internal.AbstractProducedQuery.list(AbstractProducedQuery.java:1533)
at org.hibernate.query.Query.getResultList(Query.java:165)

对应的查询调用代码如下:

@Autowired 
private final EntityManager entityManager;

void someMethod() { 
    var q = entityManager.createNativeQuery(query); 
    var rs = q.getResultList(); // 异常抛出位置
    // 其他代码 
}

最近新增了多数据源配置,怀疑此操作引发了该问题,但无法确认,需要排查思路和解决方案。


排查方向与解决方案

1. 多数据源的EntityManager配置校验

  • 确认每个数据源对应的EntityManagerFactory、EntityManager是否完全隔离,避免跨数据源的连接混用。若多个EntityManager共享连接池或配置错误,会导致连接被提前关闭。
  • 检查是否为每个数据源配置了独立的事务管理器,确保事务边界清晰,不会出现一个事务关闭另一数据源连接的情况。

2. Hikari连接池参数调整

  • 连接生命周期匹配:检查maxLifetime、idleTimeout配置,确保这两个值小于数据库端的连接超时时间(如MySQL的wait_timeout)。若连接池的连接存活时间超过数据库设置,数据库会主动关闭连接,而连接池仍认为连接可用,触发异常。
  • 开启连接泄漏检测:设置leakDetectionThreshold(如2000毫秒),若存在连接未被正确释放,会打印泄漏日志,快速定位问题点。
  • 合理设置最小空闲连接:调整minimumIdle值,避免连接池中的连接被频繁销毁重建,导致连接状态不一致。

3. EntityManager生命周期管理

  • 确认EntityManager的注入逻辑:容器管理的EntityManager(@Autowired注入)默认是事务范围的,事务结束后会自动关闭连接。若在非事务方法中使用,或手动干预了EntityManager生命周期,可能导致连接提前关闭。
  • 避免长期持有EntityManager实例:不要将EntityManager作为类成员变量长期持有,应在方法内按需获取,或通过EntityManagerFactory动态创建实例。

4. 事务边界规范

  • 检查someMethod是否添加了@Transactional注解,若未添加,EntityManager使用的是非事务性连接,连接生命周期由Hikari管理,空闲时可能被回收。如需稳定使用连接,需添加事务注解,并在多数据源场景下指定对应的事务管理器(通过value属性)。
  • 确保事务注解指定了正确的事务管理器,避免用默认事务管理器操作错误的数据源。

5. 数据库端配置检查

  • 查看数据库的连接超时设置(如MySQL的wait_timeout、interactive_timeout),确保这些值大于Hikari的maxLifetime,防止数据库主动关闭连接池中的连接。

内容的提问来源于stack exchange,提问作者Forece85

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.07 22:10:06