合理的客户端设计能够充分发挥实例性能,并提升业务的稳定性与安全性。本文从避免 DB 重用、使用连接池、增加熔断功能、配置合理密码四个方面,介绍客户端程序的设计准则。
一、避免 DB 重用
核心要求: 避免多个应用共用同一个实例。
原因: 由于内存淘汰规则的存在,多个应用的 Key 会相互影响,导致缓存命中率下降;同时,若某个应用存在大量访问,也会影响其他应用的正常使用。
建议: 将不相干的业务进行拆分,公共数据通过服务化方式共享。
二、使用连接池
实例的访问时间包含网络连接时间、命令解析时间和命令执行时间。使用连接池可复用连接、节约网络连接时间,是高并发场景下的推荐做法。
架构建议
标准架构: 建议客户端采用连接池模式,以充分发挥多个代理节点的性能。客户端连接数过多时,可使用共享连接方式,减少性能下降。
集群架构: 建议启用
ClusterNodeAdaptive 参数(尤其在单分片连接数配置值与分片数较大时),实现适应性连接管理、动态调整连接数;同时建议启用共享连接模式,减少连接建立与断开的开销。连接池关键参数
以下三个关键参数建议配置为相同数值,以保持连接规模稳定,避免连接频繁创建与销毁:
参数 | 说明 |
连接池最大连接数 | 控制业务并发量。达到上限后不再创建新连接,避免占用过多系统资源。 |
连接池最大空闲连接数 | 允许保持的最大空闲连接数。超出部分将被关闭并移除,释放资源。 |
连接池最小空闲连接数 | 必须保持的最小空闲连接数。低于此值时会创建新连接,确保高负载下有足够可用连接。 |
各语言连接池注意事项(避免热连接)
为避免连接池总是复用同一条"最热连接"导致负载不均,各语言的建议如下:
语言 / 客户端 | 问题及建议 | 连接池代码示例 |
Golang go-redis | 建议连接用完后放入队尾,获取连接时从队头拿取,避免总是获取热连接。可通过 Lifo 参数控制(true 从队头拿,false 从队尾拿)。v8.11.5及之后版本已修复队列连接方式;当前主流的 v9.x 版本已默认采用更均衡的连接复用策略,推荐升级使用。 | |
Golang redigo | 官方连接池只支持从队头取、放连接,导致最热连接被持续使用,无法负载均衡。如需均衡,可修改源代码 pool.go,增加 pushBack 方法与 Lifo 成员变量。 | |
Java Jedis | 连接池默认采用 LIFO(后进先出),易导致连接使用不均衡。建议将连接池设置为 FIFO( setLifo(false),从队头拿、队尾放),确保连接建立顺序公平。 | |
Java Lettuce | 建议将连接池设置为 FIFO( poolConfig.setLifo(false)),并配合 keepalive、tcpUserTimeout 等参数提升连接健壮性,加快故障连接的探活与剔除。 | |
Java Redisson | 建议将连接池相关参数配置为合理值,并针对故障切换场景优化重连、超时与负载均衡参数,提升高可用架构下的连接健壮性。 |
说明:
三、增加熔断功能
适用场景: 高并发场景。
做法: 在客户端添加熔断逻辑(如 Netflix Hystrix 或同类熔断组件)。
作用: 熔断器实时检测集群节点状态,当某个节点出现异常时不再向其发送请求,从而避免单个节点故障导致整体系统雪崩。
四、配置合理密码
为数据库访问配置密码可保障数据安全性,复杂度要求如下:
字符个数为 [8, 30]。
至少包含小写字母、大写字母、数字和特殊字符(
()~!@#$%^&*-+=_|{}[]:;<>,.?/`)中的2种。不能以斜杠(/)开头。
产品支持 SSL 加密认证访问,建议在敏感数据场景下开启。