Redis集群方案深度解析 Redis集群概览 Redis Cluster是Redis提供的分布式数据库解决方案,通过分片(sharding)实现数据水平扩展。Redis Cluster采用无中心架构,每个节点都可以接收读写请求,自动进行数据分片和故障转移。本文将深入讲解Redis Cluster的架构原理、部署方案及最佳实践。 Redis Cluster架构 核心概念 数据分片: 整个数据集被分为16384个哈希槽(hash slots) 每个节点负责管理一部分哈希槽 通过CRC16(key) % 16384计算key所属的槽 节点角色: 主节点(Master):负责处理读写请求 从节点(Slave):复制主节点数据,提供高可用保障 集群拓扑 部署Redis Cluster
Redis Cluster是Redis提供的分布式数据库解决方案,通过分片(sharding)实现数据水平扩展。Redis Cluster采用无中心架构,每个节点都可以接收读写请求,自动进行数据分片和故障转移。本文将深入讲解Redis Cluster的架构原理、部署方案及最佳实践。
数据分片:
节点角色:
Master 1 (Slots 0-5460) / \ Slave 1A Slave 1B Master 2 (Slots 5461-10922) / \ Slave 2A Slave 2B Master 3 (Slots 10923-16383) / \ Slave 3A Slave 3B
version: '3.8' services: redis-master-1: image: redis:7.2-alpine container_name: redis-master-1 command: redis-server --cluster-enabled yes --cluster-config-file nodes.conf --cluster-node-timeout 5000 --appendonly yes ports: - "7001:6379" - "17001:16379" volumes: - redis-master-1-data:/data networks: - redis-cluster redis-master-2: image: redis:7.2-alpine container_name: redis-master-2 command: redis-server --cluster-enabled yes --cluster-config-file nodes.conf --cluster-node-timeout 5000 --appendonly yes ports: - "7002:6379" - "17002:16379" volumes: - redis-master-2-data:/data networks: - redis-cluster redis-master-3: image: redis:7.2-alpine container_name: redis-master-3 command: redis-server --cluster-enabled yes --cluster-config-file nodes.conf --cluster-node-timeout 5000 --appendonly yes ports: - "7003:6379" - "17003:16379" volumes: - redis-master-3-data:/data networks: - redis-cluster redis-slave-1: image: redis:7.2-alpine container_name: redis-slave-1 command: redis-server --cluster-enabled yes --cluster-config-file nodes.conf --cluster-node-timeout 5000 --appendonly yes --slaveof redis-master-1 6379 ports: - "7004:6379" - "17004:16379" volumes: - redis-slave-1-data:/data networks: - redis-cluster depends_on: - redis-master-1 redis-slave-2: image: redis:7.2-alpine container_name: redis-slave-2 command: redis-server --cluster-enabled yes --cluster-config-file nodes.conf --cluster-node-timeout 5000 --appendonly yes --slaveof redis-master-2 6379 ports: - "7005:6379" - "17005:16379" volumes: - redis-slave-2-data:/data networks: - redis-cluster depends_on: - redis-master-2 redis-slave-3: image: redis:7.2-alpine container_name: redis-slave-3 command: redis-server --cluster-enabled yes --cluster-config-file nodes.conf --cluster-node-timeout 5000 --appendonly yes --slaveof redis-master-3 6379 ports: - "7006:6379" - "17006:16379" volumes: - redis-slave-3-data:/data networks: - redis-cluster depends_on: - redis-master-3 volumes: redis-master-1-data: redis-master-2-data: redis-master-3-data: redis-slave-1-data: redis-slave-2-data: redis-slave-3-data: networks: redis-cluster: driver: bridge
#!/bin/bash # 创建6个Redis实例 for port in 7001 7002 7003 7004 7005 7006; do mkdir -p /redis-cluster/node-${port} cat > /redis-cluster/node-${port}/redis.conf <<EOF port ${port} cluster-enabled yes cluster-config-file nodes-${port}.conf cluster-node-timeout 5000 appendonly yes dir /redis-cluster/node-${port} EOF redis-server /redis-cluster/node-${port}/redis.conf & done # 等待Redis启动 sleep 5 # 创建集群 redis-cli --cluster create \ 127.0.0.1:7001 127.0.0.1:7002 127.0.0.1:7003 \ 127.0.0.1:7004 127.0.0.1:7005 127.0.0.1:7006 \ --cluster-replicas 1
# 启用集群模式 cluster-enabled yes # 集群配置文件 cluster-config-file nodes.conf # 节点超时时间(毫秒) cluster-node-timeout 5000 # 主从复制延迟时间(毫秒) cluster-replica-validity-factor 10 # 故障转移超时时间(毫秒) cluster-migration-barrier 1 # 最少主节点数 cluster-require-full-coverage yes # AOF持久化 appendonly yes appendfsync everysec # 最大内存 maxmemory 2gb maxmemory-policy allkeys-lru # TCP缓冲区 tcp-backlog 511 tcp-keepalive 300
import redis.clients.jedis.HostAndPort; import redis.clients.jedis.JedisCluster; import redis.clients.jedis.ConnectionPoolConfig; public class RedisClusterExample { public static void main(String[] args) { // 配置连接池 ConnectionPoolConfig poolConfig = new ConnectionPoolConfig(); poolConfig.setMaxTotal(20); poolConfig.setMaxIdle(10); poolConfig.setMinIdle(5); // 配置集群节点 Set<HostAndPort> nodes = new HashSet<>(); nodes.add(new HostAndPort("127.0.0.1", 7001)); nodes.add(new HostAndPort("127.0.0.1", 7002)); nodes.add(new HostAndPort("127.0.0.1", 7003)); nodes.add(new HostAndPort("127.0.0.1", 7004)); nodes.add(new HostAndPort("127.0.0.1", 7005)); nodes.add(new HostAndPort("127.0.0.1", 7006)); // 创建JedisCluster实例 try (JedisCluster cluster = new JedisCluster(nodes, poolConfig)) { // 基本操作 cluster.set("user:1001", "Alice"); String value = cluster.get("user:1001"); System.out.println("Value: " + value); // 哈希操作 cluster.hset("session:abc123", "userId", "1001"); cluster.hset("session:abc123", "loginTime", "2026-03-27"); // 列表操作 cluster.lpush("tasks:pending", "task1", "task2", "task3"); // 集合操作 cluster.sadd("tags:article:123", "java", "redis", "cluster"); } } }
import io.lettuce.core.RedisClient; import io.lettuce.core.RedisURI; import io.lettuce.core.cluster.RedisClusterClient; import io.lettuce.core.cluster.api.RedisAdvancedClusterCommands; public class LettuceClusterExample { public static void main(String[] args) { // 配置集群节点 RedisURI uri1 = RedisURI.create("redis://127.0.0.1:7001"); RedisURI uri2 = RedisURI.create("redis://127.0.0.1:7002"); RedisURI uri3 = RedisURI.create("redis://127.0.0.1:7003"); // 创建RedisClusterClient RedisClusterClient client = RedisClusterClient.create( Arrays.asList(uri1, uri2, uri3) ); // 获取连接 RedisAdvancedClusterCommands<String, String> commands = client.connect().sync(); try { // 基本操作 commands.set("key1", "value1"); String value = commands.get("key1"); // 事务(注意:集群模式下只支持单key事务) commands.multi(); commands.set("key2", "value2"); commands.set("key3", "value3"); commands.exec(); // 管道(Pipelining) commands.setAutoFlushCommands(false); commands.set("key4", "value4"); commands.set("key5", "value5"); commands.flushCommands(); } finally { client.shutdown(); } } }
# 查看集群信息 redis-cli -c -p 7001 cluster nodes # 查看集群状态 redis-cli -c -p 7001 cluster info # 查看槽分配 redis-cli -c -p 7001 cluster slots
# 添加新节点 redis-cli --cluster add-node 127.0.0.1:7007 127.0.0.1:7001 # 移除节点 redis-cli --cluster del-node 127.0.0.1:7001 <node-id> # 设置从节点 redis-cli --cluster replicate <master-node-id> # 故障转移 redis-cli --cluster failover 127.0.0.1:7001
# 重新分片 redis-cli --cluster reshard 127.0.0.1:7001 \ --cluster-from <source-node-id> \ --cluster-to <target-node-id> \ --cluster-slots 1000 \ --cluster-yes # 平衡槽 redis-cli --cluster rebalance 127.0.0.1:7001
# 检查集群健康状态 redis-cli --cluster check 127.0.0.1:7001 # 查看节点信息 redis-cli -c -p 7001 info replication redis-cli -c -p 7001 info persistence
# 慢查询日志 redis-cli -c -p 7001 slowlog get 10 # 监控命令 redis-cli -c -p 7001 monitor # 统计信息 redis-cli -c -p 7001 info stats
现象:客户端收到MOVED错误
原因:数据分片发生变化
解决方案:
现象:在批量操作时收到CROSSSLOT错误
原因:多个key不在同一个槽,无法使用MGET等批量操作
解决方案:
// 使用Hash Tag redis.set("{user:1001}:name", "Alice"); redis.set("{user:1001}:age", "25"); // 这样两个key会在同一个槽,可以使用pipeline
解决方案:
hash-max-ziplist-entries 512 hash-max-ziplist-value 64 zset-max-ziplist-entries 128 zset-max-ziplist-value 64
Redis Cluster提供了强大的分布式缓存解决方案,具备高可用、高性能、易扩展的特点。在实际应用中,需要根据业务场景选择合适的部署方案和配置参数。掌握Redis Cluster的运维技能,能够让你在大规模分布式系统中游刃有余。
在2026年的技术栈中,Redis仍然是分布式缓存的首选方案。通过合理使用Redis Cluster,可以构建出高并发、高可用的缓存系统,为应用提供强有力的性能支撑。
发布日期:2026年03月27日
主题:Redis集群方案深度解析