我有一个使用 Spring Boot 和 Spring Data JPA 的 Rest API 项目,该项目托管在 tomcat 服务器中。该应用程序工作正常,但它慢慢地创建了太多不活动的 Oracle 数据库会话,并且永远不会清除。
Db.properties
# Oracle DB properties
spring.datasource.url=jdbc:oracle:thin:@***
spring.datasource.hikari.username=***
spring.datasource.hikari.schema=***
spring.datasource.hikari.password=***
spring.datasource.hikari.auto-commit=true
spring.datasource.hikari.connection-timeout=30000
spring.datasource.hikari.idle-timeout=30000
spring.datasource.hikari.maximum-pool-size=48
spring.datasource.hikari.max-lifetime=1800000
spring.datasource.hikari.leak-detection-threshold=3000000
spring.datasource.hikari.pool-name=UserDbPool
spring.datasource.hikari.driver-class-name=oracle.jdbc.OracleDriver
spring.datasource.isolation-level=TRANSACTION_READ_COMMITTED
spring.datasource.min-idle-connections=8
spring.datasource.driver.type=thin
UserController.java
@PostMapping("/process")
public PostResponse processUser(@RequestBody PostRequest inputPayLoad) {
return service.processUser(inputPayLoad);
}
UserService.java
public PostResponse processUser(PostRequest request) {
PostResponse response = new PostResponse();
String composedKey = request.getUserCode + "|" + request.getUserLastName;
User user = utils.findUser(utils.fetchUsersMap(), composedKey);
response.setUser(user);
}
Utils.java
public Map<String, User> fetchUsersMap() {
Map<String, User> usersMap = new HashMap<>();
Iterable<User> userList = userRepo.findAll();
for (User user : userList) {
usersMap.put(user.getUserCode + "|" + user.getUserLastName, user);
}
return usersMap;
}
public User findUser(Map<String, User> usersMap, String key) {
return usersMap.get(key);
}
以下是我在
catalina.out
中看到的唯一警告,完全没有错误:
4342 [01 Feb 2024 09:48:13.521] WARN *** [main] com.zaxxer.hikari.HikariConfig - UserRestApi - leakDetectionThreshold is less than 2000ms or more than maxLifetime, disabling it.
4343 [01 Feb 2024 09:48:13.522] WARN *** [main] com.zaxxer.hikari.HikariConfig - UserRestApi - idleTimeout has been set but has no effect because the pool is operating as a fixed size pool.
8816 [01 Feb 2024 09:48:17.995] WARN *** [main] org.springframework.boot.autoconfigure.orm.jpa.JpaBaseConfiguration$JpaWebConfiguration - spring.jpa.open-in-view is enabled by default. Therefore, database queries may be performed during view rendering. Explicitly configure spring.jpa.open-in-view to disable this warning
我是否遗漏了一些导致空闲数据库连接无法清除的东西?
问题似乎出在 utils.fetchUsersMap() 包含在 utils.findUser() 方法参数中。
每次调用该方法时,都会对用户表进行全面扫描。
我想这必然会给DB带来负载,DB连接也会被长期占用。
此外,将用户对象直接插入到地图中似乎也有问题。