Valkey 深度实战:从 Redis 许可证风波到每秒 10 亿请求的工程化完全指南(2026)
Redis 改了许可证,整个开源缓存生态一夜变天。Valkey 作为 Linux 基金会旗下的正统继承者,凭什么在不到两年内从 fork 走到每秒 10 亿请求?这篇文章带你从架构设计到生产部署,彻底搞懂 Valkey 9.x。
一、背景:Redis 许可证风波与 Valkey 的诞生
1.1 一场许可证引发的"开源地震"
2024 年 3 月,Redis Labs 宣布将 Redis 从 BSD 许可证切换为 RSALv2 + SSPL 双许可证。这个决定在开源社区炸了锅——简单来说:
- RSALv2(Redis Source Available License 2.0):允许你看源码、修改、分发,但如果你把 Redis 作为服务提供给第三方(比如云服务商卖 Redis 托管服务),你就违反了许可证
- SSPL(Server Side Public License):MongoDB 用过的同款许可证,要求如果你提供该软件的托管服务,必须公开你的服务端代码
这意味着什么?AWS ElastiCache、Google Memorystore、阿里云 Tair 等「卖 Redis 服务」的云厂商突然面临合规风险。更关键的是,大量使用 Redis 的企业和开发者开始担忧:我的业务会不会也受影响?
1.2 Valkey:Linux 基金会主导的社区响应
Linux 基金会联合 AWS、Google Cloud、Oracle、Ericsson、字节跳动等巨头迅速成立 Valkey 项目。核心策略很清晰:
- 从 Redis 7.2.4 之前的 BSD 代码 fork——最后一个 BSD 许可证的稳定版本
- 捐赠给 Linux 基金会——确保永久开源
- 采用 BSD 3-Clause 许可证——与原 Redis 保持一致
- 社区治理——任何人都可以贡献,不受单一公司控制
截至 2026 年 6 月,Valkey 已经发布了 8.0、9.0 和 9.1.0-rc2 三个主要版本,GitHub Stars 突破 25k,超过 270 个公开仓库围绕 Valkey 构建生态。从兼容性角度看,Valkey 8.0.0 完全兼容 Redis OSS 7.2.4,现有的 Redis 客户端几乎不需要改动。
1.3 为什么你应该关注 Valkey
抛开许可证不谈,Valkey 团队在性能优化上做得非常激进:
- 9.0 达到每秒 10 亿请求(2000 节点集群)
- 9.1 的 Lock-free IO 线程带来 8-17% 吞吐提升
- ARM NEON SIMD 优化带来 2-3x 速度提升
- 嵌入式字符串阈值从 64 提到 128 字节,GET 吞吐提升 30%
这些不是营销数字,是实实在在的 commit 和 benchmark。下面我们逐一拆解。
二、Valkey 架构设计深度解析
2.1 核心架构:一个熟悉但不同的"Redis"
Valkey 的整体架构继承了 Redis 的经典设计,但在关键路径上做了重大改造:
┌─────────────────────────────────────────────────────┐
│ Valkey Server │
├─────────────────────────────────────────────────────┤
│ Client Network Layer (TCP/TLS/RDMA) │
├─────────────────────────────────────────────────────┤
│ IO Threading Layer (Lock-free Queue) ← 9.1 新架构 │
├─────────────────────────────────────────────────────┤
│ Command Parser & Dispatcher │
├─────────────────────────────────────────────────────┤
│ Data Structure Layer │
│ ├── String (embstr up to 128B, 9.1 提升) │
│ ├── Hash (支持字段级过期, 9.0) │
│ ├── List │
│ ├── Set (SIMD 优化, 9.0) │
│ ├── Sorted Set │
│ ├── Stream │
│ ├── Bitmap (SIMD BITCOUNT, 9.0) │
│ └── Module Extension System │
├─────────────────────────────────────────────────────┤
│ Persistence Layer (RDB/AOF) │
├─────────────────────────────────────────────────────┤
│ Cluster Layer (Atomic Slot Migration, 9.0) │
└─────────────────────────────────────────────────────┘
2.2 Lock-free IO Threading:9.1 最大的性能飞跃
传统 Redis 的 IO 多线程模型使用互斥锁在线程间传递任务。当 IO 线程数增加时,锁竞争会成为瓶颈。Valkey 9.1 重构了整个 IO 线程通信模型:
旧模型(Redis 风格):
主线程 ──[mutex lock]──> 任务队列 ──[mutex unlock]──> IO 线程
IO 线程 ──[mutex lock]──> 完成队列 ──[mutex unlock]──> 主线程
新模型(Valkey 9.1 Lock-free):
主线程 ──[CAS push]──> Lock-free MPSC Queue ──[CAS pop]──> IO 线程
IO 线程 ──[CAS push]──> Lock-free SPSC Queue ──[CAS pop]──> 主线程
核心改动是将原来的互斥锁替换为无锁队列(MPSC = Multi-Producer Single-Consumer,SPSC = Single-Producer Single-Consumer),通过 CAS(Compare-And-Swap)原子操作实现线程安全。
8-17% 吞吐提升是怎么来的?
在 4 IO 线程配置下,benchmarks 显示:
- SET 操作吞吐提升:约 12%
- GET 操作吞吐提升:约 8%(结合嵌入式字符串阈值提升,实际 GET 总提升达 30%+)
- Pipeline 场景提升更显著:约 15-17%
// 简化的 Lock-free MPSC 队列核心逻辑(伪代码)
typedef struct {
atomic_uintptr_t head;
atomic_uintptr_t tail;
Node* buffer[QUEUE_SIZE];
} LockFreeMPSCQueue;
bool mpsc_push(LockFreeMPSCQueue* q, Node* node) {
uintptr_t pos;
do {
pos = atomic_load_explicit(&q->tail, memory_order_relaxed);
if (pos - atomic_load_explicit(&q->head, memory_order_acquire) >= QUEUE_SIZE) {
return false; // 队列满
}
} while (!atomic_compare_exchange_weak_explicit(
&q->tail, &pos, pos + 1,
memory_order_release, memory_order_relaxed
));
q->buffer[pos % QUEUE_SIZE] = node;
return true;
}
2.3 嵌入式字符串阈值优化:小数据大收益
Valkey 中小于等于 44 字节的字符串会使用"嵌入字符串"(embstr)编码,整个 value 和 RedisObject 一起分配在一块连续内存中,减少一次内存分配和指针间接寻址。
Valkey 9.1 将这个阈值从 64 字节提升到 128 字节。看起来改动很小,但效果惊人:
// 假设平均 key-value 大小为 50-80 字节的缓存场景
// 旧阈值 64:大约 30% 的值需要 raw 编码(两次 malloc)
// 新阈值 128:几乎所有值都用 embstr 编码(一次 malloc)
GET 吞吐提升:30%
内存占用降低:约 8%(减少碎片和元数据开销)
为什么是 128?因为 SDS(Simple Dynamic String)header 占 3 字节(sdshdr8),RedisObject 占 16 字节,加上对齐填充,64 字节以下的字符串才能和 object 一起放入 64 字节的 jemalloc bin。Valkey 团队分析后认为 128 字节在内存效率上仍然是划算的。
2.4 ARM NEON SIMD 优化
Valkey 9.1 对 pvFind() 函数(用于 vset 数据结构的查找操作)应用了 ARM NEON SIMD 指令优化,实现 2-3x 速度提升:
// 简化的 ARM NEON 优化版本
#include <arm_neon.h>
// 同时比较 16 个字节,而不是逐字节比较
static inline int pvFind_neon(const uint8_t* data, int len, uint8_t target) {
const uint8_t* ptr = data;
const uint8_t* end = data + len;
while (ptr + 16 <= end) {
uint8x16_t vec = vld1q_u8(ptr); // 加载 16 字节
uint8x16_t cmp = vceqq_u8(vec, target); // 并行比较
uint64x2_t result = vreinterpretq_u64_u8(cmp);
if (vgetq_lane_u64(result, 0) || vgetq_lane_u64(result, 1)) {
// 找到匹配,用标量回退确定精确位置
return ptr - data + __builtin_ctz(vgetq_lane_u64(result, 0));
}
ptr += 16;
}
// 处理剩余字节
for (; ptr < end; ptr++) {
if (*ptr == target) return ptr - data;
}
return -1;
}
这个优化对 ARM 服务器(如 AWS Graviton 系列)特别有价值,在 x86 上也有 SSE/AVX 等价的 SIMD 优化。
三、Valkey 9.0 核心特性详解
3.1 原子化 Slot 迁移(Atomic Slot Migration)
在 Redis Cluster 中,数据分布在 16384 个 slot 上。迁移 slot 时,传统做法是逐个 key 迁移:
传统方式(key-by-key):
1. MIGRATE key1 → 源节点发送 key1 → 目标节点
2. MIGRATE key2 → 源节点发送 key2 → 目标节点
3. MIGRATE key3 → ...
问题:
- 大集合(Sorted Set 有百万成员)可能导致迁移阻塞
- 迁移过程中客户端可能碰到 MOVED 重定向
- 多 key 命令在部分迁移完成时无法执行
Valkey 9.0 原子化迁移:
1. 源节点将整个 slot 的 AOF 重写写入临时文件
2. 通过 AOF 流式传输到目标节点
3. AOF 可以逐条发送集合元素,避免大 key 阻塞
4. 传输完成后,原子切换 slot 归属
5. 源节点删除旧数据
# 配置迁移行为(9.1 新增)
cluster-config-save-behavior yes # 节点配置变更后自动保存 nodes.conf
# 触发迁移(与 Redis 兼容)
CLUSTER SETSLOT <slot> IMPORTING <node_id>
CLUSTER SETSLOT <slot> MIGRATING <node_id>
3.2 Hash 字段级过期(Hash Field Expiration)
这是 Valkey 9.0 最实用的特性之一。之前 Hash 的过期是 key 级别的——整个 Hash 要么存在,要么消失。现在你可以给 Hash 的单个字段设置 TTL:
# 设置 Hash 字段及其过期时间(10 秒)
HSETEX session:user:123 user_name "张三" EX 10
HSETEX session:user:123 role "admin" EX 300
# 查询字段剩余时间
HTTL session:user:123 user_name # 返回剩余秒数
HPERSIST session:user:123 user_name # 取消过期
# 获取字段(如果存在且未过期)
HGETEX session:user:123 role # 类似 HGET 但可带 NX/XX 修饰
实际应用场景:
import valkey
client = valkey.Valkey(host='localhost', port=6379, decode_responses=True)
# 场景 1:分布式 Session 管理
# 用户 token 5 分钟过期,但 user_id 永不过期
pipe = client.pipeline()
pipe.hset('sess:abc123', 'user_id', '10001') # 不过期
pipe.hset('sess:abc123', 'csrf_token', 'xyz789') # 不过期
pipe.hexpire('sess:abc123', 300, 'created_at') # created_at 5分钟过期
pipe.execute()
# 场景 2:限流计数器自动清理
pipe.hset('rate:api:v1', 'ip_1.2.3.4', '15')
pipe.hexpire('rate:api:v1', 60, 'ip_1.2.3.4') # 1分钟后自动清除
pipe.execute()
# 场景 3:临时缓存字段
pipe.hset('user:10001:cache', 'profile', '{"name":"张三"}')
pipe.hset('user:10001:cache', 'settings', '{"theme":"dark"}')
pipe.hexpire('user:10001:cache', 3600, 'profile') # profile 1小时过期
pipe.hexpire('user:10001:cache', 86400, 'settings') # settings 24小时过期
pipe.execute()
3.3 集群模式支持编号数据库(Numbered Databases in Cluster)
这是一个"考古复兴"特性。Redis 很早就支持 SELECT 切换数据库(db 0 到 db 15),但 Cluster 模式下只能用 db 0。Valkey 9.0 打破了这个限制:
# 集群模式下也能切换数据库
SELECT 1
SET key1 "value_in_db1"
SELECT 5
SET key1 "value_in_db5" # 不同数据库中的同名 key 互不影响
适用场景:
- 多租户隔离(每个租户一个 db)
- 同一集群上的开发/测试/生产环境分离
- 不同业务的 key 命名空间隔离
3.4 每秒 10 亿请求的大集群能力
Valkey 9.0 在大型集群测试中达到了 1 billion RPS:
- 2000 节点集群
- 每节点 256 连接
- Pipeline 模式 + 内存预取(Pipeline Memory Prefetch,提升 40%)
- 零拷贝响应(Zero Copy Responses,提升 20%)
1000 nodes → ~500M RPS
2000 nodes → ~1B RPS (线性扩展)
3.5 其他重要特性一览
| 特性 | 说明 | 性能影响 |
|---|---|---|
| Pipeline Memory Prefetch | Pipeline 请求时预取内存,减少缓存未命中 | +40% 吞吐 |
| Zero Copy Responses | 大响应直接从输出缓冲区发送,避免内存拷贝 | +20% 吞吐 |
| Multipath TCP | 支持 MPTCP,利用多条网络路径 | -25% 延迟 |
| SIMD BITCOUNT & HyperLogLog | 位操作和基数统计使用 SIMD 加速 | +200% 吞吐 |
| 多边形地理查询 | GEOSEARCH 支持 BYPOLYGON 参数 | 新功能 |
| DELIFEQ 条件删除 | 仅当值等于指定值时才删除 key | 新功能 |
| CLIENT LIST 过滤 | 支持按 flag/name/db 等过滤客户端列表 | 运维便利 |
| 25 个"解禁"命令 | 重新评估并恢复了之前弃用的 25 个命令 | API 兼容性 |
四、Valkey 9.1 新特性详解
4.1 Lock-free IO 线程(详见 2.2 节)
4.2 立即故障转移优化
9.1 优化了 Sentinel 的故障转移逻辑:如果 replica 是最佳排名节点,则立即执行故障转移,而不是等待其他节点仲裁:
# 原有行为:等待 quorum 确认
# 新行为(9.1):replica 本身就是最佳候选时,跳过等待直接 failover
# 配置 sentinel 的 down-after-milliseconds、failover-timeout 等
4.3 Lua 引擎改为静态链接
从 9.1 开始,Lua 脚本引擎默认静态链接到 Valkey 二进制文件中,而不是动态加载 .so。好处:
- 减少部署依赖
- 避免动态库版本冲突
- 启动更快
4.4 WATCH 性能优化
WATCH 命令用于事务中的乐观锁,9.1 将重复 key 检查从 O(N) 优化到 O(1):
# 9.1 之前的 WATCH(如果 WATCH 多个 key)
pipe = client.pipeline()
pipe.watch('balance:alice', 'balance:bob')
# 内部实现:遍历 watched_keys 列表检查重复 → O(N)
# 9.1 的 WATCH(使用 per-db 哈希表)
# 内部实现:直接 O(1) 哈希查找
4.5 CLUSTERSCAN MATCH 优化
9.1 优化了 CLUSTERSCAN 命令的 MATCH 选项,支持指定 slot 进行扫描,避免全集群扫描:
# 9.1 之前:MATCH 模式需要扫描所有 slot
CLUSTERSCAN 0 MATCH user:*
# 9.1:如果知道目标 slot,可以精确扫描
CLUSTERSCAN 0 MATCH user:* USESLOT 12345
五、从 Redis 迁移到 Valkey 的工程实践
5.1 兼容性评估
完全兼容的部分:
- 所有标准数据类型命令(String/Hash/List/Set/ZSet/Stream)
- Pub/Sub 命令
- Lua 脚本(EVAL/EVALSHA)
- Sentinel 哨兵模式
- Cluster 集群模式
- 持久化(RDB/AOF)
- 大部分客户端库(Jedis、lettuce、go-redis、redis-py 等)
需要注意的差异:
- Valkey 默认二进制名是
valkey-server(提供了redis-server符号链接兼容) - 配置文件名推荐用
valkey.conf - 少数 Redis 专有模块可能不兼容
- Redis Stack 的部分功能(如 RediSearch、RedisJSON)需要找社区替代方案
5.2 迁移步骤(生产零停机)
# 步骤 1:搭建 Valkey 从节点,指向 Redis 主节点
# valkey.conf
replicaof redis-master 6379
masterauth your_password
# 步骤 2:等待同步完成
valkey-cli -h localhost INFO replication
# 确认 master_link_status:ok
# 步骤 3:切换客户端到 Valkey
# 修改 DNS 或负载均衡配置,将写流量切到 Valkey
# 步骤 4:将 Valkey 提升为主节点
valkey-cli REPLICAOF NO ONE
# 步骤 5:关闭旧 Redis 节点
5.3 Docker/Kubernetes 部署
# docker-compose.yml
version: '3.8'
services:
valkey:
image: valkey/valkey:9.0
ports:
- "6379:6379"
volumes:
- valkey-data:/data
command: >
valkey-server
--appendonly yes
--maxmemory 4gb
--maxmemory-policy allkeys-lru
--io-threads 4
--io-threads-do-reads yes
valkey-sentinel:
image: valkey/valkey:9.0
command: valkey-sentinel /etc/sentinel.conf
volumes:
- ./sentinel.conf:/etc/sentinel.conf
volumes:
valkey-data:
# Kubernetes StatefulSet (精简版)
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: valkey
spec:
serviceName: valkey-headless
replicas: 3
template:
spec:
containers:
- name: valkey
image: valkey/valkey:9.0
ports:
- containerPort: 6379
command:
- valkey-server
- --cluster-enabled yes
- --cluster-config-file nodes.conf
- --cluster-node-timeout 5000
- --appendonly yes
resources:
requests:
memory: "2Gi"
cpu: "1"
limits:
memory: "4Gi"
cpu: "2"
volumeMounts:
- name: data
mountPath: /data
volumeClaimTemplates:
- metadata:
name: data
spec:
accessModes: ["ReadWriteOnce"]
resources:
requests:
storage: 10Gi
5.4 云服务商支持
各大云厂商已经或正在推出 Valkey 托管服务:
| 云厂商 | 服务 | 状态 |
|---|---|---|
| AWS | ElastiCache for Valkey | ✅ 已支持 |
| Google Cloud | Memorystore for Valkey | ✅ 已支持 |
| 腾讯云 | 分布式缓存 TDCS | ✅ 兼容 Valkey |
| 阿里云 | Tair | ✅ 兼容 Valkey |
| Oracle Cloud | OCI for Valkey | ✅ 已支持 |
| DigitalOcean | Managed Caching for Valkey | ✅ 已支持 |
| Heroku | Key-Value Store (Valkey) | ✅ 已支持 |
| Aiven | Aiven for Valkey | ✅ 已支持 |
六、性能调优实战指南
6.1 内存优化
# valkey.conf 内存相关配置
# 最大内存限制
maxmemory 8gb
# 淘汰策略(推荐 allkeys-lru 用于缓存场景)
maxmemory-policy allkeys-lru
# 哈希表优化:当元素少于 128 个时使用 listpack 编码
hash-max-listpack-entries 128
hash-max-listpack-value 64
# 列表优化
list-max-listpack-size -2 # 每个元素不超过 512 字节
# 集合优化
set-max-intset-entries 512
set-max-listpack-entries 128
set-max-listpack-value 64
# 有序集合优化
zset-max-listpack-entries 128
zset-max-listpack-value 64
6.2 IO 线程配置
# 启用 IO 多线程(推荐 CPU 核数 ≥ 4 时开启)
io-threads 4 # IO 线程数,建议设为 CPU 核数的一半
io-threads-do-reads yes # IO 线程也处理读操作(9.x 推荐 yes)
Benchmark 对比:
# 单线程基准
valkey-benchmark -t set,get -n 1000000 -c 50
# SET: ~180K ops/sec
# GET: ~200K ops/sec
# 4 IO 线程基准
valkey-benchmark -t set,get -n 1000000 -c 50
# SET: ~240K ops/sec (+33%)
# GET: ~300K ops/sec (+50%)
6.3 持久化优化
# AOF 配置(推荐用于需要数据安全的场景)
appendonly yes
appendfsync everysec # 每秒刷盘,平衡性能和安全
auto-aof-rewrite-percentage 100
auto-aof-rewrite-min-size 64mb
# RDB 配置(适合可以容忍少量数据丢失的场景)
save 900 1 # 900秒内有1次写就触发
save 300 10 # 300秒内有10次写
save 60 10000 # 60秒内有10000次写
save ""
# 混合持久化(AOF 文件中嵌入 RDB 格式)
aof-use-rdb-preamble yes
6.4 连接优化
# TCP Keepalive
tcp-keepalive 300
# 客户端输出缓冲区限制
client-output-buffer-limit normal 0 0 0
client-output-buffer-limit replica 256mb 64mb 60
client-output-buffer-limit pubsub 32mb 8mb 60
# 超时配置
timeout 300 # 客户端空闲 300 秒后断开
tcp-backlog 511 # TCP 连接队列长度
七、监控与运维
7.1 关键监控指标
import valkey
import time
client = valkey.Valkey(host='localhost', port=6379, decode_responses=True)
def collect_metrics():
info = client.info()
stats = client.info('stats')
memory = client.info('memory')
replication = client.info('replication')
metrics = {
# 吞吐量
'ops_per_sec': stats.get('instantaneous_ops_per_sec', 0),
# 内存
'used_memory_bytes': memory['used_memory'],
'used_memory_rss_bytes': memory['used_memory_rss'],
'used_memory_peak_bytes': memory['used_memory_peak'],
'fragmentation_ratio': memory.get('mem_fragmentation_ratio', 0),
# 连接
'connected_clients': info['connected_clients'],
'blocked_clients': info.get('blocked_clients', 0),
# 持久化
'rdb_last_bgsave_status': info.get('rdb_last_bgsave_status', 'none'),
'aof_last_bgrewrite_status': info.get('aof_last_bgrewrite_status', 'none'),
# 命中率
'keyspace_hits': stats.get('keyspace_hits', 0),
'keyspace_misses': stats.get('keyspace_misses', 0),
}
hits = metrics['keyspace_hits']
misses = metrics['keyspace_misses']
total = hits + misses
metrics['hit_rate'] = hits / total if total > 0 else 0
return metrics
# 每 10 秒采集一次
while True:
m = collect_metrics()
print(f"OPS: {m['ops_per_sec']}/s | "
f"Memory: {m['used_memory_bytes'] / 1024 / 1024:.1f}MB | "
f"Hit Rate: {m['hit_rate']:.2%} | "
f"Clients: {m['connected_clients']}")
time.sleep(10)
7.2 BetterDB:专为 Valkey 设计的监控
值得注意的是,已有第三方工具 BetterDB 专为 Valkey 设计,利用 Valkey 独有的 COMMANDLOG、per-slot 指标和 async I/O threading 可见性等功能,提供了传统 Redis 监控工具无法支持的能力。
7.3 慢查询排查
# 配置慢查询阈值(微秒)
SLOWLOG CONFIG SET slowlog-log-slower-than 10000 # 10ms
SLOWLOG CONFIG SET slowlog-max-len 128
# 查看慢查询
SLOWLOG GET 10
# 常见慢查询原因及优化:
# 1. KEYS 命令(禁止在生产环境使用)
# 替代方案:使用 SCAN
SCAN 0 MATCH pattern:* COUNT 100
# 2. 大 Key 操作
# 发现大 Key
valkey-cli --bigkeys
# 3. 大批量操作
# 分批处理
for i in range(0, total, batch_size):
pipe = client.pipeline()
for item in items[i:i+batch_size]:
pipe.set(item['key'], item['value'])
pipe.execute()
# 4. Lua 脚本过长
# 将大脚本拆分为小脚本,或使用 FUNCTION + LIBRARY
八、Valkey 模块生态
8.1 扩展模块系统
Valkey 继承并增强了 Redis 的模块 API。9.1 新增了 Module Command Result Callback(模块命令结果回调),让模块可以更灵活地处理命令返回值。
// Valkey 模块开发示例
#include <valkey/valkey.h>
static int hello_command(ValkeyModuleCtx *ctx, ValkeyModuleString **argv, int argc) {
if (argc != 2) {
return ValkeyModule_ReplyWithError(ctx, "ERR wrong number of arguments");
}
ValkeyModuleString *name = argv[1];
size_t len;
const char *str = ValkeyModule_StringPtrLen(name, &len);
ValkeyModule_ReplyWithSimpleString(ctx, "hello");
return VALKEYMODULE_OK;
}
int ValkeyModule_Init(ValkeyModuleCtx *ctx, ValkeyModuleArgs **args, int export_api) {
if (ValkeyModule_Init(ctx, "hello", 1, VALKEYMODULE_APIVER_1) == VALKEYMODULE_ERR) {
return VALKEYMODULE_ERR;
}
if (ValkeyModule_CreateCommand(ctx, "hello.world", hello_command, "readonly", 1, 1, 1) == VALKEYMODULE_ERR) {
return VALKEYMODULE_ERR;
}
return VALKEYMODULE_OK;
}
8.2 热门模块替代方案
| 原 Redis Stack 模块 | Valkey 社区替代 | 说明 |
|---|---|---|
| RediSearch | Valkey-search / Dragonfly Search | 全文搜索 |
| RedisJSON | ValkeyJSON | JSON 数据类型 |
| RedisTimeSeries | ValkeyTimeSeries | 时序数据 |
| RedisBloom | ValkeyBloom | 概率数据结构 |
| RedisGraph | — | 暂无成熟替代 |
九、Valkey vs Redis:一个程序员的真实选择
9.1 功能对比矩阵
| 特性 | Redis 8.x | Valkey 9.x |
|---|---|---|
| 许可证 | SSPL + RSALv2 | BSD 3-Clause |
| Hash 字段过期 | ❌ | ✅ (9.0) |
| 原子 Slot 迁移 | ❌ | ✅ (9.0) |
| 集群编号数据库 | ❌ | ✅ (9.0) |
| Lock-free IO | ❌ | ✅ (9.1) |
| SIMD 优化 | 有限 | 广泛 (NEON/SSE/AVX) |
| 大集群 RPS | ~500M | 1B+ |
| Multipath TCP | ❌ | ✅ (9.0) |
| RediSearch 等 | 内置 Stack | 需第三方模块 |
| SENTINEL | ✅ | ✅ (增强版) |
| Streams | ✅ | ✅ |
9.2 选择建议
选 Valkey 的场景:
- 你在用 AWS/GCP/阿里云托管服务,云厂商已支持 Valkey
- 你需要 Hash 字段级过期
- 你有大型集群(100+ 节点),需要原生 Slot 迁移
- 你的法律/合规团队要求 BSD 许可证
- 你运行在 ARM 服务器(如 Graviton),能受益 SIMD 优化
- 你想要社区治理而非单公司控制
暂缓迁移的场景:
- 你重度依赖 Redis Stack 的 RediSearch/RedisJSON 等专有模块
- 你的 Redis 版本很老(6.x 以下),需要先升级到 7.2.4+
- 你的运维团队对变更极度保守
十、未来展望
Valkey 项目正处于快速发展期。从已发布的 roadmap 和社区讨论来看:
- TLS 安全增强:9.1-rc2 延后了严格的 TLS 证书验证,预期会在 10.0 中完成
- RDMA 支持:实验性 RDMA 模块正在开发中,有望大幅降低数据中心内延迟
- 更多 SIMD 优化:计划覆盖更多数据结构和操作
- 模块生态成熟:ValkeyBloom 等官方模块逐步完善
- 可观测性增强:COMMANDLOG、per-slot 指标等独有功能持续完善
从工程角度看,Valkey 不仅仅是一个 Redis fork。它代表了开源社区对「云厂商绑架开源项目」的一次成功反击,同时用扎实的性能优化证明了社区驱动的开发模式可以产出比商业版本更好的软件。
如果你正在评估缓存/键值存储方案,Valkey 已经不是一个"备选项"——它是一个值得认真对待的首选方案。
总结
这篇文章覆盖了 Valkey 从诞生背景到 9.1 版本的完整技术栈:
- 背景:Redis 许可证变更催生 Valkey,Linux 基金会主导社区治理
- 架构:Lock-free IO、嵌入式字符串优化、ARM SIMD,每一项都是实打实的性能提升
- 9.0 特性:原子 Slot 迁移、Hash 字段过期、集群编号数据库、10 亿 RPS 大集群
- 9.1 特性:Lock-free 队列、立即故障转移、Lua 静态链接、WATCH O(1) 优化
- 迁移实战:兼容性评估、零停机迁移、Docker/K8s 部署、云厂商支持
- 性能调优:内存、IO 线程、持久化、连接全方位优化配置
- 监控运维:关键指标采集、慢查询排查、BetterDB 工具
- 模块生态:模块 API 增强、Stack 功能替代方案
- 选型对比:程序员视角的客观建议
Valkey 的故事告诉我们:好的开源项目不需要被一家公司绑架。当社区团结起来,完全可以做出更好的东西。