1

I'm a bit new to the Solidity-thing and am asking myself the question what to do with functions that specify a certain (set of) return parameter(s) and then fail to compute/find the desired return value(s).

In Java etc, I'd return a null at this point or throw an Exception. Yet apparently, returning null is not an option in Solidity and Exceptions are only doable via revert().

Assume we have a struct and a mapping defined as follows

struct MyStruct(int x);

mapping (address => MyStruct) private;

and my function wants to return the data stored in the mapping for the requester's address - only if it is in the mapping. Now, in case this function would not have the requested data it would have to return an error or a null. In solidity, I see these two approaches to handle a case like this:

  1. Create an empty struct object to return. Bad practice, I would say.

  2. Use revert() to cancel further execution of the contract's code. Sounds reasonable as unnecessary Gas is not burnt. Anyhow, causes an error that needs to be caught and handled by the client logic.

Is there a more elegant way to do this?

1

In a mapping all entries always exists. The uintXXX/intXXX/bytesXX fields are zeros, strings and arrays fields are empty, bool fields are false, etc.

If you have mapping (address => MyStruct) private infos then infos[myAddress] will never fail, it will always return a MyStruct.

For cases where it is important that distinction it is common to add a boolean field or use another field for such purpose, an address for example.

pragma solidity >=0.4.21 <0.8;
pragma experimental ABIEncoderV2;

contract Test {
    struct MyStruct {
        uint256 amount;
        address user;
        bool initialized;
    }

    mapping (address => MyStruct) private infos;

    function getStruct(address user) public view returns (MyStruct memory) {
        MyStruct memory myStruct = infos[user];
        require(myStruct.initialized, "! initialized");

        return myStruct;
    }
}
2

Returning entire structures is not supported in "classic" solidity. You can pass the structure component by elements. In this case, if there is no value in the mapping, the value 0x00 will be returned to the place of the corresponding element.

pragma solidity >=0.5.8 <0.6.0;

contract Test
{
    struct DataRow
    {
      bytes32  name ;
      uint256  value ;
    }

    mapping (bytes32 => DataRow)  Data ;

//
   constructor() public
   {
   }
// 
   function ProcessData(bytes32  idx_) public
   {
      bytes32  name ;
      uint256  x ;

              (name, x)=GetData(idx_) ;

      if(name==bytes32(0x00))
      {
        //  Данных нет
      } 
   }
//
    function GetData(bytes32  idx_) public view returns (bytes32, uint256 retVal)
    {
       return(Data[idx_].name, Data[idx_].value) ;
    }

}

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.