Skip to content

feat(splitter): implement bounded cascade distribution helper - #275

Closed
Opulencechuks wants to merge 4 commits into
tributary-protocol:mainfrom
Opulencechuks:main
Closed

feat(splitter): implement bounded cascade distribution helper#275
Opulencechuks wants to merge 4 commits into
tributary-protocol:mainfrom
Opulencechuks:main

Conversation

@Opulencechuks

Copy link
Copy Markdown
Contributor

Closes #49

Pull Request Description

Draining a nested split tree currently needs one distribute call per node. This change introduces a distribute_cascade function that distributes a parent split and recursively distributes any freshly-credited direct children (and their children, etc.) in a single call.

The cascade is bounded by a max_depth parameter up to MAX_CASCADE_DEPTH (5) to protect against Soroban gas limit exhaustion.

A private helper distribute_node is extracted to reuse the balance-draining logic. Unit tests cover a two-level tree, depth bounds, and maximum depth limits.

What this changes

  • Refactoring & Helpers: Extracted the core balance-draining logic into a private distribute_node function. Added a recursive helper distribute_recursive.
  • New API Endpoint: Implemented distribute_cascade(env: Env, id: u64, token: Address, max_depth: u32) -> Result<i128, Error> on the Splitter contract.
  • Constant Depth Bound: Added MAX_CASCADE_DEPTH (5) to limit the recursion and prevent stack/gas exhaustion.
  • Typed Error: Added a new typed error Error::MaxDepthExceeded (Code 13) when the specified recursion depth exceeds the allowed maximum.
  • Comprehensive Tests: Added unit tests covering basic two-level cascade routing, depth-0 boundary behavior, and max depth limits validation.

Why
Draining nested split trees previously required a separate external distribute invocation for each individual node in the tree. This cascade helper improves UX by allowing client applications to route and drain multiple levels of a tree in a single, atomic on-chain call.

Checklist

  • cargo fmt --all and cargo clippy --all-targets -- -D warnings pass
  • cargo test passes
  • New behavior has tests
  • Linked issue, if there is one

Draining a nested split tree currently needs one distribute call per node.
This change introduces a `distribute_cascade` function that distributes a
parent split and recursively distributes any freshly-credited direct children
(and their children, etc.) in a single call.

The cascade is bounded by a `max_depth` parameter up to `MAX_CASCADE_DEPTH` (5)
to protect against Soroban gas limit exhaustion.

A private helper `distribute_node` is extracted to reuse the balance-draining
logic. Unit tests cover a two-level tree, depth bounds, and maximum depth limits.
@Spagero763

Copy link
Copy Markdown
Contributor

@Opulencechuks kindly resolve conflicts

@Spagero763 Spagero763 mentioned this pull request Jul 20, 2026
4 tasks
@Spagero763

Copy link
Copy Markdown
Contributor

Heads up: this looks like the same feature as #284 (both titled "implement bounded cascade distribution helper"), and equivalent functionality (distribute_cascade / distribute_all_tokens) already merged to main via #285. Your contract build is also failing on a missing Error::NoPendingTransfer variant, a side effect of that merge renumbering the error enum. Given the feature's already on main, you may want to check #285 and either close this or find something additive on top of it rather than fixing the compile error.

@Spagero763

Copy link
Copy Markdown
Contributor

Closing as duplicate/redundant — distribute_cascade already shipped via #285 (closing #49). Thanks for the contribution, but this PR's diff would now conflict with the existing implementation. Feel free to pick up something else from the open issues.

@Spagero763 Spagero763 closed this Jul 30, 2026
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.

Add distribute_all to cascade through nested child splits

2 participants