Skip to content
This repository has been archived by the owner on Oct 19, 2024. It is now read-only.

feat: add EthEvent proc macro derive support #227

Merged
merged 13 commits into from
Mar 15, 2021

Conversation

mattsse
Copy link
Collaborator

@mattsse mattsse commented Mar 14, 2021

This PR builds on top of #226 with support for deriving custom solidity events

Motivation

This is the first to make working with events more convenient by allowing the user to declare their own types.

Solution

Two new proc macros are introduced:

  • EthAbiType: that automatically derives the Tokenizable and therefor automatically the DeTokenizeable trait for custom structs as long as all members are Tokenizable, see the derive test file for examples.
  • EthEvent: derives the new EthEvent trait, that was introduced based on what is already generated for Event filters at the moment name(), signature(), abi_signature() and derives Tokenizable as well,

Thanks to the sync crate EthEvent tries to derive the ABI from the target rust struct without further information, however this only checks against the names of the types.
For example this is all that is necessary to derive a EthEvent implementation for ABI Event(address,string):

#[derive(Debug, PartialEq, EthEvent)]
pub struct Event {
    old_author: Address,
    new_value: String,
}

Supported are the rust types Address, i<bits>, u<bits>, String, bool, H160, H256, H512, as well as their Vec<> version.
The can_detect_various_event_abi_types test provides a demonstration.

The EthEvent has several attributes:

  • [ethevent(name= "..."]: overrides what is returned as EthEvent::name
  • [ethevent(signature = "66b73eb17a..."]: overrides the EthEvent::signature where the provided signature is a hex string
  • [ethevent(abi = "Event(address,string)"]: overrides the EthEvent::abi_signature

Current limitations:
Deriving automatic types only works for fields of elementary types, because there is currently no way to get the ABI for custom types (e.g. structs that derive EthAbiType) based on their types alone.
This could be mitigated by making the abi_signature a trait constant and computing the ABI for such cases at runtime with static Lazy::.
Due to a limitation in the argument parser introduced in #226 providing an ABI with tuples does not work yet, since a signature of e.g. Event((int,int),address) isn't technically a valid solidity syntax, however support for this could be added to the AbiParser

The derive.rs test provides an overview of the features

@gakonst gakonst self-requested a review March 15, 2021 11:40
Copy link
Owner

@gakonst gakonst left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

We should also implement EthEvent for the generated code in events.rs, but that can be in a separate PR in the future.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants