Skip to content

perf: streamline grouped sorted-set validation and point insertion - #358

Merged
thweetkomputer merged 2 commits into
eloqdata:mainfrom
thweetkomputer:perf/zset-point-edits-20261019
Oct 19, 2026
Merged

thweetkomputer merged 2 commits into
eloqdata:mainfrom
thweetkomputer:perf/zset-point-edits-20261019

Conversation

@thweetkomputer

@thweetkomputer thweetkomputer commented Oct 19, 2026 •

Copy link
Copy Markdown
Collaborator

Context

Grouped sorted-set point writes rebuild a duplicate-member hash set during final encoding and sort the entire ordered leaf when inserting one member. This removes that repeated work while preserving validation at the boundary where mutable data becomes a checked after-image.

Behavior before and after

Command semantics and the durable format stay the same. A validated immutable ordered leaf can now be encoded without repeating duplicate-member hashing. Single-member ZADD inserts at its ordered position and splices a checked member-index leaf when it fits; larger, batched and split cases retain their existing paths.

Implementation

  • Introduce an immutable checked ordered after-image; ordinary decoding and recovery still validate duplicate members, identity, framing, order, scores and links.
  • Use lower_bound for a single new member, preserving score/member ordering.
  • Prepare a checked member-index point insertion before transferring its budget or publishing its after-image; retain full preparation for unsupported shapes.
  • Add five unit tests and two grouped ZSet end-to-end tests for validation, insertion, overflow/fallback and recovery behavior.

Design decisions and alternatives

Validation is reused only through an immutable checked representation. Skipping validation for arbitrary encoded input would weaken corruption detection. Fast paths remain narrow so batch operations and structural changes use the established implementation.

Documentation and comments

Updated nearby comments, including the absent-member validation paths. No module, lifecycle or durable-format claim changes, so architecture documentation is unchanged.

Test plan

Linux x86-64 GCC 13 Debug: 125 unit tests and 33 grouped end-to-end tests passed. Commands below were run from the test build directory; lavik was the corresponding Debug server.

./lavik_unit_tests --gtest_filter='GroupedCollectionTest.*:GroupedSortedRewriteTest.*:GroupedHashTest.*:HashGroupPointProbe.*:HashGroupEdits.*:CompactHashEdit.*:OrderedCompactCodecTest.*'
./lavik_grouped_ordered_write_e2e_test ./lavik --gtest_filter='GroupedSortedSetWriteE2e.*:GroupedDemotionE2e.StringListSetSortedSetGeoAndStreamRecoverCompact-GroupedSortedSetWriteE2e.AggregateAbove512MiBRemainsBoundedAndRecovers'

git diff --check and clang-format 23.1.1 checks passed for changed C++ files. The full repository suite was not run. Runtime validation used 32bdd6b4; the final 001442e8 commit changes only a nearby comment.

A single 80-connection crossover with 8,192 keys per size is archived in the benchmark report. Full-window QPS changed by +28.2% for grouped 1 MiB ZINCRBY and +3.0% for grouped ZREM/ZADD. However, candidate ZINCRBY slowed from roughly 36.6k QPS during the first 40 seconds to 27.1k during the final 20 seconds; the aggregate is not a demonstrated steady-state gain. Compact 8 KiB points changed by -5.6% and -3.2%, but their resident background data differed. The fixed main-then-candidate order and continuing data state limit causal interpretation. Raw results, time series and limitations are in the linked report.

Risk assessment

The main risk is accidentally treating mutable or insufficiently validated state as checked. The checked representation is immutable, raw/recovery paths keep full validation, and tests cover rejected malformed input plus point-write recovery. Performance observations remain preliminary because of the limitations above.

Rollback plan

Revert these two commits; no data migration or format downgrade is needed.

Reviewer guide

Start with the checked ordered-leaf API and encoder, then inspect single-member planning in grouped/zset.cpp and member-index insertion in grouped/zset_members.cpp. The tests exercise both fast and fallback paths.

Follow-up work

A separate one-round benchmark of #357 stacked on this branch is now in the linked report: all fourteen 8 KiB commands at 80 connections completed successfully. Throughput differences versus the earlier main run range from -1.7% to +2.8%; process CPU decreased for SETRANGE and ZINCRBY by 18.2% and 9.3%, respectively, with polling included. These measurements do not isolate either patch’s contribution. The #357 code is not included in this PR.

@coderabbitai

coderabbitai Bot commented Oct 19, 2026

Copy link
Copy Markdown

Warning

Review limit reached

You've used all free OSS reviews for now. Wait for the free limit to reset to keep reviewing this public repository.

Next included review available in 50 minutes.

Check out review usage here.

View limit details

Limit details: You’ve used the included review currently available.

Learn how review limits work.

Review configuration:

⚙️ Run configuration
  • Configuration used: Organization UI
  • Review profile: CHILL
  • Plan: Advanced
  • Run ID: d64a5828-f9b7-4de2-8fa3-1b7e7b18fec0
📥 Commits

Reviewing files that changed from the base of the PR and between 684894d and 001442e.

📒 Files selected for processing: 9
  • include/lavik/storage/detail/grouped/collection.h
  • src/storage/engine/grouped/collection.cpp
  • src/storage/engine/grouped/hash.cpp
  • src/storage/engine/grouped/ordered_mutation.cpp
  • src/storage/engine/grouped/zset.cpp
  • src/storage/engine/grouped/zset_members.cpp
  • src/storage/engine/impl.h
  • tests/grouped/collection_test.cpp
  • tests/grouped/zset_write_e2e_test.cpp
  • Autofix · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@thweetkomputer
thweetkomputer merged commit 6a3d186 into eloqdata:main Oct 19, 2026
20 checks passed
@thweetkomputer
thweetkomputer deleted the perf/zset-point-edits-20261019 branch October 19, 2026 10:58
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant