diff --git a/e2e/rust/src/main.rs b/e2e/rust/src/main.rs index 27d1f85d..2ad2cb1a 100644 --- a/e2e/rust/src/main.rs +++ b/e2e/rust/src/main.rs @@ -4,8 +4,8 @@ use candid::{candid_method, Principal}; use ic_cdk_macros::update; use evm_rpc_types::{ - Block, BlockTag, EthMainnetService, Hex32, MultiRpcResult, ProviderError, RpcError, RpcService, - RpcServices, + Block, BlockTag, ConsensusStrategy, EthMainnetService, Hex32, MultiRpcResult, ProviderError, + RpcConfig, RpcError, RpcResult, RpcService, RpcServices, }; fn main() {} @@ -82,7 +82,13 @@ pub async fn test() { EthMainnetService::Llama, EthMainnetService::PublicNode, ])), - (), + Some(RpcConfig { + response_consensus: Some(ConsensusStrategy::Threshold { + total: None, + min: 2, + }), + ..Default::default() + }), BlockTag::Number(19709434_u32.into()), ), 10000000000, @@ -103,8 +109,25 @@ pub async fn test() { Err(err) => ic_cdk::trap(&format!("error in `eth_getBlockByNumber`: {:?}", err)), }, MultiRpcResult::Inconsistent(results) => ic_cdk::trap(&format!( - "inconsistent results in `eth_getBlockByNumber`: {:?}", - results + "inconsistent results in `eth_getBlockByNumber`: {}", + debug_inconsistent(&results) )), } } + +fn debug_inconsistent(results: &[(RpcService, RpcResult)]) -> String { + results + .iter() + .map(|(service, result)| { + let res_str = match result { + // A block contains too much information and in case of inconsistencies + // not all results can be displayed, so we only display the block number + // assuming that responses with the same block number should be equal. + Ok(block) => format!("Ok({}, ...)", block.number), + Err(err) => format!("Err({err})"), + }; + format!("{service:?}: {res_str}") + }) + .collect::>() + .join(", ") +} diff --git a/src/providers.rs b/src/providers.rs index b127735e..527c2219 100644 --- a/src/providers.rs +++ b/src/providers.rs @@ -56,7 +56,7 @@ pub const PROVIDERS: &[Provider] = &[ auth: RpcAuth::UrlParameter { url_pattern: "https://ethereum.blockpi.network/v1/rpc/{API_KEY}", }, - public_url: Some("https://ethereum.blockpi.network/v1/rpc/public"), + public_url: Some("https://ethereum.public.blockpi.network/v1/rpc/public"), }, alias: Some(SupportedRpcService::EthMainnet(EthMainnetService::BlockPi)), }, @@ -86,7 +86,7 @@ pub const PROVIDERS: &[Provider] = &[ auth: RpcAuth::UrlParameter { url_pattern: "https://ethereum-sepolia.blockpi.network/v1/rpc/{API_KEY}", }, - public_url: Some("https://ethereum-sepolia.blockpi.network/v1/rpc/public"), + public_url: None, }, alias: Some(SupportedRpcService::EthSepolia(EthSepoliaService::BlockPi)), }, @@ -151,7 +151,7 @@ pub const PROVIDERS: &[Provider] = &[ auth: RpcAuth::UrlParameter { url_pattern: "https://arbitrum.blockpi.network/v1/rpc/{API_KEY}", }, - public_url: Some("https://arbitrum.blockpi.network/v1/rpc/public"), + public_url: Some("https://arbitrum.public.blockpi.network/v1/rpc/public"), }, alias: Some(SupportedRpcService::ArbitrumOne(L2MainnetService::BlockPi)), }, @@ -194,7 +194,7 @@ pub const PROVIDERS: &[Provider] = &[ auth: RpcAuth::UrlParameter { url_pattern: "https://base.blockpi.network/v1/rpc/{API_KEY}", }, - public_url: Some("https://base.blockpi.network/v1/rpc/public"), + public_url: Some("https://base.public.blockpi.network/v1/rpc/public"), }, alias: Some(SupportedRpcService::BaseMainnet(L2MainnetService::BlockPi)), }, @@ -239,7 +239,7 @@ pub const PROVIDERS: &[Provider] = &[ auth: RpcAuth::UrlParameter { url_pattern: "https://optimism.blockpi.network/v1/rpc/{API_KEY}", }, - public_url: Some("https://optimism.blockpi.network/v1/rpc/public"), + public_url: Some("https://optimism.public.blockpi.network/v1/rpc/public"), }, alias: Some(SupportedRpcService::OptimismMainnet( L2MainnetService::BlockPi, diff --git a/src/types/tests.rs b/src/types/tests.rs index 65d20b99..7d7296cc 100644 --- a/src/types/tests.rs +++ b/src/types/tests.rs @@ -120,13 +120,15 @@ fn arb_override_provider() -> impl Strategy { } mod override_provider { + use crate::memory::insert_api_key; use crate::providers::PROVIDERS; - use crate::types::{OverrideProvider, RegexSubstitution}; + use crate::types::{ApiKey, OverrideProvider, RegexSubstitution}; use evm_rpc_types::RpcApi; use ic_management_canister_types::HttpHeader; #[test] fn should_override_provider_with_localhost() { + setup_api_keys(); let override_provider = override_to_localhost(); for provider in PROVIDERS { let overriden_provider = override_provider.apply(provider.api()); @@ -142,6 +144,7 @@ mod override_provider { #[test] fn should_be_noop_when_empty() { + setup_api_keys(); let no_override = OverrideProvider::default(); for provider in PROVIDERS { let initial_api = provider.api(); @@ -152,6 +155,7 @@ mod override_provider { #[test] fn should_use_replacement_pattern() { + setup_api_keys(); let identity_override = OverrideProvider { override_url: Some(RegexSubstitution { pattern: "(?.*)".into(), @@ -160,13 +164,15 @@ mod override_provider { }; for provider in PROVIDERS { let initial_api = provider.api(); - let overriden_provider = identity_override.apply(initial_api.clone()); - assert_eq!(overriden_provider, Ok(initial_api)) + let overriden_provider = identity_override.apply(initial_api.clone()).unwrap(); + assert_eq!(overriden_provider.headers, None); + assert_eq!(overriden_provider.url, initial_api.url) } } #[test] fn should_override_headers() { + setup_api_keys(); let identity_override = OverrideProvider { override_url: Some(RegexSubstitution { pattern: "(.*)".into(), @@ -192,6 +198,15 @@ mod override_provider { } } + fn setup_api_keys() { + for provider in PROVIDERS { + insert_api_key( + provider.provider_id, + ApiKey::try_from("unit-test-key".to_string()).unwrap(), + ) + } + } + fn override_to_localhost() -> OverrideProvider { OverrideProvider { override_url: Some(RegexSubstitution {