Redis 如何配置 TLS

TLS 是一种安全传输层协议,用于加密数据传输,最主要的作用是防止中间人攻击,保护客户端与 Redis 服务端之间的数据传输。

如何配置 TLS

修改 redis.conf 文件。

1. 启用 TLS 端口

port 0           # 禁用明文端口(可选)
tls-port 6380    # 启用 TLS 端口

或者同时开启明文和 TLS(不推荐用于生产环境,生产建议关闭明文端口):

port 6379
tls-port 6380

2. 配置 TLS 证书与密钥

tls-cert-file /etc/redis/redis.crt   # 服务器证书(PEM 格式)
tls-key-file /etc/redis/redis.key    # 私钥(PEM 格式),redis.key 权限 600,属主 redis 用户
tls-key-file-pass secret             # 私钥密码,用于解密私钥

证书需由可信 CA 签发,或者自建 CA 并让客户端信任该自建 CA。

3. 配置 DH 参数(增强前向保密)

tls-dh-params-file /etc/redis/redis.dh  # DH 参数文件,PEM 格式

可用 openssl 生成 DH 参数文件:

openssl dhparam -out /etc/redis/redis.dh 2048

4. 配置 TLS 客户端认证

tls-ca-cert-file /etc/redis/ca.crt  # CA 证书文件
tls-ca-cert-dir /etc/ssl/certs      # CA 证书目录

至少配置其中之一,用于验证客户端证书以及验证主从/集群节点证书。

5. 配置客户端证书认证(双向 TLS 控制)

tls-auth-client no       # 单向 TLS(仅服务器端认证,最常用)
tls-auth-client yes      # 双向 TLS(服务器端和客户端都认证,默认值)
tls-auth-client optional # 客户端可选提供证书

大多数场景推荐将 tls-auth-client 设置为 no,通过 ACL 用户对客户端进行密码认证。

6. 配置主从复制启用 TLS

tls-replication yes

默认情况下,主从复制不启用 TLS,需将其设为 yes 启用。主从双方都需要配置 TLS 证书和 tls-replication yes,从节点 replicaof 指向主节点的 TLS 端口。

7. 配置集群启用 TLS

tls-cluster yes

默认情况下 Redis 集群不启用 TLS,需将其设为 yes 启用。

8. 配置 TLS 协议与加密套件

tls-protocols "TLSv1.2 TLSv1.3"   # 配置 TLS 协议版本,默认为 TLSv1.2
tls-ciphers DEFAULT:!MEDIUM       # TLSv1.2 以下加密套件
tls-ciphersuites TLS_CHACHA20_POLY1305_SHA256  # TLSv1.3 加密套件
tls-prefer-server-ciphers yes     # 优先使用服务器的加密套件

9. 配置 TLS 会话缓存(性能优化)

tls-session-caching yes    # 默认开启缓存,no 关闭缓存
tls-session-cache-size 20480   # 默认缓存大小 20480,设置为 0 表示缓存无限制
tls-session-cache-timeout 300   # 超时 300 秒

配置示例

一、创建一个私有 CA

首先创建证书和密钥文件(自签名方式),用它来签发 Redis 服务器证书。

# 创建证书目录
mkdir certs

# 生成 CA 私钥
openssl genrsa -out ca.key 4096
# 生成 CA 证书
openssl req -new -x509 -days 3650 -key ca.key -out ca.crt -nodes -sha256 -subj "/C=CN/ST=Zhejiang/L=Hangzhou/O=MyOrg/CN=Redis CA"

生成的 ca.crt 是 CA 证书,包含 CA 的公钥、CA 的身份信息、CA 的数字签名(自签名)、有效期、序列号等,用来验证其他证书是否由该 CA 合法签发。其安全性依赖于 CA 的私钥,CA 的私钥必须严格保密。

查看证书内容:

openssl x509 -in ca.crt -text

(输出包含 Version、Serial Number、Issuer/Subject、Public-Key、X509v3 extensions(含 CA:TRUE)以及签名值等,此处省略冗长的十六进制转储。)

二、创建服务器证书签名请求(CSR)

CSR(Certificate Signing Request,证书签名请求)是向 CA 申请数字证书时提交的标准化请求文件,包含申请者的公钥和身份信息。其作用是:

  • 安全传递公钥:在不泄露私钥的情况下,将公钥提供给 CA
  • 身份声明:声明申请者的身份信息
  • 签名准备:为 CA 提供待签名的数据
# 创建服务器私钥
openssl genrsa -out redis.key 2048
chmod 600 redis.key

# 生成服务器证书签名请求
openssl req -new -key redis.key -out redis.csr -subj "/C=CN/ST=Zhejiang/L=Hangzhou/O=MyOrg/CN=redis.example.com"

可以查看 CSR 内容:

openssl req -in redis.csr -text

(输出包含 Subject、Subject Public Key Info(2048-bit RSA 公钥)以及签名值,此处省略冗长的十六进制转储。)

支持 IP 和多域名(使用 SAN):创建 redis.ext 文件:

cat > redis.ext <<EOF
authorityKeyIdentifier=keyid,issuer
basicConstraints=CA:FALSE
keyUsage = digitalSignature, nonRepudiation, keyEncipherment, dataEncipherment
subjectAltName = @alt_names

[alt_names]
DNS.1 = redis.example.com
DNS.2 = localhost
IP.1 = 127.0.0.1
IP.2 = 192.168.232.128   # ← 替换为你的实际 IP
EOF

SAN(Subject Alternative Name,主题备用名称)是 X.509 证书的一个扩展字段,用于指定一个证书可以保护哪些域名、IP 地址或其他标识。 CN(Common Name,通用名称)是 X.509 证书中 Subject 字段的一个属性,用于标识证书持有者的身份。

三、CA 签发证书

CA 根据 CSR 请求,用 CA 的私钥和 CA 证书签发 Redis 服务器证书,实质是 CA 用私钥对服务器证书进行签名。客户端使用 CA 的公钥(来自 ca.crt)验证该签名是否合法。

openssl x509 -req -in redis.csr \
  -CA ca.crt -CAkey ca.key -CAcreateserial \
  -out redis.crt \
  -days 365 -sha256 \
  -extfile redis.ext
# Certificate request self-signature ok
# subject=C = CN, ST = Zhejiang, L = Hangzhou, O = MyOrg, CN = redis.example.co

ca.srl 是证书序列号文件,由 openssl 在签署证书时生成和维护,用于确保每个颁发的证书都有唯一且递增的序列号。首次签署证书时通过 -CAcreateserial 生成序列号文件 ca.srl,后续使用时会自动读取和更新。

# 后续签署证书时,会自动使用并更新 ca.srl
openssl x509 -req -in client.csr \
  -CA ca.crt -CAkey ca.key \
  -CAserial ca.srl \
  -out client.crt -days 365

四、生成 DH 参数,增强前向保密

DH 参数用于支持 DHE(Ephemeral Diffie-Hellman)或 ECDHE(Elliptic Curve DHE)密钥交换,从而实现前向保密(Forward Secrecy)。

openssl dhparam -out redis.dh 2048
chmod 600 redis.dh

签发证书后,配置 redis.conf 中 TLS/SSL 部分参数(证书存放位置根据实际路径调整):

port 0
tls-port 6380
# 服务器证书和私钥
tls-cert-file /etc/redis/certs/redis.crt
tls-key-file /etc/redis/certs/redis.key

# CA 证书(用于验证客户端)
tls-ca-cert-file /etc/redis/certs/ca.crt

# DH 参数
tls-dh-params-file /etc/redis/certs/redis.dh

# 客户端证书认证:设为 no 表示仅服务端认证,单向 TLS
tls-auth-client no

# 启用主从复制 TLS,主节点为 no,从节点为 yes
tls-replication no

# 仅允许安全协议
tls-protocols "TLSv1.2 TLSv1.3"

# 加密套件(禁用弱算法)
tls-ciphers DEFAULT:!MEDIUM
tls-ciphersuites TLS_CHACHA20_POLY1305_SHA256

# 优先使用服务器选择的加密套件
tls-prefer-server-ciphers yes

从节点需要配置 replicaof,注意端口为主节点的 TLS 端口:

replicaof 127.0.0.1 6380

客户端连接时需要提供 CA 证书(由 CA 提供,或自建 CA 时由服务提供方安全分发给应用)。客户端用 ca.crt 验证服务端证书是否合法。向客户端分发 CA 证书必须保证安全分发。

./bin/redis-cli --tls --cacert certs/ca.crt -p 6380
127.0.0.1:6380> ping
PONG
127.0.0.1:6380> keys *
(empty array)
127.0.0.1:6380> set k1 v1
OK

注意事项

如果启用 TLS,编译 Redis 时需要加上 make BUILD_TLS=yes

参考文档:Redis TLS 支持

主从复制

Redis 主服务器以相同的方式处理连接客户端和从节点,因此上述 tls-porttls-auth-client 指令也适用于主从连接。在从节点服务器端,需要指定 tls-replication yes 以对与主服务器的传出连接使用 TLS。

集群

使用 Redis 集群时,请使用 tls-cluster yes 以对集群总线和跨节点连接启用 TLS。

哨兵

哨兵从通用 Redis 配置继承其网络配置,因此上述所有内容也适用于哨兵。在连接到主服务器时,哨兵将使用 tls-replication 指令来确定是否需要 TLS 连接。同一个 tls-replication 指令还将决定 Sentinel 的端口(接受来自其他 Sentinel 的连接)是否支持 TLS——当且仅当启用了 tls-replication 时,Sentinel 才会使用 tls-port 进行配置。

最佳实践

  1. 为 Redis CA 单独创建 ca.srl 文件
  2. 定期备份序列号文件
  3. 监控序列号使用情况
  4. 使用脚本自动化证书签发
  5. 确保序列号长度足够支持预期证书数量

示例目录结构:

/etc/redis/tls/
├── ca/
   ├── redis-ca.crt
   ├── redis-ca.key
   └── redis-ca.srl    # 序列号文件
├── server/
   ├── redis-server.crt
   └── redis-server.key
└── client/
    ├── redis-client.crt
    └── redis-client.key

补充知识点

CA(Certificate Authority):根证书颁发机构,用于创建其他证书的签名。

信任原理分析:首先,根信任是信任 CA 的私钥,由 CA 的私钥生成 CA 证书;然后,客户端信任的是 CA 证书,用 CA 证书验证服务端的证书。服务端向 CA 提交证书请求,CA 用私钥对服务器证书(服务器公钥)进行签名,表示这个服务端是经过认证的合法服务端。非法的服务端没有 CA 的签名,即使伪造服务器端证书,由于 CA 的私钥是保密的,伪造的证书也无法通过客户端 CA 证书(CA 的公钥)的验证。这样就保证了客户端能够确认对方是合法的服务端。