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

Add transparent multicall middleware #2684

Open
wants to merge 31 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
31 commits
Select commit Hold shift + click to select a range
a862354
Add skeleton of multicall middleware
yorhodes Nov 22, 2023
5a35009
Add vector of callbacks
yorhodes Nov 22, 2023
10fc677
Add another TODO for ABI support
yorhodes Nov 22, 2023
d93a521
Use non-blocking mpsc try_recv
yorhodes Nov 22, 2023
7373531
Fix build
yorhodes Nov 23, 2023
f044444
Add skeleton of test
yorhodes Nov 23, 2023
eba790b
Succesfully deploy multicall to anvil in tests
yorhodes Nov 23, 2023
12ec70c
Add some working tests
yorhodes Nov 23, 2023
7aac46f
Some cleanup
yorhodes Nov 23, 2023
4b5c39b
Improve error handling
yorhodes Nov 23, 2023
51a8672
Add get_block_number and get_balance
yorhodes Nov 24, 2023
a23aaed
Improve blocking logic of processor
yorhodes Nov 24, 2023
a8aa1b0
Test new endpoints
yorhodes Nov 24, 2023
ad69c2a
Reuse call_from_tx helper
yorhodes Nov 24, 2023
a2cd445
Reuse multicall ABI matching
yorhodes Nov 24, 2023
b2ba459
Reuse call in block and balance middlewares
yorhodes Nov 24, 2023
35117d2
Restore changes to base contract
yorhodes Nov 25, 2023
d80349b
Improve error handling and unit tests
yorhodes Nov 26, 2023
52390ae
Fix compiler warnings
yorhodes Nov 26, 2023
23e2f53
Fix clippy
yorhodes Nov 27, 2023
e57fe64
Fix doc
yorhodes Nov 27, 2023
21cd2cb
Fix cargo fmt
yorhodes Nov 27, 2023
0e57f5e
Fix wasm target compilation
yorhodes Nov 27, 2023
207682f
Fix cargo fmt with nightly
yorhodes Nov 27, 2023
cfe476e
Merge branch 'master' into multicall-middleware
yorhodes Nov 29, 2023
4c1e2a7
Address pr comments
yorhodes Nov 29, 2023
58b6e25
Disable celo feature for multicall it tests
yorhodes Nov 30, 2023
9bffd32
Derive Eq for MockParams
yorhodes Nov 30, 2023
8196ce2
Update multicall.rs
yorhodes Dec 4, 2023
59270a6
Update multicall.rs
yorhodes Dec 4, 2023
e461b53
rustfmt
mattsse Dec 5, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion ethers-contract/src/base.rs
Original file line number Diff line number Diff line change
Expand Up @@ -200,7 +200,8 @@ impl BaseContract {
decode_function_data_raw(function, bytes, false)
}

fn get_fn_from_input(&self, input: &[u8]) -> Result<&Function, AbiError> {
/// Returns the function from the input bytes (useful for going from tx.data to function)
pub fn get_fn_from_input(&self, input: &[u8]) -> Result<&Function, AbiError> {
let sig: [u8; 4] = input
.get(0..4)
.ok_or(AbiError::WrongSelector)?
Expand Down
24 changes: 24 additions & 0 deletions ethers-contract/src/call.rs
Original file line number Diff line number Diff line change
Expand Up @@ -176,6 +176,30 @@ pub struct FunctionCall<B, M, D> {
pub(crate) _m: PhantomData<M>,
}

impl<B, M, D> FunctionCall<B, M, D>
where
B: Borrow<M>,
M: Middleware,
D: Detokenize,
{
/// Creates a new function call object
pub fn new(
tx: TypedTransaction,
function: Function,
client: B,
block: Option<BlockId>,
) -> Self {
Self {
tx,
function,
client,
block,
datatype: PhantomData,
_m: PhantomData,
}
}
}

impl<B, M, D> Clone for FunctionCall<B, M, D>
where
B: Clone,
Expand Down
2 changes: 1 addition & 1 deletion ethers-contract/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ pub mod stream;

#[cfg(feature = "abigen")]
#[cfg_attr(docsrs, doc(cfg(feature = "abigen")))]
mod multicall;
pub mod multicall;
#[cfg(feature = "abigen")]
#[cfg_attr(docsrs, doc(cfg(feature = "abigen")))]
pub use multicall::{
Expand Down
9 changes: 9 additions & 0 deletions ethers-contract/src/multicall/constants.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,14 @@
use ethers_core::types::{Chain, H160};

/// presigned tx that will deploy multicall3
pub const SIGNED_DEPLOY_MULTICALL_TX: &str = "0xf90f538085174876e800830f42408080b90f00608060405234801561001057600080fd5b50610ee0806100206000396000f3fe6080604052600436106100f35760003560e01c80634d2301cc1161008a578063a8b0574e11610059578063a8b0574e1461025a578063bce38bd714610275578063c3077fa914610288578063ee82ac5e1461029b57600080fd5b80634d2301cc146101ec57806372425d9d1461022157806382ad56cb1461023457806386d516e81461024757600080fd5b80633408e470116100c65780633408e47014610191578063399542e9146101a45780633e64a696146101c657806342cbb15c146101d957600080fd5b80630f28c97d146100f8578063174dea711461011a578063252dba421461013a57806327e86d6e1461015b575b600080fd5b34801561010457600080fd5b50425b6040519081526020015b60405180910390f35b61012d610128366004610a85565b6102ba565b6040516101119190610bbe565b61014d610148366004610a85565b6104ef565b604051610111929190610bd8565b34801561016757600080fd5b50437fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0140610107565b34801561019d57600080fd5b5046610107565b6101b76101b2366004610c60565b610690565b60405161011193929190610cba565b3480156101d257600080fd5b5048610107565b3480156101e557600080fd5b5043610107565b3480156101f857600080fd5b50610107610207366004610ce2565b73ffffffffffffffffffffffffffffffffffffffff163190565b34801561022d57600080fd5b5044610107565b61012d610242366004610a85565b6106ab565b34801561025357600080fd5b5045610107565b34801561026657600080fd5b50604051418152602001610111565b61012d610283366004610c60565b61085a565b6101b7610296366004610a85565b610a1a565b3480156102a757600080fd5b506101076102b6366004610d18565b4090565b60606000828067ffffffffffffffff8111156102d8576102d8610d31565b60405190808252806020026020018201604052801561031e57816020015b6040805180820190915260008152606060208201528152602001906001900390816102f65790505b5092503660005b8281101561047757600085828151811061034157610341610d60565b6020026020010151905087878381811061035d5761035d610d60565b905060200281019061036f9190610d8f565b6040810135958601959093506103886020850185610ce2565b73ffffffffffffffffffffffffffffffffffffffff16816103ac6060870187610dcd565b6040516103ba929190610e32565b60006040518083038185875af1925050503d80600081146103f7576040519150601f19603f3d011682016040523d82523d6000602084013e6103fc565b606091505b50602080850191909152901515808452908501351761046d577f08c379a000000000000000000000000000000000000000000000000000000000600052602060045260176024527f4d756c746963616c6c333a2063616c6c206661696c656400000000000000000060445260846000fd5b5050600101610325565b508234146104e6576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601a60248201527f4d756c746963616c6c333a2076616c7565206d69736d6174636800000000000060448201526064015b60405180910390fd5b50505092915050565b436060828067ffffffffffffffff81111561050c5761050c610d31565b60405190808252806020026020018201604052801561053f57816020015b606081526020019060019003908161052a5790505b5091503660005b8281101561068657600087878381811061056257610562610d60565b90506020028101906105749190610e42565b92506105836020840184610ce2565b73ffffffffffffffffffffffffffffffffffffffff166105a66020850185610dcd565b6040516105b4929190610e32565b6000604051808303816000865af19150503d80600081146105f1576040519150601f19603f3d011682016040523d82523d6000602084013e6105f6565b606091505b5086848151811061060957610609610d60565b602090810291909101015290508061067d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601760248201527f4d756c746963616c6c333a2063616c6c206661696c656400000000000000000060448201526064016104dd565b50600101610546565b5050509250929050565b43804060606106a086868661085a565b905093509350939050565b6060818067ffffffffffffffff8111156106c7576106c7610d31565b60405190808252806020026020018201604052801561070d57816020015b6040805180820190915260008152606060208201528152602001906001900390816106e55790505b5091503660005b828110156104e657600084828151811061073057610730610d60565b6020026020010151905086868381811061074c5761074c610d60565b905060200281019061075e9190610e76565b925061076d6020840184610ce2565b73ffffffffffffffffffffffffffffffffffffffff166107906040850185610dcd565b60405161079e929190610e32565b6000604051808303816000865af19150503d80600081146107db576040519150601f19603f3d011682016040523d82523d6000602084013e6107e0565b606091505b506020808401919091529015158083529084013517610851577f08c379a000000000000000000000000000000000000000000000000000000000600052602060045260176024527f4d756c746963616c6c333a2063616c6c206661696c656400000000000000000060445260646000fd5b50600101610714565b6060818067ffffffffffffffff81111561087657610876610d31565b6040519080825280602002602001820160405280156108bc57816020015b6040805180820190915260008152606060208201528152602001906001900390816108945790505b5091503660005b82811015610a105760008482815181106108df576108df610d60565b602002602001015190508686838181106108fb576108fb610d60565b905060200281019061090d9190610e42565b925061091c6020840184610ce2565b73ffffffffffffffffffffffffffffffffffffffff1661093f6020850185610dcd565b60405161094d929190610e32565b6000604051808303816000865af19150503d806000811461098a576040519150601f19603f3d011682016040523d82523d6000602084013e61098f565b606091505b506020830152151581528715610a07578051610a07576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601760248201527f4d756c746963616c6c333a2063616c6c206661696c656400000000000000000060448201526064016104dd565b506001016108c3565b5050509392505050565b6000806060610a2b60018686610690565b919790965090945092505050565b60008083601f840112610a4b57600080fd5b50813567ffffffffffffffff811115610a6357600080fd5b6020830191508360208260051b8501011115610a7e57600080fd5b9250929050565b60008060208385031215610a9857600080fd5b823567ffffffffffffffff811115610aaf57600080fd5b610abb85828601610a39565b90969095509350505050565b6000815180845260005b81811015610aed57602081850181015186830182015201610ad1565b81811115610aff576000602083870101525b50601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169290920160200192915050565b600082825180855260208086019550808260051b84010181860160005b84811015610bb1578583037fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe001895281518051151584528401516040858501819052610b9d81860183610ac7565b9a86019a9450505090830190600101610b4f565b5090979650505050505050565b602081526000610bd16020830184610b32565b9392505050565b600060408201848352602060408185015281855180845260608601915060608160051b870101935082870160005b82811015610c52577fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffa0888703018452610c40868351610ac7565b95509284019290840190600101610c06565b509398975050505050505050565b600080600060408486031215610c7557600080fd5b83358015158114610c8557600080fd5b9250602084013567ffffffffffffffff811115610ca157600080fd5b610cad86828701610a39565b9497909650939450505050565b838152826020820152606060408201526000610cd96060830184610b32565b95945050505050565b600060208284031215610cf457600080fd5b813573ffffffffffffffffffffffffffffffffffffffff81168114610bd157600080fd5b600060208284031215610d2a57600080fd5b5035919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b600082357fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff81833603018112610dc357600080fd5b9190910192915050565b60008083357fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe1843603018112610e0257600080fd5b83018035915067ffffffffffffffff821115610e1d57600080fd5b602001915036819003821315610a7e57600080fd5b8183823760009101908152919050565b600082357fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc1833603018112610dc357600080fd5b600082357fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffa1833603018112610dc357600080fdfea2646970667358221220bb2b5c71a328032f97c676ae39a1ec2148d3e5d6f73d95e9b17910152d61f16264736f6c634300080c00331ca0edce47092c0f398cebf3ffc267f05c8e7076e3b89445e0fe50f6332273d4569ba01b0b9d000e19b24c5869b0fc3b22b0d6fa47cd63316875cbbd577d76e6fde086";

/// address to be funded for `SIGNED_DEPLOY_MULTICALL_TX` to succeed
pub const DEPLOYER_ADDRESS: H160 = H160([
0x05, 0xf3, 0x2B, 0x3c, 0xC3, 0x88, 0x84, 0x53, 0xff, 0x71, 0xB0, 0x11, 0x35, 0xB3, 0x4F, 0xF8,
0xe4, 0x12, 0x63, 0xF2,
]);

/// The Multicall3 contract address that is deployed in [`MULTICALL_SUPPORTED_CHAIN_IDS`]:
/// [`0xcA11bde05977b3631167028862bE2a173976CA11`](https://etherscan.io/address/0xcA11bde05977b3631167028862bE2a173976CA11)
pub const MULTICALL_ADDRESS: H160 = H160([
Expand Down
1 change: 1 addition & 0 deletions ethers-contract/src/multicall/middleware.rs
Original file line number Diff line number Diff line change
Expand Up @@ -202,6 +202,7 @@ impl<M: Middleware> Multicall<M> {
let address: Address = match address {
Some(addr) => addr,
None => {
// TODO: replace with eth_getCode?
let chain_id = client
.get_chainid()
.await
Expand Down
4 changes: 4 additions & 0 deletions ethers-contract/src/multicall/mod.rs
Original file line number Diff line number Diff line change
@@ -1,14 +1,18 @@
//! Contains the `Multicall` contract which enables batching `eth_call` RPC requests

use std::result::Result as StdResult;

/// The Multicall contract bindings. Auto-generated with `abigen`.
pub mod contract;

/// vendored constants from [Multicall repo](https://github.com/mds1/multicall#new-deployments)
pub mod constants;

if_providers! {
mod middleware;
pub use middleware::{Call, Multicall, MulticallContract};

/// The Multicall error types.
pub mod error;
}

Expand Down
2 changes: 2 additions & 0 deletions ethers-middleware/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ For more information, please refer to the [book](https://gakonst.com/ethers-rs).
- [`Transformer`](./transformer/trait.Transformer.html): Allows intercepting and
transforming a transaction to be broadcasted via a proxy wallet, e.g.
[`DSProxy`](./transformer/struct.DsProxy.html).
- [`MultiCall`](./multicall/struct.MulticallMiddleware.html): transparently batches multiple `eth_call` requests into a single
`eth_call` request, reducing the number of round trips to the RPC and saving API CU usage.

## Examples

Expand Down
5 changes: 5 additions & 0 deletions ethers-middleware/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,11 @@ pub use policy::{
pub mod timelag;
pub use timelag::TimeLag;

/// The [MulticallMiddleware] provides a way to batch multiple calls into a single call
pub mod multicall;
#[cfg(not(target_arch = "wasm32"))]
pub use multicall::MulticallMiddleware;

/// [MiddlewareBuilder] provides a way to compose many [`Middleware`]s in a concise way.
pub mod builder;
pub use builder::MiddlewareBuilder;
Expand Down
Loading
Loading