TypeScript SDK
Owned Object Pool
Custom SplitStrategy

Defining a custom SplitStrategy

⚠️

Sui Owned Object Pools (SuiOOP) will likely be replaced by ParallelTransactionExecutor from @mysten/sui/transactions

Sui Owned Object Pools (SuiOOP) is a beta library. Enhancements and changes are likely during development.

The prior example does not define a split strategy explicitly, so it uses the DefaultSplitStrategy.

This default split strategy only selects enough gas coins (coins of type 0x2::coin::Coin<0x2::sui::SUI>) from the mainPool that their sum of balances surpasses a minimum threshold, and creates a new worker pool only containing these gas coins.

It fulfils the minimum requirement needed for a transaction to be executed, as the client should always be able to pay for the gas of the transaction.

However, in more complex scenarios, you might want to define your own split strategy.

Assume that you want to execute multiple transactions that transfer an object of type CapyNFT, each to a different recipient.

For this to work, the ExecutorServiceHandler needs to split the mainPool in a way such that every worker:

  • Contains at least one CapyNFT object.
  • Contains at least a coin (or set of coins) with a total balance enough to pay for the gas of the transaction.

To do this, you have to implement the SplitStrategy interface. In detail:

class MyCustomSplitStrategy implements SplitStrategy {
	private capyIncluded = false;
	private balanceSoFar = 0;
	private readonly minimumBalance;
 
	public pred(obj: PoolObject | undefined) {
		if (!obj) throw new Error('No object found!.');
		// If each requirement is fulfilled then terminate the split by returning null
		// This stops the split process and the worker pool is created
		const terminateWhen = this.balanceSoFar >= this.minimumBalance && this.capyIncluded;
		if (terminateWhen) {
			return null;
		}
		// If a CapyNFT object is not already included, and the object is a CapyNFT, then include it
		if (!capyIncluded && obj.type.includes('CapyNFT')) {
			this.capyIncluded = true;
			return true;
		}
		// If the object is a coin and coins are still needed, then include it to the new pool
		if (this.balanceSoFar >= this.minimumBalance && isCoin(obj.type)) {
			this.balanceSoFar += obj.balance ?? 0;
			return true;
		} else {
			return false;
		}
	}
	// This function is called during the split process to check if the split was successful
	public succeeded() {
		return this.balanceSoFar >= this.minimumBalance && this.adminCapIncluded;
	}
}

You can find more examples of split strategies (including an admin cap inclusion case) in the splitStrategies.ts file (opens in a new tab).