← 中文资源

简体中文版本

Go Redis Universal 客户端配置

用 go-redis 的 Universal 客户端统一三种拓扑:连接池与超时纪律完整声明,管道批量执行命令,单配置可平滑升级集群。

阅读英文原文

示例说明

开发单机、上线哨兵或集群是常见的演进路径,UniversalClient 的价值是配置结构不变——Addrs 给单节点或集群节点,加 MasterName 与 Sentinels 即切换哨兵模式。超时三件套(拨号、读、写)与池参数是线上纪律:过长的超时让慢查询拖垮调用方,过小的池在高并发下排队等待。

技术要点

  • 一份配置覆盖三种部署拓扑
  • 池大小与保活连接数显式声明
  • Pipeline 批量往返摊薄延迟

代码解读

newRedisClient 构造 UniversalOptions:两秒拨号、八百毫秒读写、二十连接配五个保活,重试两次且退避封顶。main 用 Pipeline 把 SET 与 TTL 两条命令打包一次往返——两条独立往返的网络延迟合并为一。Exec 返回后从各命令对象取结果。

使用建议

读写超时要大于最慢合法命令耗时。池大小按 Redis 服务端的连接预算分配。生产环境开启只读副本读写分离要评估一致性。

代码示例

package main

import (
	"context"
	"fmt"
	"time"

	"github.com/redis/go-redis/v9"
)

func newRedisClient() redis.UniversalClient {
	opts := &redis.UniversalOptions{
		Addrs:        []string{"127.0.0.1:6379"},
		DialTimeout:  2 * time.Second,
		ReadTimeout:  800 * time.Millisecond,
		WriteTimeout: 800 * time.Millisecond,

		PoolSize:        20,
		MinIdleConns:    5,
		PoolTimeout:     2 * time.Second,
		MaxIdleConns:    10,
		ConnMaxIdleTime: 5 * time.Minute,

		// 同一份配置可透明升级为哨兵或集群:
		// MasterName: "mymaster",
		// Sentinels:  []*redis.SentinelAddr{{...}},
		// 或 Addrs 直接给多个集群节点

		MaxRetries:      2,
		MinRetryBackoff: 50 * time.Millisecond,
		MaxRetryBackoff: 500 * time.Millisecond,
	}

	return redis.NewUniversalClient(opts)
}

func main() {
	client := newRedisClient()

	ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second)
	defer cancel()

	pipe := client.Pipeline()
	setCmd := pipe.Set(ctx, "session:42", "active", 30*time.Minute)
	ttlCmd := pipe.TTL(ctx, "session:42")
	_, err := pipe.Exec(ctx)
	if err != nil {
		fmt.Println("pipeline failed:", err)
		return
	}
	fmt.Println("set ok:", setCmd.Val(), "ttl:", ttlCmd.Val())

	defer client.Close()
}