subql
subql copied to clipboard
[$1200 in SQT] Support custom types in the topic0 encoding
Description
We allow user put event definition in the topic0 filter, and then encode it via keccak256. It worked well except for custom types in the event parameters.
- enum type
- custom struct
Details
We will need to load the abi to understand what kind the custom type is.
- For enum, we need to replace it to uint8
- For struct we need to replace it with nested form of basic type tuples. see here
- For unknown type, we can warn user and exit.
Example
Smart Contract Sample code that shows an enum and struct in events
struct MoreData
{
bytes32 id1;
bytes32 id2;
}
enum DisputeType {
POI,
Query
}
event Deposit(
address indexed _from,
bytes32 indexed _id,
uint _value,
MoreData _moreData
);
event DisputeOpen(
uint256 indexed disputeId,
address fisherman,
address runner,
DisputeType _type
);
A snippet of a subquery manifest with the desired filters
options:
abi: disputeManager
address: '0xd82a8f11645f6FEF2b863CEe19755bA22decD42a'
mapping:
file: ./dist/index.js
handlers:
- handler: handleDisputeOpen
kind: ethereum/LogHandler
filter:
topics:
# DisputeType should be resolved to uint8 before keccak256 encoding
- DisputeOpen(uint256 indexed disputeId, address fisherman, address indexer, DisputeType _type)
- handler: handleDeposit
kind: ethereum/LogHandler
filter:
topics:
# MoreData should be resolved to (bytes32, bytes32) before keccak256 encoding
- Deposit(address indexed _from, bytes32 indexed _id, uint _value, MoreData _moreData)
Other requirements
- Documentation should be updated to include the feature
- Changes should have test coverage of 80% on the relevant code changes
Needs more clarification if we want to add this to developer guild
Hi @jamesbayly, Could you please assign me this task?
@jamesbayly @stwiname
I was checking few ABIs with enum and struct datatypes, it seems these datatypes are already being replaced by uint8 and tuples by default, while the ABI file is generated from smart contracts.
Can we get more details on the requirement, and also if possible please do share contract and ABI with required types?
@AK46rocks i've added an example. Hopefully that clarifies things
@stwiname
After compling the underlying example smart contract code you provided, The ABI file already converts enums to their underlying integer types (e.g., uint8) and structs to tuples of basic types. Therefore, if the ABI file is already providing this conversion, there might be no need to perform additional conversion steps in the code.
//Example Smart Contract Code
struct MoreData
{
bytes32 id1;
bytes32 id2;
}
enum DisputeType {
POI,
Query
}
event Deposit(
address indexed _from,
bytes32 indexed _id,
uint _value,
MoreData _moreData
);
event DisputeOpen(
uint256 indexed disputeId,
address fisherman,
address runner,
DisputeType _type
);
When complied and generated ABI file, output is coming as follows
handlers:
- handler: handleDisputeOpen
kind: ethereum/LogHandler
filter:
topics:
-DisputeOpen(uint256,address,address,uint8)
- handler: handleDeposit
kind: ethereum/LogHandler
filter:
topics:
-Deposit(address,bytes32,uint256,(bytes32,bytes32))
@AK46rocks the handler should be like in the example i provided, not the resolved types. It should resolve them at runtime when indexing.
Are you using the CLI to generate/update projects through adding ABIs? Thats not what this task is about. Its for manually defined handlers and a runtime feature not a codegen feature
@stwiname For better understanding, Can we schedule a call?
Hi @stwiname, We are currently very busy and will need to postpone this task. If someone else is available to take it up, that would be greatly appreciated. Apologies for the inconvenience.
Thank you!