-
-
Notifications
You must be signed in to change notification settings - Fork 7
CosmWasm MsgExecuteContract Indexing Strategy ‐ Pre‐Development
Peter edited this page Jun 27, 2024
·
5 revisions
- Contracts are at known (or discoverable) contract addresses
- Contracts deploy known (or discoverable) code IDs
- Contracts are executed by specifying the contract address in the MsgExecuteContract message type
- Some contract protocols have many contracts deployed on-chain
- Contracts allow executing contract specific behavior through the use of raw contract Msg types
- Contract messages are JSON maps - See the CosmWasm repo README and the docs at this search on the CosmWasm docsite
- Support for CosmWasm MsgExecuteContract indexing in a generalized manner
- Way to register contract specific support for known contract types
- By code ID or;
- By known contract address. Then;
- By contract execution JSON message formats based on contract execution requirements
- Way to check if a contract execution JSON message fits known formats on contract addresses we have not registered
- Either throw warning or fail entire block so we can ensure support is valid
- Contract addresses should be linkable to execution-specific message type handlers that parse the message into taxable data, but generalized enough that the entrypoint does not care what is called
- We will rely on known code IDs and contract addresses to determine parsing requirements
- This will require research and continued development if contracts are continually deployed
- This may be a losing approach if we cannot ensure we have valid contract addresses across the blockchain
- Using contract message fields as the parser finder will be avoided in preference to (1)
- Since its possibly more error prone if contracts share fields
- If the above is determined to be not an issue, the generalization goal should make it easy to switch if needed
- If (1) is not sufficient, it may require (1) and (2) to determine parser
We should add a single entrypoint handler in the cosmwasm
package. We should add registration functionality in the same package. The goal for these will be:
- Registration will happen on application configuration time.
- It will handle registering known, hard-coded contract addresses based on chain ID
- It will handle registering code IDs, which can be used to query for current deployed addresses to register as well
- It will then register types of indexable contract address execution formats
- During indexing, a function will be executed as a single entrypoint for all MsgExecuteContract calls
- It will check the contract address against the known contract addresses
- If a match is found, execute parsers
- If a match is not found, check the execution JSON format against our type registry
- If a type match is found, either:
- Throw an error and fail the entire block, so we can ensure we check the block for support
- Throw a warning
- Possibly create a new table for this specific case so we can save the data but not fail the entire block
- If a type match is not found, do nothing
- If a type match is found, either:
- Early decision needed: Should the entrypoint handle type parsing and calling a subsequent function, or should it be passed down to a contract specific type checker?
These registries will handle identifying known contracts we have specific support for.
- Contract address registry: A map of string keys that can be looked up quickly
- Execution Message Type registry:
- Contract Level: Each contract support will require its own type registry for indexable/non-indexable contract execution message types. These will determine the path for the parser.
- Entrypoint level:
- We may need a type registry at the entrypoint
- This will allow us to check types and throw errors if we see a contract executing where we are not tracking the address properly
- We should consider using json.RawMessage as much as possible to
- Since contracts execution messages are raw JSON, we need either:
- Struct types for deserialization - would make type checks
- Generic JSON parsers and search for fields
For contract support, the goal will be the following:
- Add types for deserializing supported message types
- Add parser support for each supported message type
We will want the type deserialization to be fast and efficient.
There will be a few options, all with potential significant performance impacts due to JSON parsing requirements.
- Most likely inefficiant approaches:
- Attempt to parse the type out into all known types, use the first type match
- For each contract address, build a single type that contains top level fields we care about:
- Either:
- json.RawMessage as values
- Pointers to underlying types as values
- Parse out the type and determine what fields matched
- Use the fields to determine the parser
- Either:
- Using a
map[string]json.RawMessage
- Attempt to make use of more efficient libraries to deal with unmarshalling known data with possible other unknown data
- E.g. marshmallow
We will use one of the naive approaces to determine if the MsgExecuteContract parsing is a performance bottleneck to avoid premature optimization.
Once the underlying contract or type has been determined, we can pass the cosmos message to downstream parsers.