Highlights: This release continues to improve Redis compatibility and operational visibility. New command coverage includes CLIENT PAUSE/CLIENT UNPAUSE, CLIENT SETINFO, LATENCY, TDIGEST.TRIMMED_MEAN, BITPOS BYTE/BIT range units, conditional SET options (IFEQ, IFNE, IFDEQ, IFDNE), DUMP support for the SortedInt type, and CLUSTERX FLUSHSLOTS for clearing slot ranges in cluster mode.
This version also strengthens cluster and observability workflows by propagating slave failure state in CLUSTER NODES, exposing worker thread CPU time, adding more KMETADATA output, and introducing dictionary compression settings.
Stability and security were improved with Lua and LuaJIT hardening, safer replication/fullsync handling, stricter command permissions, RDB malformed intset validation, data race fixes, and multiple correctness fixes across Streams, Geo, TDigest, Set, ZSet, HyperLogLog, and scripting. Dependencies were also refreshed, including RocksDB v11.1.1, jsoncons v1.7.0, jemalloc v5.3.1, oneTBB v2023.0.0, zlib v2.3.3, and fast_float v8.2.7.
This release contains internal groundwork for Hash Field Expiration, but the HFE user-facing feature was disabled for the 2.16.0 release and should not be treated as available functionality in this version.
New Features
- feat(rdb): add DUMP support for SortedInt type by @Zakir032002 in #3366
- feat(command): add FLUSHSLOTS command to clear keys in specified slot ranges in cluster mode by @sryanyuan in #3375
- feat(info): add thread CPU time measurement for worker thread monitoring by @sryanyuan in #3379
- feat(client): Add support for the CLIENT PAUSE/UNPAUSE commands to provide a temporary solution for failover by @Paragrf in #3378
- feat(cluster): propagate slave failure state via CLUSTER NODES fail flag by @Paragrf in #3386
- feat(tdigest): implement TDIGEST.TRIMMED_MEAN command by @chakkk309 in #3312
- feat: Add support for dictionary compression settings by @nagisa-kunhah in #3425
- feat(commands): expose hash, list and json metadata in kmetadata by @PragmaTwice in #3454
- feat(string): add digest length validation for DelEX IFDEQ/IFDNE by @kirito632 in #3453
- feat(server): implement LATENCY command set (Redis 7.0+ compatibility) by @gongna-au in #3461
- feat(commands): implement CLIENT SETINFO subcommand by @gongna-au in #3465
- feat(bit): add BYTE/BIT option support for BITPOS command by @gongna-au in #3460
- feat(string): support IFEQ/IFNE/IFDEQ/IFDNE in SET command by @kirito632 in #3475
Bug Fixes
- fix(stream): accept
~modifier in XADD and XTRIM by @XYenon in #3403 - fix(server): data race when accessing the db scan infos in GetLatestKeyNumStats by @songqing in #3414
- fix(conf): cap proto-max-bulk-len to 4 GiB instead of UINT64_MAX by @songqing in #3419
- fix(stream): correct subkey prefix encoding in DestroyGroup by @songqing in #3420
- fix(zset): initialize *inter_cnt before early return in InterCard by @songqing in #3421
- fix(string,hash): use compact float format in IncrByFloat to match Redis by @songqing in #3427
- fix(set): propagate storage errors in Set instead of treating as NotFound by @songqing in #3428
- fix(command): fix static initialization crash on Kunpeng/Kylin platform by @sryanyuan in #3416
- fix(stream): correct XREVRANGE minimum argument count from 2 to 4 by @songqing in #3438
- fix(geo): use strict weak ordering in sortGeoPointDESC comparator by @songqing in #3439
- fix(tdigest): merge into existing dest without OVERRIDE by @Tangruilin in #3412
- fix(tdigest): correct TDIGEST.MERGE parser for COMPRESSION parameter by @Tangruilin in #3449
- fix(hyperloglog): use namespace-prefixed key in PFMERGE GetMetadata by @songqing in #3441
- fix(stream): allow group and consumer names starting with digits by @songqing in #3442
- fix(geo): delete store_key instead of user_key in SearchStore by @songqing in #3456
- fix(geo): make geo store commands return the resulting set size with COUNT by @jihuayu in #3457
- fix(tdigest): fix incorrect min/max default initialization by @Tangruilin in #3463
- fix(stream): align XPENDING ID parsing and PEL range with XRANGE (incomplete IDs, exclusive bounds) by @songqing in #3437
- fix(scripting): reject negative FCALL key count by @songqing in #3466
- fix(bitfield): support Redis positional '#N' offset syntax by @nkroker in #3470
- fix(zset): register zdiffstore as write command by @jihuayu in #3486
Security & Hardening
- fix(script): upgrade Lua version to fix CVE-2024-31449 and CVE-2025-49844 by @jihuayu in #3435
- fix(command): APPLYBATCH should use the admin permission by @git-hulk in #3458
- fix(replication): require admin for transfer commands by @git-hulk in #3484
- fix(replication): reject unsafe fullsync file names by @git-hulk in #3483
- fix(scripting): bump LuaJIT to reject bytecode loading by @git-hulk in #3492
- fix(scripting): sanitize lua error replies by @jihuayu in #3494
- fix(rdb): reject malformed intset lengths by @git-hulk in #3519
- chore(security): add draft threat model and SECURITY.md for security-model discoverability by @potiuk in #3509
Improvements
- refactor: use stderr for CLI error output by @sanjana2505006 in #3372
- chore(util): replace strtof/strtod with fast-float by @PragmaTwice in #3394
- chore(config): remove the deprecated configuration
rocksdb.max_background_{compactions,flushes}and set default to -1 by @yatriks in #3398 - chore(scan): remove additional abstraction for subkey scanning by @PragmaTwice in #3490
Hash Field Expiration Groundwork (Disabled in 2.16.0)
- feat(hash): initialize field expiration metadata and subkey en/decoding by @PragmaTwice in #3444
- feat(hash): track persistent hash fields & support hash field expiration commands by @PragmaTwice in #3472
- feat(hash): restrict condition for hash encoding mode by @PragmaTwice in #3488
- feat(hash): implement hlen scan repair by @PragmaTwice in #3501
- feat(hash): support HFE compaction filter by @PragmaTwice in #3503
- feat(hash): add HFE expire and TTL commands by @PragmaTwice in #3506
- release: disable HFE feature for 2.16 release by @PragmaTwice in ec870bc
Build & CI
- chore(ci): bump golang lint to v2.9.0 by @aleksraiden in #3370
- chore(ci): bump all used actions to latest by @aleksraiden in #3383
- chore(ci): bump docker/build-push-action to v7 by @aleksraiden in #3384
- chore(ci): Use the lastest version of clang-format-18 & clang-tidy-18 by @jihuayu in #3389
- chore(ci): fix sonarcloud security hotspots by @jihuayu in #3392
- chore(ci): use git-hash in actions for ASF actions approval list by @LindaSummer in #3400
- fix(ci): failure in macOS due to the unavailable cmake version by @git-hulk in #3415
- chore(ci): bump typos action to version 1.45.0 by @aleksraiden in #3422
- fix(ci): add check-and-lint success as a merge condition by @jihuayu in #3423
- chore(ci): Update paths-filter and header action versions by @jihuayu in #3426
- fix(ci): modify Redis build cache keys by @jihuayu in #3430
- build: disable LTO by default by @PragmaTwice in #3440
- feat(ci): add caching for CMake FetchContent in CI workflow by @jihuayu in #3448
- chore(build): Move environment variables from RUN to dedicated ENV instruction by @aleksraiden in #3477
- chore(build): jemalloc disable flag for ArchLinux build by @aleksraiden in #3480
- chore(build): change base docker image to debian:trixie-slim by @aleksraiden in #3478
- chore(build): bump golangci-lint to 2.12.1 by @aleksraiden in #3476
- chore(test): bump Go-version to 1.25 for tests by @aleksraiden in #3485
- ci: exclude kvrocks2redis from sonar coverage by @jihuayu in #3512
- release: fix version of docker/login-action by @PragmaTwice in f9b0d59
Dependency Updates
- chore(deps): Bump zlib version to v2.3.3 by @aleksraiden in #3361
- chore(deps): bump jsoncons version to v1.6.0 by @aleksraiden in #3401
- chore(deps): bump jemalloc to 5.3.1 by @aleksraiden in #3451
- chore(deps): bump jsoncons to v1.7.0 by @aleksraiden in #3464
- chore(ci): bump crate-ci/typos to v1.46.0 by @aleksraiden in #3474
- chore(deps): bump oneTBB to v2023.0.0 by @aleksraiden in #3473
- chore(deps): bump rocksdb to v11.1.1 by @aleksraiden in #3468
- chore(deps): bump fast_float to 8.2.5 by @aleksraiden in #3479
- chore(deps): bump fast_float to v8.2.7 by @aleksraiden in #3513
Chores & Maintenance
- chore(docs): add AGENTS.md for AI coding agent guidance by @git-hulk in #3369
- chore: update copyright year in NOTICE by @caicancai in #3374
- chore(.asf.yaml): add 2.15 into protected branches by @git-hulk in #3376
- chore: fix typos in README and redis_bitmap.cc by @sanjana2505006 in #3390
- docs(agents): clarify agent workflow guidance by @PragmaTwice in #3455
- release: prepare source release apache-kvrocks-2.16.0 by @PragmaTwice in 28440b5
New Contributors
- @Zakir032002 made their first contribution in #3366
- @Paragrf made their first contribution in #3378
- @sanjana2505006 made their first contribution in #3372
- @yatriks made their first contribution in #3398
- @XYenon made their first contribution in #3403
- @songqing made their first contribution in #3414
- @nagisa-kunhah made their first contribution in #3425
- @kirito632 made their first contribution in #3453
- @gongna-au made their first contribution in #3461
- @nkroker made their first contribution in #3470
- @potiuk made their first contribution in #3509
Full Changelog: v2.15.0...v2.16.0