Solidity revert with custom error explained with example !!

Solidity revert with custom error explained with example !!

Since v0.8.4, Solidity has introduced an additional way to revert a transaction. The new method allows users to define a custom error and pass it while reverting a transaction.

Custom error

Custom errors are defined using the error statement in a syntax similar to events.

error CustomErrorName( **arg1** , **arg2** );

Custom errors can be defined on contract level or file level. It can further used inside methods to revert the transaction as:

revert CustomError( **arg1, arg2** );

Old ways of using revert like revert() and revert(“description”) are still valid but revert with custom error helps in passing dynamic data with the error and is less expensive for contract deployment.

Natspec documentation can be also added to explain the custom errors in contract.

Example

Let’s understand it with a simple example. This contract reverts custom error if value sent in transaction is less than to a preset amount.

// SPDX-License-Identifier: GPL-3.0
pragma solidity ^0.8.4;

/// Invalid balance to transfer. Needed `minRequired` but sent `amount`
/// [@param](http://twitter.com/param) sent sent amount.
/// [@param](http://twitter.com/param) minRequired minimum amount to send.
error InvalidAmount (uint256 sent, uint256 minRequired);

contract TestToken {
    mapping(address => uint) balances;
    uint minRequired;

    constructor (uint256 _minRequired) {
        minRequired = _minRequired;
    }

    function list() public payable {
        uint256 amount = msg.value;
        if (amount < minRequired) {
            revert InvalidAmount({
                sent: amount,
                minRequired: minRequired
            });
        }
        balances[msg.sender] += amount;
    }
}

Demo using Remix

Deploy the contract and run test with a value less that minRequired , Information of custom error will appear in Remix Terminal.

Demo using Hardhat

Put above code in hardhat project’s contracts directory, compile it. Write a script in scripts directory as:

deployAndRun.js

const hre = require("hardhat");

async function main() {

  // We get the contract to deploy

  const CError = await hre.ethers.getContractFactory("CustomError");

  const cerr = await CError.deploy(20);

  await cerr.deployed();

  console.log("CustomError deployed to:", cerr.address);

  await cerr.list({value: 16});

}

main()

.then(() => process.exit(0))

.catch(error => {

console.error(error);

process.exit(1);

});

Run hardhat node and execute script, it shows custom error details as:

% npx hardhat run --network localhost scripts/deployAndRun.js

CustomError deployed to: 0x5FbDB2315678afecb367f032d93F642f64180aa3

ProviderError: Error: VM Exception while processing transaction: reverted with custom error 'InvalidAmount(16, 20)'

DO YOU KNOW: You can also compile and deploy contract to hardhat using Remix IDE. Read about Remix IDE Hardhat Integration.

Thanks for reading !!!

References:

157