外观
Redis Docker/K8s 部署指南
Docker 部署 Redis
使用 Docker 部署 Redis 是一种轻量级、快速的部署方式,适合开发环境和小规模生产环境。以下是几种常见的 Docker 部署方案。
单实例部署
单实例部署是最简单的 Redis 部署方式,适合开发测试或对高可用性要求不高的场景。
基本部署 这是 Redis 单实例的最基础部署方式,使用默认配置启动 Redis 服务。
bash# 拉取 Redis 镜像(使用轻量级的 Alpine 版本) docker pull redis:7.2-alpine # 启动 Redis 容器,映射主机 6379 端口到容器 6379 端口 docker run -d \ --name redis \ -p 6379:6379 \ redis:7.2-alpine带密码的部署 为了提高安全性,建议为 Redis 设置密码。使用
--requirepass参数可以在启动时设置密码。bashdocker run -d \ --name redis \ -p 6379:6379 \ redis:7.2-alpine \ redis-server --requirepass "your_strong_password"使用自定义配置文件 对于需要复杂配置的生产环境,建议使用自定义配置文件。这种方式可以更灵活地调整 Redis 的各项参数。
bash# 创建配置文件目录 mkdir -p /data/redis/config # 创建 redis.conf 文件,配置绑定地址、端口、密码和持久化等参数 cat > /data/redis/config/redis.conf << EOF bind 0.0.0.0 # 允许所有IP访问 port 6379 # 监听端口 requirepass your_strong_password # 设置访问密码 appendonly yes # 开启 AOF 持久化 dir /data # 数据存储目录 EOF # 启动容器,挂载配置文件和数据目录 docker run -d \ --name redis \ -p 6379:6379 \ -v /data/redis/config/redis.conf:/etc/redis/redis.conf \ -v /data/redis/data:/data \ redis:7.2-alpine \ redis-server /etc/redis/redis.conf
主从复制部署
主从复制是 Redis 实现高可用性的基础,通过将主节点的数据复制到从节点,可以实现读写分离,提高系统的吞吐量和可用性。
创建主节点 首先创建主节点,主节点负责处理写请求,并将数据同步到从节点。
bashdocker run -d \ --name redis-master \ -p 6379:6379 \ -v /data/redis/master/data:/data \ redis:7.2-alpine \ redis-server --requirepass "master_password" --masterauth "master_password"创建从节点 然后创建从节点,从节点通过
--replicaof参数指定主节点的 IP 和端口,实现数据同步。bash# 获取主节点的 IP 地址 MASTER_IP=$(docker inspect -f '{{range.NetworkSettings.Networks}}{{.IPAddress}}{{end}}' redis-master) # 启动从节点,指定主节点地址和端口 docker run -d \ --name redis-slave \ -p 6380:6379 \ -v /data/redis/slave/data:/data \ redis:7.2-alpine \ redis-server --requirepass "master_password" --masterauth "master_password" --replicaof $MASTER_IP 6379验证主从关系 使用
info replication命令可以查看 Redis 的主从复制状态,验证主从关系是否正常建立。bash# 连接主节点,查看复制状态 docker exec -it redis-master redis-cli -a "master_password" info replication # 连接从节点,查看复制状态 docker exec -it redis-slave redis-cli -a "master_password" info replication
持久化配置
Redis 持久化是指将内存中的数据保存到磁盘,以防止数据丢失。Redis 支持两种持久化方式:RDB(快照)和 AOF(追加文件),以及混合持久化方式。
RDB 持久化 RDB 持久化是将 Redis 在某个时间点的数据生成快照并保存到磁盘。适合用于备份和灾难恢复。
bashdocker run -d \ --name redis \ -p 6379:6379 \ -v /data/redis/data:/data \ redis:7.2-alpine \ redis-server --save 900 1 --save 300 10 --save 60 10000--save 900 1:900秒内至少有1个键被修改,生成快照--save 300 10:300秒内至少有10个键被修改,生成快照--save 60 10000:60秒内至少有10000个键被修改,生成快照
AOF 持久化 AOF 持久化是将 Redis 执行的每个写命令追加到文件末尾。适合用于需要更高数据安全性的场景。
bashdocker run -d \ --name redis \ -p 6379:6379 \ -v /data/redis/data:/data \ redis:7.2-alpine \ redis-server --appendonly yes --appendfsync everysec--appendonly yes:开启 AOF 持久化--appendfsync everysec:每秒将缓冲区内容写入磁盘
混合持久化 混合持久化结合了 RDB 和 AOF 的优点,AOF 文件的前半部分是 RDB 格式的快照,后半部分是 AOF 格式的命令。
bashdocker run -d \ --name redis \ -p 6379:6379 \ -v /data/redis/data:/data \ redis:7.2-alpine \ redis-server --appendonly yes --appendfsync everysec --aof-use-rdb-preamble yes--aof-use-rdb-preamble yes:开启混合持久化
Docker Compose 部署
Docker Compose 是一个用于定义和运行多容器 Docker 应用程序的工具。使用 Docker Compose 可以更方便地管理 Redis 及其相关服务。
单实例部署 使用 Docker Compose 部署单实例 Redis,便于管理配置和数据卷。
yamlversion: '3' # 使用 Compose 文件格式版本 3 services: redis: # 服务名称 image: redis:7.2-alpine # 使用的 Redis 镜像 container_name: redis # 容器名称 ports: - "6379:6379" # 端口映射,主机端口:容器端口 volumes: - ./data:/data # 数据卷,主机目录:容器目录 - ./redis.conf:/etc/redis/redis.conf # 配置文件映射 command: redis-server /etc/redis/redis.conf # 启动命令 restart: always # 总是重启策略 environment: - TZ=Asia/Shanghai # 设置时区主从复制部署 使用 Docker Compose 可以快速部署 Redis 主从复制架构,简化了多节点的管理。
yamlversion: '3' services: redis-master: # 主节点服务 image: redis:7.2-alpine container_name: redis-master ports: - "6379:6379" volumes: - ./master/data:/data # 主节点数据目录 command: redis-server --requirepass "master_password" --masterauth "master_password" restart: always environment: - TZ=Asia/Shanghai redis-slave1: # 第一个从节点 image: redis:7.2-alpine container_name: redis-slave1 ports: - "6380:6379" volumes: - ./slave1/data:/data # 从节点1数据目录 command: redis-server --requirepass "master_password" --masterauth "master_password" --replicaof redis-master 6379 restart: always depends_on: - redis-master # 依赖主节点,主节点启动后再启动从节点 environment: - TZ=Asia/Shanghai redis-slave2: # 第二个从节点 image: redis:7.2-alpine container_name: redis-slave2 ports: - "6381:6379" volumes: - ./slave2/data:/data # 从节点2数据目录 command: redis-server --requirepass "master_password" --masterauth "master_password" --replicaof redis-master 6379 restart: always depends_on: - redis-master # 依赖主节点 environment: - TZ=Asia/Shanghai
Kubernetes 部署 Redis
Kubernetes 是一个容器编排平台,适合部署大规模、高可用性的 Redis 集群。以下是几种常见的 Kubernetes 部署方案。
单实例部署(Deployment)
单实例部署适合开发测试环境或对高可用性要求不高的场景。使用 Deployment 可以方便地管理 Redis 实例的生命周期。
创建 ConfigMap ConfigMap 用于存储 Redis 的配置信息,便于集中管理和更新配置。
yamlapiVersion: v1 # API 版本 kind: ConfigMap # 资源类型 metadata: name: redis-config # ConfigMap 名称 namespace: default # 命名空间 data: redis.conf: | # 配置文件内容 bind 0.0.0.0 # 允许所有 IP 访问 port 6379 # 监听端口 requirepass your_strong_password # 设置访问密码 appendonly yes # 开启 AOF 持久化 appendfsync everysec # 每秒将缓冲区内容写入磁盘 dir /data # 数据存储目录创建 Deployment Deployment 用于管理 Pod 的创建、更新和删除,确保指定数量的副本运行。
yamlapiVersion: apps/v1 # API 版本 kind: Deployment # 资源类型 metadata: name: redis # Deployment 名称 namespace: default # 命名空间 spec: replicas: 1 # 副本数量 selector: matchLabels: # 标签选择器,用于匹配 Pod app: redis template: metadata: labels: app: redis # Pod 标签 spec: containers: - name: redis # 容器名称 image: redis:7.2-alpine # 容器镜像 ports: - containerPort: 6379 # 容器内端口 volumeMounts: # 卷挂载 - name: redis-config # 引用卷名称 mountPath: /etc/redis/redis.conf # 挂载路径 subPath: redis.conf # 子路径,用于指定挂载 ConfigMap 中的特定文件 - name: redis-data # 引用数据卷 mountPath: /data # 数据挂载路径 args: # 容器启动参数 - redis-server - /etc/redis/redis.conf resources: # 资源限制 requests: # 请求资源 memory: "256Mi" cpu: "100m" limits: # 限制资源 memory: "512Mi" cpu: "500m" livenessProbe: # 存活探针,用于检测容器是否存活 exec: # 执行命令进行检测 command: - redis-cli - -a - your_strong_password - ping initialDelaySeconds: 30 # 启动后 30 秒开始检测 periodSeconds: 10 # 每 10 秒检测一次 readinessProbe: # 就绪探针,用于检测容器是否就绪 exec: command: - redis-cli - -a - your_strong_password - ping initialDelaySeconds: 5 # 启动后 5 秒开始检测 periodSeconds: 10 # 每 10 秒检测一次 volumes: # 卷定义 - name: redis-config # 卷名称 configMap: # 使用 ConfigMap 作为卷源 name: redis-config # 引用上面创建的 ConfigMap - name: redis-data # 数据卷名称 emptyDir: {} # 使用临时目录作为数据卷,适合开发测试环境创建 Service Service 用于暴露 Redis 服务,使集群内或外部的客户端可以访问 Redis。
yamlapiVersion: v1 # API 版本 kind: Service # 资源类型 metadata: name: redis # Service 名称 namespace: default # 命名空间 spec: selector: # 标签选择器,用于匹配 Pod app: redis ports: - port: 6379 # Service 端口 targetPort: 6379 # 目标 Pod 端口 nodePort: 30379 # NodePort 类型,暴露到节点的端口 type: NodePort # Service 类型,NodePort 表示暴露到节点端口
主从复制部署
主从复制是Redis实现高可用性的基础,通过将主节点的数据复制到从节点,可以实现读写分离,提高系统的吞吐量和可用性。在Kubernetes中,可以使用Deployment和StatefulSet来部署主从复制架构。
创建主节点 ConfigMap 首先创建主节点的配置文件,包括绑定地址、端口、密码和持久化等配置:
yamlapiVersion: v1 # API 版本 kind: ConfigMap # 资源类型 metadata: name: redis-master-config # ConfigMap 名称 namespace: default # 命名空间 data: redis.conf: | # 配置文件内容 bind 0.0.0.0 # 允许所有 IP 访问 port 6379 # 监听端口 requirepass your_strong_password # 设置访问密码 masterauth your_strong_password # 主从复制认证密码 appendonly yes # 开启 AOF 持久化 appendfsync everysec # 每秒将缓冲区内容写入磁盘 dir /data # 数据存储目录创建从节点 ConfigMap 然后创建从节点的配置文件,从节点的配置与主节点基本相同,但会通过命令行参数指定主节点地址:
yamlapiVersion: v1 # API 版本 kind: ConfigMap # 资源类型 metadata: name: redis-slave-config # ConfigMap 名称 namespace: default # 命名空间 data: redis.conf: | # 配置文件内容 bind 0.0.0.0 # 允许所有 IP 访问 port 6379 # 监听端口 requirepass your_strong_password # 设置访问密码 masterauth your_strong_password # 主从复制认证密码 appendonly yes # 开启 AOF 持久化 appendfsync everysec # 每秒将缓冲区内容写入磁盘 dir /data # 数据存储目录创建主节点 Deployment 使用Deployment部署主节点,确保主节点稳定运行:
yamlapiVersion: apps/v1 # API 版本 kind: Deployment # 资源类型 metadata: name: redis-master # Deployment 名称 namespace: default # 命名空间 spec: replicas: 1 # 主节点只需要1个副本 selector: matchLabels: # 标签选择器,用于匹配 Pod app: redis-master template: metadata: labels: app: redis-master # Pod 标签 spec: containers: - name: redis # 容器名称 image: redis:7.2-alpine # 容器镜像 ports: - containerPort: 6379 # 容器内端口 volumeMounts: # 卷挂载 - name: redis-master-config # 引用主节点配置 mountPath: /etc/redis/redis.conf # 挂载路径 subPath: redis.conf # 子路径 - name: redis-master-data # 引用主节点数据卷 mountPath: /data # 数据挂载路径 args: # 启动参数 - redis-server - /etc/redis/redis.conf resources: # 资源限制 requests: # 请求资源 memory: "256Mi" cpu: "100m" limits: # 限制资源 memory: "512Mi" cpu: "500m" volumes: # 卷定义 - name: redis-master-config # 配置卷 configMap: name: redis-master-config # 引用上面创建的主节点 ConfigMap - name: redis-master-data # 数据卷 persistentVolumeClaim: # 使用持久卷声明 claimName: redis-master-pvc # 持久卷声明名称创建从节点 StatefulSet 使用StatefulSet部署从节点,StatefulSet适合需要稳定网络标识和持久存储的应用:
yamlapiVersion: apps/v1 # API 版本 kind: StatefulSet # 资源类型 metadata: name: redis-slave # StatefulSet 名称 namespace: default # 命名空间 spec: serviceName: redis-slave # 关联的 Headless Service 名称 replicas: 2 # 从节点数量 selector: matchLabels: # 标签选择器 app: redis-slave template: metadata: labels: app: redis-slave # Pod 标签 spec: containers: - name: redis # 容器名称 image: redis:7.2-alpine # 容器镜像 ports: - containerPort: 6379 # 容器内端口 volumeMounts: # 卷挂载 - name: redis-slave-config # 引用从节点配置 mountPath: /etc/redis/redis.conf # 挂载路径 subPath: redis.conf # 子路径 - name: redis-slave-data # 引用从节点数据卷 mountPath: /data # 数据挂载路径 args: # 启动参数,指定主节点地址 - redis-server - /etc/redis/redis.conf - --replicaof # 指定为从节点 - redis-master.default.svc.cluster.local # 主节点的 DNS 名称 - "6379" # 主节点端口 resources: # 资源限制 requests: # 请求资源 memory: "256Mi" cpu: "100m" limits: # 限制资源 memory: "512Mi" cpu: "500m" volumes: # 卷定义 - name: redis-slave-config # 配置卷 configMap: name: redis-slave-config # 引用上面创建的从节点 ConfigMap - name: redis-slave-data # 数据卷 persistentVolumeClaim: # 使用持久卷声明 claimName: redis-slave-pvc # 持久卷声明名称创建 Services 为了让主从节点之间能够通信,需要创建对应的Service:
yaml# 主节点 Service,用于主从节点之间的通信 apiVersion: v1 # API 版本 kind: Service # 资源类型 metadata: name: redis-master # Service 名称 namespace: default # 命名空间 spec: selector: # 标签选择器,匹配主节点 Pod app: redis-master ports: - port: 6379 # Service 端口 targetPort: 6379 # 目标 Pod 端口 # 从节点 Service,用于客户端访问从节点 apiVersion: v1 # API 版本 kind: Service # 资源类型 metadata: name: redis-slave # Service 名称 namespace: default # 命名空间 spec: selector: # 标签选择器,匹配从节点 Pod app: redis-slave ports: - port: 6379 # Service 端口 targetPort: 6379 # 目标 Pod 端口
Redis Sentinel 部署
Redis Sentinel 是 Redis 的高可用性解决方案,用于监控 Redis 主从集群,并在主节点故障时自动进行故障转移。在 Kubernetes 中部署 Sentinel 可以确保 Redis 集群的高可用性。
创建 Sentinel ConfigMap 首先创建 Sentinel 的配置文件,包括监控的主节点信息、认证密码、故障转移参数等:
yamlapiVersion: v1 # API 版本 kind: ConfigMap # 资源类型 metadata: name: redis-sentinel-config # ConfigMap 名称 namespace: default # 命名空间 data: sentinel.conf: | # Sentinel 配置文件内容 port 26379 # Sentinel 监听端口 dir /tmp # 工作目录 # 监控名为 mymaster 的主节点,指定主节点的 DNS 名称、端口和法定人数(需要2个Sentinel同意才能进行故障转移) sentinel monitor mymaster redis-master.default.svc.cluster.local 6379 2 sentinel auth-pass mymaster your_strong_password # 主节点的认证密码 sentinel down-after-milliseconds mymaster 5000 # 认为主节点宕机的超时时间(毫秒) sentinel failover-timeout mymaster 10000 # 故障转移超时时间(毫秒) sentinel parallel-syncs mymaster 1 # 故障转移时,同时同步数据的从节点数量创建 Sentinel Deployment 使用 Deployment 部署 Sentinel 集群,通常需要至少3个 Sentinel 实例来确保高可用性:
yamlapiVersion: apps/v1 # API 版本 kind: Deployment # 资源类型 metadata: name: redis-sentinel # Deployment 名称 namespace: default # 命名空间 spec: replicas: 3 # Sentinel 实例数量,建议至少3个 selector: matchLabels: # 标签选择器,用于匹配 Pod app: redis-sentinel template: metadata: labels: app: redis-sentinel # Pod 标签 spec: containers: - name: redis-sentinel # 容器名称 image: redis:7.2-alpine # 容器镜像,使用与 Redis 相同版本的 Sentinel ports: - containerPort: 26379 # Sentinel 监听端口 volumeMounts: # 卷挂载 - name: redis-sentinel-config # 引用 Sentinel 配置 mountPath: /etc/redis/sentinel.conf # 挂载路径 subPath: sentinel.conf # 子路径 args: # 启动参数,指定运行 Sentinel 并使用配置文件 - redis-sentinel - /etc/redis/sentinel.conf resources: # 资源限制 requests: # 请求资源 memory: "128Mi" cpu: "50m" limits: # 限制资源 memory: "256Mi" cpu: "200m" volumes: # 卷定义 - name: redis-sentinel-config # 配置卷 configMap: name: redis-sentinel-config # 引用上面创建的 Sentinel ConfigMap创建 Sentinel Service 为了让应用能够访问 Sentinel 集群,需要创建对应的 Service:
yamlapiVersion: v1 # API 版本 kind: Service # 资源类型 metadata: name: redis-sentinel # Service 名称 namespace: default # 命名空间 spec: selector: # 标签选择器,匹配 Sentinel Pod app: redis-sentinel ports: - port: 26379 # Service 端口 targetPort: 26379 # 目标 Pod 端口验证 Sentinel 状态 部署完成后,需要验证 Sentinel 集群是否正常工作,包括监控主节点和从节点的状态:
bash# 连接到一个 Sentinel Pod,查看监控的主节点信息 kubectl exec -it redis-sentinel-<pod-name> -- redis-cli -p 26379 sentinel masters # 查看 Sentinel 监控的从节点信息 kubectl exec -it redis-sentinel-<pod-name> -- redis-cli -p 26379 sentinel slaves mymaster
通过以上步骤,我们在 Kubernetes 中部署了一个完整的 Redis Sentinel 集群,它可以监控 Redis 主从集群,并在主节点故障时自动进行故障转移,确保 Redis 服务的高可用性。
Redis Cluster 部署
Redis Cluster 是 Redis 官方提供的分布式解决方案,可以自动分片、故障转移和水平扩展。在 Kubernetes 中部署 Redis Cluster 可以获得高可用性和可扩展性,适合大规模应用场景。
创建 ConfigMap 首先创建 Redis Cluster 的配置文件,启用集群模式并配置相关参数:
yamlapiVersion: v1 kind: ConfigMap metadata: name: redis-cluster-config namespace: default data: redis.conf: | bind 0.0.0.0 port 6379 cluster-enabled yes cluster-config-file nodes.conf cluster-node-timeout 5000 cluster-require-full-coverage no appendonly yes appendfsync everysec requirepass your_strong_password masterauth your_strong_password dir /data创建 StatefulSet 使用 StatefulSet 部署 Redis Cluster 节点,StatefulSet 提供稳定的网络标识和持久存储,非常适合 Redis Cluster:
yamlapiVersion: apps/v1 kind: StatefulSet metadata: name: redis-cluster namespace: default spec: serviceName: redis-cluster replicas: 6 selector: matchLabels: app: redis-cluster template: metadata: labels: app: redis-cluster spec: containers: - name: redis image: redis:7.2-alpine ports: - containerPort: 6379 name: client - containerPort: 16379 name: gossip command: - redis-server - /etc/redis/redis.conf volumeMounts: - name: redis-cluster-config mountPath: /etc/redis/redis.conf subPath: redis.conf - name: redis-cluster-data mountPath: /data resources: requests: memory: "256Mi" cpu: "100m" limits: memory: "512Mi" cpu: "500m" volumes: - name: redis-cluster-config configMap: name: redis-cluster-config - name: redis-cluster-data persistentVolumeClaim: claimName: redis-cluster-pvc创建 Headless Service 创建 Headless Service 用于 Redis Cluster 节点之间的通信,Headless Service 提供稳定的 DNS 解析:
yamlapiVersion: v1 kind: Service metadata: name: redis-cluster namespace: default spec: clusterIP: None selector: app: redis-cluster ports: - name: client port: 6379 - name: gossip port: 16379初始化集群 部署完成后,需要初始化 Redis Cluster,分配槽位并建立主从关系:
bash# 获取所有 Redis 节点的 IP kubectl get pods -l app=redis-cluster -o jsonpath='{range.items[*]}{.status.podIP}:6379 '{\n}'' > redis-nodes.txt # 连接到一个 Redis 节点 kubectl exec -it redis-cluster-0 -- redis-cli -a your_strong_password --cluster create --cluster-replicas 1 $(cat redis-nodes.txt) # 验证集群状态 kubectl exec -it redis-cluster-0 -- redis-cli -a your_strong_password cluster info kubectl exec -it redis-cluster-0 -- redis-cli -a your_strong_password cluster nodes
通过以上步骤,我们在 Kubernetes 中部署了一个完整的 Redis Cluster 集群,包含3个主节点和3个从节点,实现了数据的自动分片和高可用性。Redis Cluster 可以根据业务需求水平扩展,提高系统的吞吐量和容量,适合处理大规模数据和高并发请求。
持久化配置
持久化配置是确保Redis数据在容器重启或故障时不丢失的重要保障。在Kubernetes中,可以使用Persistent Volume (PV)和Persistent Volume Claim (PVC)来实现持久化存储。
Persistent Volume (PV) 和 Persistent Volume Claim (PVC)
PV是集群级别的存储资源,由管理员配置或动态创建;PVC是Pod级别的存储请求,由用户创建,用于申请PV资源。以下是在Kubernetes中配置Redis持久化存储的方法:
创建 PV Persistent Volume (PV) 是集群中的存储资源,以下示例创建一个基于hostPath的PV,适用于开发和测试环境:
yamlapiVersion: v1 kind: PersistentVolume metadata: name: redis-pv namespace: default spec: capacity: storage: 1Gi accessModes: - ReadWriteOnce persistentVolumeReclaimPolicy: Retain hostPath: path: /data/redis type: DirectoryOrCreate创建 PVC Persistent Volume Claim (PVC) 是对PV资源的请求,以下示例创建两个PVC,分别用于Redis主节点和从节点:
yamlapiVersion: v1 kind: PersistentVolumeClaim metadata: name: redis-master-pvc namespace: default spec: accessModes: - ReadWriteOnce resources: requests: storage: 1Gi --- apiVersion: v1 kind: PersistentVolumeClaim metadata: name: redis-slave-pvc namespace: default spec: accessModes: - ReadWriteOnce resources: requests: storage: 1Gi使用 StorageClass StorageClass 用于动态创建PV,适合生产环境,可以根据需求自动分配存储资源:
yamlapiVersion: storage.k8s.io/v1 kind: StorageClass metadata: name: redis-storage-class provisioner: kubernetes.io/gce-pd parameters: type: pd-standard reclaimPolicy: Retain allowVolumeExpansion: true --- apiVersion: v1 kind: PersistentVolumeClaim metadata: name: redis-pvc namespace: default spec: storageClassName: redis-storage-class accessModes: - ReadWriteOnce resources: requests: storage: 1Gi
配置管理
配置管理是Kubernetes中管理应用配置的重要部分,通过配置管理可以实现配置的集中管理、版本控制和动态更新。Redis的配置管理可以使用ConfigMap和Secret来实现。
使用 ConfigMap 管理配置
ConfigMap用于存储非敏感的配置信息,如Redis的配置文件、环境变量等。以下是使用ConfigMap管理Redis配置的方法:
创建 ConfigMap
yamlapiVersion: v1 kind: ConfigMap metadata: name: redis-config namespace: default data: redis.conf: | bind 0.0.0.0 port 6379 daemonize no requirepass your_strong_password appendonly yes appendfsync everysec dir /data maxmemory 512mb maxmemory-policy allkeys-lru在 Deployment 中使用 ConfigMap
yamlapiVersion: apps/v1 kind: Deployment metadata: name: redis namespace: default spec: # ... template: spec: containers: - name: redis image: redis:7.2-alpine volumeMounts: - name: redis-config mountPath: /etc/redis/redis.conf subPath: redis.conf args: - redis-server - /etc/redis/redis.conf volumes: - name: redis-config configMap: name: redis-config # ...更新 ConfigMap
bash# 编辑 ConfigMap kubectl edit configmap redis-config -n default # 或者使用 kubectl apply kubectl apply -f redis-config.yaml # 重启 Pod 以应用新配置 kubectl rollout restart deployment redis -n default
使用 Secret 管理敏感信息
Secret用于存储敏感的配置信息,如Redis的密码、证书等。使用Secret可以避免将敏感信息直接存储在配置文件中,提高安全性。
创建 Secret 可以通过文件或直接命令创建Secret,以下是两种常见的创建方式:
bash# 从文件创建 Secret echo -n "your_strong_password" > password.txt kubectl create secret generic redis-secret --from-file=password.txt # 或者直接创建,更方便快捷 kubectl create secret generic redis-secret --from-literal=redis-password=your_strong_password在 Deployment 中使用 Secret 创建Secret后,可以在Deployment中通过环境变量或卷挂载的方式使用Secret中的敏感信息:
yamlapiVersion: apps/v1 kind: Deployment metadata: name: redis namespace: default spec: # ... template: spec: containers: - name: redis image: redis:7.2-alpine env: - name: REDIS_PASSWORD # 定义环境变量名 valueFrom: # 从Secret获取值 secretKeyRef: name: redis-secret # Secret名称 key: redis-password # Secret中的键名 command: # 使用环境变量作为启动参数 - redis-server - --requirepass - $(REDIS_PASSWORD) # ...
监控和日志
监控和日志是Redis运维的重要组成部分,通过监控可以实时了解Redis的运行状态和性能指标,通过日志可以排查和分析问题。
Docker 监控和日志
在Docker环境中,可以使用Docker自带的命令来监控Redis容器和查看日志:
查看 Docker 日志 Docker日志包含了Redis的所有输出信息,可以帮助排查问题:
bash# 查看 Redis 容器日志 docker logs redis # 实时查看日志,跟踪最新的日志输出 docker logs -f redis # 查看最近 100 行日志,避免输出过多内容 docker logs --tail 100 redis使用 Docker Stats Docker Stats 可以实时查看容器的资源使用情况,包括CPU、内存、网络和磁盘I/O:
bash# 查看 Redis 容器的资源使用情况 docker stats redis
Kubernetes 监控
在Kubernetes环境中,可以使用多种工具来监控Redis,包括kubectl命令、Prometheus和Grafana等。
使用 kubectl 查看日志 kubectl 是Kubernetes的命令行工具,可以用来查看Pod日志:
bash# 查看单个 Pod 的日志 kubectl logs redis-<pod-name> # 实时查看 Pod 日志 kubectl logs -f redis-<pod-name> # 查看 Deployment 下所有 Pod 的日志 kubectl logs deployment/redis使用 Prometheus 和 Grafana Prometheus 和 Grafana 是一套强大的监控解决方案,可以实现Redis的全面监控:
yaml# Redis Exporter Deployment,用于采集Redis指标 apiVersion: apps/v1 kind: Deployment metadata: name: redis-exporter namespace: default spec: replicas: 1 # 只需要1个副本 selector: matchLabels: app: redis-exporter template: metadata: labels: app: redis-exporter spec: containers: - name: redis-exporter image: oliver006/redis_exporter:latest # 使用最新版本的Redis Exporter ports: - containerPort: 9121 # Exporter 监听端口 env: - name: REDIS_ADDR value: redis://redis:6379 # Redis 服务地址 - name: REDIS_PASSWORD valueFrom: # 从Secret获取密码 secretKeyRef: name: redis-secret key: redis-password # Redis Exporter Service,用于Prometheus采集指标 apiVersion: v1 kind: Service metadata: name: redis-exporter namespace: default annotations: prometheus.io/scrape: "true" # 启用Prometheus自动发现 prometheus.io/port: "9121" # 告诉Prometheus采集的端口 spec: selector: app: redis-exporter ports: - port: 9121 targetPort: 9121Grafana 仪表盘 Grafana 用于可视化监控数据,可以通过导入现成的Redis仪表盘来快速实现监控:
- 导入 Redis 仪表盘(ID: 763),这是一个成熟的Redis监控仪表盘
- 配置 Prometheus 数据源,将Grafana连接到Prometheus
- 监控 Redis 关键指标,如内存使用、连接数、命中率、命令执行速度等
最佳实践
最佳实践是在生产环境中部署和管理Redis的重要指导原则,遵循这些实践可以提高Redis的安全性、性能和可靠性。
安全配置
安全配置是保护Redis实例免受未授权访问和攻击的关键措施:
设置强密码
- 使用至少 16 位的强密码,包含大小写字母、数字和特殊字符
- 避免使用容易猜测的密码,如"password"、"redis"等
- 在Kubernetes环境中使用Secret管理密码,避免直接明文存储
限制网络访问
- 在Docker中使用自定义网络,避免Redis实例暴露在公共网络中
- 在Kubernetes中使用Network Policies,只允许特定的Pod访问Redis
- 示例 Network Policy,限制只有带有app=allowed-app标签的Pod可以访问Redis:yaml
apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: redis-network-policy namespace: default spec: podSelector: matchLabels: app: redis policyTypes: - Ingress ingress: - from: - podSelector: matchLabels: app: allowed-app ports: - protocol: TCP port: 6379
启用 SSL/TLS
- Redis 6.0+ 原生支持 SSL/TLS,可以加密客户端和服务器之间的通信
- 在Kubernetes中使用TLS证书,保护数据在传输过程中的安全性
- 示例配置,创建用于Redis的TLS Secret:yaml
apiVersion: v1 kind: Secret metadata: name: redis-tls type: kubernetes.io/tls data: tls.crt: <base64-encoded-cert> tls.key: <base64-encoded-key>
性能优化
资源限制
- 合理设置 CPU 和内存限制
- 根据实际负载调整资源请求
- 示例:yaml
resources: requests: memory: "256Mi" cpu: "100m" limits: memory: "512Mi" cpu: "500m"
使用 Alpine 镜像
- Alpine 镜像体积小,启动快
- 减少攻击面
- 示例:
redis:7.2-alpine
调整持久化策略
- 根据业务需求选择合适的持久化方式
- 平衡性能和数据安全性
- 示例:yaml
command: - redis-server - --appendonly - "yes" - --appendfsync - everysec
高可用性
部署多副本
- 在 Kubernetes 中使用 StatefulSet 部署 Redis Cluster
- 配置合适的副本数
- 示例:yaml
apiVersion: apps/v1 kind: StatefulSet metadata: name: redis-cluster spec: serviceName: redis-cluster replicas: 6 # ...
配置健康检查
- 配置 livenessProbe 和 readinessProbe
- 确保 Pod 健康状态准确反映 Redis 服务状态
- 示例:yaml
livenessProbe: exec: command: - redis-cli - -a - your_strong_password - ping initialDelaySeconds: 30 periodSeconds: 10 readinessProbe: exec: command: - redis-cli - -a - your_strong_password - ping initialDelaySeconds: 5 periodSeconds: 10
自动扩缩容
- 使用 Horizontal Pod Autoscaler (HPA) 根据负载自动调整副本数
- 示例:yaml
apiVersion: autoscaling/v2 kind: HorizontalPodAutoscaler metadata: name: redis-hpa spec: scaleTargetRef: apiVersion: apps/v1 kind: Deployment name: redis minReplicas: 1 maxReplicas: 3 metrics: - type: Resource resource: name: cpu target: type: Utilization averageUtilization: 80 - type: Resource resource: name: memory target: type: Utilization averageUtilization: 80
常见问题(FAQ)
问题 1: Redis 容器启动失败,提示 "Address already in use"
原因: 端口已被占用。
解决方案:
bash
# 检查端口占用情况
kubectl get pods -o wide
# 或者
docker ps
# 修改 Service 的 NodePort
# 或者修改容器的 hostPort问题 2: Redis 主从复制失败
原因: 网络问题、密码错误或配置不当。
解决方案:
bash
# 检查主从节点网络连接
kubectl exec -it redis-slave-0 -- ping redis-master
# 检查密码配置
kubectl logs redis-slave-0
# 验证主从配置
kubectl exec -it redis-slave-0 -- redis-cli -a your_strong_password info replication问题 3: Redis Cluster 节点无法加入集群
原因: 网络通信问题、gossip 端口未开放或配置错误。
解决方案:
bash
# 检查 gossip 端口
kubectl get services
# 检查集群配置
kubectl exec -it redis-cluster-0 -- redis-cli -a your_strong_password cluster nodes
# 重启集群初始化
kubectl exec -it redis-cluster-0 -- redis-cli -a your_strong_password cluster reset问题 4: 持久化数据丢失
原因: 使用了 emptyDir 或 hostPath 在错误的节点上。
解决方案:
yaml
# 使用 Persistent Volume Claim
volumeMounts:
- name: redis-data
mountPath: /data
volumes:
- name: redis-data
persistentVolumeClaim:
claimName: redis-pvc问题 5: Redis 性能不佳
原因: 资源限制不足、配置不当或查询优化问题。
解决方案:
bash
# 检查资源使用情况
kubectl top pods
# 优化配置
kubectl edit configmap redis-config
# 分析慢查询
kubectl exec -it redis-0 -- redis-cli -a your_strong_password slowlog get