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

Fix invalid version vector check logic for backward compatibility #1105

Merged
merged 2 commits into from
Dec 19, 2024

Conversation

JOOHOJANG
Copy link
Contributor

@JOOHOJANG JOOHOJANG commented Dec 19, 2024

What this PR does / why we need it:
This PR is related to #1096
Fix missing handling vv related deletion logics for Text and Tree.

Since VersionVector and MaxCreatedAtMapByActor are always exist, comparing them with nil is incorrect, because they are empty not nil.

Which issue(s) this PR fixes:

Fixes #

Special notes for your reviewer:

Does this PR introduce a user-facing change?:


Additional documentation:


Checklist:

  • Added relevant tests or not required
  • Addressed and resolved all CodeRabbit review comments
  • Didn't break anything

Summary by CodeRabbit

  • New Features

    • Enhanced logic for handling node deletion and versioning in the document structure.
    • Improved clarity in the handling of local edits and version vector comparisons.
  • Bug Fixes

    • Streamlined checks for empty version vectors and maximum created-at maps, improving code readability and maintainability.
  • Documentation

    • Refined comments for clarity regarding node deletion and management of boundaries.
  • Refactor

    • Introduced boolean flags to simplify conditional logic across multiple methods related to version management and node manipulation.

@JOOHOJANG JOOHOJANG self-assigned this Dec 19, 2024
Copy link

coderabbitai bot commented Dec 19, 2024

Warning

Rate limit exceeded

@hackerwins has exceeded the limit for the number of commits or files that can be reviewed per hour. Please wait 23 minutes and 50 seconds before requesting another review.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

📥 Commits

Reviewing files that changed from the base of the PR and between c516ded and e37c3ea.

📒 Files selected for processing (3)
  • pkg/document/crdt/rga_tree_split.go (2 hunks)
  • pkg/document/crdt/text.go (2 hunks)
  • pkg/document/crdt/tree.go (6 hunks)

Walkthrough

This pull request introduces modifications to three files in the pkg/document/crdt/ directory, focusing on improving version vector and node deletion logic. The changes primarily involve adding two boolean variables, isVersionVectorEmpty and isMaxCreatedAtMapByActorEmpty, to streamline conditional checks across rga_tree_split.go, text.go, and tree.go. These modifications aim to enhance code readability and simplify the logic for handling local edits, version vector comparisons, and node manipulations without altering the fundamental functionality of the CRDT (Conflict-free Replicated Data Type) implementation.

Changes

File Change Summary
pkg/document/crdt/rga_tree_split.go - Added boolean flags isVersionVectorEmpty and isMaxCreatedAtMapByActorEmpty
- Refined deleteNodes method logic
- Improved comments for clarity
pkg/document/crdt/text.go - Introduced boolean flags for version vector and max created-at map checks
- Simplified conditional logic in Style method
- Replaced direct nil checks with new boolean variables
pkg/document/crdt/tree.go - Added boolean flags for version vector and max created-at map checks
- Modified collectBetween, Style, and RemoveStyle methods
- Streamlined version management and node manipulation logic

Possibly related PRs

Suggested reviewers

  • JOOHOJANG

Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media?

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Generate unit testing code for this file.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai generate unit testing code for this file.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

Copy link

codecov bot commented Dec 19, 2024

Codecov Report

Attention: Patch coverage is 50.00000% with 20 lines in your changes missing coverage. Please review.

Project coverage is 46.82%. Comparing base (2bd6d39) to head (e37c3ea).
Report is 1 commits behind head on main.

Files with missing lines Patch % Lines
pkg/document/crdt/tree.go 44.00% 12 Missing and 2 partials ⚠️
pkg/document/crdt/rga_tree_split.go 57.14% 2 Missing and 1 partial ⚠️
pkg/document/crdt/text.go 62.50% 2 Missing and 1 partial ⚠️
Additional details and impacted files
@@           Coverage Diff           @@
##             main    #1105   +/-   ##
=======================================
  Coverage   46.82%   46.82%           
=======================================
  Files          84       84           
  Lines       12257    12282   +25     
=======================================
+ Hits         5739     5751   +12     
- Misses       5941     5954   +13     
  Partials      577      577           

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

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (3)
pkg/document/crdt/tree.go (3)

875-878: Refine comment about "local edit" logic
The inline comment clarifies that a local edit uses the maximum lamport value to bypass concurrency checks. Consider explaining the scenario in which lamport comparisons might not apply, for instance, if a version vector is introduced later in the workflow.


1006-1008: Explicitly naming boolean variables
Defining isVersionVectorEmpty and isMaxCreatedAtMapByActorEmpty fosters code readability. Ensure these variable names remain consistent throughout the codebase.


1090-1093: Clarify fallback lamport
The fallback to clientLamportAtChange = 0 remains consistent with the earlier pattern. Revisit if 0 fully captures “untracked” actor states or if an alternative constant is more descriptive.

📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 2bd6d39 and 6f98675.

📒 Files selected for processing (3)
  • pkg/document/crdt/rga_tree_split.go (2 hunks)
  • pkg/document/crdt/text.go (2 hunks)
  • pkg/document/crdt/tree.go (6 hunks)
🔇 Additional comments (7)
pkg/document/crdt/tree.go (3)

845-847: Nice addition of clear boolean checks for emptiness
Using these flags for version vector emptiness checks clarifies the logic. This is a straightforward approach that helps prevent nil comparisons and avoids confusion between an empty vector vs. a nil object.


1018-1021: Confirm coverage for version vector with missing actor entries
We see if versionVector.Get(actorID) fails, clientLamportAtChange is set to 0. Verify if 0 is an intentional default or if a more explicit sentinel would prevent confusion.


1078-1080: Consistent logic usage
This block mirrors the pattern seen earlier for handling emptiness checks, preserving uniformity in style removal logic. Good job maintaining consistency.

pkg/document/crdt/text.go (2)

315-317: Ensuring distinction between nil and empty checks
Consistently handling these boolean checks helps avoid brittle nil checks. This also makes the flow for local vs. remote edits more transparent.


326-329: Streamlined local edit fallback
Using time.MaxLamport as a fallback is a neat approach to handle local edits. Confirm that tests cover edge cases where concurrency might occur, ensuring that local edits and remote edits don’t conflict unexpectedly.

pkg/document/crdt/rga_tree_split.go (2)

530-531: Clear initialization for new boolean flags
These lines effectively handle the distinction between an empty version vector and an empty MaxCreatedAtMapByActor. Good job making the code more explicit.


550-553: Maintain clarity on fallback lamport values
Following the same pattern as other files ensures consistent concurrency resolution logic. As with previous code, consider verifying that lamport=0 is handled properly in your test suite or that a more descriptive sentinel is used.

Copy link
Contributor

@chacha912 chacha912 left a comment

Choose a reason for hiding this comment

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

Thanks for this PR. 🙏

Copy link
Member

@hackerwins hackerwins left a comment

Choose a reason for hiding this comment

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

Thanks for your contribution.

@hackerwins hackerwins force-pushed the add-missing-vv-features branch from c516ded to 478be9b Compare December 19, 2024 08:23
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Caution

Inline review comments failed to post. This is likely due to GitHub's limits when posting large numbers of comments.

Actionable comments posted: 2

🛑 Comments failed to post (2)
pkg/document/crdt/tree.go (2)

845-847: 🛠️ Refactor suggestion

Consider extracting version handling logic into a helper function.

The version handling logic is duplicated across multiple methods (collectBetween, Style, RemoveStyle). Consider extracting it into a helper function to improve maintainability and reduce duplication.

Example implementation:

+// getClientLamportAtChange determines the client lamport value based on version vectors
+func getClientLamportAtChange(
+    versionVector time.VersionVector,
+    maxCreatedAtMapByActor map[string]*time.Ticket,
+    actorID string,
+    actorIDHex string,
+) (int64, *time.Ticket) {
+    isVersionVectorEmpty := len(versionVector) == 0
+    isMaxCreatedAtMapByActorEmpty := len(maxCreatedAtMapByActor) == 0
+
+    // Case 1: local editing from json package
+    if isVersionVectorEmpty && isMaxCreatedAtMapByActorEmpty {
+        return time.MaxLamport, nil
+    }
+
+    // Case 2: from operation with version vector(After v0.5.7)
+    if !isVersionVectorEmpty {
+        if lamport, ok := versionVector.Get(actorID); ok {
+            return lamport, nil
+        }
+        return 0, nil
+    }
+
+    // Case 3: from operation without version vector(Before v0.5.6)
+    if createdAt, ok := maxCreatedAtMapByActor[actorIDHex]; ok {
+        return 0, createdAt
+    }
+    return 0, time.InitialTicket
+}

Then use it in the methods:

-    isVersionVectorEmpty := len(versionVector) == 0
-    isMaxCreatedAtMapByActorEmpty := len(maxCreatedAtMapByActor) == 0
-
-    // Case 1: local editing from json package
-    if isVersionVectorEmpty && isMaxCreatedAtMapByActorEmpty {
-        clientLamportAtChange = time.MaxLamport
-    // Case 2: from operation with version vector(After v0.5.7)
-    } else if !isVersionVectorEmpty {
-        lamport, ok := versionVector.Get(actorID)
-        if ok {
-            clientLamportAtChange = lamport
-        } else {
-            clientLamportAtChange = 0
-        }
-    // Case 3: from operation without version vector(Before v0.5.6)
-    } else {
-        createdAt, ok := maxCreatedAtMapByActor[actorIDHex]
-        if ok {
-            maxCreatedAt = createdAt
-        } else {
-            maxCreatedAt = time.InitialTicket
-        }
-    }
+    clientLamportAtChange, maxCreatedAt = getClientLamportAtChange(
+        versionVector,
+        maxCreatedAtMapByActor,
+        actorID,
+        actorIDHex,
+    )

Also applies to: 875-887


1009-1011: 🛠️ Refactor suggestion

Duplicated version handling logic in Style and RemoveStyle methods.

The same version handling logic is duplicated in both Style and RemoveStyle methods. This should also use the suggested helper function above.

Also applies to: 1021-1032, 1083-1085, 1095-1106

@hackerwins hackerwins force-pushed the add-missing-vv-features branch from 478be9b to e37c3ea Compare December 19, 2024 08:25
Copy link

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

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

Go Benchmark

Benchmark suite Current: e37c3ea Previous: 6f98675 Ratio
BenchmarkDocument/constructor_test 1459 ns/op 1337 B/op 24 allocs/op 1498 ns/op 1337 B/op 24 allocs/op 0.97
BenchmarkDocument/constructor_test - ns/op 1459 ns/op 1498 ns/op 0.97
BenchmarkDocument/constructor_test - B/op 1337 B/op 1337 B/op 1
BenchmarkDocument/constructor_test - allocs/op 24 allocs/op 24 allocs/op 1
BenchmarkDocument/status_test 957.2 ns/op 1305 B/op 22 allocs/op 979.1 ns/op 1305 B/op 22 allocs/op 0.98
BenchmarkDocument/status_test - ns/op 957.2 ns/op 979.1 ns/op 0.98
BenchmarkDocument/status_test - B/op 1305 B/op 1305 B/op 1
BenchmarkDocument/status_test - allocs/op 22 allocs/op 22 allocs/op 1
BenchmarkDocument/equals_test 7742 ns/op 7529 B/op 134 allocs/op 7745 ns/op 7529 B/op 134 allocs/op 1.00
BenchmarkDocument/equals_test - ns/op 7742 ns/op 7745 ns/op 1.00
BenchmarkDocument/equals_test - B/op 7529 B/op 7529 B/op 1
BenchmarkDocument/equals_test - allocs/op 134 allocs/op 134 allocs/op 1
BenchmarkDocument/nested_update_test 16938 ns/op 12395 B/op 264 allocs/op 16926 ns/op 12395 B/op 264 allocs/op 1.00
BenchmarkDocument/nested_update_test - ns/op 16938 ns/op 16926 ns/op 1.00
BenchmarkDocument/nested_update_test - B/op 12395 B/op 12395 B/op 1
BenchmarkDocument/nested_update_test - allocs/op 264 allocs/op 264 allocs/op 1
BenchmarkDocument/delete_test 26452 ns/op 15923 B/op 347 allocs/op 24576 ns/op 15923 B/op 347 allocs/op 1.08
BenchmarkDocument/delete_test - ns/op 26452 ns/op 24576 ns/op 1.08
BenchmarkDocument/delete_test - B/op 15923 B/op 15923 B/op 1
BenchmarkDocument/delete_test - allocs/op 347 allocs/op 347 allocs/op 1
BenchmarkDocument/object_test 8806 ns/op 7073 B/op 122 allocs/op 9423 ns/op 7073 B/op 122 allocs/op 0.93
BenchmarkDocument/object_test - ns/op 8806 ns/op 9423 ns/op 0.93
BenchmarkDocument/object_test - B/op 7073 B/op 7073 B/op 1
BenchmarkDocument/object_test - allocs/op 122 allocs/op 122 allocs/op 1
BenchmarkDocument/array_test 29692 ns/op 12203 B/op 278 allocs/op 29771 ns/op 12203 B/op 278 allocs/op 1.00
BenchmarkDocument/array_test - ns/op 29692 ns/op 29771 ns/op 1.00
BenchmarkDocument/array_test - B/op 12203 B/op 12203 B/op 1
BenchmarkDocument/array_test - allocs/op 278 allocs/op 278 allocs/op 1
BenchmarkDocument/text_test 32325 ns/op 15324 B/op 492 allocs/op 32058 ns/op 15323 B/op 492 allocs/op 1.01
BenchmarkDocument/text_test - ns/op 32325 ns/op 32058 ns/op 1.01
BenchmarkDocument/text_test - B/op 15324 B/op 15323 B/op 1.00
BenchmarkDocument/text_test - allocs/op 492 allocs/op 492 allocs/op 1
BenchmarkDocument/text_composition_test 30494 ns/op 18718 B/op 504 allocs/op 30627 ns/op 18718 B/op 504 allocs/op 1.00
BenchmarkDocument/text_composition_test - ns/op 30494 ns/op 30627 ns/op 1.00
BenchmarkDocument/text_composition_test - B/op 18718 B/op 18718 B/op 1
BenchmarkDocument/text_composition_test - allocs/op 504 allocs/op 504 allocs/op 1
BenchmarkDocument/rich_text_test 84112 ns/op 40179 B/op 1183 allocs/op 85780 ns/op 40180 B/op 1183 allocs/op 0.98
BenchmarkDocument/rich_text_test - ns/op 84112 ns/op 85780 ns/op 0.98
BenchmarkDocument/rich_text_test - B/op 40179 B/op 40180 B/op 1.00
BenchmarkDocument/rich_text_test - allocs/op 1183 allocs/op 1183 allocs/op 1
BenchmarkDocument/counter_test 18424 ns/op 11874 B/op 258 allocs/op 18616 ns/op 11874 B/op 258 allocs/op 0.99
BenchmarkDocument/counter_test - ns/op 18424 ns/op 18616 ns/op 0.99
BenchmarkDocument/counter_test - B/op 11874 B/op 11874 B/op 1
BenchmarkDocument/counter_test - allocs/op 258 allocs/op 258 allocs/op 1
BenchmarkDocument/text_edit_gc_100 1347742 ns/op 872544 B/op 17283 allocs/op 1356063 ns/op 872578 B/op 17281 allocs/op 0.99
BenchmarkDocument/text_edit_gc_100 - ns/op 1347742 ns/op 1356063 ns/op 0.99
BenchmarkDocument/text_edit_gc_100 - B/op 872544 B/op 872578 B/op 1.00
BenchmarkDocument/text_edit_gc_100 - allocs/op 17283 allocs/op 17281 allocs/op 1.00
BenchmarkDocument/text_edit_gc_1000 52215657 ns/op 50546256 B/op 186741 allocs/op 52786270 ns/op 50546143 B/op 186741 allocs/op 0.99
BenchmarkDocument/text_edit_gc_1000 - ns/op 52215657 ns/op 52786270 ns/op 0.99
BenchmarkDocument/text_edit_gc_1000 - B/op 50546256 B/op 50546143 B/op 1.00
BenchmarkDocument/text_edit_gc_1000 - allocs/op 186741 allocs/op 186741 allocs/op 1
BenchmarkDocument/text_split_gc_100 1959477 ns/op 1589124 B/op 15951 allocs/op 2038663 ns/op 1589032 B/op 15951 allocs/op 0.96
BenchmarkDocument/text_split_gc_100 - ns/op 1959477 ns/op 2038663 ns/op 0.96
BenchmarkDocument/text_split_gc_100 - B/op 1589124 B/op 1589032 B/op 1.00
BenchmarkDocument/text_split_gc_100 - allocs/op 15951 allocs/op 15951 allocs/op 1
BenchmarkDocument/text_split_gc_1000 118468431 ns/op 141482619 B/op 186143 allocs/op 119081801 ns/op 141482256 B/op 186149 allocs/op 0.99
BenchmarkDocument/text_split_gc_1000 - ns/op 118468431 ns/op 119081801 ns/op 0.99
BenchmarkDocument/text_split_gc_1000 - B/op 141482619 B/op 141482256 B/op 1.00
BenchmarkDocument/text_split_gc_1000 - allocs/op 186143 allocs/op 186149 allocs/op 1.00
BenchmarkDocument/text_delete_all_10000 16179823 ns/op 10211682 B/op 55679 allocs/op 16938139 ns/op 10212719 B/op 55684 allocs/op 0.96
BenchmarkDocument/text_delete_all_10000 - ns/op 16179823 ns/op 16938139 ns/op 0.96
BenchmarkDocument/text_delete_all_10000 - B/op 10211682 B/op 10212719 B/op 1.00
BenchmarkDocument/text_delete_all_10000 - allocs/op 55679 allocs/op 55684 allocs/op 1.00
BenchmarkDocument/text_delete_all_100000 255105479 ns/op 142987600 B/op 561758 allocs/op 300649978 ns/op 142965700 B/op 561674 allocs/op 0.85
BenchmarkDocument/text_delete_all_100000 - ns/op 255105479 ns/op 300649978 ns/op 0.85
BenchmarkDocument/text_delete_all_100000 - B/op 142987600 B/op 142965700 B/op 1.00
BenchmarkDocument/text_delete_all_100000 - allocs/op 561758 allocs/op 561674 allocs/op 1.00
BenchmarkDocument/text_100 231094 ns/op 120491 B/op 5182 allocs/op 222669 ns/op 120491 B/op 5182 allocs/op 1.04
BenchmarkDocument/text_100 - ns/op 231094 ns/op 222669 ns/op 1.04
BenchmarkDocument/text_100 - B/op 120491 B/op 120491 B/op 1
BenchmarkDocument/text_100 - allocs/op 5182 allocs/op 5182 allocs/op 1
BenchmarkDocument/text_1000 2528065 ns/op 1171264 B/op 51086 allocs/op 2424413 ns/op 1171277 B/op 51086 allocs/op 1.04
BenchmarkDocument/text_1000 - ns/op 2528065 ns/op 2424413 ns/op 1.04
BenchmarkDocument/text_1000 - B/op 1171264 B/op 1171277 B/op 1.00
BenchmarkDocument/text_1000 - allocs/op 51086 allocs/op 51086 allocs/op 1
BenchmarkDocument/array_1000 1285367 ns/op 1091645 B/op 11833 allocs/op 1213484 ns/op 1091554 B/op 11833 allocs/op 1.06
BenchmarkDocument/array_1000 - ns/op 1285367 ns/op 1213484 ns/op 1.06
BenchmarkDocument/array_1000 - B/op 1091645 B/op 1091554 B/op 1.00
BenchmarkDocument/array_1000 - allocs/op 11833 allocs/op 11833 allocs/op 1
BenchmarkDocument/array_10000 13425848 ns/op 9799931 B/op 120298 allocs/op 13298552 ns/op 9799755 B/op 120296 allocs/op 1.01
BenchmarkDocument/array_10000 - ns/op 13425848 ns/op 13298552 ns/op 1.01
BenchmarkDocument/array_10000 - B/op 9799931 B/op 9799755 B/op 1.00
BenchmarkDocument/array_10000 - allocs/op 120298 allocs/op 120296 allocs/op 1.00
BenchmarkDocument/array_gc_100 156482 ns/op 133271 B/op 1266 allocs/op 147927 ns/op 133276 B/op 1266 allocs/op 1.06
BenchmarkDocument/array_gc_100 - ns/op 156482 ns/op 147927 ns/op 1.06
BenchmarkDocument/array_gc_100 - B/op 133271 B/op 133276 B/op 1.00
BenchmarkDocument/array_gc_100 - allocs/op 1266 allocs/op 1266 allocs/op 1
BenchmarkDocument/array_gc_1000 1474984 ns/op 1159699 B/op 12882 allocs/op 1398726 ns/op 1159650 B/op 12882 allocs/op 1.05
BenchmarkDocument/array_gc_1000 - ns/op 1474984 ns/op 1398726 ns/op 1.05
BenchmarkDocument/array_gc_1000 - B/op 1159699 B/op 1159650 B/op 1.00
BenchmarkDocument/array_gc_1000 - allocs/op 12882 allocs/op 12882 allocs/op 1
BenchmarkDocument/counter_1000 209757 ns/op 193336 B/op 5773 allocs/op 200667 ns/op 193337 B/op 5773 allocs/op 1.05
BenchmarkDocument/counter_1000 - ns/op 209757 ns/op 200667 ns/op 1.05
BenchmarkDocument/counter_1000 - B/op 193336 B/op 193337 B/op 1.00
BenchmarkDocument/counter_1000 - allocs/op 5773 allocs/op 5773 allocs/op 1
BenchmarkDocument/counter_10000 2216298 ns/op 2088267 B/op 59780 allocs/op 2144519 ns/op 2088265 B/op 59780 allocs/op 1.03
BenchmarkDocument/counter_10000 - ns/op 2216298 ns/op 2144519 ns/op 1.03
BenchmarkDocument/counter_10000 - B/op 2088267 B/op 2088265 B/op 1.00
BenchmarkDocument/counter_10000 - allocs/op 59780 allocs/op 59780 allocs/op 1
BenchmarkDocument/object_1000 1466568 ns/op 1428334 B/op 9851 allocs/op 1361573 ns/op 1428402 B/op 9851 allocs/op 1.08
BenchmarkDocument/object_1000 - ns/op 1466568 ns/op 1361573 ns/op 1.08
BenchmarkDocument/object_1000 - B/op 1428334 B/op 1428402 B/op 1.00
BenchmarkDocument/object_1000 - allocs/op 9851 allocs/op 9851 allocs/op 1
BenchmarkDocument/object_10000 15401331 ns/op 12167511 B/op 100568 allocs/op 15339947 ns/op 12168956 B/op 100571 allocs/op 1.00
BenchmarkDocument/object_10000 - ns/op 15401331 ns/op 15339947 ns/op 1.00
BenchmarkDocument/object_10000 - B/op 12167511 B/op 12168956 B/op 1.00
BenchmarkDocument/object_10000 - allocs/op 100568 allocs/op 100571 allocs/op 1.00
BenchmarkDocument/tree_100 1066448 ns/op 943959 B/op 6103 allocs/op 1043555 ns/op 943958 B/op 6103 allocs/op 1.02
BenchmarkDocument/tree_100 - ns/op 1066448 ns/op 1043555 ns/op 1.02
BenchmarkDocument/tree_100 - B/op 943959 B/op 943958 B/op 1.00
BenchmarkDocument/tree_100 - allocs/op 6103 allocs/op 6103 allocs/op 1
BenchmarkDocument/tree_1000 79665669 ns/op 86460842 B/op 60117 allocs/op 76325258 ns/op 86460570 B/op 60116 allocs/op 1.04
BenchmarkDocument/tree_1000 - ns/op 79665669 ns/op 76325258 ns/op 1.04
BenchmarkDocument/tree_1000 - B/op 86460842 B/op 86460570 B/op 1.00
BenchmarkDocument/tree_1000 - allocs/op 60117 allocs/op 60116 allocs/op 1.00
BenchmarkDocument/tree_10000 9842051532 ns/op 8580661504 B/op 600228 allocs/op 9560562048 ns/op 8580672256 B/op 600240 allocs/op 1.03
BenchmarkDocument/tree_10000 - ns/op 9842051532 ns/op 9560562048 ns/op 1.03
BenchmarkDocument/tree_10000 - B/op 8580661504 B/op 8580672256 B/op 1.00
BenchmarkDocument/tree_10000 - allocs/op 600228 allocs/op 600240 allocs/op 1.00
BenchmarkDocument/tree_delete_all_1000 80212371 ns/op 87511269 B/op 75273 allocs/op 74754727 ns/op 87509132 B/op 75268 allocs/op 1.07
BenchmarkDocument/tree_delete_all_1000 - ns/op 80212371 ns/op 74754727 ns/op 1.07
BenchmarkDocument/tree_delete_all_1000 - B/op 87511269 B/op 87509132 B/op 1.00
BenchmarkDocument/tree_delete_all_1000 - allocs/op 75273 allocs/op 75268 allocs/op 1.00
BenchmarkDocument/tree_edit_gc_100 4023608 ns/op 4148492 B/op 15147 allocs/op 3764618 ns/op 4147128 B/op 15146 allocs/op 1.07
BenchmarkDocument/tree_edit_gc_100 - ns/op 4023608 ns/op 3764618 ns/op 1.07
BenchmarkDocument/tree_edit_gc_100 - B/op 4148492 B/op 4147128 B/op 1.00
BenchmarkDocument/tree_edit_gc_100 - allocs/op 15147 allocs/op 15146 allocs/op 1.00
BenchmarkDocument/tree_edit_gc_1000 325058560 ns/op 383744780 B/op 154863 allocs/op 303402050 ns/op 383746754 B/op 154860 allocs/op 1.07
BenchmarkDocument/tree_edit_gc_1000 - ns/op 325058560 ns/op 303402050 ns/op 1.07
BenchmarkDocument/tree_edit_gc_1000 - B/op 383744780 B/op 383746754 B/op 1.00
BenchmarkDocument/tree_edit_gc_1000 - allocs/op 154863 allocs/op 154860 allocs/op 1.00
BenchmarkDocument/tree_split_gc_100 2686342 ns/op 2413024 B/op 11131 allocs/op 2500709 ns/op 2413070 B/op 11131 allocs/op 1.07
BenchmarkDocument/tree_split_gc_100 - ns/op 2686342 ns/op 2500709 ns/op 1.07
BenchmarkDocument/tree_split_gc_100 - B/op 2413024 B/op 2413070 B/op 1.00
BenchmarkDocument/tree_split_gc_100 - allocs/op 11131 allocs/op 11131 allocs/op 1
BenchmarkDocument/tree_split_gc_1000 197278035 ns/op 222255037 B/op 122013 allocs/op 184870231 ns/op 222250552 B/op 121990 allocs/op 1.07
BenchmarkDocument/tree_split_gc_1000 - ns/op 197278035 ns/op 184870231 ns/op 1.07
BenchmarkDocument/tree_split_gc_1000 - B/op 222255037 B/op 222250552 B/op 1.00
BenchmarkDocument/tree_split_gc_1000 - allocs/op 122013 allocs/op 121990 allocs/op 1.00
BenchmarkRPC/client_to_server 415396011 ns/op 20418178 B/op 216627 allocs/op 410502490 ns/op 19259706 B/op 216100 allocs/op 1.01
BenchmarkRPC/client_to_server - ns/op 415396011 ns/op 410502490 ns/op 1.01
BenchmarkRPC/client_to_server - B/op 20418178 B/op 19259706 B/op 1.06
BenchmarkRPC/client_to_server - allocs/op 216627 allocs/op 216100 allocs/op 1.00
BenchmarkRPC/client_to_client_via_server 764049301 ns/op 43410636 B/op 454508 allocs/op 755296594 ns/op 40738956 B/op 451943 allocs/op 1.01
BenchmarkRPC/client_to_client_via_server - ns/op 764049301 ns/op 755296594 ns/op 1.01
BenchmarkRPC/client_to_client_via_server - B/op 43410636 B/op 40738956 B/op 1.07
BenchmarkRPC/client_to_client_via_server - allocs/op 454508 allocs/op 451943 allocs/op 1.01
BenchmarkRPC/attach_large_document 1339052352 ns/op 1895746544 B/op 12070 allocs/op 1547858668 ns/op 1922560360 B/op 11926 allocs/op 0.87
BenchmarkRPC/attach_large_document - ns/op 1339052352 ns/op 1547858668 ns/op 0.87
BenchmarkRPC/attach_large_document - B/op 1895746544 B/op 1922560360 B/op 0.99
BenchmarkRPC/attach_large_document - allocs/op 12070 allocs/op 11926 allocs/op 1.01
BenchmarkRPC/adminCli_to_server 526758970 ns/op 35986440 B/op 289719 allocs/op 529972911 ns/op 35993908 B/op 289699 allocs/op 0.99
BenchmarkRPC/adminCli_to_server - ns/op 526758970 ns/op 529972911 ns/op 0.99
BenchmarkRPC/adminCli_to_server - B/op 35986440 B/op 35993908 B/op 1.00
BenchmarkRPC/adminCli_to_server - allocs/op 289719 allocs/op 289699 allocs/op 1.00
BenchmarkLocker 66.55 ns/op 16 B/op 1 allocs/op 65.98 ns/op 16 B/op 1 allocs/op 1.01
BenchmarkLocker - ns/op 66.55 ns/op 65.98 ns/op 1.01
BenchmarkLocker - B/op 16 B/op 16 B/op 1
BenchmarkLocker - allocs/op 1 allocs/op 1 allocs/op 1
BenchmarkLockerParallel 39.18 ns/op 0 B/op 0 allocs/op 39.43 ns/op 0 B/op 0 allocs/op 0.99
BenchmarkLockerParallel - ns/op 39.18 ns/op 39.43 ns/op 0.99
BenchmarkLockerParallel - B/op 0 B/op 0 B/op 1
BenchmarkLockerParallel - allocs/op 0 allocs/op 0 allocs/op 1
BenchmarkLockerMoreKeys 151.7 ns/op 15 B/op 0 allocs/op 149.7 ns/op 15 B/op 0 allocs/op 1.01
BenchmarkLockerMoreKeys - ns/op 151.7 ns/op 149.7 ns/op 1.01
BenchmarkLockerMoreKeys - B/op 15 B/op 15 B/op 1
BenchmarkLockerMoreKeys - allocs/op 0 allocs/op 0 allocs/op 1
BenchmarkChange/Push_10_Changes 4376340 ns/op 150024 B/op 1575 allocs/op 4411068 ns/op 149656 B/op 1575 allocs/op 0.99
BenchmarkChange/Push_10_Changes - ns/op 4376340 ns/op 4411068 ns/op 0.99
BenchmarkChange/Push_10_Changes - B/op 150024 B/op 149656 B/op 1.00
BenchmarkChange/Push_10_Changes - allocs/op 1575 allocs/op 1575 allocs/op 1
BenchmarkChange/Push_100_Changes 15730967 ns/op 796247 B/op 8285 allocs/op 16381381 ns/op 791267 B/op 8287 allocs/op 0.96
BenchmarkChange/Push_100_Changes - ns/op 15730967 ns/op 16381381 ns/op 0.96
BenchmarkChange/Push_100_Changes - B/op 796247 B/op 791267 B/op 1.01
BenchmarkChange/Push_100_Changes - allocs/op 8285 allocs/op 8287 allocs/op 1.00
BenchmarkChange/Push_1000_Changes 125644858 ns/op 7122171 B/op 77294 allocs/op 128887322 ns/op 7006741 B/op 77296 allocs/op 0.97
BenchmarkChange/Push_1000_Changes - ns/op 125644858 ns/op 128887322 ns/op 0.97
BenchmarkChange/Push_1000_Changes - B/op 7122171 B/op 7006741 B/op 1.02
BenchmarkChange/Push_1000_Changes - allocs/op 77294 allocs/op 77296 allocs/op 1.00
BenchmarkChange/Pull_10_Changes 3614331 ns/op 124046 B/op 1406 allocs/op 3643054 ns/op 123773 B/op 1406 allocs/op 0.99
BenchmarkChange/Pull_10_Changes - ns/op 3614331 ns/op 3643054 ns/op 0.99
BenchmarkChange/Pull_10_Changes - B/op 124046 B/op 123773 B/op 1.00
BenchmarkChange/Pull_10_Changes - allocs/op 1406 allocs/op 1406 allocs/op 1
BenchmarkChange/Pull_100_Changes 5215697 ns/op 352687 B/op 5040 allocs/op 5231054 ns/op 352117 B/op 5040 allocs/op 1.00
BenchmarkChange/Pull_100_Changes - ns/op 5215697 ns/op 5231054 ns/op 1.00
BenchmarkChange/Pull_100_Changes - B/op 352687 B/op 352117 B/op 1.00
BenchmarkChange/Pull_100_Changes - allocs/op 5040 allocs/op 5040 allocs/op 1
BenchmarkChange/Pull_1000_Changes 10490679 ns/op 2227031 B/op 43656 allocs/op 10802458 ns/op 2228752 B/op 43654 allocs/op 0.97
BenchmarkChange/Pull_1000_Changes - ns/op 10490679 ns/op 10802458 ns/op 0.97
BenchmarkChange/Pull_1000_Changes - B/op 2227031 B/op 2228752 B/op 1.00
BenchmarkChange/Pull_1000_Changes - allocs/op 43656 allocs/op 43654 allocs/op 1.00
BenchmarkSnapshot/Push_3KB_snapshot 18040406 ns/op 915851 B/op 8288 allocs/op 18050768 ns/op 912588 B/op 8287 allocs/op 1.00
BenchmarkSnapshot/Push_3KB_snapshot - ns/op 18040406 ns/op 18050768 ns/op 1.00
BenchmarkSnapshot/Push_3KB_snapshot - B/op 915851 B/op 912588 B/op 1.00
BenchmarkSnapshot/Push_3KB_snapshot - allocs/op 8288 allocs/op 8287 allocs/op 1.00
BenchmarkSnapshot/Push_30KB_snapshot 130314584 ns/op 8125777 B/op 86568 allocs/op 130591981 ns/op 8241350 B/op 86795 allocs/op 1.00
BenchmarkSnapshot/Push_30KB_snapshot - ns/op 130314584 ns/op 130591981 ns/op 1.00
BenchmarkSnapshot/Push_30KB_snapshot - B/op 8125777 B/op 8241350 B/op 0.99
BenchmarkSnapshot/Push_30KB_snapshot - allocs/op 86568 allocs/op 86795 allocs/op 1.00
BenchmarkSnapshot/Pull_3KB_snapshot 7427286 ns/op 1142089 B/op 19606 allocs/op 7340579 ns/op 1141689 B/op 19605 allocs/op 1.01
BenchmarkSnapshot/Pull_3KB_snapshot - ns/op 7427286 ns/op 7340579 ns/op 1.01
BenchmarkSnapshot/Pull_3KB_snapshot - B/op 1142089 B/op 1141689 B/op 1.00
BenchmarkSnapshot/Pull_3KB_snapshot - allocs/op 19606 allocs/op 19605 allocs/op 1.00
BenchmarkSnapshot/Pull_30KB_snapshot 19591926 ns/op 9336673 B/op 189551 allocs/op 19650276 ns/op 9344888 B/op 189559 allocs/op 1.00
BenchmarkSnapshot/Pull_30KB_snapshot - ns/op 19591926 ns/op 19650276 ns/op 1.00
BenchmarkSnapshot/Pull_30KB_snapshot - B/op 9336673 B/op 9344888 B/op 1.00
BenchmarkSnapshot/Pull_30KB_snapshot - allocs/op 189551 allocs/op 189559 allocs/op 1.00
BenchmarkSplayTree/stress_test_100000 0.1948 ns/op 0 B/op 0 allocs/op 0.2018 ns/op 0 B/op 0 allocs/op 0.97
BenchmarkSplayTree/stress_test_100000 - ns/op 0.1948 ns/op 0.2018 ns/op 0.97
BenchmarkSplayTree/stress_test_100000 - B/op 0 B/op 0 B/op 1
BenchmarkSplayTree/stress_test_100000 - allocs/op 0 allocs/op 0 allocs/op 1
BenchmarkSplayTree/stress_test_200000 0.3988 ns/op 0 B/op 0 allocs/op 0.416 ns/op 0 B/op 0 allocs/op 0.96
BenchmarkSplayTree/stress_test_200000 - ns/op 0.3988 ns/op 0.416 ns/op 0.96
BenchmarkSplayTree/stress_test_200000 - B/op 0 B/op 0 B/op 1
BenchmarkSplayTree/stress_test_200000 - allocs/op 0 allocs/op 0 allocs/op 1
BenchmarkSplayTree/stress_test_300000 0.5959 ns/op 0 B/op 0 allocs/op 0.5706 ns/op 0 B/op 0 allocs/op 1.04
BenchmarkSplayTree/stress_test_300000 - ns/op 0.5959 ns/op 0.5706 ns/op 1.04
BenchmarkSplayTree/stress_test_300000 - B/op 0 B/op 0 B/op 1
BenchmarkSplayTree/stress_test_300000 - allocs/op 0 allocs/op 0 allocs/op 1
BenchmarkSplayTree/random_access_100000 0.01266 ns/op 0 B/op 0 allocs/op 0.01297 ns/op 0 B/op 0 allocs/op 0.98
BenchmarkSplayTree/random_access_100000 - ns/op 0.01266 ns/op 0.01297 ns/op 0.98
BenchmarkSplayTree/random_access_100000 - B/op 0 B/op 0 B/op 1
BenchmarkSplayTree/random_access_100000 - allocs/op 0 allocs/op 0 allocs/op 1
BenchmarkSplayTree/random_access_200000 0.03426 ns/op 0 B/op 0 allocs/op 0.03026 ns/op 0 B/op 0 allocs/op 1.13
BenchmarkSplayTree/random_access_200000 - ns/op 0.03426 ns/op 0.03026 ns/op 1.13
BenchmarkSplayTree/random_access_200000 - B/op 0 B/op 0 B/op 1
BenchmarkSplayTree/random_access_200000 - allocs/op 0 allocs/op 0 allocs/op 1
BenchmarkSplayTree/random_access_300000 0.04312 ns/op 0 B/op 0 allocs/op 0.04509 ns/op 0 B/op 0 allocs/op 0.96
BenchmarkSplayTree/random_access_300000 - ns/op 0.04312 ns/op 0.04509 ns/op 0.96
BenchmarkSplayTree/random_access_300000 - B/op 0 B/op 0 B/op 1
BenchmarkSplayTree/random_access_300000 - allocs/op 0 allocs/op 0 allocs/op 1
BenchmarkSplayTree/editing_trace_bench 0.001782 ns/op 0 B/op 0 allocs/op 0.002151 ns/op 0 B/op 0 allocs/op 0.83
BenchmarkSplayTree/editing_trace_bench - ns/op 0.001782 ns/op 0.002151 ns/op 0.83
BenchmarkSplayTree/editing_trace_bench - B/op 0 B/op 0 B/op 1
BenchmarkSplayTree/editing_trace_bench - allocs/op 0 allocs/op 0 allocs/op 1
BenchmarkSync/memory_sync_10_test 8472 ns/op 3765 B/op 69 allocs/op 8561 ns/op 3765 B/op 69 allocs/op 0.99
BenchmarkSync/memory_sync_10_test - ns/op 8472 ns/op 8561 ns/op 0.99
BenchmarkSync/memory_sync_10_test - B/op 3765 B/op 3765 B/op 1
BenchmarkSync/memory_sync_10_test - allocs/op 69 allocs/op 69 allocs/op 1
BenchmarkSync/memory_sync_100_test 54485 ns/op 11118 B/op 303 allocs/op 54603 ns/op 11122 B/op 304 allocs/op 1.00
BenchmarkSync/memory_sync_100_test - ns/op 54485 ns/op 54603 ns/op 1.00
BenchmarkSync/memory_sync_100_test - B/op 11118 B/op 11122 B/op 1.00
BenchmarkSync/memory_sync_100_test - allocs/op 303 allocs/op 304 allocs/op 1.00
BenchmarkSync/memory_sync_1000_test 587666 ns/op 77120 B/op 2157 allocs/op 597495 ns/op 76943 B/op 2143 allocs/op 0.98
BenchmarkSync/memory_sync_1000_test - ns/op 587666 ns/op 597495 ns/op 0.98
BenchmarkSync/memory_sync_1000_test - B/op 77120 B/op 76943 B/op 1.00
BenchmarkSync/memory_sync_1000_test - allocs/op 2157 allocs/op 2143 allocs/op 1.01
BenchmarkSync/memory_sync_10000_test 7213530 ns/op 757234 B/op 20603 allocs/op 7825106 ns/op 761227 B/op 20456 allocs/op 0.92
BenchmarkSync/memory_sync_10000_test - ns/op 7213530 ns/op 7825106 ns/op 0.92
BenchmarkSync/memory_sync_10000_test - B/op 757234 B/op 761227 B/op 0.99
BenchmarkSync/memory_sync_10000_test - allocs/op 20603 allocs/op 20456 allocs/op 1.01
BenchmarkTextEditing 5281823006 ns/op 3982609408 B/op 20647712 allocs/op 5228174705 ns/op 3982587552 B/op 20647677 allocs/op 1.01
BenchmarkTextEditing - ns/op 5281823006 ns/op 5228174705 ns/op 1.01
BenchmarkTextEditing - B/op 3982609408 B/op 3982587552 B/op 1.00
BenchmarkTextEditing - allocs/op 20647712 allocs/op 20647677 allocs/op 1.00
BenchmarkTree/10000_vertices_to_protobuf 4229838 ns/op 6263012 B/op 70025 allocs/op 4312679 ns/op 6263048 B/op 70025 allocs/op 0.98
BenchmarkTree/10000_vertices_to_protobuf - ns/op 4229838 ns/op 4312679 ns/op 0.98
BenchmarkTree/10000_vertices_to_protobuf - B/op 6263012 B/op 6263048 B/op 1.00
BenchmarkTree/10000_vertices_to_protobuf - allocs/op 70025 allocs/op 70025 allocs/op 1
BenchmarkTree/10000_vertices_from_protobuf 219718658 ns/op 442173636 B/op 290039 allocs/op 227543641 ns/op 442173576 B/op 290039 allocs/op 0.97
BenchmarkTree/10000_vertices_from_protobuf - ns/op 219718658 ns/op 227543641 ns/op 0.97
BenchmarkTree/10000_vertices_from_protobuf - B/op 442173636 B/op 442173576 B/op 1.00
BenchmarkTree/10000_vertices_from_protobuf - allocs/op 290039 allocs/op 290039 allocs/op 1
BenchmarkTree/20000_vertices_to_protobuf 9200083 ns/op 12721673 B/op 140028 allocs/op 9205251 ns/op 12722027 B/op 140028 allocs/op 1.00
BenchmarkTree/20000_vertices_to_protobuf - ns/op 9200083 ns/op 9205251 ns/op 1.00
BenchmarkTree/20000_vertices_to_protobuf - B/op 12721673 B/op 12722027 B/op 1.00
BenchmarkTree/20000_vertices_to_protobuf - allocs/op 140028 allocs/op 140028 allocs/op 1
BenchmarkTree/20000_vertices_from_protobuf 841980539 ns/op 1697263580 B/op 580041 allocs/op 880694898 ns/op 1697267684 B/op 580042 allocs/op 0.96
BenchmarkTree/20000_vertices_from_protobuf - ns/op 841980539 ns/op 880694898 ns/op 0.96
BenchmarkTree/20000_vertices_from_protobuf - B/op 1697263580 B/op 1697267684 B/op 1.00
BenchmarkTree/20000_vertices_from_protobuf - allocs/op 580041 allocs/op 580042 allocs/op 1.00
BenchmarkTree/30000_vertices_to_protobuf 14151866 ns/op 19318344 B/op 210030 allocs/op 14343398 ns/op 19318315 B/op 210030 allocs/op 0.99
BenchmarkTree/30000_vertices_to_protobuf - ns/op 14151866 ns/op 14343398 ns/op 0.99
BenchmarkTree/30000_vertices_to_protobuf - B/op 19318344 B/op 19318315 B/op 1.00
BenchmarkTree/30000_vertices_to_protobuf - allocs/op 210030 allocs/op 210030 allocs/op 1
BenchmarkTree/30000_vertices_from_protobuf 1960585477 ns/op 3752048848 B/op 870096 allocs/op 1958465358 ns/op 3752052856 B/op 870136 allocs/op 1.00
BenchmarkTree/30000_vertices_from_protobuf - ns/op 1960585477 ns/op 1958465358 ns/op 1.00
BenchmarkTree/30000_vertices_from_protobuf - B/op 3752048848 B/op 3752052856 B/op 1.00
BenchmarkTree/30000_vertices_from_protobuf - allocs/op 870096 allocs/op 870136 allocs/op 1.00

This comment was automatically generated by workflow using github-action-benchmark.

@hackerwins hackerwins changed the title Fix missing handling for vv related deletion logics Fix invalid version vector check logic for backward compatibility Dec 19, 2024
@hackerwins hackerwins merged commit 3a615c6 into main Dec 19, 2024
5 checks passed
@hackerwins hackerwins deleted the add-missing-vv-features branch December 19, 2024 08:35
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.

3 participants