数据库连接池(一)HikariCP

一、介绍

1、简介

  • JDBC 连接池:应用从池里借/还连接,而不是每次请求都新建/关闭连接。
  • 特点:高性能("zero-overhead")、体积小(约 165KB)、配置简单、被 Spring Boot 2.x/3.x 选为默认连接池。
  • 设计:极简配置、时间单位统一为毫秒、不做 Statement 缓存(建议用驱动自带缓存)。

二、集成方式和应用

1、集成方式

只要引入了 spring-boot-starter-jdbc(或带 JDBC 的 starter),Spring Boot 会:

  • 自动使用 HikariCP 作为 DataSource 实现;
  • 根据配置自动创建 HikariDataSource Bean,不需要再单独加 HikariCP 依赖。

2、连接池参数

如果不配置数据库连接池的参数,默认如下:

参数 默认值 说明
maximum-pool-size 10 连接池最大连接数
minimum-idle 与 maximum-pool-size 相同(即 10) 最少保留的空闲连接数
connection-timeout 30000(30 秒) 从池中获取连接的最长等待时间,超时抛异常
idle-timeout 600000(10 分钟) 空闲连接超过该时间可被回收
max-lifetime 1800000(30 分钟) 连接在池中的最大存活时间
pool-name 自动生成(如 "HikariPool-1") 未配置时由 HikariCP 自动命名

示例:

复制代码
spring.datasource.primary.db.jdbc-url=jdbc:mysql://xxx?autoReconnect=true&useAffectedRows=true&characterEncoding=UTF-8&allowMultiQueries=true&rewriteBatchedStatements=true
spring.datasource.primary.db.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.primary.db.pool-name=primary_wtyydb
spring.datasource.primary.db.tracking=true
spring.datasource.primary.db.max-lifetime=500000
spring.datasource.primary.db.keep-alivetime=50000
spring.datasource.primary.db.maximum-pool-size=100
spring.datasource.primary.db.minimum-idle=20
spring.datasource.primary.db.connection-test-query=select 1
spring.datasource.primary.db.username=${spring.datasource.username}
spring.datasource.primary.db.password=${spring.datasource.password}
spring.datasource.primary.db.csms-rotate-username-key=spring.datasource.username
spring.datasource.primary.db.csms-rotate-password-key=spring.datasource.password
spring.datasource.primary.mybatis-plus.mapper-locations=classpath*:mapper/*.xml
spring.datasource.primary.mybatis-plus.type-aliases-package=xxx
spring.datasource.primary.mybatis-plus.configuration.cache-enabled=true
spring.datasource.primary.mybatis-plus.configuration.patch_account_condition=true
spring.datasource.primary.mybatis-plus.configuration.log-impl=org.apache.ibatis.logging.nologging.NoLoggingImpl

spring.datasource.slaver.db.jdbc-url=jdbc:mysql://xxx?autoReconnect=true&useAffectedRows=true&characterEncoding=UTF-8&allowMultiQueries=true&rewriteBatchedStatements=true
spring.datasource.slaver.db.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.slaver.db.pool-name=slaver_wtyydb
spring.datasource.slaver.db.tracking=true
spring.datasource.slaver.db.max-lifetime=500000
spring.datasource.slaver.db.keep-alivetime=50000
spring.datasource.slaver.db.maximum-pool-size=100
spring.datasource.slaver.db.minimum-idle=20
spring.datasource.slaver.db.url-dns-number=1
spring.datasource.slaver.db.connection-test-query=select 1
spring.datasource.slaver.db.username=${spring.datasource.username}
spring.datasource.slaver.db.password=${spring.datasource.password}
spring.datasource.slaver.db.csms-rotate-username-key=spring.datasource.username
spring.datasource.slaver.db.csms-rotate-password-key=spring.datasource.password
spring.datasource.slaver.mybatis-plus.mapper-locations=classpath*:read-mapper/*.xml
spring.datasource.slaver.mybatis-plus.type-aliases-package=xxxx
spring.datasource.slaver.mybatis-plus.configuration.cache-enabled=true
spring.datasource.slaver.mybatis-plus.configuration.patch_account_condition=true
spring.datasource.slaver.mybatis-plus.configuration.log-impl=org.apache.ibatis.logging.nologging.NoLoggingImpl

3、代码里怎么用

  • 常规用法:注入 DataSource,正常做 JDBC / MyBatis 等操作即可,底层就是 HikariCP。
  • 要查池状态:若当前 Bean 是 HikariCP(或被包装了一层),可以 unwrap(HikariDataSource.class) 后取 HikariPoolMXBean,就像你项目里的 PoolTestController 那样。

三、demo

1、pom

复制代码
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>3.2.5</version>
        <relativePath/>
    </parent>

    <groupId>com.example</groupId>
    <artifactId>dbpool-demo</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>dbpool-demo</name>
    <description>Spring Boot Demo Project</description>

    <properties>
        <java.version>17</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-jdbc</artifactId>
        </dependency>
        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-spring-boot3-starter</artifactId>
            <version>3.5.5</version>
        </dependency>
        <dependency>
            <groupId>com.mysql</groupId>
            <artifactId>mysql-connector-j</artifactId>
            <scope>runtime</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>
</project>

2、配置文件

复制代码
server.port=8080

spring.application.name=dbpool-demo

spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.url=jdbc:mysql://localhost:3308/demo?useUnicode=true&characterEncoding=utf-8&useSSL=false
spring.datasource.username=root
spring.datasource.password=wtyy

spring.datasource.hikari.pool-name=primary_demo
spring.datasource.hikari.minimum-idle=5
spring.datasource.hikari.maximum-pool-size=20
spring.datasource.hikari.connection-timeout=30000
spring.datasource.hikari.idle-timeout=600000
spring.datasource.hikari.max-lifetime=1800000

spring.datasource.logging.enabled=true
spring.datasource.logging.slow-threshold-ms=500
spring.datasource.logging.log-every-get=true

mybatis-plus.configuration.map-underscore-to-camel-case=true
配置项 含义
pool-name 连接池名称,便于区分
minimum-idle 池中最小空闲连接数
maximum-pool-size 池中最大连接数,超过则等待/超时
connection-timeout 从池中取连接的最大等待时间(毫秒)
idle-timeout 空闲连接超过此时间会被回收
max-lifetime 连接在池中的最大存活时间
logging.enabled 是否开启"拿连接"日志
logging.slow-threshold-ms 超过该毫秒数算慢,打 WARN
logging.log-every-get 是否每次拿连接都打 INFO
map-underscore-to-camel-case 表字段下划线转驼峰(如 role_name → roleName)

3、日志配置

(1)ConnectionPoolLoggingDataSource

复制代码
package com.example.dbpooldemo.config;

import com.zaxxer.hikari.HikariDataSource;
import com.zaxxer.hikari.HikariPoolMXBean;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.sql.DataSource;
import java.io.PrintWriter;
import java.sql.Connection;
import java.sql.SQLException;
import java.sql.SQLFeatureNotSupportedException;
import java.util.concurrent.atomic.AtomicLong;

/**
 * DataSource 包装器:每次 getConnection 时打印耗时 + 连接池状态(active/idle/total/threadsAwaiting),
 * 便于证明"连接池满时其他请求需等待连接"。
 */
public class ConnectionPoolLoggingDataSource implements DataSource {

    private static final Logger log = LoggerFactory.getLogger(ConnectionPoolLoggingDataSource.class);

    private final DataSource delegate;
    private final long slowThresholdMs;
    private final boolean logEveryGet;
    private final String poolName;
    private final AtomicLong connectionGetCounter = new AtomicLong(0);

    public ConnectionPoolLoggingDataSource(DataSource delegate, long slowThresholdMs, boolean logEveryGet) {
        this.delegate = delegate;
        this.slowThresholdMs = slowThresholdMs;
        this.logEveryGet = logEveryGet;
        this.poolName = resolvePoolName(delegate);
    }

    private static String resolvePoolName(DataSource ds) {
        if (ds instanceof HikariDataSource) {
            return ((HikariDataSource) ds).getPoolName();
        }
        return ds.getClass().getSimpleName();
    }

    @Override
    public Connection getConnection() throws SQLException {
        long start = System.currentTimeMillis();
        long seq = connectionGetCounter.incrementAndGet();
        try {
            Connection conn = delegate.getConnection();
            long cost = System.currentTimeMillis() - start;
            afterGetConnection(cost, seq);
            return conn;
        } catch (SQLException e) {
            long cost = System.currentTimeMillis() - start;
            log.warn("[DB连接] getConnection 失败, 等待耗时={}ms, poolName={}, seq={}, thread={}", cost, poolName, seq, threadName(), e);
            throw e;
        }
    }

    @Override
    public Connection getConnection(String username, String password) throws SQLException {
        long start = System.currentTimeMillis();
        long seq = connectionGetCounter.incrementAndGet();
        try {
            Connection conn = delegate.getConnection(username, password);
            long cost = System.currentTimeMillis() - start;
            afterGetConnection(cost, seq);
            return conn;
        } catch (SQLException e) {
            long cost = System.currentTimeMillis() - start;
            log.warn("[DB连接] getConnection 失败, 等待耗时={}ms, poolName={}, seq={}, thread={}", cost, poolName, seq, threadName(), e);
            throw e;
        }
    }

    private void afterGetConnection(long costMs, long seq) {
        PoolStats stats = getPoolStats();
        boolean slow = costMs >= slowThresholdMs;
        boolean shouldLog = logEveryGet || slow;

        if (!shouldLog) {
            return;
        }

        if (slow) {
            log.warn("[DB连接] 拿到连接过慢 | 等待耗时={}ms | poolName={} | active={} idle={} total={} threadsAwaiting={} | seq={} thread={}",
                    costMs, poolName, stats.active, stats.idle, stats.total, stats.threadsAwaiting, seq, threadName());
        } else {
            log.info("[DB连接] 拿到连接 | 等待耗时={}ms | poolName={} | active={} idle={} total={} threadsAwaiting={} | seq={} thread={}",
                    costMs, poolName, stats.active, stats.idle, stats.total, stats.threadsAwaiting, seq, threadName());
        }
    }

    private PoolStats getPoolStats() {
        if (!(delegate instanceof HikariDataSource)) {
            return PoolStats.NA;
        }
        HikariPoolMXBean pool = ((HikariDataSource) delegate).getHikariPoolMXBean();
        if (pool == null) {
            return PoolStats.NA;
        }
        return new PoolStats(pool.getActiveConnections(), pool.getIdleConnections(), pool.getTotalConnections(), pool.getThreadsAwaitingConnection());
    }

    private static String threadName() {
        return Thread.currentThread().getName();
    }

    @Override
    public PrintWriter getLogWriter() throws SQLException {
        return delegate.getLogWriter();
    }

    @Override
    public void setLogWriter(PrintWriter out) throws SQLException {
        delegate.setLogWriter(out);
    }

    @Override
    public void setLoginTimeout(int seconds) throws SQLException {
        delegate.setLoginTimeout(seconds);
    }

    @Override
    public int getLoginTimeout() throws SQLException {
        return delegate.getLoginTimeout();
    }

    @Override
    public java.util.logging.Logger getParentLogger() throws SQLFeatureNotSupportedException {
        return delegate.getParentLogger();
    }

    @Override
    public <T> T unwrap(Class<T> iface) throws SQLException {
        if (iface.isInstance(this)) {
            return iface.cast(this);
        }
        return delegate.unwrap(iface);
    }

    @Override
    public boolean isWrapperFor(Class<?> iface) throws SQLException {
        return iface.isInstance(this) || delegate.isWrapperFor(iface);
    }

    private static class PoolStats {
        final int active;
        final int idle;
        final int total;
        final int threadsAwaiting;

        PoolStats(int active, int idle, int total, int threadsAwaiting) {
            this.active = active;
            this.idle = idle;
            this.total = total;
            this.threadsAwaiting = threadsAwaiting;
        }

        static final PoolStats NA = new PoolStats(-1, -1, -1, -1);
    }
}

作用:对真正的 DataSource(例如 HikariCP)做一层包装,实现 DataSource 接口。

做的事:

  • 每次有人调 getConnection() 时,先记一下时间,再转给里面的真实 DataSource 拿连接。
  • 根据"拿连接耗时"和配置决定是否打日志:
  • 耗时 ≥ slow-threshold-ms → 打 WARN(拿连接过慢)。
  • 若开启了"每次拿连接都打日志",再打 INFO,内容里带上:等待耗时、poolName、active/idle/total/threadsAwaiting、seq、线程名。

目的:方便你看"每次 SQL 用连接"的耗时和当时连接池状态,用来验证连接池满时请求在等连接。

(2)DataSourceLoggingConfig

复制代码
package com.example.dbpooldemo.config;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import javax.sql.DataSource;

/**
 * 将容器中的 DataSource 包装为带"获取连接耗时 + 连接池状态"日志的 DataSource。
 */
@Configuration
public class DataSourceLoggingConfig {

    @Bean
    @ConditionalOnProperty(name = "spring.datasource.logging.enabled", havingValue = "true", matchIfMissing = false)
    public BeanPostProcessor dataSourceLoggingBeanPostProcessor(DataSourceLoggingProperties properties) {
        return new BeanPostProcessor() {
            @Override
            public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
                if (bean instanceof DataSource && !(bean instanceof ConnectionPoolLoggingDataSource)) {
                    return new ConnectionPoolLoggingDataSource(
                            (DataSource) bean,
                            properties.getSlowThresholdMs(),
                            properties.isLogEveryGet()
                    );
                }
                return bean;
            }
        };
    }

    @Bean
    @ConditionalOnProperty(name = "spring.datasource.logging.enabled", havingValue = "true")
    public DataSourceLoggingProperties dataSourceLoggingProperties() {
        return new DataSourceLoggingProperties();
    }

    @ConfigurationProperties(prefix = "spring.datasource.logging")
    public static class DataSourceLoggingProperties {
        /** 超过该耗时(ms)打 WARN:拿到连接过慢 */
        private long slowThresholdMs = 500;
        /** true=每次 getConnection 都打 INFO(含等待耗时+池状态),便于证明连接池满时请求在等连接 */
        private boolean logEveryGet = false;

        public long getSlowThresholdMs() {
            return slowThresholdMs;
        }

        public void setSlowThresholdMs(long slowThresholdMs) {
            this.slowThresholdMs = slowThresholdMs;
        }

        public boolean isLogEveryGet() {
            return logEveryGet;
        }

        public void setLogEveryGet(boolean logEveryGet) {
            this.logEveryGet = logEveryGet;
        }
    }
}

作用:Spring 配置类,负责"把上面的包装套到数据源上"和"读配置"。

做的事:

  • 定义一个 BeanPostProcessor:在 Spring 容器里,等真正的 DataSource(如 HikariCP)创建好后,用 ConnectionPoolLoggingDataSource 把它包一层,之后整个应用拿到的就是带日志的 DataSource。
  • 定义一个 DataSourceLoggingProperties:从 spring.datasource.logging.* 读 slow-threshold-ms、log-every-get、enabled 等,并只在 spring.datasource.logging.enabled=true 时注册上面这个 Processor 和包装。

目的:不写死在代码里,通过配置开关和参数控制"是否打拿连接日志、多慢算慢、是否每次拿连接都打"。

4、启动类

复制代码
package com.example.dbpooldemo;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class DbpoolDemoApplication {

    public static void main(String[] args) {
        SpringApplication.run(DbpoolDemoApplication.class, args);
    }
}

5、业务接口

(1)TestController

复制代码
package com.example.dbpooldemo.controller;

import com.example.dbpooldemo.service.UserService;
import com.zaxxer.hikari.HikariDataSource;
import com.zaxxer.hikari.HikariPoolMXBean;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

import javax.sql.DataSource;
import java.sql.Connection;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;

/**
 * 用于验证连接池行为的测试接口(查看池状态、多线程并发占用连接以模拟连接池满)。
 */
@RestController
@RequestMapping("/api/test")
public class PoolTestController {

    private final DataSource dataSource;
    private final UserService userService;

    public PoolTestController(DataSource dataSource, UserService userService) {
        this.dataSource = dataSource;
        this.userService = userService;
    }

    /**
     * 查看当前连接池状态,便于确认是否"连接数满了"。
     */
    @GetMapping("/pool-stats")
    public ResponseEntity<Map<String, Object>> poolStats() {
        HikariDataSource hikari = unwrapHikari(dataSource);
        if (hikari == null) {
            return ResponseEntity.ok(Map.of("message", "DataSource 不是 HikariCP,无法获取池状态"));
        }
        HikariPoolMXBean pool = hikari.getHikariPoolMXBean();
        if (pool == null) {
            try (Connection c = dataSource.getConnection()) {
            } catch (Exception ignored) {
            }
            pool = hikari.getHikariPoolMXBean();
        }
        if (pool == null) {
            return ResponseEntity.ok(Map.of(
                    "message", "HikariPoolMXBean 不可用(池未就绪或已被包装)",
                    "poolName", hikari.getPoolName(),
                    "maxPoolSize", hikari.getMaximumPoolSize()
            ));
        }
        Map<String, Object> stats = new LinkedHashMap<>();
        stats.put("poolName", hikari.getPoolName());
        stats.put("active", pool.getActiveConnections());
        stats.put("idle", pool.getIdleConnections());
        stats.put("total", pool.getTotalConnections());
        stats.put("threadsAwaiting", pool.getThreadsAwaitingConnection());
        stats.put("maxPoolSize", hikari.getMaximumPoolSize());
        stats.put("full", pool.getActiveConnections() >= hikari.getMaximumPoolSize());
        return ResponseEntity.ok(stats);
    }

    /**
     * 多线程并发调用 UserService 占用连接,模拟连接池满。
     * 每个线程调用 holdConnectionForSeconds,从池中取一条连接并占用 N 秒;
     * 线程数大于 maxPoolSize 时,多余线程会等待或超时。
     *
     * @param seconds 每个连接占用秒数,1--60
     * @param threads 并发线程数,建议大于连接池 maximum-pool-size 以观察池满
     */
    @GetMapping("/lock-table")
    public ResponseEntity<Map<String, Object>> lockTable(
            @RequestParam(defaultValue = "5") int seconds,
            @RequestParam(defaultValue = "10") int threads) {
        int safeSeconds = Math.min(60, Math.max(1, seconds));
        int safeThreads = Math.min(100, Math.max(1, threads));

        long start = System.currentTimeMillis();
        CountDownLatch latch = new CountDownLatch(safeThreads);
        AtomicInteger completed = new AtomicInteger(0);
        AtomicInteger errors = new AtomicInteger(0);
        List<String> errorMessages = new ArrayList<>();

        ExecutorService executor = Executors.newFixedThreadPool(safeThreads);
        for (int i = 0; i < safeThreads; i++) {
            final int index = i;
            executor.submit(() -> {
                try {
                    userService.holdConnectionForSeconds(safeSeconds);
                    completed.incrementAndGet();
                } catch (Exception e) {
                    errors.incrementAndGet();
                    errorMessages.add("thread-" + index + ": " + e.getMessage());
                } finally {
                    latch.countDown();
                }
            });
        }

        try {
            latch.await(60, TimeUnit.SECONDS);
        } catch (InterruptedException e) {
            Thread.currentThread().interrupt();
        }
        executor.shutdown();
        try {
            executor.awaitTermination(5, TimeUnit.SECONDS);
        } catch (InterruptedException e) {
            Thread.currentThread().interrupt();
        }

        long cost = System.currentTimeMillis() - start;
        Map<String, Object> result = new LinkedHashMap<>();
        result.put("message", "多线程并发占用连接: " + safeThreads + " 线程, 每连接 " + safeSeconds + " 秒");
        result.put("threads", safeThreads);
        result.put("secondsPerConnection", safeSeconds);
        result.put("completed", completed.get());
        result.put("errors", errors.get());
        result.put("actualMs", cost);
        if (!errorMessages.isEmpty()) {
            result.put("errorSamples", errorMessages.size() > 5 ? errorMessages.subList(0, 5) : errorMessages);
        }
        return ResponseEntity.ok(result);
    }

    private static HikariDataSource unwrapHikari(DataSource ds) {
        if (ds instanceof HikariDataSource) {
            return (HikariDataSource) ds;
        }
        try {
            return ds.unwrap(HikariDataSource.class);
        } catch (Exception e) {
            return null;
        }
    }
}

(2)RoleContoller

复制代码
@RestController
@RequestMapping("/api/roles")
public class RoleController {

    ......
@PutMapping("/{id}")
    public ResponseEntity<Void> updateRoleById(@PathVariable Integer id, @RequestBody Role role) {
        roleService.updateRoleById(id, role);
        return ResponseEntity.ok().build();
    }
}

(3)UserServiceImpl:

复制代码
@Override
    public void holdConnectionForSeconds(int seconds) {
        userMapper.sleep(seconds);
    }

(4)RoleServiceImpl

复制代码
 @Override
    public void updateRoleById(Integer id, Role role) {
        Role existing = roleMapper.selectById(id);
        roleMapper.updateById(existing);
    }

6、测试

(1)直接调用updateRoleById,响应很快

复制代码
Testkit submitReq  method:function-call reqId:jJtgj53LBXtwoDAG
2026-02-14T11:12:52.772+08:00  INFO 14348 --- [dbpool-demo] [pool-3-thread-1] com.zaxxer.hikari.HikariDataSource       : primary_demo - Starting...
2026-02-14T11:12:52.904+08:00  INFO 14348 --- [dbpool-demo] [pool-3-thread-1] com.zaxxer.hikari.pool.HikariPool        : primary_demo - Added connection com.mysql.cj.jdbc.ConnectionImpl@7f852dc6
2026-02-14T11:12:52.906+08:00  INFO 14348 --- [dbpool-demo] [pool-3-thread-1] com.zaxxer.hikari.HikariDataSource       : primary_demo - Start completed.
2026-02-14T11:12:52.908+08:00  INFO 14348 --- [dbpool-demo] [pool-3-thread-1] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=136ms | poolName=primary_demo | active=1 idle=0 total=1 threadsAwaiting=0 | seq=1 thread=pool-3-thread-1
2026-02-14T11:12:52.986+08:00  INFO 14348 --- [dbpool-demo] [pool-3-thread-1] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=1 idle=0 total=1 threadsAwaiting=0 | seq=2 thread=pool-3-thread-1
TESTKIT_DETAIL tool:function-call cost:235 params:{argTypes=["java.lang.Integer","com.example.dbpooldemo.entity.Role"], args=[1,{"roleName":"test1"}], original=false, typeClass=com.example.dbpooldemo.controller.RoleController, methodName=updateRoleById, req_id=jJtgj53LBXtwoDAG} ret:<200 OK OK,[]> e:null

(2)获取连接变慢

先调用http://localhost:8080/api/test/lock-table?seconds=30&threads=22

再调用http://localhost:8080/api/roles/updateRoleById 会发现卡顿

复制代码
2026-02-14T11:13:54.520+08:00  INFO 14348 --- [dbpool-demo] [nio-8080-exec-2] o.a.c.c.C.[Tomcat].[localhost].[/]       : Initializing Spring DispatcherServlet 'dispatcherServlet'
2026-02-14T11:13:54.520+08:00  INFO 14348 --- [dbpool-demo] [nio-8080-exec-2] o.s.web.servlet.DispatcherServlet        : Initializing Servlet 'dispatcherServlet'
2026-02-14T11:13:54.529+08:00  INFO 14348 --- [dbpool-demo] [nio-8080-exec-2] o.s.web.servlet.DispatcherServlet        : Completed initialization in 9 ms
2026-02-14T11:13:54.712+08:00  INFO 14348 --- [dbpool-demo] [pool-4-thread-1] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=3 idle=2 total=5 threadsAwaiting=0 | seq=3 thread=pool-4-thread-1
2026-02-14T11:13:54.712+08:00  INFO 14348 --- [dbpool-demo] [pool-4-thread-2] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=3 idle=2 total=5 threadsAwaiting=0 | seq=4 thread=pool-4-thread-2
2026-02-14T11:13:54.712+08:00  INFO 14348 --- [dbpool-demo] [pool-4-thread-3] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=4 idle=1 total=5 threadsAwaiting=0 | seq=5 thread=pool-4-thread-3
2026-02-14T11:13:54.721+08:00  INFO 14348 --- [dbpool-demo] [pool-4-thread-4] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=9ms | poolName=primary_demo | active=4 idle=1 total=5 threadsAwaiting=0 | seq=6 thread=pool-4-thread-4
2026-02-14T11:13:54.721+08:00  INFO 14348 --- [dbpool-demo] [pool-4-thread-5] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=5 idle=0 total=5 threadsAwaiting=1 | seq=7 thread=pool-4-thread-5
2026-02-14T11:13:54.754+08:00  INFO 14348 --- [dbpool-demo] [pool-4-thread-7] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=33ms | poolName=primary_demo | active=6 idle=0 total=6 threadsAwaiting=16 | seq=9 thread=pool-4-thread-7
2026-02-14T11:13:54.788+08:00  INFO 14348 --- [dbpool-demo] [pool-4-thread-8] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=67ms | poolName=primary_demo | active=7 idle=0 total=7 threadsAwaiting=15 | seq=10 thread=pool-4-thread-8
2026-02-14T11:13:54.830+08:00  INFO 14348 --- [dbpool-demo] [pool-4-thread-6] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=109ms | poolName=primary_demo | active=8 idle=0 total=8 threadsAwaiting=14 | seq=8 thread=pool-4-thread-6
2026-02-14T11:13:54.872+08:00  INFO 14348 --- [dbpool-demo] [pool-4-thread-9] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=151ms | poolName=primary_demo | active=9 idle=0 total=9 threadsAwaiting=13 | seq=11 thread=pool-4-thread-9
2026-02-14T11:13:54.905+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-10] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=184ms | poolName=primary_demo | active=10 idle=0 total=10 threadsAwaiting=12 | seq=12 thread=pool-4-thread-10
2026-02-14T11:13:54.939+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-11] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=210ms | poolName=primary_demo | active=11 idle=0 total=11 threadsAwaiting=11 | seq=13 thread=pool-4-thread-11
2026-02-14T11:13:54.980+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-12] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=251ms | poolName=primary_demo | active=12 idle=0 total=12 threadsAwaiting=10 | seq=14 thread=pool-4-thread-12
2026-02-14T11:13:55.013+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-13] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=284ms | poolName=primary_demo | active=13 idle=0 total=13 threadsAwaiting=9 | seq=15 thread=pool-4-thread-13
2026-02-14T11:13:55.046+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-14] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=317ms | poolName=primary_demo | active=14 idle=0 total=14 threadsAwaiting=8 | seq=16 thread=pool-4-thread-14
2026-02-14T11:13:55.071+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-15] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=342ms | poolName=primary_demo | active=15 idle=0 total=15 threadsAwaiting=7 | seq=17 thread=pool-4-thread-15
2026-02-14T11:13:55.105+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-16] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=376ms | poolName=primary_demo | active=16 idle=0 total=16 threadsAwaiting=6 | seq=18 thread=pool-4-thread-16
2026-02-14T11:13:55.130+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-17] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=392ms | poolName=primary_demo | active=17 idle=0 total=17 threadsAwaiting=5 | seq=19 thread=pool-4-thread-17
2026-02-14T11:13:55.162+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-18] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=424ms | poolName=primary_demo | active=18 idle=0 total=18 threadsAwaiting=4 | seq=20 thread=pool-4-thread-18
2026-02-14T11:13:55.187+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-19] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=449ms | poolName=primary_demo | active=19 idle=0 total=19 threadsAwaiting=3 | seq=21 thread=pool-4-thread-19
2026-02-14T11:13:55.220+08:00  INFO 14348 --- [dbpool-demo] [ool-4-thread-20] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=482ms | poolName=primary_demo | active=20 idle=0 total=20 threadsAwaiting=2 | seq=22 thread=pool-4-thread-20
Testkit submitReq  method:function-call reqId:ouIbmEFhfs4U5nLU
2026-02-14T11:14:24.744+08:00  WARN 14348 --- [dbpool-demo] [ool-4-thread-21] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接过慢 | 等待耗时=29998ms | poolName=primary_demo | active=17 idle=3 total=20 threadsAwaiting=1 | seq=23 thread=pool-4-thread-21
2026-02-14T11:14:24.744+08:00  WARN 14348 --- [dbpool-demo] [pool-3-thread-2] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接过慢 | 等待耗时=25189ms | poolName=primary_demo | active=18 idle=2 total=20 threadsAwaiting=0 | seq=25 thread=pool-3-thread-2
2026-02-14T11:14:24.744+08:00  WARN 14348 --- [dbpool-demo] [ool-4-thread-22] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接过慢 | 等待耗时=29998ms | poolName=primary_demo | active=17 idle=3 total=20 threadsAwaiting=1 | seq=24 thread=pool-4-thread-22
2026-02-14T11:14:24.746+08:00  INFO 14348 --- [dbpool-demo] [pool-3-thread-2] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=18 idle=2 total=20 threadsAwaiting=0 | seq=26 thread=pool-3-thread-2
TESTKIT_DETAIL tool:function-call cost:25198 params:{argTypes=["java.lang.Integer","com.example.dbpooldemo.entity.Role"], args=[1,{"roleName":"test1"}], original=false, typeClass=com.example.dbpooldemo.controller.RoleController, methodName=updateRoleById, req_id=ouIbmEFhfs4U5nLU} ret:<200 OK OK,[]> e:null

(3)获取连接超时

调大lock-table的参数,同时调用updateRoleById可能会报错

复制代码
2026-02-14T11:17:06.162+08:00  INFO 14348 --- [dbpool-demo] [pool-5-thread-1] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=3 idle=17 total=20 threadsAwaiting=0 | seq=27 thread=pool-5-thread-1
2026-02-14T11:17:06.162+08:00  INFO 14348 --- [dbpool-demo] [pool-5-thread-2] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=3 idle=17 total=20 threadsAwaiting=0 | seq=28 thread=pool-5-thread-2
2026-02-14T11:17:06.162+08:00  INFO 14348 --- [dbpool-demo] [pool-5-thread-3] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=5 idle=15 total=20 threadsAwaiting=0 | seq=29 thread=pool-5-thread-3
2026-02-14T11:17:06.162+08:00  INFO 14348 --- [dbpool-demo] [pool-5-thread-4] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=5 idle=15 total=20 threadsAwaiting=0 | seq=30 thread=pool-5-thread-4
2026-02-14T11:17:06.162+08:00  INFO 14348 --- [dbpool-demo] [pool-5-thread-5] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=5 idle=15 total=20 threadsAwaiting=0 | seq=31 thread=pool-5-thread-5
2026-02-14T11:17:06.163+08:00  INFO 14348 --- [dbpool-demo] [pool-5-thread-6] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=8 idle=12 total=20 threadsAwaiting=0 | seq=32 thread=pool-5-thread-6
2026-02-14T11:17:06.163+08:00  INFO 14348 --- [dbpool-demo] [pool-5-thread-7] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=8 idle=12 total=20 threadsAwaiting=0 | seq=33 thread=pool-5-thread-7
2026-02-14T11:17:06.163+08:00  INFO 14348 --- [dbpool-demo] [pool-5-thread-8] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=8 idle=12 total=20 threadsAwaiting=0 | seq=34 thread=pool-5-thread-8
2026-02-14T11:17:06.164+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-10] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=10 idle=10 total=20 threadsAwaiting=0 | seq=35 thread=pool-5-thread-10
2026-02-14T11:17:06.164+08:00  INFO 14348 --- [dbpool-demo] [pool-5-thread-9] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=10 idle=10 total=20 threadsAwaiting=0 | seq=36 thread=pool-5-thread-9
2026-02-14T11:17:06.165+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-12] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=12 idle=8 total=20 threadsAwaiting=0 | seq=37 thread=pool-5-thread-12
2026-02-14T11:17:06.165+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-11] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=12 idle=8 total=20 threadsAwaiting=0 | seq=38 thread=pool-5-thread-11
2026-02-14T11:17:06.166+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-13] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=14 idle=6 total=20 threadsAwaiting=0 | seq=39 thread=pool-5-thread-13
2026-02-14T11:17:06.166+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-14] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=14 idle=6 total=20 threadsAwaiting=0 | seq=40 thread=pool-5-thread-14
2026-02-14T11:17:06.167+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-15] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=15 idle=5 total=20 threadsAwaiting=1 | seq=41 thread=pool-5-thread-15
2026-02-14T11:17:06.168+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-16] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=16 idle=4 total=20 threadsAwaiting=0 | seq=42 thread=pool-5-thread-16
2026-02-14T11:17:06.190+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-18] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=19 idle=1 total=20 threadsAwaiting=0 | seq=43 thread=pool-5-thread-18
2026-02-14T11:17:06.190+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-17] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=19 idle=1 total=20 threadsAwaiting=0 | seq=44 thread=pool-5-thread-17
2026-02-14T11:17:06.191+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-19] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=1ms | poolName=primary_demo | active=20 idle=0 total=20 threadsAwaiting=0 | seq=45 thread=pool-5-thread-19
2026-02-14T11:17:06.191+08:00  INFO 14348 --- [dbpool-demo] [ool-5-thread-20] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] 拿到连接 | 等待耗时=0ms | poolName=primary_demo | active=20 idle=0 total=20 threadsAwaiting=0 | seq=46 thread=pool-5-thread-20
Testkit submitReq  method:function-call reqId:UckbAnky8JlYIboP
2026-02-14T11:17:36.203+08:00  WARN 14348 --- [dbpool-demo] [ool-5-thread-22] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] getConnection 失败, 等待耗时=30011ms, poolName=primary_demo, seq=48, thread=pool-5-thread-22

java.sql.SQLTransientConnectionException: primary_demo - Connection is not available, request timed out after 30010ms.
	at com.zaxxer.hikari.pool.HikariPool.createTimeoutException(HikariPool.java:696) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:181) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:146) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:128) ~[HikariCP-5.0.1.jar:na]
	at com.example.dbpooldemo.config.ConnectionPoolLoggingDataSource.getConnection(ConnectionPoolLoggingDataSource.java:48) ~[classes/:na]
	at org.springframework.jdbc.datasource.DataSourceUtils.fetchConnection(DataSourceUtils.java:160) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.doGetConnection(DataSourceUtils.java:118) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:81) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.mybatis.spring.transaction.SpringManagedTransaction.openConnection(SpringManagedTransaction.java:80) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.mybatis.spring.transaction.SpringManagedTransaction.getConnection(SpringManagedTransaction.java:67) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.apache.ibatis.executor.BaseExecutor.getConnection(BaseExecutor.java:348) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.prepareStatement(SimpleExecutor.java:89) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.doQuery(SimpleExecutor.java:64) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.queryFromDatabase(BaseExecutor.java:336) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.query(BaseExecutor.java:158) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:110) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:90) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:154) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:147) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:142) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectOne(DefaultSqlSession.java:75) ~[mybatis-3.5.15.jar:3.5.15]
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103) ~[na:na]
	at java.base/java.lang.reflect.Method.invoke(Method.java:580) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:425) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at jdk.proxy2/jdk.proxy2.$Proxy62.selectOne(Unknown Source) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate.selectOne(SqlSessionTemplate.java:160) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at com.baomidou.mybatisplus.core.override.MybatisMapperMethod.execute(MybatisMapperMethod.java:87) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy$PlainMethodInvoker.invoke(MybatisMapperProxy.java:152) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy.invoke(MybatisMapperProxy.java:89) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at jdk.proxy2/jdk.proxy2.$Proxy67.sleep(Unknown Source) ~[na:na]
	at com.example.dbpooldemo.service.impl.UserServiceImpl.holdConnectionForSeconds(UserServiceImpl.java:74) ~[classes/:na]
	at com.example.dbpooldemo.controller.PoolTestController.lambda$lockTable$0(PoolTestController.java:99) ~[classes/:na]
	at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:572) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:317) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642) ~[na:na]
	at java.base/java.lang.Thread.run(Thread.java:1583) ~[na:na]

2026-02-14T11:17:36.203+08:00  WARN 14348 --- [dbpool-demo] [ool-5-thread-25] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] getConnection 失败, 等待耗时=30009ms, poolName=primary_demo, seq=51, thread=pool-5-thread-25

java.sql.SQLTransientConnectionException: primary_demo - Connection is not available, request timed out after 30008ms.
	at com.zaxxer.hikari.pool.HikariPool.createTimeoutException(HikariPool.java:696) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:181) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:146) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:128) ~[HikariCP-5.0.1.jar:na]
	at com.example.dbpooldemo.config.ConnectionPoolLoggingDataSource.getConnection(ConnectionPoolLoggingDataSource.java:48) ~[classes/:na]
	at org.springframework.jdbc.datasource.DataSourceUtils.fetchConnection(DataSourceUtils.java:160) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.doGetConnection(DataSourceUtils.java:118) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:81) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.mybatis.spring.transaction.SpringManagedTransaction.openConnection(SpringManagedTransaction.java:80) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.mybatis.spring.transaction.SpringManagedTransaction.getConnection(SpringManagedTransaction.java:67) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.apache.ibatis.executor.BaseExecutor.getConnection(BaseExecutor.java:348) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.prepareStatement(SimpleExecutor.java:89) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.doQuery(SimpleExecutor.java:64) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.queryFromDatabase(BaseExecutor.java:336) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.query(BaseExecutor.java:158) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:110) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:90) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:154) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:147) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:142) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectOne(DefaultSqlSession.java:75) ~[mybatis-3.5.15.jar:3.5.15]
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103) ~[na:na]
	at java.base/java.lang.reflect.Method.invoke(Method.java:580) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:425) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at jdk.proxy2/jdk.proxy2.$Proxy62.selectOne(Unknown Source) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate.selectOne(SqlSessionTemplate.java:160) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at com.baomidou.mybatisplus.core.override.MybatisMapperMethod.execute(MybatisMapperMethod.java:87) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy$PlainMethodInvoker.invoke(MybatisMapperProxy.java:152) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy.invoke(MybatisMapperProxy.java:89) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at jdk.proxy2/jdk.proxy2.$Proxy67.sleep(Unknown Source) ~[na:na]
	at com.example.dbpooldemo.service.impl.UserServiceImpl.holdConnectionForSeconds(UserServiceImpl.java:74) ~[classes/:na]
	at com.example.dbpooldemo.controller.PoolTestController.lambda$lockTable$0(PoolTestController.java:99) ~[classes/:na]
	at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:572) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:317) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642) ~[na:na]
	at java.base/java.lang.Thread.run(Thread.java:1583) ~[na:na]

2026-02-14T11:17:36.203+08:00  WARN 14348 --- [dbpool-demo] [ool-5-thread-24] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] getConnection 失败, 等待耗时=30010ms, poolName=primary_demo, seq=50, thread=pool-5-thread-24

java.sql.SQLTransientConnectionException: primary_demo - Connection is not available, request timed out after 30009ms.
	at com.zaxxer.hikari.pool.HikariPool.createTimeoutException(HikariPool.java:696) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:181) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:146) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:128) ~[HikariCP-5.0.1.jar:na]
	at com.example.dbpooldemo.config.ConnectionPoolLoggingDataSource.getConnection(ConnectionPoolLoggingDataSource.java:48) ~[classes/:na]
	at org.springframework.jdbc.datasource.DataSourceUtils.fetchConnection(DataSourceUtils.java:160) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.doGetConnection(DataSourceUtils.java:118) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:81) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.mybatis.spring.transaction.SpringManagedTransaction.openConnection(SpringManagedTransaction.java:80) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.mybatis.spring.transaction.SpringManagedTransaction.getConnection(SpringManagedTransaction.java:67) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.apache.ibatis.executor.BaseExecutor.getConnection(BaseExecutor.java:348) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.prepareStatement(SimpleExecutor.java:89) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.doQuery(SimpleExecutor.java:64) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.queryFromDatabase(BaseExecutor.java:336) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.query(BaseExecutor.java:158) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:110) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:90) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:154) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:147) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:142) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectOne(DefaultSqlSession.java:75) ~[mybatis-3.5.15.jar:3.5.15]
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103) ~[na:na]
	at java.base/java.lang.reflect.Method.invoke(Method.java:580) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:425) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at jdk.proxy2/jdk.proxy2.$Proxy62.selectOne(Unknown Source) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate.selectOne(SqlSessionTemplate.java:160) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at com.baomidou.mybatisplus.core.override.MybatisMapperMethod.execute(MybatisMapperMethod.java:87) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy$PlainMethodInvoker.invoke(MybatisMapperProxy.java:152) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy.invoke(MybatisMapperProxy.java:89) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at jdk.proxy2/jdk.proxy2.$Proxy67.sleep(Unknown Source) ~[na:na]
	at com.example.dbpooldemo.service.impl.UserServiceImpl.holdConnectionForSeconds(UserServiceImpl.java:74) ~[classes/:na]
	at com.example.dbpooldemo.controller.PoolTestController.lambda$lockTable$0(PoolTestController.java:99) ~[classes/:na]
	at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:572) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:317) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642) ~[na:na]
	at java.base/java.lang.Thread.run(Thread.java:1583) ~[na:na]

2026-02-14T11:17:36.203+08:00  WARN 14348 --- [dbpool-demo] [ool-5-thread-23] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] getConnection 失败, 等待耗时=30011ms, poolName=primary_demo, seq=49, thread=pool-5-thread-23

java.sql.SQLTransientConnectionException: primary_demo - Connection is not available, request timed out after 30010ms.
	at com.zaxxer.hikari.pool.HikariPool.createTimeoutException(HikariPool.java:696) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:181) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:146) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:128) ~[HikariCP-5.0.1.jar:na]
	at com.example.dbpooldemo.config.ConnectionPoolLoggingDataSource.getConnection(ConnectionPoolLoggingDataSource.java:48) ~[classes/:na]
	at org.springframework.jdbc.datasource.DataSourceUtils.fetchConnection(DataSourceUtils.java:160) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.doGetConnection(DataSourceUtils.java:118) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:81) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.mybatis.spring.transaction.SpringManagedTransaction.openConnection(SpringManagedTransaction.java:80) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.mybatis.spring.transaction.SpringManagedTransaction.getConnection(SpringManagedTransaction.java:67) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.apache.ibatis.executor.BaseExecutor.getConnection(BaseExecutor.java:348) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.prepareStatement(SimpleExecutor.java:89) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.doQuery(SimpleExecutor.java:64) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.queryFromDatabase(BaseExecutor.java:336) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.query(BaseExecutor.java:158) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:110) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:90) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:154) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:147) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:142) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectOne(DefaultSqlSession.java:75) ~[mybatis-3.5.15.jar:3.5.15]
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103) ~[na:na]
	at java.base/java.lang.reflect.Method.invoke(Method.java:580) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:425) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at jdk.proxy2/jdk.proxy2.$Proxy62.selectOne(Unknown Source) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate.selectOne(SqlSessionTemplate.java:160) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at com.baomidou.mybatisplus.core.override.MybatisMapperMethod.execute(MybatisMapperMethod.java:87) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy$PlainMethodInvoker.invoke(MybatisMapperProxy.java:152) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy.invoke(MybatisMapperProxy.java:89) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at jdk.proxy2/jdk.proxy2.$Proxy67.sleep(Unknown Source) ~[na:na]
	at com.example.dbpooldemo.service.impl.UserServiceImpl.holdConnectionForSeconds(UserServiceImpl.java:74) ~[classes/:na]
	at com.example.dbpooldemo.controller.PoolTestController.lambda$lockTable$0(PoolTestController.java:99) ~[classes/:na]
	at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:572) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:317) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642) ~[na:na]
	at java.base/java.lang.Thread.run(Thread.java:1583) ~[na:na]

2026-02-14T11:17:36.203+08:00  WARN 14348 --- [dbpool-demo] [ool-5-thread-21] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] getConnection 失败, 等待耗时=30012ms, poolName=primary_demo, seq=47, thread=pool-5-thread-21

java.sql.SQLTransientConnectionException: primary_demo - Connection is not available, request timed out after 30011ms.
	at com.zaxxer.hikari.pool.HikariPool.createTimeoutException(HikariPool.java:696) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:181) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:146) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:128) ~[HikariCP-5.0.1.jar:na]
	at com.example.dbpooldemo.config.ConnectionPoolLoggingDataSource.getConnection(ConnectionPoolLoggingDataSource.java:48) ~[classes/:na]
	at org.springframework.jdbc.datasource.DataSourceUtils.fetchConnection(DataSourceUtils.java:160) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.doGetConnection(DataSourceUtils.java:118) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:81) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.mybatis.spring.transaction.SpringManagedTransaction.openConnection(SpringManagedTransaction.java:80) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.mybatis.spring.transaction.SpringManagedTransaction.getConnection(SpringManagedTransaction.java:67) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.apache.ibatis.executor.BaseExecutor.getConnection(BaseExecutor.java:348) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.prepareStatement(SimpleExecutor.java:89) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.doQuery(SimpleExecutor.java:64) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.queryFromDatabase(BaseExecutor.java:336) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.query(BaseExecutor.java:158) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:110) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:90) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:154) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:147) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:142) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectOne(DefaultSqlSession.java:75) ~[mybatis-3.5.15.jar:3.5.15]
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103) ~[na:na]
	at java.base/java.lang.reflect.Method.invoke(Method.java:580) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:425) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at jdk.proxy2/jdk.proxy2.$Proxy62.selectOne(Unknown Source) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate.selectOne(SqlSessionTemplate.java:160) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at com.baomidou.mybatisplus.core.override.MybatisMapperMethod.execute(MybatisMapperMethod.java:87) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy$PlainMethodInvoker.invoke(MybatisMapperProxy.java:152) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy.invoke(MybatisMapperProxy.java:89) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at jdk.proxy2/jdk.proxy2.$Proxy67.sleep(Unknown Source) ~[na:na]
	at com.example.dbpooldemo.service.impl.UserServiceImpl.holdConnectionForSeconds(UserServiceImpl.java:74) ~[classes/:na]
	at com.example.dbpooldemo.controller.PoolTestController.lambda$lockTable$0(PoolTestController.java:99) ~[classes/:na]
	at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:572) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:317) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642) ~[na:na]
	at java.base/java.lang.Thread.run(Thread.java:1583) ~[na:na]

2026-02-14T11:17:36.844+08:00  WARN 14348 --- [dbpool-demo] [pool-3-thread-3] c.e.d.c.ConnectionPoolLoggingDataSource  : [DB连接] getConnection 失败, 等待耗时=30013ms, poolName=primary_demo, seq=52, thread=pool-3-thread-3

java.sql.SQLTransientConnectionException: primary_demo - Connection is not available, request timed out after 30013ms.
	at com.zaxxer.hikari.pool.HikariPool.createTimeoutException(HikariPool.java:696) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:181) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:146) ~[HikariCP-5.0.1.jar:na]
	at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:128) ~[HikariCP-5.0.1.jar:na]
	at com.example.dbpooldemo.config.ConnectionPoolLoggingDataSource.getConnection(ConnectionPoolLoggingDataSource.java:48) ~[classes/:na]
	at org.springframework.jdbc.datasource.DataSourceUtils.fetchConnection(DataSourceUtils.java:160) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.doGetConnection(DataSourceUtils.java:118) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:81) ~[spring-jdbc-6.1.6.jar:6.1.6]
	at org.mybatis.spring.transaction.SpringManagedTransaction.openConnection(SpringManagedTransaction.java:80) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.mybatis.spring.transaction.SpringManagedTransaction.getConnection(SpringManagedTransaction.java:67) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at org.apache.ibatis.executor.BaseExecutor.getConnection(BaseExecutor.java:348) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.prepareStatement(SimpleExecutor.java:89) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.SimpleExecutor.doQuery(SimpleExecutor.java:64) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.queryFromDatabase(BaseExecutor.java:336) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.BaseExecutor.query(BaseExecutor.java:158) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:110) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:90) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:154) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:147) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:142) ~[mybatis-3.5.15.jar:3.5.15]
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectOne(DefaultSqlSession.java:75) ~[mybatis-3.5.15.jar:3.5.15]
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103) ~[na:na]
	at java.base/java.lang.reflect.Method.invoke(Method.java:580) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:425) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at jdk.proxy2/jdk.proxy2.$Proxy62.selectOne(Unknown Source) ~[na:na]
	at org.mybatis.spring.SqlSessionTemplate.selectOne(SqlSessionTemplate.java:160) ~[mybatis-spring-3.0.3.jar:3.0.3]
	at com.baomidou.mybatisplus.core.override.MybatisMapperMethod.execute(MybatisMapperMethod.java:87) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy$PlainMethodInvoker.invoke(MybatisMapperProxy.java:152) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy.invoke(MybatisMapperProxy.java:89) ~[mybatis-plus-core-3.5.5.jar:3.5.5]
	at jdk.proxy2/jdk.proxy2.$Proxy71.selectById(Unknown Source) ~[na:na]
	at com.example.dbpooldemo.service.impl.RoleServiceImpl.updateRoleById(RoleServiceImpl.java:26) ~[classes/:na]
	at com.example.dbpooldemo.controller.RoleController.updateRoleById(RoleController.java:35) ~[classes/:na]
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103) ~[na:na]
	at java.base/java.lang.reflect.Method.invoke(Method.java:580) ~[na:na]
	at com.testkit.server.ReflexBox.execute(ReflexBox.java:90) ~[testkit-starter-1.0.jar:na]
	at com.testkit.server.FunctionCallTool$1.execute(FunctionCallTool.java:74) ~[testkit-starter-1.0.jar:na]
	at com.testkit.server.TestkitServer.processReq(TestkitServer.java:395) ~[testkit-starter-1.0.jar:na]
	at com.testkit.server.TestkitServer.access$500(TestkitServer.java:26) ~[testkit-starter-1.0.jar:na]
	at com.testkit.server.TestkitServer$2.call(TestkitServer.java:283) ~[testkit-starter-1.0.jar:na]
	at com.testkit.server.TestkitServer$2.call(TestkitServer.java:280) ~[testkit-starter-1.0.jar:na]
	at java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:317) ~[na:na]
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144) ~[na:na]
	at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642) ~[na:na]
	at java.base/java.lang.Thread.run(Thread.java:1583) ~[na:na]

TESTKIT tool execute error, errorType:java.lang.reflect.InvocationTargetException, nulljava.lang.reflect.InvocationTargetException
java.lang.reflect.InvocationTargetException
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:118)
	at java.base/java.lang.reflect.Method.invoke(Method.java:580)
	at com.testkit.server.ReflexBox.execute(ReflexBox.java:90)
	at com.testkit.server.FunctionCallTool$1.execute(FunctionCallTool.java:74)
	at com.testkit.server.TestkitServer.processReq(TestkitServer.java:395)
	at com.testkit.server.TestkitServer.access$500(TestkitServer.java:26)
	at com.testkit.server.TestkitServer$2.call(TestkitServer.java:283)
	at com.testkit.server.TestkitServer$2.call(TestkitServer.java:280)
	at java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:317)
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java)
	at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144)
	at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642)
	at java.base/java.lang.Thread.run(Thread.java:1583)
Caused by: org.mybatis.spring.MyBatisSystemException
	at org.mybatis.spring.MyBatisExceptionTranslator.translateExceptionIfPossible(MyBatisExceptionTranslator.java:97)
	at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:439)
	at jdk.proxy2/jdk.proxy2.$Proxy62.selectOne(Unknown Source)
	at org.mybatis.spring.SqlSessionTemplate.selectOne(SqlSessionTemplate.java:160)
	at com.baomidou.mybatisplus.core.override.MybatisMapperMethod.execute(MybatisMapperMethod.java:87)
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy$PlainMethodInvoker.invoke(MybatisMapperProxy.java:152)
	at com.baomidou.mybatisplus.core.override.MybatisMapperProxy.invoke(MybatisMapperProxy.java:89)
	at jdk.proxy2/jdk.proxy2.$Proxy71.selectById(Unknown Source)
	at com.example.dbpooldemo.service.impl.RoleServiceImpl.updateRoleById(RoleServiceImpl.java:26)
	at com.example.dbpooldemo.controller.RoleController.updateRoleById(RoleController.java:35)
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103)
	... 12 more
Caused by: org.apache.ibatis.exceptions.PersistenceException: 
### Error querying database.  Cause: org.springframework.jdbc.CannotGetJdbcConnectionException: Failed to obtain JDBC Connection
### The error may exist in com/example/dbpooldemo/mapper/RoleMapper.java (best guess)
### The error may involve com.example.dbpooldemo.mapper.RoleMapper.selectById
### The error occurred while executing a query
### Cause: org.springframework.jdbc.CannotGetJdbcConnectionException: Failed to obtain JDBC Connection
	at org.apache.ibatis.exceptions.ExceptionFactory.wrapException(ExceptionFactory.java:30)
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:156)
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:147)
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:142)
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectOne(DefaultSqlSession.java:75)
	at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103)
	at java.base/java.lang.reflect.Method.invoke(Method.java:580)
	at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:425)
	... 21 more
Caused by: org.springframework.jdbc.CannotGetJdbcConnectionException: Failed to obtain JDBC Connection
	at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:84)
	at org.mybatis.spring.transaction.SpringManagedTransaction.openConnection(SpringManagedTransaction.java:80)
	at org.mybatis.spring.transaction.SpringManagedTransaction.getConnection(SpringManagedTransaction.java:67)
	at org.apache.ibatis.executor.BaseExecutor.getConnection(BaseExecutor.java:348)
	at org.apache.ibatis.executor.SimpleExecutor.prepareStatement(SimpleExecutor.java:89)
	at org.apache.ibatis.executor.SimpleExecutor.doQuery(SimpleExecutor.java:64)
	at org.apache.ibatis.executor.BaseExecutor.queryFromDatabase(BaseExecutor.java:336)
	at org.apache.ibatis.executor.BaseExecutor.query(BaseExecutor.java:158)
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:110)
	at org.apache.ibatis.executor.CachingExecutor.query(CachingExecutor.java:90)
	at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:154)
	... 27 more
Caused by: java.sql.SQLTransientConnectionException: primary_demo - Connection is not available, request timed out after 30013ms.
	at com.zaxxer.hikari.pool.HikariPool.createTimeoutException(HikariPool.java:696)
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:181)
	at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:146)
	at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:128)
	at com.example.dbpooldemo.config.ConnectionPoolLoggingDataSource.getConnection(ConnectionPoolLoggingDataSource.java:48)
	at org.springframework.jdbc.datasource.DataSourceUtils.fetchConnection(DataSourceUtils.java:160)
	at org.springframework.jdbc.datasource.DataSourceUtils.doGetConnection(DataSourceUtils.java:118)
	at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:81)
	... 37 more
TESTKIT_DETAIL tool:function-call cost:30021 params:{argTypes=["java.lang.Integer","com.example.dbpooldemo.entity.Role"], args=[1,{"roleName":"test1"}], original=false, typeClass=com.example.dbpooldemo.controller.RoleController, methodName=updateRoleById, req_id=UckbAnky8JlYIboP} ret:null e:org.mybatis.spring.MyBatisSystemException
相关推荐
sheji70092 小时前
Springboot家教平台中心系统53754--(程序+源码+数据库+调试部署+开发环境)
java·数据库·spring boot·后端·spring·旅游
小宋10213 小时前
Java 数据库访问 vs Python 数据库访问:JDBC vs ORM
java·数据库·python
少云清3 小时前
【安全测试】6_数据库安全性测试 _数据备份、加密、审计、认证
数据库·安全性测试
kyle~3 小时前
Redis(Remote Dictionary Server)
数据库·redis·缓存
砚边数影3 小时前
架构实战:如何利用融合数据库破解用户画像系统的存储瓶颈?
数据库·mongodb·架构·kingbase·数据库平替用金仓·金仓数据库
不剪发的Tony老师4 小时前
FlySpeed:一款通用的SQL查询工具
数据库·sql
攻城狮7号4 小时前
物联网时代2026年时序数据库选型指南
数据库·物联网·时序数据库·apache iotdb
+VX:Fegn08954 小时前
计算机毕业设计|基于springboot + vue动漫交流与推荐平台系统(源码+数据库+文档)
数据库·vue.js·spring boot·后端·课程设计
云姜.4 小时前
如何在idea上使用数据库
java·数据库·intellij-idea