anvil_core/eth/
mod.rs

1use crate::{eth::subscription::SubscriptionId, types::ReorgOptions};
2use alloy_primitives::{Address, B64, B256, Bytes, TxHash, U256};
3use alloy_rpc_types::{
4    BlockId, BlockNumberOrTag as BlockNumber, BlockOverrides, Filter, Index,
5    anvil::{Forking, MineOptions},
6    pubsub::{Params as SubscriptionParams, SubscriptionKind},
7    request::TransactionRequest,
8    simulate::SimulatePayload,
9    state::StateOverride,
10    trace::{
11        filter::TraceFilter,
12        geth::{GethDebugTracingCallOptions, GethDebugTracingOptions},
13    },
14};
15use alloy_serde::WithOtherFields;
16use foundry_common::serde_helpers::{
17    deserialize_number, deserialize_number_opt, deserialize_number_seq,
18};
19
20pub mod block;
21pub mod subscription;
22pub mod transaction;
23pub mod wallet;
24
25pub mod serde_helpers;
26use self::serde_helpers::*;
27
28/// Wrapper type that ensures the type is named `params`
29#[derive(Clone, Debug, PartialEq, Eq, serde::Deserialize)]
30pub struct Params<T: Default> {
31    #[serde(default)]
32    pub params: T,
33}
34
35/// Represents ethereum JSON-RPC API
36#[derive(Clone, Debug, serde::Deserialize)]
37#[serde(tag = "method", content = "params")]
38#[allow(clippy::large_enum_variant)]
39pub enum EthRequest {
40    #[serde(rename = "web3_clientVersion", with = "empty_params")]
41    Web3ClientVersion(()),
42
43    #[serde(rename = "web3_sha3", with = "sequence")]
44    Web3Sha3(Bytes),
45
46    /// Returns the current Ethereum protocol version.
47    #[serde(rename = "eth_protocolVersion", with = "empty_params")]
48    EthProtocolVersion(()),
49
50    #[serde(rename = "eth_chainId", with = "empty_params")]
51    EthChainId(()),
52
53    #[serde(rename = "eth_networkId", alias = "net_version", with = "empty_params")]
54    EthNetworkId(()),
55
56    #[serde(rename = "net_listening", with = "empty_params")]
57    NetListening(()),
58
59    /// Returns the number of hashes per second with which the node is mining.
60    #[serde(rename = "eth_hashrate", with = "empty_params")]
61    EthHashrate(()),
62
63    #[serde(rename = "eth_gasPrice", with = "empty_params")]
64    EthGasPrice(()),
65
66    #[serde(rename = "eth_maxPriorityFeePerGas", with = "empty_params")]
67    EthMaxPriorityFeePerGas(()),
68
69    #[serde(rename = "eth_blobBaseFee", with = "empty_params")]
70    EthBlobBaseFee(()),
71
72    #[serde(rename = "eth_accounts", alias = "eth_requestAccounts", with = "empty_params")]
73    EthAccounts(()),
74
75    #[serde(rename = "eth_blockNumber", with = "empty_params")]
76    EthBlockNumber(()),
77
78    /// Returns the client coinbase address.
79    #[serde(rename = "eth_coinbase", with = "empty_params")]
80    EthCoinbase(()),
81
82    #[serde(rename = "eth_getBalance")]
83    EthGetBalance(Address, Option<BlockId>),
84
85    #[serde(rename = "eth_getAccount")]
86    EthGetAccount(Address, Option<BlockId>),
87
88    #[serde(rename = "eth_getAccountInfo")]
89    EthGetAccountInfo(Address, Option<BlockId>),
90
91    #[serde(rename = "eth_getStorageAt")]
92    EthGetStorageAt(Address, U256, Option<BlockId>),
93
94    #[serde(rename = "eth_getBlockByHash")]
95    EthGetBlockByHash(B256, bool),
96
97    #[serde(rename = "eth_getBlockByNumber")]
98    EthGetBlockByNumber(
99        #[serde(deserialize_with = "lenient_block_number::lenient_block_number")] BlockNumber,
100        bool,
101    ),
102
103    #[serde(rename = "eth_getTransactionCount")]
104    EthGetTransactionCount(Address, Option<BlockId>),
105
106    #[serde(rename = "eth_getBlockTransactionCountByHash", with = "sequence")]
107    EthGetTransactionCountByHash(B256),
108
109    #[serde(
110        rename = "eth_getBlockTransactionCountByNumber",
111        deserialize_with = "lenient_block_number::lenient_block_number_seq"
112    )]
113    EthGetTransactionCountByNumber(BlockNumber),
114
115    #[serde(rename = "eth_getUncleCountByBlockHash", with = "sequence")]
116    EthGetUnclesCountByHash(B256),
117
118    #[serde(
119        rename = "eth_getUncleCountByBlockNumber",
120        deserialize_with = "lenient_block_number::lenient_block_number_seq"
121    )]
122    EthGetUnclesCountByNumber(BlockNumber),
123
124    #[serde(rename = "eth_getCode")]
125    EthGetCodeAt(Address, Option<BlockId>),
126
127    /// Returns the account and storage values of the specified account including the Merkle-proof.
128    /// This call can be used to verify that the data you are pulling from is not tampered with.
129    #[serde(rename = "eth_getProof")]
130    EthGetProof(Address, Vec<B256>, Option<BlockId>),
131
132    /// The sign method calculates an Ethereum specific signature with:
133    #[serde(rename = "eth_sign")]
134    EthSign(Address, Bytes),
135
136    /// The sign method calculates an Ethereum specific signature, equivalent to eth_sign:
137    /// <https://docs.metamask.io/wallet/reference/personal_sign/>
138    #[serde(rename = "personal_sign")]
139    PersonalSign(Bytes, Address),
140
141    #[serde(rename = "eth_signTransaction", with = "sequence")]
142    EthSignTransaction(Box<WithOtherFields<TransactionRequest>>),
143
144    /// Signs data via [EIP-712](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-712.md).
145    #[serde(rename = "eth_signTypedData")]
146    EthSignTypedData(Address, serde_json::Value),
147
148    /// Signs data via [EIP-712](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-712.md).
149    #[serde(rename = "eth_signTypedData_v3")]
150    EthSignTypedDataV3(Address, serde_json::Value),
151
152    /// Signs data via [EIP-712](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-712.md), and includes full support of arrays and recursive data structures.
153    #[serde(rename = "eth_signTypedData_v4")]
154    EthSignTypedDataV4(Address, alloy_dyn_abi::TypedData),
155
156    #[serde(rename = "eth_sendTransaction", with = "sequence")]
157    EthSendTransaction(Box<WithOtherFields<TransactionRequest>>),
158
159    #[serde(rename = "eth_sendTransactionSync", with = "sequence")]
160    EthSendTransactionSync(Box<WithOtherFields<TransactionRequest>>),
161
162    #[serde(rename = "eth_sendRawTransaction", with = "sequence")]
163    EthSendRawTransaction(Bytes),
164
165    #[serde(rename = "eth_sendRawTransactionSync", with = "sequence")]
166    EthSendRawTransactionSync(Bytes),
167
168    #[serde(rename = "eth_call")]
169    EthCall(
170        WithOtherFields<TransactionRequest>,
171        #[serde(default)] Option<BlockId>,
172        #[serde(default)] Option<StateOverride>,
173        #[serde(default)] Option<Box<BlockOverrides>>,
174    ),
175
176    #[serde(rename = "eth_simulateV1")]
177    EthSimulateV1(SimulatePayload, #[serde(default)] Option<BlockId>),
178
179    #[serde(rename = "eth_createAccessList")]
180    EthCreateAccessList(WithOtherFields<TransactionRequest>, #[serde(default)] Option<BlockId>),
181
182    #[serde(rename = "eth_estimateGas")]
183    EthEstimateGas(
184        WithOtherFields<TransactionRequest>,
185        #[serde(default)] Option<BlockId>,
186        #[serde(default)] Option<StateOverride>,
187        #[serde(default)] Option<Box<BlockOverrides>>,
188    ),
189
190    #[serde(rename = "eth_fillTransaction", with = "sequence")]
191    EthFillTransaction(WithOtherFields<TransactionRequest>),
192
193    #[serde(rename = "eth_getTransactionByHash", with = "sequence")]
194    EthGetTransactionByHash(TxHash),
195
196    /// Returns the blob for a given blob versioned hash.
197    #[serde(rename = "anvil_getBlobByHash", with = "sequence")]
198    GetBlobByHash(B256),
199
200    /// Returns the blobs for a given transaction hash.
201    #[serde(rename = "anvil_getBlobsByTransactionHash", with = "sequence")]
202    GetBlobByTransactionHash(TxHash),
203
204    /// Returns the genesis time for the chain
205    #[serde(rename = "anvil_getGenesisTime", with = "empty_params")]
206    GetGenesisTime(()),
207
208    #[serde(rename = "eth_getTransactionByBlockHashAndIndex")]
209    EthGetTransactionByBlockHashAndIndex(B256, Index),
210
211    #[serde(rename = "eth_getTransactionByBlockNumberAndIndex")]
212    EthGetTransactionByBlockNumberAndIndex(BlockNumber, Index),
213
214    #[serde(rename = "eth_getRawTransactionByHash", with = "sequence")]
215    EthGetRawTransactionByHash(TxHash),
216
217    #[serde(rename = "eth_getRawTransactionByBlockHashAndIndex")]
218    EthGetRawTransactionByBlockHashAndIndex(B256, Index),
219
220    #[serde(rename = "eth_getRawTransactionByBlockNumberAndIndex")]
221    EthGetRawTransactionByBlockNumberAndIndex(BlockNumber, Index),
222
223    #[serde(rename = "eth_getTransactionReceipt", with = "sequence")]
224    EthGetTransactionReceipt(B256),
225
226    #[serde(rename = "eth_getBlockReceipts", with = "sequence")]
227    EthGetBlockReceipts(BlockId),
228
229    #[serde(rename = "eth_getUncleByBlockHashAndIndex")]
230    EthGetUncleByBlockHashAndIndex(B256, Index),
231
232    #[serde(rename = "eth_getUncleByBlockNumberAndIndex")]
233    EthGetUncleByBlockNumberAndIndex(
234        #[serde(deserialize_with = "lenient_block_number::lenient_block_number")] BlockNumber,
235        Index,
236    ),
237
238    #[serde(rename = "eth_getLogs", with = "sequence")]
239    EthGetLogs(Filter),
240
241    /// Creates a filter object, based on filter options, to notify when the state changes (logs).
242    #[serde(rename = "eth_newFilter", with = "sequence")]
243    EthNewFilter(Filter),
244
245    /// Polling method for a filter, which returns an array of logs which occurred since last poll.
246    #[serde(rename = "eth_getFilterChanges", with = "sequence")]
247    EthGetFilterChanges(String),
248
249    /// Creates a filter in the node, to notify when a new block arrives.
250    /// To check if the state has changed, call `eth_getFilterChanges`.
251    #[serde(rename = "eth_newBlockFilter", with = "empty_params")]
252    EthNewBlockFilter(()),
253
254    /// Creates a filter in the node, to notify when new pending transactions arrive.
255    /// To check if the state has changed, call `eth_getFilterChanges`.
256    #[serde(rename = "eth_newPendingTransactionFilter", with = "empty_params")]
257    EthNewPendingTransactionFilter(()),
258
259    /// Returns an array of all logs matching filter with given id.
260    #[serde(rename = "eth_getFilterLogs", with = "sequence")]
261    EthGetFilterLogs(String),
262
263    /// Removes the filter, returns true if the filter was installed
264    #[serde(rename = "eth_uninstallFilter", with = "sequence")]
265    EthUninstallFilter(String),
266
267    #[serde(rename = "eth_getWork", with = "empty_params")]
268    EthGetWork(()),
269
270    #[serde(rename = "eth_submitWork")]
271    EthSubmitWork(B64, B256, B256),
272
273    #[serde(rename = "eth_submitHashrate")]
274    EthSubmitHashRate(U256, B256),
275
276    #[serde(rename = "eth_feeHistory")]
277    EthFeeHistory(
278        #[serde(deserialize_with = "deserialize_number")] U256,
279        BlockNumber,
280        #[serde(default)] Vec<f64>,
281    ),
282
283    #[serde(rename = "eth_syncing", with = "empty_params")]
284    EthSyncing(()),
285
286    #[serde(rename = "eth_config", with = "empty_params")]
287    EthConfig(()),
288
289    /// geth's `debug_getRawTransaction`  endpoint
290    #[serde(rename = "debug_getRawTransaction", with = "sequence")]
291    DebugGetRawTransaction(TxHash),
292
293    /// geth's `debug_traceTransaction`  endpoint
294    #[serde(rename = "debug_traceTransaction")]
295    DebugTraceTransaction(B256, #[serde(default)] GethDebugTracingOptions),
296
297    /// geth's `debug_traceCall`  endpoint
298    #[serde(rename = "debug_traceCall")]
299    DebugTraceCall(
300        WithOtherFields<TransactionRequest>,
301        #[serde(default)] Option<BlockId>,
302        #[serde(default)] GethDebugTracingCallOptions,
303    ),
304
305    /// reth's `debug_codeByHash` endpoint
306    #[serde(rename = "debug_codeByHash")]
307    DebugCodeByHash(B256, #[serde(default)] Option<BlockId>),
308
309    /// reth's `debug_dbGet` endpoint
310    #[serde(rename = "debug_dbGet")]
311    DebugDbGet(String),
312
313    /// Trace transaction endpoint for parity's `trace_transaction`
314    #[serde(rename = "trace_transaction", with = "sequence")]
315    TraceTransaction(B256),
316
317    /// Trace transaction endpoint for parity's `trace_block`
318    #[serde(
319        rename = "trace_block",
320        deserialize_with = "lenient_block_number::lenient_block_number_seq"
321    )]
322    TraceBlock(BlockNumber),
323
324    // Return filtered traces over blocks
325    #[serde(rename = "trace_filter", with = "sequence")]
326    TraceFilter(TraceFilter),
327
328    // Custom endpoints, they're not extracted to a separate type out of serde convenience
329    /// send transactions impersonating specific account and contract addresses.
330    #[serde(
331        rename = "anvil_impersonateAccount",
332        alias = "hardhat_impersonateAccount",
333        with = "sequence"
334    )]
335    ImpersonateAccount(Address),
336    /// Stops impersonating an account if previously set with `anvil_impersonateAccount`
337    #[serde(
338        rename = "anvil_stopImpersonatingAccount",
339        alias = "hardhat_stopImpersonatingAccount",
340        with = "sequence"
341    )]
342    StopImpersonatingAccount(Address),
343    /// Will make every account impersonated
344    #[serde(
345        rename = "anvil_autoImpersonateAccount",
346        alias = "hardhat_autoImpersonateAccount",
347        with = "sequence"
348    )]
349    AutoImpersonateAccount(bool),
350
351    /// Registers a signature/address pair for faking `ecrecover` results
352    #[serde(rename = "anvil_impersonateSignature", with = "sequence")]
353    ImpersonateSignature(Bytes, Address),
354
355    /// Returns true if automatic mining is enabled, and false.
356    #[serde(rename = "anvil_getAutomine", alias = "hardhat_getAutomine", with = "empty_params")]
357    GetAutoMine(()),
358    /// Mines a series of blocks
359    #[serde(rename = "anvil_mine", alias = "hardhat_mine")]
360    Mine(
361        /// Number of blocks to mine, if not set `1` block is mined
362        #[serde(default, deserialize_with = "deserialize_number_opt")]
363        Option<U256>,
364        /// The time interval between each block in seconds, defaults to `1` seconds
365        /// The interval is applied only to blocks mined in the given method invocation, not to
366        /// blocks mined afterwards. Set this to `0` to instantly mine _all_ blocks
367        #[serde(default, deserialize_with = "deserialize_number_opt")]
368        Option<U256>,
369    ),
370
371    /// Enables or disables, based on the single boolean argument, the automatic mining of new
372    /// blocks with each new transaction submitted to the network.
373    #[serde(rename = "anvil_setAutomine", alias = "evm_setAutomine", with = "sequence")]
374    SetAutomine(bool),
375
376    /// Sets the mining behavior to interval with the given interval (seconds)
377    #[serde(rename = "anvil_setIntervalMining", alias = "evm_setIntervalMining", with = "sequence")]
378    SetIntervalMining(u64),
379
380    /// Gets the current mining behavior
381    #[serde(rename = "anvil_getIntervalMining", with = "empty_params")]
382    GetIntervalMining(()),
383
384    /// Removes transactions from the pool
385    #[serde(rename = "anvil_dropTransaction", alias = "hardhat_dropTransaction", with = "sequence")]
386    DropTransaction(B256),
387
388    /// Removes transactions from the pool
389    #[serde(
390        rename = "anvil_dropAllTransactions",
391        alias = "hardhat_dropAllTransactions",
392        with = "empty_params"
393    )]
394    DropAllTransactions(),
395
396    /// Reset the fork to a fresh forked state, and optionally update the fork config
397    #[serde(rename = "anvil_reset", alias = "hardhat_reset")]
398    Reset(#[serde(default)] Option<Params<Option<Forking>>>),
399
400    /// Sets the backend rpc url
401    #[serde(rename = "anvil_setRpcUrl", with = "sequence")]
402    SetRpcUrl(String),
403
404    /// Modifies the balance of an account.
405    #[serde(
406        rename = "anvil_setBalance",
407        alias = "hardhat_setBalance",
408        alias = "tenderly_setBalance"
409    )]
410    SetBalance(Address, #[serde(deserialize_with = "deserialize_number")] U256),
411
412    /// Increases the balance of an account.
413    #[serde(
414        rename = "anvil_addBalance",
415        alias = "hardhat_addBalance",
416        alias = "tenderly_addBalance"
417    )]
418    AddBalance(Address, #[serde(deserialize_with = "deserialize_number")] U256),
419
420    /// Modifies the ERC20 balance of an account.
421    #[serde(
422        rename = "anvil_dealERC20",
423        alias = "hardhat_dealERC20",
424        alias = "anvil_setERC20Balance"
425    )]
426    DealERC20(Address, Address, #[serde(deserialize_with = "deserialize_number")] U256),
427
428    /// Sets the ERC20 allowance for a spender
429    #[serde(rename = "anvil_setERC20Allowance")]
430    SetERC20Allowance(
431        Address,
432        Address,
433        Address,
434        #[serde(deserialize_with = "deserialize_number")] U256,
435    ),
436
437    /// Sets the code of a contract
438    #[serde(rename = "anvil_setCode", alias = "hardhat_setCode")]
439    SetCode(Address, Bytes),
440
441    /// Sets the nonce of an address
442    #[serde(rename = "anvil_setNonce", alias = "hardhat_setNonce", alias = "evm_setAccountNonce")]
443    SetNonce(Address, #[serde(deserialize_with = "deserialize_number")] U256),
444
445    /// Writes a single slot of the account's storage
446    #[serde(rename = "anvil_setStorageAt", alias = "hardhat_setStorageAt")]
447    SetStorageAt(
448        Address,
449        /// slot
450        U256,
451        /// value
452        B256,
453    ),
454
455    /// Sets the coinbase address
456    #[serde(rename = "anvil_setCoinbase", alias = "hardhat_setCoinbase", with = "sequence")]
457    SetCoinbase(Address),
458
459    /// Sets the chain id
460    #[serde(rename = "anvil_setChainId", with = "sequence")]
461    SetChainId(u64),
462
463    /// Enable or disable logging
464    #[serde(
465        rename = "anvil_setLoggingEnabled",
466        alias = "hardhat_setLoggingEnabled",
467        with = "sequence"
468    )]
469    SetLogging(bool),
470
471    /// Set the minimum gas price for the node
472    #[serde(
473        rename = "anvil_setMinGasPrice",
474        alias = "hardhat_setMinGasPrice",
475        deserialize_with = "deserialize_number_seq"
476    )]
477    SetMinGasPrice(U256),
478
479    /// Sets the base fee of the next block
480    #[serde(
481        rename = "anvil_setNextBlockBaseFeePerGas",
482        alias = "hardhat_setNextBlockBaseFeePerGas",
483        deserialize_with = "deserialize_number_seq"
484    )]
485    SetNextBlockBaseFeePerGas(U256),
486
487    /// Sets the specific timestamp
488    /// Accepts timestamp (Unix epoch) with millisecond precision and returns the number of seconds
489    /// between the given timestamp and the current time.
490    #[serde(
491        rename = "anvil_setTime",
492        alias = "evm_setTime",
493        deserialize_with = "deserialize_number_seq"
494    )]
495    EvmSetTime(U256),
496
497    /// Serializes the current state (including contracts code, contract's storage, accounts
498    /// properties, etc.) into a saveable data blob
499    #[serde(rename = "anvil_dumpState", alias = "hardhat_dumpState")]
500    DumpState(#[serde(default)] Option<Params<Option<bool>>>),
501
502    /// Adds state previously dumped with `DumpState` to the current chain
503    #[serde(rename = "anvil_loadState", alias = "hardhat_loadState", with = "sequence")]
504    LoadState(Bytes),
505
506    /// Retrieves the Anvil node configuration params
507    #[serde(rename = "anvil_nodeInfo", with = "empty_params")]
508    NodeInfo(()),
509
510    /// Retrieves the Anvil node metadata.
511    #[serde(rename = "anvil_metadata", alias = "hardhat_metadata", with = "empty_params")]
512    AnvilMetadata(()),
513
514    // Ganache compatible calls
515    /// Snapshot the state of the blockchain at the current block.
516    ///
517    /// Ref <https://github.com/trufflesuite/ganache/blob/ef1858d5d6f27e4baeb75cccd57fb3dc77a45ae8/src/chains/ethereum/ethereum/RPC-METHODS.md#evm_snapshot>
518    #[serde(rename = "anvil_snapshot", alias = "evm_snapshot", with = "empty_params")]
519    EvmSnapshot(()),
520
521    /// Revert the state of the blockchain to a previous snapshot.
522    /// Takes a single parameter, which is the snapshot id to revert to.
523    ///
524    /// Ref <https://github.com/trufflesuite/ganache/blob/ef1858d5d6f27e4baeb75cccd57fb3dc77a45ae8/src/chains/ethereum/ethereum/RPC-METHODS.md#evm_revert>
525    #[serde(
526        rename = "anvil_revert",
527        alias = "evm_revert",
528        deserialize_with = "deserialize_number_seq"
529    )]
530    EvmRevert(U256),
531
532    /// Jump forward in time by the given amount of time, in seconds.
533    #[serde(
534        rename = "anvil_increaseTime",
535        alias = "evm_increaseTime",
536        deserialize_with = "deserialize_number_seq"
537    )]
538    EvmIncreaseTime(U256),
539
540    /// Similar to `evm_increaseTime` but takes the exact timestamp that you want in the next block
541    #[serde(
542        rename = "anvil_setNextBlockTimestamp",
543        alias = "evm_setNextBlockTimestamp",
544        deserialize_with = "deserialize_number_seq"
545    )]
546    EvmSetNextBlockTimeStamp(U256),
547
548    /// Set the exact gas limit that you want in the next block
549    #[serde(
550        rename = "anvil_setBlockGasLimit",
551        alias = "evm_setBlockGasLimit",
552        deserialize_with = "deserialize_number_seq"
553    )]
554    EvmSetBlockGasLimit(U256),
555
556    /// Similar to `evm_increaseTime` but takes sets a block timestamp `interval`.
557    ///
558    /// The timestamp of the next block will be computed as `lastBlock_timestamp + interval`.
559    #[serde(rename = "anvil_setBlockTimestampInterval", with = "sequence")]
560    EvmSetBlockTimeStampInterval(u64),
561
562    /// Removes a `anvil_setBlockTimestampInterval` if it exists
563    #[serde(rename = "anvil_removeBlockTimestampInterval", with = "empty_params")]
564    EvmRemoveBlockTimeStampInterval(()),
565
566    /// Mine a single block
567    #[serde(rename = "evm_mine")]
568    EvmMine(#[serde(default)] Option<Params<Option<MineOptions>>>),
569
570    /// Mine a single block and return detailed data
571    ///
572    /// This behaves exactly as `EvmMine` but returns different output, for compatibility reasons
573    /// this is a separate call since `evm_mine` is not an anvil original.
574    #[serde(rename = "anvil_mine_detailed", alias = "evm_mine_detailed")]
575    EvmMineDetailed(#[serde(default)] Option<Params<Option<MineOptions>>>),
576
577    /// Execute a transaction regardless of signature status
578    #[serde(rename = "eth_sendUnsignedTransaction", with = "sequence")]
579    EthSendUnsignedTransaction(Box<WithOtherFields<TransactionRequest>>),
580
581    /// Turn on call traces for transactions that are returned to the user when they execute a
582    /// transaction (instead of just txhash/receipt)
583    #[serde(rename = "anvil_enableTraces", with = "empty_params")]
584    EnableTraces(()),
585
586    /// Returns the number of transactions currently pending for inclusion in the next block(s), as
587    /// well as the ones that are being scheduled for future execution only.
588    /// Ref: <https://geth.ethereum.org/docs/rpc/ns-txpool#txpool_status>
589    #[serde(rename = "txpool_status", with = "empty_params")]
590    TxPoolStatus(()),
591
592    /// Returns a summary of all the transactions currently pending for inclusion in the next
593    /// block(s), as well as the ones that are being scheduled for future execution only.
594    /// Ref: <https://geth.ethereum.org/docs/rpc/ns-txpool#txpool_inspect>
595    #[serde(rename = "txpool_inspect", with = "empty_params")]
596    TxPoolInspect(()),
597
598    /// Returns the details of all transactions currently pending for inclusion in the next
599    /// block(s), as well as the ones that are being scheduled for future execution only.
600    /// Ref: <https://geth.ethereum.org/docs/rpc/ns-txpool#txpool_content>
601    #[serde(rename = "txpool_content", with = "empty_params")]
602    TxPoolContent(()),
603
604    /// Otterscan's `ots_getApiLevel` endpoint
605    /// Otterscan currently requires this endpoint, even though it's not part of the ots_*
606    /// <https://github.com/otterscan/otterscan/blob/071d8c55202badf01804f6f8d53ef9311d4a9e47/src/useProvider.ts#L71>
607    /// Related upstream issue: <https://github.com/otterscan/otterscan/issues/1081>
608    #[serde(rename = "erigon_getHeaderByNumber")]
609    ErigonGetHeaderByNumber(
610        #[serde(deserialize_with = "lenient_block_number::lenient_block_number_seq")] BlockNumber,
611    ),
612
613    /// Otterscan's `ots_getApiLevel` endpoint
614    /// Used as a simple API versioning scheme for the ots_* namespace
615    #[serde(rename = "ots_getApiLevel", with = "empty_params")]
616    OtsGetApiLevel(()),
617
618    /// Otterscan's `ots_getInternalOperations` endpoint
619    /// Traces internal ETH transfers, contracts creation (CREATE/CREATE2) and self-destructs for a
620    /// certain transaction.
621    #[serde(rename = "ots_getInternalOperations", with = "sequence")]
622    OtsGetInternalOperations(B256),
623
624    /// Otterscan's `ots_hasCode` endpoint
625    /// Check if an ETH address contains code at a certain block number.
626    #[serde(rename = "ots_hasCode")]
627    OtsHasCode(
628        Address,
629        #[serde(deserialize_with = "lenient_block_number::lenient_block_number", default)]
630        BlockNumber,
631    ),
632
633    /// Otterscan's `ots_traceTransaction` endpoint
634    /// Trace a transaction and generate a trace call tree.
635    #[serde(rename = "ots_traceTransaction", with = "sequence")]
636    OtsTraceTransaction(B256),
637
638    /// Otterscan's `ots_getTransactionError` endpoint
639    /// Given a transaction hash, returns its raw revert reason.
640    #[serde(rename = "ots_getTransactionError", with = "sequence")]
641    OtsGetTransactionError(B256),
642
643    /// Otterscan's `ots_getBlockDetails` endpoint
644    /// Given a block number, return its data. Similar to the standard eth_getBlockByNumber/Hash
645    /// method, but can be optimized by excluding unnecessary data such as transactions and
646    /// logBloom
647    #[serde(rename = "ots_getBlockDetails")]
648    OtsGetBlockDetails(
649        #[serde(deserialize_with = "lenient_block_number::lenient_block_number_seq", default)]
650        BlockNumber,
651    ),
652
653    /// Otterscan's `ots_getBlockDetails` endpoint
654    /// Same as `ots_getBlockDetails`, but receiving a block hash instead of number
655    #[serde(rename = "ots_getBlockDetailsByHash", with = "sequence")]
656    OtsGetBlockDetailsByHash(B256),
657
658    /// Otterscan's `ots_getBlockTransactions` endpoint
659    /// Gets paginated transaction data for a certain block. Return data is similar to
660    /// eth_getBlockBy* + eth_getTransactionReceipt.
661    #[serde(rename = "ots_getBlockTransactions")]
662    OtsGetBlockTransactions(u64, usize, usize),
663
664    /// Otterscan's `ots_searchTransactionsBefore` endpoint
665    /// Address history navigation. searches backwards from certain point in time.
666    #[serde(rename = "ots_searchTransactionsBefore")]
667    OtsSearchTransactionsBefore(Address, u64, usize),
668
669    /// Otterscan's `ots_searchTransactionsAfter` endpoint
670    /// Address history navigation. searches forward from certain point in time.
671    #[serde(rename = "ots_searchTransactionsAfter")]
672    OtsSearchTransactionsAfter(Address, u64, usize),
673
674    /// Otterscan's `ots_getTransactionBySenderAndNonce` endpoint
675    /// Given a sender address and a nonce, returns the tx hash or null if not found. It returns
676    /// only the tx hash on success, you can use the standard eth_getTransactionByHash after that
677    /// to get the full transaction data.
678    #[serde(rename = "ots_getTransactionBySenderAndNonce")]
679    OtsGetTransactionBySenderAndNonce(
680        Address,
681        #[serde(deserialize_with = "deserialize_number")] U256,
682    ),
683
684    /// Returns the transaction by sender and nonce
685    /// Returns the full transaction data.
686    #[serde(rename = "eth_getTransactionBySenderAndNonce")]
687    EthGetTransactionBySenderAndNonce(
688        Address,
689        #[serde(deserialize_with = "deserialize_number")] U256,
690    ),
691
692    /// Otterscan's `ots_getTransactionBySenderAndNonce` endpoint
693    /// Given an ETH contract address, returns the tx hash and the direct address who created the
694    /// contract.
695    #[serde(rename = "ots_getContractCreator", with = "sequence")]
696    OtsGetContractCreator(Address),
697
698    /// Removes transactions from the pool by sender origin.
699    #[serde(rename = "anvil_removePoolTransactions", with = "sequence")]
700    RemovePoolTransactions(Address),
701
702    /// Reorg the chain
703    #[serde(rename = "anvil_reorg")]
704    Reorg(ReorgOptions),
705
706    /// Rollback the chain
707    #[serde(rename = "anvil_rollback", with = "sequence")]
708    Rollback(Option<u64>),
709
710    /// Wallet
711    #[serde(rename = "wallet_getCapabilities", with = "empty_params")]
712    WalletGetCapabilities(()),
713
714    /// Add an address to the delegation capability of the wallet
715    #[serde(rename = "anvil_addCapability", with = "sequence")]
716    AnvilAddCapability(Address),
717
718    /// Set the executor (sponsor) wallet
719    #[serde(rename = "anvil_setExecutor", with = "sequence")]
720    AnvilSetExecutor(String),
721}
722
723/// Represents ethereum JSON-RPC API
724#[derive(Clone, Debug, PartialEq, Eq, serde::Deserialize)]
725#[serde(tag = "method", content = "params")]
726pub enum EthPubSub {
727    /// Subscribe to an eth subscription
728    #[serde(rename = "eth_subscribe")]
729    EthSubscribe(SubscriptionKind, #[serde(default)] Box<SubscriptionParams>),
730
731    /// Unsubscribe from an eth subscription
732    #[serde(rename = "eth_unsubscribe", with = "sequence")]
733    EthUnSubscribe(SubscriptionId),
734}
735
736/// Container type for either a request or a pub sub
737#[derive(Clone, Debug, serde::Deserialize)]
738#[serde(untagged)]
739pub enum EthRpcCall {
740    Request(Box<EthRequest>),
741    PubSub(EthPubSub),
742}
743
744#[cfg(test)]
745mod tests {
746    use super::*;
747
748    #[test]
749    fn test_web3_client_version() {
750        let s = r#"{"method": "web3_clientVersion", "params":[]}"#;
751        let value: serde_json::Value = serde_json::from_str(s).unwrap();
752        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
753    }
754
755    #[test]
756    fn test_web3_sha3() {
757        let s = r#"{"method": "web3_sha3", "params":["0x68656c6c6f20776f726c64"]}"#;
758        let value: serde_json::Value = serde_json::from_str(s).unwrap();
759        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
760    }
761
762    #[test]
763    fn test_eth_accounts() {
764        let s = r#"{"method": "eth_accounts", "params":[]}"#;
765        let value: serde_json::Value = serde_json::from_str(s).unwrap();
766        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
767    }
768
769    #[test]
770    fn test_eth_network_id() {
771        let s = r#"{"method": "eth_networkId", "params":[]}"#;
772        let value: serde_json::Value = serde_json::from_str(s).unwrap();
773        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
774    }
775
776    #[test]
777    fn test_eth_get_proof() {
778        let s = r#"{"method":"eth_getProof","params":["0x7F0d15C7FAae65896648C8273B6d7E43f58Fa842",["0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421"],"latest"]}"#;
779        let value: serde_json::Value = serde_json::from_str(s).unwrap();
780        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
781    }
782
783    #[test]
784    fn test_eth_chain_id() {
785        let s = r#"{"method": "eth_chainId", "params":[]}"#;
786        let value: serde_json::Value = serde_json::from_str(s).unwrap();
787        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
788    }
789
790    #[test]
791    fn test_net_listening() {
792        let s = r#"{"method": "net_listening", "params":[]}"#;
793        let value: serde_json::Value = serde_json::from_str(s).unwrap();
794        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
795    }
796
797    #[test]
798    fn test_eth_block_number() {
799        let s = r#"{"method": "eth_blockNumber", "params":[]}"#;
800        let value: serde_json::Value = serde_json::from_str(s).unwrap();
801        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
802    }
803
804    #[test]
805    fn test_eth_max_priority_fee() {
806        let s = r#"{"method": "eth_maxPriorityFeePerGas", "params":[]}"#;
807        let value: serde_json::Value = serde_json::from_str(s).unwrap();
808        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
809    }
810
811    #[test]
812    fn test_eth_syncing() {
813        let s = r#"{"method": "eth_syncing", "params":[]}"#;
814        let value: serde_json::Value = serde_json::from_str(s).unwrap();
815        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
816    }
817
818    #[test]
819    fn test_custom_impersonate_account() {
820        let s = r#"{"method": "anvil_impersonateAccount", "params":
821["0xd84de507f3fada7df80908082d3239466db55a71"]}"#;
822        let value: serde_json::Value = serde_json::from_str(s).unwrap();
823        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
824    }
825
826    #[test]
827    fn test_custom_stop_impersonate_account() {
828        let s = r#"{"method": "anvil_stopImpersonatingAccount",  "params":
829["0x364d6D0333432C3Ac016Ca832fb8594A8cE43Ca6"]}"#;
830        let value: serde_json::Value = serde_json::from_str(s).unwrap();
831        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
832    }
833
834    #[test]
835    fn test_custom_auto_impersonate_account() {
836        let s = r#"{"method": "anvil_autoImpersonateAccount",  "params": [true]}"#;
837        let value: serde_json::Value = serde_json::from_str(s).unwrap();
838        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
839    }
840
841    #[test]
842    fn test_custom_get_automine() {
843        let s = r#"{"method": "anvil_getAutomine", "params": []}"#;
844        let value: serde_json::Value = serde_json::from_str(s).unwrap();
845        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
846    }
847
848    #[test]
849    fn test_custom_mine() {
850        let s = r#"{"method": "anvil_mine", "params": []}"#;
851        let value: serde_json::Value = serde_json::from_str(s).unwrap();
852        let req = serde_json::from_value::<EthRequest>(value).unwrap();
853        match req {
854            EthRequest::Mine(num, time) => {
855                assert!(num.is_none());
856                assert!(time.is_none());
857            }
858            _ => unreachable!(),
859        }
860        let s = r#"{"method": "anvil_mine", "params":
861["0xd84de507f3fada7df80908082d3239466db55a71"]}"#;
862        let value: serde_json::Value = serde_json::from_str(s).unwrap();
863        let req = serde_json::from_value::<EthRequest>(value).unwrap();
864        match req {
865            EthRequest::Mine(num, time) => {
866                assert!(num.is_some());
867                assert!(time.is_none());
868            }
869            _ => unreachable!(),
870        }
871        let s = r#"{"method": "anvil_mine", "params": ["0xd84de507f3fada7df80908082d3239466db55a71", "0xd84de507f3fada7df80908082d3239466db55a71"]}"#;
872        let value: serde_json::Value = serde_json::from_str(s).unwrap();
873        let req = serde_json::from_value::<EthRequest>(value).unwrap();
874        match req {
875            EthRequest::Mine(num, time) => {
876                assert!(num.is_some());
877                assert!(time.is_some());
878            }
879            _ => unreachable!(),
880        }
881    }
882
883    #[test]
884    fn test_custom_auto_mine() {
885        let s = r#"{"method": "anvil_setAutomine", "params": [false]}"#;
886        let value: serde_json::Value = serde_json::from_str(s).unwrap();
887        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
888        let s = r#"{"method": "evm_setAutomine", "params": [false]}"#;
889        let value: serde_json::Value = serde_json::from_str(s).unwrap();
890        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
891    }
892
893    #[test]
894    fn test_custom_interval_mining() {
895        let s = r#"{"method": "anvil_setIntervalMining", "params": [100]}"#;
896        let value: serde_json::Value = serde_json::from_str(s).unwrap();
897        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
898        let s = r#"{"method": "evm_setIntervalMining", "params": [100]}"#;
899        let value: serde_json::Value = serde_json::from_str(s).unwrap();
900        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
901    }
902
903    #[test]
904    fn test_custom_drop_tx() {
905        let s = r#"{"method": "anvil_dropTransaction", "params":
906["0x4a3b0fce2cb9707b0baa68640cf2fe858c8bb4121b2a8cb904ff369d38a560ff"]}"#;
907        let value: serde_json::Value = serde_json::from_str(s).unwrap();
908        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
909    }
910
911    #[test]
912    fn test_custom_reset() {
913        let s = r#"{"method": "anvil_reset", "params": [{"forking": {"jsonRpcUrl": "https://ethereumpublicnode.com",
914        "blockNumber": "18441649"
915      }
916    }]}"#;
917        let value: serde_json::Value = serde_json::from_str(s).unwrap();
918        let req = serde_json::from_value::<EthRequest>(value).unwrap();
919        match req {
920            EthRequest::Reset(forking) => {
921                let forking = forking.and_then(|f| f.params);
922                assert_eq!(
923                    forking,
924                    Some(Forking {
925                        json_rpc_url: Some("https://ethereumpublicnode.com".into()),
926                        block_number: Some(18441649)
927                    })
928                )
929            }
930            _ => unreachable!(),
931        }
932
933        let s = r#"{"method": "anvil_reset", "params": [ { "forking": {
934                "jsonRpcUrl": "https://eth-mainnet.alchemyapi.io/v2/<key>",
935                "blockNumber": 11095000
936        }}]}"#;
937        let value: serde_json::Value = serde_json::from_str(s).unwrap();
938        let req = serde_json::from_value::<EthRequest>(value).unwrap();
939        match req {
940            EthRequest::Reset(forking) => {
941                let forking = forking.and_then(|f| f.params);
942                assert_eq!(
943                    forking,
944                    Some(Forking {
945                        json_rpc_url: Some(
946                            "https://eth-mainnet.alchemyapi.io/v2/<key>".to_string()
947                        ),
948                        block_number: Some(11095000)
949                    })
950                )
951            }
952            _ => unreachable!(),
953        }
954
955        let s = r#"{"method": "anvil_reset", "params": [ { "forking": {
956                "jsonRpcUrl": "https://eth-mainnet.alchemyapi.io/v2/<key>"
957        }}]}"#;
958        let value: serde_json::Value = serde_json::from_str(s).unwrap();
959        let req = serde_json::from_value::<EthRequest>(value).unwrap();
960        match req {
961            EthRequest::Reset(forking) => {
962                let forking = forking.and_then(|f| f.params);
963                assert_eq!(
964                    forking,
965                    Some(Forking {
966                        json_rpc_url: Some(
967                            "https://eth-mainnet.alchemyapi.io/v2/<key>".to_string()
968                        ),
969                        block_number: None
970                    })
971                )
972            }
973            _ => unreachable!(),
974        }
975
976        let s = r#"{"method":"anvil_reset","params":[{"jsonRpcUrl": "http://localhost:8545", "blockNumber": 14000000}]}"#;
977        let value: serde_json::Value = serde_json::from_str(s).unwrap();
978        let req = serde_json::from_value::<EthRequest>(value).unwrap();
979        match req {
980            EthRequest::Reset(forking) => {
981                let forking = forking.and_then(|f| f.params);
982                assert_eq!(
983                    forking,
984                    Some(Forking {
985                        json_rpc_url: Some("http://localhost:8545".to_string()),
986                        block_number: Some(14000000)
987                    })
988                )
989            }
990            _ => unreachable!(),
991        }
992
993        let s = r#"{"method":"anvil_reset","params":[{ "blockNumber": 14000000}]}"#;
994        let value: serde_json::Value = serde_json::from_str(s).unwrap();
995        let req = serde_json::from_value::<EthRequest>(value).unwrap();
996        match req {
997            EthRequest::Reset(forking) => {
998                let forking = forking.and_then(|f| f.params);
999                assert_eq!(
1000                    forking,
1001                    Some(Forking { json_rpc_url: None, block_number: Some(14000000) })
1002                )
1003            }
1004            _ => unreachable!(),
1005        }
1006
1007        let s = r#"{"method":"anvil_reset","params":[{ "blockNumber": "14000000"}]}"#;
1008        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1009        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1010        match req {
1011            EthRequest::Reset(forking) => {
1012                let forking = forking.and_then(|f| f.params);
1013                assert_eq!(
1014                    forking,
1015                    Some(Forking { json_rpc_url: None, block_number: Some(14000000) })
1016                )
1017            }
1018            _ => unreachable!(),
1019        }
1020
1021        let s = r#"{"method":"anvil_reset","params":[{"jsonRpcUrl": "http://localhost:8545"}]}"#;
1022        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1023        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1024        match req {
1025            EthRequest::Reset(forking) => {
1026                let forking = forking.and_then(|f| f.params);
1027                assert_eq!(
1028                    forking,
1029                    Some(Forking {
1030                        json_rpc_url: Some("http://localhost:8545".to_string()),
1031                        block_number: None
1032                    })
1033                )
1034            }
1035            _ => unreachable!(),
1036        }
1037
1038        let s = r#"{"method": "anvil_reset"}"#;
1039        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1040        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1041        match req {
1042            EthRequest::Reset(forking) => {
1043                assert!(forking.is_none())
1044            }
1045            _ => unreachable!(),
1046        }
1047    }
1048
1049    #[test]
1050    fn test_custom_set_balance() {
1051        let s = r#"{"method": "anvil_setBalance", "params":
1052["0xd84de507f3fada7df80908082d3239466db55a71", "0x0"]}"#;
1053        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1054        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1055
1056        let s = r#"{"method": "anvil_setBalance", "params":
1057["0xd84de507f3fada7df80908082d3239466db55a71", 1337]}"#;
1058        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1059        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1060    }
1061
1062    #[test]
1063    fn test_custom_set_code() {
1064        let s = r#"{"method": "anvil_setCode", "params":
1065["0xd84de507f3fada7df80908082d3239466db55a71", "0x0123456789abcdef"]}"#;
1066        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1067        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1068
1069        let s = r#"{"method": "anvil_setCode", "params":
1070["0xd84de507f3fada7df80908082d3239466db55a71", "0x"]}"#;
1071        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1072        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1073
1074        let s = r#"{"method": "anvil_setCode", "params":
1075["0xd84de507f3fada7df80908082d3239466db55a71", ""]}"#;
1076        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1077        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1078    }
1079
1080    #[test]
1081    fn test_custom_set_nonce() {
1082        let s = r#"{"method": "anvil_setNonce", "params":
1083["0xd84de507f3fada7df80908082d3239466db55a71", "0x0"]}"#;
1084        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1085        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1086        let s = r#"{"method":
1087"hardhat_setNonce", "params": ["0xd84de507f3fada7df80908082d3239466db55a71", "0x0"]}"#;
1088        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1089        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1090        let s = r#"{"method": "evm_setAccountNonce", "params":
1091["0xd84de507f3fada7df80908082d3239466db55a71", "0x0"]}"#;
1092        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1093        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1094    }
1095
1096    #[test]
1097    fn test_serde_custom_set_storage_at() {
1098        let s = r#"{"method": "anvil_setStorageAt", "params":
1099["0x295a70b2de5e3953354a6a8344e616ed314d7251", "0x0",
1100"0x0000000000000000000000000000000000000000000000000000000000003039"]}"#;
1101        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1102        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1103
1104        let s = r#"{"method": "hardhat_setStorageAt", "params":
1105["0xe9e7CEA3DedcA5984780Bafc599bD69ADd087D56",
1106"0xa6eef7e35abe7026729641147f7915573c7e97b47efa546f5f6e3230263bcb49",
1107"0x0000000000000000000000000000000000000000000000000000000000003039"]}"#;
1108        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1109        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1110    }
1111
1112    #[test]
1113    fn test_serde_custom_coinbase() {
1114        let s = r#"{"method": "anvil_setCoinbase", "params":
1115["0x295a70b2de5e3953354a6a8344e616ed314d7251"]}"#;
1116        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1117        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1118    }
1119
1120    #[test]
1121    fn test_serde_custom_logging() {
1122        let s = r#"{"method": "anvil_setLoggingEnabled", "params": [false]}"#;
1123        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1124        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1125    }
1126
1127    #[test]
1128    fn test_serde_custom_min_gas_price() {
1129        let s = r#"{"method": "anvil_setMinGasPrice", "params": ["0x0"]}"#;
1130        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1131        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1132    }
1133
1134    #[test]
1135    fn test_serde_custom_next_block_base_fee() {
1136        let s = r#"{"method": "anvil_setNextBlockBaseFeePerGas", "params": ["0x0"]}"#;
1137        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1138        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1139    }
1140
1141    #[test]
1142    fn test_serde_set_time() {
1143        let s = r#"{"method": "anvil_setTime", "params": ["0x0"]}"#;
1144        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1145        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1146
1147        let s = r#"{"method": "anvil_increaseTime", "params": 1}"#;
1148        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1149        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1150    }
1151
1152    #[test]
1153    fn test_serde_custom_dump_state() {
1154        let s = r#"{"method": "anvil_dumpState", "params": [true]}"#;
1155        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1156        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1157
1158        let s = r#"{"method": "anvil_dumpState"}"#;
1159        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1160        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1161        match req {
1162            EthRequest::DumpState(param) => {
1163                assert!(param.is_none());
1164            }
1165            _ => unreachable!(),
1166        }
1167    }
1168
1169    #[test]
1170    fn test_serde_custom_load_state() {
1171        let s = r#"{"method": "anvil_loadState", "params": ["0x0001"] }"#;
1172        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1173        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1174    }
1175
1176    #[test]
1177    fn test_serde_custom_snapshot() {
1178        let s = r#"{"method": "anvil_snapshot", "params": [] }"#;
1179        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1180        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1181
1182        let s = r#"{"method": "evm_snapshot", "params": [] }"#;
1183        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1184        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1185    }
1186
1187    #[test]
1188    fn test_serde_custom_revert() {
1189        let s = r#"{"method": "anvil_revert", "params": ["0x0"]}"#;
1190        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1191        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1192    }
1193
1194    #[test]
1195    fn test_serde_custom_increase_time() {
1196        let s = r#"{"method": "anvil_increaseTime", "params": ["0x0"]}"#;
1197        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1198        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1199
1200        let s = r#"{"method": "anvil_increaseTime", "params": [1]}"#;
1201        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1202        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1203
1204        let s = r#"{"method": "anvil_increaseTime", "params": 1}"#;
1205        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1206        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1207
1208        let s = r#"{"method": "evm_increaseTime", "params": ["0x0"]}"#;
1209        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1210        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1211
1212        let s = r#"{"method": "evm_increaseTime", "params": [1]}"#;
1213        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1214        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1215
1216        let s = r#"{"method": "evm_increaseTime", "params": 1}"#;
1217        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1218        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1219    }
1220
1221    #[test]
1222    fn test_serde_custom_next_timestamp() {
1223        let s = r#"{"method": "anvil_setNextBlockTimestamp", "params": [100]}"#;
1224        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1225        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1226        let s = r#"{"method": "evm_setNextBlockTimestamp", "params": [100]}"#;
1227        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1228        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1229        let s = r#"{"method": "evm_setNextBlockTimestamp", "params": ["0x64e0f308"]}"#;
1230        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1231        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1232    }
1233
1234    #[test]
1235    fn test_serde_custom_timestamp_interval() {
1236        let s = r#"{"method": "anvil_setBlockTimestampInterval", "params": [100]}"#;
1237        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1238        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1239    }
1240
1241    #[test]
1242    fn test_serde_custom_remove_timestamp_interval() {
1243        let s = r#"{"method": "anvil_removeBlockTimestampInterval", "params": []}"#;
1244        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1245        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1246    }
1247
1248    #[test]
1249    fn test_serde_custom_evm_mine() {
1250        let s = r#"{"method": "evm_mine", "params": [100]}"#;
1251        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1252        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1253        let s = r#"{"method": "evm_mine", "params": [{
1254            "timestamp": 100,
1255            "blocks": 100
1256        }]}"#;
1257        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1258        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1259        match req {
1260            EthRequest::EvmMine(params) => {
1261                assert_eq!(
1262                    params.unwrap().params.unwrap_or_default(),
1263                    MineOptions::Options { timestamp: Some(100), blocks: Some(100) }
1264                )
1265            }
1266            _ => unreachable!(),
1267        }
1268
1269        let s = r#"{"method": "evm_mine"}"#;
1270        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1271        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1272
1273        match req {
1274            EthRequest::EvmMine(params) => {
1275                assert!(params.is_none())
1276            }
1277            _ => unreachable!(),
1278        }
1279
1280        let s = r#"{"method": "evm_mine", "params": []}"#;
1281        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1282        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1283    }
1284
1285    #[test]
1286    fn test_serde_custom_evm_mine_detailed() {
1287        let s = r#"{"method": "anvil_mine_detailed", "params": [100]}"#;
1288        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1289        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1290        let s = r#"{"method": "anvil_mine_detailed", "params": [{
1291            "timestamp": 100,
1292            "blocks": 100
1293        }]}"#;
1294        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1295        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1296        match req {
1297            EthRequest::EvmMineDetailed(params) => {
1298                assert_eq!(
1299                    params.unwrap().params.unwrap_or_default(),
1300                    MineOptions::Options { timestamp: Some(100), blocks: Some(100) }
1301                )
1302            }
1303            _ => unreachable!(),
1304        }
1305
1306        let s = r#"{"method": "evm_mine_detailed"}"#;
1307        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1308        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1309
1310        match req {
1311            EthRequest::EvmMineDetailed(params) => {
1312                assert!(params.is_none())
1313            }
1314            _ => unreachable!(),
1315        }
1316
1317        let s = r#"{"method": "anvil_mine_detailed", "params": []}"#;
1318        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1319        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1320    }
1321
1322    #[test]
1323    fn test_serde_custom_evm_mine_hex() {
1324        let s = r#"{"method": "evm_mine", "params": ["0x63b6ff08"]}"#;
1325        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1326        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1327        match req {
1328            EthRequest::EvmMine(params) => {
1329                assert_eq!(
1330                    params.unwrap().params.unwrap_or_default(),
1331                    MineOptions::Timestamp(Some(1672937224))
1332                )
1333            }
1334            _ => unreachable!(),
1335        }
1336
1337        let s = r#"{"method": "evm_mine", "params": [{"timestamp": "0x63b6ff08"}]}"#;
1338        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1339        let req = serde_json::from_value::<EthRequest>(value).unwrap();
1340        match req {
1341            EthRequest::EvmMine(params) => {
1342                assert_eq!(
1343                    params.unwrap().params.unwrap_or_default(),
1344                    MineOptions::Options { timestamp: Some(1672937224), blocks: None }
1345                )
1346            }
1347            _ => unreachable!(),
1348        }
1349    }
1350
1351    #[test]
1352    fn test_eth_uncle_count_by_block_hash() {
1353        let s = r#"{"jsonrpc":"2.0","method":"eth_getUncleCountByBlockHash","params":["0x4a3b0fce2cb9707b0baa68640cf2fe858c8bb4121b2a8cb904ff369d38a560ff"]}"#;
1354        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1355        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1356    }
1357
1358    #[test]
1359    fn test_eth_block_tx_count_by_block_hash() {
1360        let s = r#"{"jsonrpc":"2.0","method":"eth_getBlockTransactionCountByHash","params":["0x4a3b0fce2cb9707b0baa68640cf2fe858c8bb4121b2a8cb904ff369d38a560ff"]}"#;
1361        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1362        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1363    }
1364
1365    #[test]
1366    fn test_eth_get_logs() {
1367        let s = r#"{"jsonrpc":"2.0","method":"eth_getLogs","params":[{"topics":["0x000000000000000000000000a94f5374fce5edbc8e2a8697c15331677e6ebf0b"]}],"id":74}"#;
1368        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1369        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1370    }
1371
1372    #[test]
1373    fn test_eth_new_filter() {
1374        let s = r#"{"method": "eth_newFilter", "params": [{"topics":["0x000000000000000000000000a94f5374fce5edbc8e2a8697c15331677e6ebf0b"]}],"id":73}"#;
1375        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1376        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1377    }
1378
1379    #[test]
1380    fn test_serde_eth_unsubscribe() {
1381        let s = r#"{"id": 1, "method": "eth_unsubscribe", "params":
1382["0x9cef478923ff08bf67fde6c64013158d"]}"#;
1383        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1384        let _req = serde_json::from_value::<EthPubSub>(value).unwrap();
1385    }
1386
1387    #[test]
1388    fn test_serde_eth_subscribe() {
1389        let s = r#"{"id": 1, "method": "eth_subscribe", "params": ["newHeads"]}"#;
1390        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1391        let _req = serde_json::from_value::<EthPubSub>(value).unwrap();
1392
1393        let s = r#"{"id": 1, "method": "eth_subscribe", "params": ["logs", {"address":
1394"0x8320fe7702b96808f7bbc0d4a888ed1468216cfd", "topics":
1395["0xd78a0cb8bb633d06981248b816e7bd33c2a35a6089241d099fa519e361cab902"]}]}"#;
1396        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1397        let _req = serde_json::from_value::<EthPubSub>(value).unwrap();
1398
1399        let s = r#"{"id": 1, "method": "eth_subscribe", "params": ["newPendingTransactions"]}"#;
1400        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1401        let _req = serde_json::from_value::<EthPubSub>(value).unwrap();
1402
1403        let s = r#"{"id": 1, "method": "eth_subscribe", "params": ["syncing"]}"#;
1404        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1405        let _req = serde_json::from_value::<EthPubSub>(value).unwrap();
1406    }
1407
1408    #[test]
1409    fn test_serde_debug_raw_transaction() {
1410        let s = r#"{"jsonrpc":"2.0","method":"debug_getRawTransaction","params":["0x3ed3a89bc10115a321aee238c02de214009f8532a65368e5df5eaf732ee7167c"],"id":1}"#;
1411        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1412        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1413
1414        let s = r#"{"jsonrpc":"2.0","method":"eth_getRawTransactionByHash","params":["0x3ed3a89bc10115a321aee238c02de214009f8532a65368e5df5eaf732ee7167c"],"id":1}"#;
1415        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1416        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1417
1418        let s = r#"{"jsonrpc":"2.0","method":"eth_getRawTransactionByBlockHashAndIndex","params":["0x3ed3a89bc10115a321aee238c02de214009f8532a65368e5df5eaf732ee7167c",1],"id":1}"#;
1419        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1420        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1421
1422        let s = r#"{"jsonrpc":"2.0","method":"eth_getRawTransactionByBlockNumberAndIndex","params":["0x3ed3a89b",0],"id":1}"#;
1423        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1424        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1425    }
1426
1427    #[test]
1428    fn test_serde_debug_trace_transaction() {
1429        let s = r#"{"method": "debug_traceTransaction", "params":
1430["0x4a3b0fce2cb9707b0baa68640cf2fe858c8bb4121b2a8cb904ff369d38a560ff"]}"#;
1431        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1432        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1433
1434        let s = r#"{"method": "debug_traceTransaction", "params":
1435["0x4a3b0fce2cb9707b0baa68640cf2fe858c8bb4121b2a8cb904ff369d38a560ff", {}]}"#;
1436        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1437        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1438
1439        let s = r#"{"method": "debug_traceTransaction", "params":
1440["0x4a3b0fce2cb9707b0baa68640cf2fe858c8bb4121b2a8cb904ff369d38a560ff", {"disableStorage":
1441true}]}"#;
1442        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1443        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1444    }
1445
1446    #[test]
1447    fn test_serde_debug_trace_call() {
1448        let s = r#"{"method": "debug_traceCall", "params": [{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}]}"#;
1449        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1450        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1451
1452        let s = r#"{"method": "debug_traceCall", "params": [{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}, { "blockNumber": "latest" }]}"#;
1453        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1454        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1455
1456        let s = r#"{"method": "debug_traceCall", "params": [{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}, { "blockNumber": "0x0" }]}"#;
1457        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1458        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1459
1460        let s = r#"{"method": "debug_traceCall", "params": [{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}, { "blockHash": "0xd4e56740f876aef8c010b86a40d5f56745a118d0906a34e69aec8c0db1cb8fa3" }]}"#;
1461        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1462        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1463
1464        let s = r#"{"method": "debug_traceCall", "params": [{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}, { "blockNumber": "0x0" }, {"disableStorage": true}]}"#;
1465        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1466        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1467    }
1468
1469    #[test]
1470    fn test_serde_eth_storage() {
1471        let s = r#"{"method": "eth_getStorageAt", "params":
1472["0x295a70b2de5e3953354a6a8344e616ed314d7251", "0x0", "latest"]}"#;
1473        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1474        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1475    }
1476
1477    #[test]
1478    fn test_eth_call() {
1479        let req = r#"{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}"#;
1480        let _req = serde_json::from_str::<TransactionRequest>(req).unwrap();
1481
1482        let s = r#"{"method": "eth_call", "params":[{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"},"latest"]}"#;
1483        let _req = serde_json::from_str::<EthRequest>(s).unwrap();
1484
1485        let s = r#"{"method": "eth_call", "params":[{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}]}"#;
1486        let _req = serde_json::from_str::<EthRequest>(s).unwrap();
1487
1488        let s = r#"{"method": "eth_call", "params":[{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}, { "blockNumber": "latest" }]}"#;
1489        let _req = serde_json::from_str::<EthRequest>(s).unwrap();
1490
1491        let s = r#"{"method": "eth_call", "params":[{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}, { "blockNumber": "0x0" }]}"#;
1492        let _req = serde_json::from_str::<EthRequest>(s).unwrap();
1493
1494        let s = r#"{"method": "eth_call", "params":[{"data":"0xcfae3217","from":"0xd84de507f3fada7df80908082d3239466db55a71","to":"0xcbe828fdc46e3b1c351ec90b1a5e7d9742c0398d"}, { "blockHash":"0xd4e56740f876aef8c010b86a40d5f56745a118d0906a34e69aec8c0db1cb8fa3" }]}"#;
1495        let _req = serde_json::from_str::<EthRequest>(s).unwrap();
1496    }
1497
1498    #[test]
1499    fn test_serde_eth_balance() {
1500        let s = r#"{"method": "eth_getBalance", "params":
1501["0x295a70b2de5e3953354a6a8344e616ed314d7251", "latest"]}"#;
1502        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1503
1504        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1505    }
1506
1507    #[test]
1508    fn test_serde_eth_block_by_number() {
1509        let s = r#"{"method": "eth_getBlockByNumber", "params": ["0x0", true]}"#;
1510        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1511        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1512        let s = r#"{"method": "eth_getBlockByNumber", "params": ["latest", true]}"#;
1513        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1514        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1515        let s = r#"{"method": "eth_getBlockByNumber", "params": ["earliest", true]}"#;
1516        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1517        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1518        let s = r#"{"method": "eth_getBlockByNumber", "params": ["pending", true]}"#;
1519        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1520        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1521
1522        // this case deviates from the spec, but we're supporting this for legacy reasons: <https://github.com/foundry-rs/foundry/issues/1868>
1523        let s = r#"{"method": "eth_getBlockByNumber", "params": [0, true]}"#;
1524        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1525        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1526    }
1527
1528    #[test]
1529    fn test_eth_sign() {
1530        let s = r#"{"method": "eth_sign", "params":
1531["0xd84de507f3fada7df80908082d3239466db55a71", "0x00"]}"#;
1532        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1533        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1534        let s = r#"{"method": "personal_sign", "params":
1535["0x00", "0xd84de507f3fada7df80908082d3239466db55a71"]}"#;
1536        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1537        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1538    }
1539
1540    #[test]
1541    fn test_eth_sign_typed_data() {
1542        let s = r#"{"method":"eth_signTypedData_v4","params":["0xCD2a3d9F938E13CD947Ec05AbC7FE734Df8DD826", {"types":{"EIP712Domain":[{"name":"name","type":"string"},{"name":"version","type":"string"},{"name":"chainId","type":"uint256"},{"name":"verifyingContract","type":"address"}],"Person":[{"name":"name","type":"string"},{"name":"wallet","type":"address"}],"Mail":[{"name":"from","type":"Person"},{"name":"to","type":"Person"},{"name":"contents","type":"string"}]},"primaryType":"Mail","domain":{"name":"Ether Mail","version":"1","chainId":1,"verifyingContract":"0xCcCCccccCCCCcCCCCCCcCcCccCcCCCcCcccccccC"},"message":{"from":{"name":"Cow","wallet":"0xCD2a3d9F938E13CD947Ec05AbC7FE734Df8DD826"},"to":{"name":"Bob","wallet":"0xbBbBBBBbbBBBbbbBbbBbbbbBBbBbbbbBbBbbBBbB"},"contents":"Hello, Bob!"}}]}"#;
1543        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1544        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1545    }
1546
1547    #[test]
1548    fn test_remove_pool_transactions() {
1549        let s = r#"{"method": "anvil_removePoolTransactions",  "params":["0x364d6D0333432C3Ac016Ca832fb8594A8cE43Ca6"]}"#;
1550        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1551        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1552    }
1553
1554    #[test]
1555    fn test_serde_anvil_reorg() {
1556        // TransactionData::JSON
1557        let s = r#"
1558        {
1559            "method": "anvil_reorg",
1560            "params": [
1561                5,
1562                [
1563                    [
1564                        {
1565                            "from": "0x976EA74026E726554dB657fA54763abd0C3a0aa9",
1566                            "to": "0x1199bc69f16FDD6690DC40339EC445FaE1b6DD11",
1567                            "value": 100
1568                        },
1569                        1
1570                    ],
1571                    [
1572                        {
1573                            "from": "0x976EA74026E726554dB657fA54763abd0C3a0aa9",
1574                            "to": "0x1199bc69f16FDD6690DC40339EC445FaE1b6DD11",
1575                            "value": 200
1576                        },
1577                        2
1578                    ]
1579                ]
1580            ]
1581        }
1582        "#;
1583        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1584        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1585        // TransactionData::Raw
1586        let s = r#"
1587        {
1588            "method": "anvil_reorg",
1589            "params": [
1590                5,
1591                [
1592                    [
1593                        "0x19d55c67e1ba8f1bbdfed75f8ad524ebf087e4ecb848a2d19881d7a5e3d2c54e1732cb1b462da3b3fdb05bdf4c4d3c8e3c9fcebdc2ab5fa5d59a3f752888f27e1b",
1594                        1
1595                    ]
1596                ]
1597            ]
1598        }
1599        "#;
1600        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1601        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1602        // TransactionData::Raw and TransactionData::JSON
1603        let s = r#"
1604        {
1605            "method": "anvil_reorg",
1606            "params": [
1607                5,
1608                [
1609                    [
1610                        "0x19d55c67e1ba8f1bbdfed75f8ad524ebf087e4ecb848a2d19881d7a5e3d2c54e1732cb1b462da3b3fdb05bdf4c4d3c8e3c9fcebdc2ab5fa5d59a3f752888f27e1b",
1611                        1
1612                    ],
1613                    [
1614                        {
1615                            "from": "0x976EA74026E726554dB657fA54763abd0C3a0aa9",
1616                            "to": "0x1199bc69f16FDD6690DC40339EC445FaE1b6DD11",
1617                            "value": 200
1618                        },
1619                        2
1620                    ]
1621                ]
1622            ]
1623        }
1624        "#;
1625        let value: serde_json::Value = serde_json::from_str(s).unwrap();
1626        let _req = serde_json::from_value::<EthRequest>(value).unwrap();
1627    }
1628}