RedisJSON 技术揭秘`JSON.ARRTRIM`用窗口裁剪,让数组保持“刚刚好”

发布于:2025-07-14 ⋅ 阅读:(22) ⋅ 点赞:(0)

1、指令速查

JSON.ARRTRIM <key> <path> <start> <stop>
  • key:Redis 键名

  • path:JSONPath,默认 $ 根;可用 .[*]/.. 多路径匹配

  • start / stop:要保留的 [start, stop] 闭区间索引

    • 支持负值(从尾部数)
    • 越界也不会报错,而是自动钳位
    • start > stopstart ≥ 数组长度 ⇒ 结果为空数组,返回 0

返回值:与路径对应的新数组长度;若路径不是数组 ⇒ nil

时间复杂度

  • 单路径 → O(N),N 为数组长度
  • 多路径 → O(N × 匹配数)

2、核心特性 & 场景

功能 应用示例
滑动窗口 日志只保留最近 k 条、限流计数器
排行榜截断 取前 100 名:start=0 stop=99
RingBuffer 写前 ARRTRIM -capacity -1
批量归档 ARRTRIM 保留近档,再把弹出数据写冷库

3、CLI 实战:给耳机音量档裁剪“窗口”

3.1 初始化并追加

# 12 个档位
JSON.ARRAPPEND key $.[1].max_level 140 160 180 200 220 240 260 280
# -> (integer) 12

3.2 仅保留第 5-9 位(含 4 – 8)

redis> JSON.ARRTRIM key $.[1].max_level 4 8
1) (integer) 5

数组变为 [140, 160, 180, 200, 220]

3.3 保留最近 3 条(负索引)

redis> JSON.ARRTRIM key $.[1].max_level -3 -1
1) (integer) 3

4、越界 & 容错细节(v2.0+)

  • start < 0 → 从尾部数
  • stop > len-1 → 自动截到尾
  • start > stop → 数组置空,返回 0
  • 空数组裁剪仍返回 0 而非错误

因此大胆裁剪不必先算长度,适合高并发窗口滑动。

5、跨语言实战

5.1 Python(redis-py ≥ 5.0)

from redis import Redis
r = Redis(decode_responses=True)

# 仅保留最近 100 条
r.execute_command("JSON.ARRTRIM", "chat:room:42", "$.msgs", -100, -1)

5.2 Node.js(@redis/client)

import { createClient } from 'redis';
const cli = createClient(); await cli.connect();

// 排行榜:只留前 50
await cli.json.arrTrim('rank:game', '$.players', 0, 49);

5.3 Go(go-redis/v9)

_, _ = rdb.Do(ctx, "JSON.ARRTRIM",
    "sensor:temp", "$.records", -3600, -1).Result() // 保留最近一小时秒级点

6、最佳实践

  1. 写后即裁

    JSON.ARRAPPEND key $.logs '"new"'  \
    && JSON.ARRTRIM key $.logs -1000 -1   # 保 1000 条
    

    两条指令可用 MULTI/EXEC 或 Lua 保证原子顺序。

  2. 配合定时任务
    对历史不敏感场景,每 N 分钟统一裁剪降压。

  3. 避免大范围多路径
    通配 $..* 上万数组会致 O(N²);拆文档或逐键裁剪。

  4. 链式操作
    ARRTRIM 后再 ARRLEN 检测是否需缩容或归档。

7、与数组家族的最终协同

需求 推荐组合
固定大小消息队列 ARRAPPENDARRTRIM -max -1
排行榜更新 分数变动后排序(客户端)→ ARRTRIM 0 99
限流计数 写前 ARRTRIM -window -1ARRLEN 判断是否超阈
热→冷数据迁移 ARRTRIM 出窗口外数据,用 ARRPOP 逐条搬迁

8、结语:数组六神技大集合

ARRAPPEND / ARRINSERT ARRINDEX ARRPOP ARRLEN ARRPOP ARRTRIM

至此,RedisJSON 数组全家桶已完全解锁:

  • :动态插入 / 追加
  • :定位元素
  • :获取长度
  • :单条弹出 or 批量裁剪

合理组合即可构建高效、原子、安全的数组数据结构。希望本系列能让你在高并发 JSON 数据处理上游刃有余!🎉


网站公告

今日签到

点亮在社区的每一天
去签到