背景
由于一个历史项目第一次接入redis,故在添加redis的相关配置的时候就直接从其他项目中把redis的配置copy过来了,然后在测试环境和预生产环境测试都没有什么问题,最后发布到生产环境之后过了一段时间线上的redis连接池直接爆了,连接数一直激增。
前提条件:
- 该项目测试环境和预生产环境实例节点数为个位数
- 生产环境实例节点数>200,
- 从其他项目copy过来的redis配置如下:
spring:
redis:
database: 0
host: ******
port: 6379
password: ****
timeout: 3600
jedis:
pool:
max-active: 100
min-idle: 200
max-idle: 800
max-wait: 10000
-
后面通过一番调查发现问题出现在这个redis的配置上面,由于是直接copy的配置并没有修改jedis连接池的相关配置,min-idle为200,max-idle为800,就会导致项目启动后spring-boot就会预加载一部分的redis连接(min-idle)到连接池中,项目启动的时候就会有200个节点*min-idle(200)=40000个redis连接,然后导致redis连接池中的连接数激增,最后将redis的连接池撑爆了,最后将对应的redis连接池的参数按照实际节点和使用业务场景进行更改后然后重启服务后一切就恢复正常了。
-
至于为什么在测试环境和预生产环境没有出现问题,是因为这两个环境的实例节点数少,不会对连接池造成太大的影响。
-
最后将对应的redis配置修改为如下配置:
spring:
redis:
database: 0
host: ******
port: 6379
password: ****
timeout: 3600
jedis:
pool:
# 最大的连接存活数
max-active: 10
# 最小空闲连接数(至少需要保持的空闲连接数) 预加载数量
min-idle: 1
# 最大空闲连接数(最大保留的空闲连接数)
max-idle: 10
# 最大等待时间
max-wait: 10000
总结
redis的配置不能胡乱进行配置,否则会出大乱子,要根据实际的实例节点数,和当前业务的实际需要情况进行对应的配置。
写在最后,为什么我们的这个服务的节点会有>200个,由于我们的业务比较复杂,需要有很多个实例节点来保证这一块服务的处理速度,还有最初的架构设计导致每台机器上实例必须要有2个节点,所以节点数的过多导致redis连接池中的预加载的连接数过多