Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Replace keep-while cond reverse index with a prefix tree #298

Merged
merged 4 commits into from
Oct 1, 2024

Conversation

the-mikedavis
Copy link
Member

When handling a deletion, khepri_tree:eval_keep_while_conditions/2 folded over the reverse index of keep while conditions and evaluated any for which the removed path was a prefix. This meant folding over each non-leaf node in the tree. We can eliminate nodes very quickly though to limit the impact of this search by using a prefix tree instead.

This change switches out the keep_while_conds_revidx field in #khepri_tree{} to a new khepri_prefix_tree type when the Khepri cluster reaches the new effective machine version of 2.

@the-mikedavis the-mikedavis self-assigned this Sep 24, 2024
Copy link

codecov bot commented Sep 24, 2024

Codecov Report

Attention: Patch coverage is 94.44444% with 4 lines in your changes missing coverage. Please review.

Project coverage is 89.69%. Comparing base (b113424) to head (1d74ff8).
Report is 8 commits behind head on main.

Files with missing lines Patch % Lines
src/khepri_tree.erl 87.50% 4 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main     #298      +/-   ##
==========================================
+ Coverage   89.34%   89.69%   +0.34%     
==========================================
  Files          21       22       +1     
  Lines        3191     3259      +68     
==========================================
+ Hits         2851     2923      +72     
+ Misses        340      336       -4     
Flag Coverage Δ
erlang-25 88.80% <94.44%> (+0.33%) ⬆️
erlang-26 89.35% <94.44%> (+0.22%) ⬆️
erlang-27 89.62% <94.44%> (+0.44%) ⬆️
os-ubuntu-latest 89.69% <94.44%> (+0.43%) ⬆️
os-windows-latest 89.50% <94.44%> (+0.22%) ⬆️

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

@the-mikedavis the-mikedavis marked this pull request as ready for review September 24, 2024 21:20
@the-mikedavis
Copy link
Member Author

Dialyzer looks to get stuck in recursion on the Ubuntu + Erlang/OTP 27 runner, I can reproduce locally

src/khepri_machine.erl Outdated Show resolved Hide resolved
src/khepri_tree.erl Outdated Show resolved Hide resolved
Refactoring `convert_state/3` this way allows us to write
`convert_state1/3` so that it always acts on a single version upgrade.
@the-mikedavis the-mikedavis force-pushed the md/keep-while-revidx-prefix-tree branch from 3426952 to 1c32d4c Compare September 26, 2024 13:10
src/khepri_machine.erl Outdated Show resolved Hide resolved
This type is otherwise completely private to the `khepri_tree` module
and type. We'll take advantage of its private nature in the child
commits to change its representation. This value was only exposed for
a single test.
This will be used in the child commit to replace the keep-while
conditions reverse index which currently uses a map of paths to
watchers.

The design is very similar to- but simpler than the existing trees in
`khepri_tree` and `khepri_pattern_tree`.
@the-mikedavis the-mikedavis force-pushed the md/keep-while-revidx-prefix-tree branch from 1c32d4c to 1e8b3b9 Compare September 30, 2024 16:35
Copy link
Member

@dumbbell dumbbell left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This time, I tested my suggestions to make sure Dialyzer doesn’t loop indefinitely :)

src/khepri_machine.erl Outdated Show resolved Hide resolved
src/khepri_machine_v0.erl Outdated Show resolved Hide resolved
src/khepri_tree.hrl Outdated Show resolved Hide resolved
When deleting tree nodes in the `khepri_tree` we lookup in the reverse
index to find any conditions that are associated to paths which are
prefixes of the deleted path.

Prior to this commit we folded over the keep-while conditions reverse
index - a map - and used `lists:prefix/2` to find prefixing paths. In a
store with many nodes and tracking many keep-while conditions this can
become very expensive while deleting many nodes at once.

The parent commit introduced a prefix tree type which allows quick
lookup, given a path, of any tree nodes associated with a path which is
a prefix of the given path. We set a version 2 for khepri_machine which
upgrades the reverse index use to this new type.

Because the reverse index is private to the khepri_tree type I have
avoided introducing versioning for the `khepri_tree` module. Instead
the reverse index can either be a map - as in prior versions - or a
prefix tree. We act on the reverse index using the appropriate functions
for the type, which we detect at runtime.
@the-mikedavis the-mikedavis force-pushed the md/keep-while-revidx-prefix-tree branch from 1e8b3b9 to 1d74ff8 Compare October 1, 2024 13:43
@dumbbell dumbbell merged commit caf1ae3 into main Oct 1, 2024
12 checks passed
@dumbbell dumbbell deleted the md/keep-while-revidx-prefix-tree branch October 1, 2024 14:32
@dumbbell dumbbell added the enhancement New feature or request label Oct 1, 2024
@dumbbell dumbbell added this to the v0.17.0 milestone Oct 1, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants