suiboxer.xyz

Why your sui programmable transaction block failed with executionerror

If a Sui Programmable Transaction Block (PTB) fails, the error ExecutionError is the generic wrapper Sui returns when a command inside the block cannot complete. It is not a single, specific fault; it is the network's way of saying "one of the steps you requested violated the rules of the move function, the object graph, or the gas schedule." The answer to why it failed is almost always found in the error's nested ExecutionFailureStatus, which contains the precise reason. You fix it by reading that inner status, identifying which command in the block triggered it, and correcting the move call, the object reference, or the input value.

What an executionerror actually tells you

A PTB is a list of commands: move calls, split or merge operations, transfers, or even other PTBs. The Sui validator processes these commands in sequence, but it does not necessarily execute them one at a time. Instead, it checks the entire block for validity against the current state, then simulates or executes it. When something fails, the client SDK (Rust, TypeScript, or the CLI) surfaces an ExecutionError object.

That object has two parts of interest:

The ExecutionFailureStatus is an enum with dozens of variants. Common ones include:

Your first step, always, is to print the full error object. Do not rely on the top-level message. The CLI does this when you add --json. In TypeScript, log the effects field. The inner status is the actual diagnosis.

Step-by-Step: reading the failure

  1. Reproduce the failure with full output. Run the transaction again with sui client call or sui client ptb and add --json (or --dump for the CLI). Capture the entire error object.

  2. Locate ExecutionFailureStatus. In the JSON, find "status": {"ExecutionError": {"error": ...}}. The error field contains the variant.

  3. Find the command_index. The error object usually includes a command_index field. This tells you which command in your PTB (0-based) failed. If you built the PTB programmatically, this maps directly to the order you added commands.

  4. Look for nested details. For MoveAbort, you will see a MoveLocation (the module, function, and bytecode offset) and a MoveAbortCode. For object errors, you will see an ObjectID or ObjectVersion. For gas errors, you will see the balance and required cost.

  5. Fix the root cause, not the symptom. The most common causes are: passing an object by value when it was already used (moved) earlier in the block; referencing an object version that no longer exists (often because a previous command in the same block created or mutated it); passing a Coin object that does not have enough balance for a split or transfer; or calling a function with an argument that violates an assertion in the Move code.

The three most common root causes

1. Object Version or ID Mismatch

Sui objects are immutable references to a specific version. If you fetch an object, then a previous command in the same PTB mutates or transfers that object, the later command that references the old version will fail with ObjectFetcherObjectNotExist or ObjectReadError. This is not a race condition; it is the system correctly refusing to let you use a stale reference.

Fix: Fetch the object again after the mutation, or restructure the PTB so you do not need the old version. For example, if you split a coin and then want to use the original coin, you must use the version returned from the split command, not the one you fetched before the PTB started.

2. MoveAbort with a Non-Zero Code

A MoveAbort means the Move function you called hit an abort statement. The code is a u64 that the module's author defined. It is not a Sui error; it is an application-level error. For example, a DEX might abort with code 1 for "insufficient liquidity" and code 2 for "slippage too high".

Fix: Look up the abort code in the module's documentation or source. If the module is on-chain, you can sui client call the move view function if the author exposes one, or read the module's bytecode with sui move disassemble (requires the package source). A common cause is passing a value of zero where the function requires a positive integer, or passing a list that is empty.

3. Gas and Coin Balance Issues

InsufficientGas is straightforward: the PTB ran out of gas. But a subtler failure is CoinBalanceOverflow or CoinDenyList errors. If you are splitting a coin, the total of all splits must equal the original balance. If you try to split a coin into amounts that sum to more than the balance, you get a failure.

Fix: For gas, increase the gas_budget (not the coin value) and retry. For split errors, check your arithmetic. For CoinDenyList, the coin you are using is on a deny list for the specific address or the network; this is rare but possible on Sui testnets.

When the Error Is Not in the Status

Sometimes the ExecutionError is not a failure of your commands but of the transaction itself. For example:

For these, check the network's current gas parameters and your sender's ownership. The fix is usually to resubmit with a different gas object or price.

A worked example (pseudocode)

Assume you have a PTB that does the following:

1. Call `balance_of(account)` -> returns a coin.
2. Split that coin into two.
3. Transfer one split to address A.
4. Transfer the other split to address B.

If step 2 fails, the error will say MoveAbort or CoinBalanceOverflow. If step 3 fails because the coin was already transferred in step 2, you will see ObjectNotTransferable or ObjectUsed. The command index will point to step 3, but the fix is to realize you transferred the original object, not a copy.

Practical Checklist

The Sui documentation on PTB commands and the sui-errors crate (in Rust) list all possible statuses. Reading those two pages will resolve most of your issues faster than trial and error.

Not financial advice. suiboxer.xyz publishes market data and general information about digital assets. Crypto assets are volatile and you can lose everything you put in. Nothing here is a recommendation to buy, sell or hold, and we make no price predictions.

Prices are sourced from third parties and may be delayed or wrong. Verify anything you intend to act on against a primary source.

Back to sui & aptos