Skip to content

feat(storage): use IS and selected groups for zset range reads - #435

Merged
thweetkomputer merged 2 commits into
mainfrom
zset-range-intent-reads
Nov 6, 2026
Merged

thweetkomputer merged 2 commits into
mainfrom
zset-range-intent-reads

Conversation

@thweetkomputer

@thweetkomputer thweetkomputer commented Nov 5, 2026 •

Copy link
Copy Markdown
Collaborator

Context

Grouped range, rank and count reads take whole-key S and wait for unrelated group writers. Let these projections use key IS and protect only the payload groups they require.

Behavior before and after

Grouped ZRANGE aliases, ZRANK/ZREVRANK, ZCOUNT and ZLEXCOUNT acquire the required group S holds in identity order, revalidate routing and capture one immutable directory for counts and bounds. Rank also protects its member leaf. Ambiguous routing falls back once to key S.

Score counts lock partial boundary pages. Score LIMIT/OFFSET uses resident ranks to skip unrelated pages, including reverse ranges. Mixed-score lexical projections protect every ordered page because there is no lexical directory.

Implementation

Page loaders validate protected group revisions while unrelated roots publish. The common logical view is captured after acquisition, so concurrent changes to preceding cardinality cannot shift a range midway through its read.

Optional OnlineLatencyTrace* diagnostics is the final parameter in the affected storage helpers. Group-lock flags, retry outputs and deferred commit state precede it. Declarations, definitions and callers use the same order; callers that supply diagnostics explicitly supply any preceding default control argument. The dependent PRs apply the same convention to their additional helpers and calls.

Design decisions and alternatives

Retain group holds across waits and IO, with one whole-key fallback when routing cannot be validated. Parameter reordering preserves each argument value and default, including group_locked; it does not treat a diagnostic pointer as a Boolean flag.

Documentation and comments

The grouped-collections architecture describes IS range/rank/count projections and their common-view boundary. Existing ownership and lock-precondition comments remain applicable to the parameter-order cleanup, which does not change that architectural model.

Test plan

The Debug build for this PR passed, followed by 25 focused tests: 24 CTest cases plus the trace lifecycle metrics test. Coverage includes range/rank/count semantics, lock wait/wakeup, member projections, recovery, native replication, dependent commits and latency tracing.

cmake --build build_debug --target lavik lavik_unit_tests lavik_grouped_ordered_write_e2e_test lavik_metrics_e2e_test --parallel 4
ctest --test-dir build_debug --output-on-failure --stop-on-failure -R '^(StorageGroupedReadDeathTest|StorageGroupedReadTest|LatencyIntervalsTest)\.|^StorageWriteBufferResumeTest\.PreparedSameKeyPlansMergeWithoutLosingEitherGraph$|^lavik_grouped_ordered_write_e2e\.GroupedSortedSetWriteE2e\.(MemberReadsLockOnlyRequestedLeaves|RangeReadsKeepOneCutWhileOtherGroupsPublish|ConcurrentGroupsWaitWakeAndRecover|ConcurrentPointCommandsPreserveBothIndexes|MemberScoreProjectionPreservesOrderAndRecovery|MemberRanksSkipUnrelatedPagesAfterRecovery|ScoreBoundsSkipUnrelatedPagesAfterRecovery|ScoreCountsSkipInteriorPagesAfterRecovery|ScoreCountsTrackBoundsMutationsAndRecovery|ScoreOffsetsSkipInteriorPagesAfterRecovery|ScoreOffsetsRespectBoundsAndTiesAcrossPages|BoundedRangeAliasesRanksBoundsAndMixedScoreLex|RangeRemovalFitsSelectedPagesAndRecovers|RandomAndRangeRemovalPreserveSemantics|GeoPointReadsPreserveRepliesAndExecVisibility)$|^lavik_latency_diagnostics_e2e$|^lavik_native_replicaof_e2e$|^lavik_tx_commit_retry_e2e\.dependent$'
build_debug/lavik_metrics_e2e_test build_debug/lavik --gtest_filter=MetricsE2eTest.OnlineLatencyTraceLifecycleAndThreshold

The first latency E2E attempt received HTTP 502 because the environment proxied its loopback metrics request. That case and the remaining dependent-commit case passed with loopback proxy bypass:

NO_PROXY=127.0.0.1,localhost no_proxy=127.0.0.1,localhost ctest --test-dir build_debug --output-on-failure --stop-on-failure -R '^lavik_latency_diagnostics_e2e$|^lavik_tx_commit_retry_e2e\.dependent$'

The complete stack through #441 also built and passed 17 focused tests for Hash/Set intents and sampling, replication TTL fallback, zset batch/selected writes and latency diagnostics:

cmake --build build_debug --target lavik lavik_unit_tests lavik_grouped_ordered_write_e2e_test lavik_grouped_hash_write_e2e_test --parallel 4
NO_PROXY=127.0.0.1,localhost no_proxy=127.0.0.1,localhost ctest --test-dir build_debug --output-on-failure --stop-on-failure -R '^lavik_grouped_hash_write_e2e\.(GroupedHashWriteE2e\.(Intent.*|ConcurrentFinalDeletionRetriesUnderKeyX)|GroupedSetIntentE2e\..*|GroupedHashSetSamplingE2e\..*)$|^lavik_grouped_ordered_write_e2e\.GroupedSortedSetWriteE2e\.(SamplingReadsLockOnlyTheirWindow|BatchWritesOrderAllGroupsAndPublishAtomically|SelectedWritesProtectPredicatesAndAllowMemberReads|PopRevalidatesSelectionAfterReleasingReadLocks)$|^lavik_latency_diagnostics_e2e$'

Formatting checks passed. Each rebased tree was checked against the prior source with only the parameter-order transformation applied.

Risk assessment

The relevant boundaries are routing revalidation, group-lock lifetime, common-view consistency and trace forwarding. The focused tests exercise these paths, including disjoint progress and conflicting writers. Compact values and externally locked transaction callers retain their existing protection; durable formats and wire replies are unchanged.

Rollback plan

Revert the feature and helper-signature changes together with dependent call-site updates. No storage migration is required.

Reviewer guide

Start with TryConcurrentSortedSetRangeRead, then the grouped page loaders and ExecuteGroupedSortedSetLocked. The parameter-order cleanup is a separate commit. This PR is based directly on main.

Follow-up work

PRs #436–#441 extend intent locking to sampling, additional writes and Hash/Set operations. Their callers have been adapted to the final diagnostics parameter and remain independently reviewable against their immediate bases.

@coderabbitai

coderabbitai Bot commented Nov 5, 2026 •

Copy link
Copy Markdown

Explain Change →

Caution

Review failed

The pull request is closed.

  • Autofix · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

Warning

Some tools did not complete. Review the errors below.

Cppcheck (2.22.0)

src/storage/engine/grouped/list.cpp

Cppcheck timed out; analysis of this file is incomplete

src/storage/engine/grouped/ordered_io.cpp

Cppcheck timed out; analysis of this file is incomplete

src/storage/engine/compact_api.cpp

Cppcheck timed out; analysis of this file is incomplete

  • 12 others

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

@thweetkomputer
thweetkomputer force-pushed the zset-range-intent-reads branch from 819ecde to b30065a Compare November 5, 2026 11:12
@thweetkomputer
thweetkomputer force-pushed the zset-cardinality-intent-read branch 2 times, most recently from e5a303d to 698772c Compare November 5, 2026 12:35
@thweetkomputer
thweetkomputer force-pushed the zset-range-intent-reads branch 2 times, most recently from 5681af9 to 54d48dd Compare November 6, 2026 05:07
@thweetkomputer
thweetkomputer force-pushed the zset-cardinality-intent-read branch 2 times, most recently from 54698e3 to ad0146c Compare November 6, 2026 06:13
@thweetkomputer
thweetkomputer force-pushed the zset-range-intent-reads branch from 54d48dd to 88784f8 Compare November 6, 2026 06:13
@thweetkomputer
thweetkomputer force-pushed the zset-cardinality-intent-read branch from ad0146c to 9b9bd17 Compare November 6, 2026 06:49
@thweetkomputer
thweetkomputer force-pushed the zset-range-intent-reads branch 2 times, most recently from 2d57e86 to 9b90efd Compare November 6, 2026 07:38
@thweetkomputer
thweetkomputer force-pushed the zset-cardinality-intent-read branch 2 times, most recently from a2e82c6 to 262f033 Compare November 6, 2026 07:53
@thweetkomputer
thweetkomputer force-pushed the zset-range-intent-reads branch 2 times, most recently from 17551b7 to fe76457 Compare November 6, 2026 08:18
@thweetkomputer
thweetkomputer force-pushed the zset-cardinality-intent-read branch from 262f033 to 265fd1c Compare November 6, 2026 08:18
@thweetkomputer
thweetkomputer force-pushed the zset-range-intent-reads branch from fe76457 to c94dfd7 Compare November 6, 2026 08:22
@thweetkomputer
thweetkomputer changed the base branch from zset-cardinality-intent-read to main November 6, 2026 08:22
Move optional diagnostics after group-lock and commit-control arguments, and update declarations, definitions and every caller while preserving effective argument values and defaults.
@thweetkomputer
thweetkomputer merged commit ba8c018 into main Nov 6, 2026
6 checks passed
@thweetkomputer
thweetkomputer deleted the zset-range-intent-reads branch November 6, 2026 09:04
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