How to Expose Enum in Solidity Contracts

eventssolidity

If you create a contract with a function like:

contract MyContract {
  enum MyEnum { Foo, Bar }
  event ThingHappened(MyEnum indexed _e)
  function foo(MyEnum _e) {
    // Code, code code...
  }
}

Solidity compiles that enum variable type down an int8 (unless the enum has more than 8 options, in which case it walks up the int type scale), but that simply changes the signature of the foo function to be:

function foo(int8 _e)

and the event to be:

event ThingHappened(int8 indexed _e)

I'm not seeing a spelling out in the generated ABI JSON somewhere that spells out which int value goes with which enum value (e.g. 0 = Foo, 1 = Bar, etc.).

How best should contracts handle accepting an enum as an argument, or having an enum in an event, to share with the world what those integer values map to?

Best Answer

You can create some getters to return the string representations of your enum.

Example:

contract MyContract {
  enum MyEnum { Foo, Bar }

  event ThingHappened(string _e);

  function getMyEnumKeys() public constant returns (string, string) {
    return ("Foo", "Bar");
  }

  function getMyEnumKeyByValue (MyEnum myEnum) public constant returns (string) {
    if (MyEnum.Foo == myEnum) return "Foo";
    if (MyEnum.Bar == myEnum) return "Bar";
    return "";
  }

  function getMyEnumValueByKey (string myEnum) external constant returns (MyEnum) {
    if (sha3(myEnum) == sha3("Foo")) return MyEnum.Foo;
    if (sha3(myEnum) == sha3("Bar")) return MyEnum.Bar;
    revert();
  }

  function foo(string _e) {
    MyEnum myEnum = getMyEnumValueByKey(_e);
    // do something with myEnum
    ThingHappened(_e);
  }
}

However, I think the best solution would be to just have it in your public documentation that Foo is 0 and Bar is 1.

Related Topic