-
Notifications
You must be signed in to change notification settings - Fork 79
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat: add cli options for server configuration #487
Changes from all commits
b8f57c0
59eae51
f9f63f4
d54b085
f620ac4
9b2df93
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,21 +1,32 @@ | ||
use crate::utils::LockedPort; | ||
use crate::utils::{LockedPort,get_node_binary_path}; | ||
use crate::ReceiptExt; | ||
use alloy::network::primitives::{BlockTransactionsKind, HeaderResponse as _}; | ||
use alloy::network::{Network, ReceiptResponse as _, TransactionBuilder}; | ||
use alloy::primitives::{Address, U256}; | ||
use alloy::signers::local::LocalSigner; | ||
use alloy::providers::{ | ||
PendingTransaction, PendingTransactionBuilder, PendingTransactionError, Provider, RootProvider, | ||
SendableTx, WalletProvider, | ||
}; | ||
use alloy::rpc::types::{Block, TransactionRequest}; | ||
use alloy::transports::http::{reqwest, Http}; | ||
use alloy::rpc::{ | ||
types::{Block, TransactionRequest}, | ||
client::RpcClient, | ||
}; | ||
use alloy::transports::http::{ | ||
reqwest, | ||
reqwest::{ | ||
header::HeaderMap, | ||
Client, | ||
}, | ||
Http | ||
}; | ||
use alloy::transports::{RpcError, Transport, TransportErrorKind, TransportResult}; | ||
use alloy_zksync::network::header_response::HeaderResponse; | ||
use alloy_zksync::network::receipt_response::ReceiptResponse; | ||
use alloy_zksync::network::transaction_response::TransactionResponse; | ||
use alloy_zksync::network::Zksync; | ||
use alloy_zksync::node_bindings::EraTestNode; | ||
use alloy_zksync::provider::{zksync_provider, ProviderBuilderExt}; | ||
use alloy_zksync::node_bindings::{EraTestNode,EraTestNodeError::NoKeysAvailable}; | ||
use alloy_zksync::provider::{zksync_provider, ProviderBuilderExt, layers::era_test_node::EraTestNodeLayer}; | ||
use alloy_zksync::wallet::ZksyncWallet; | ||
use anyhow::Context as _; | ||
use itertools::Itertools; | ||
|
@@ -71,10 +82,7 @@ pub async fn init_testing_provider( | |
.with_recommended_fillers() | ||
.on_era_test_node_with_wallet_and_config(|node| { | ||
f(node | ||
.path( | ||
std::env::var("ANVIL_ZKSYNC_BINARY_PATH") | ||
.unwrap_or("../target/release/anvil-zksync".to_string()), | ||
) | ||
.path(get_node_binary_path()) | ||
.port(locked_port.port)) | ||
}); | ||
|
||
|
@@ -93,6 +101,66 @@ pub async fn init_testing_provider( | |
}) | ||
} | ||
|
||
// Init testing provider which sends specified HTTP headers e.g. for authentication | ||
// Outside of `TestingProvider` to avoid specifying `P` | ||
pub async fn init_testing_provider_with_http_headers( | ||
headers: HeaderMap, | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Also, isn't it possible to express the logic of adding headers as a Note that function is composable, so we can wrap any number of layers here, e.g. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. No, because it's not the setting on the node, it's the setting on provider. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We could extend the provider code of |
||
f: impl FnOnce(EraTestNode) -> EraTestNode, | ||
) -> anyhow::Result< | ||
TestingProvider<impl FullZksyncProvider<Http<reqwest::Client>>, Http<reqwest::Client>>, | ||
> { | ||
use alloy::signers::Signer; | ||
|
||
let locked_port = LockedPort::acquire_unused().await?; | ||
let node_layer = EraTestNodeLayer::from( | ||
f( | ||
EraTestNode::new() | ||
.path(get_node_binary_path()) | ||
.port(locked_port.port) | ||
) | ||
); | ||
|
||
let client_with_headers = Client::builder().default_headers(headers).build()?; | ||
let rpc_url = node_layer.endpoint_url(); | ||
let http = Http::with_client(client_with_headers, rpc_url); | ||
let rpc_client = RpcClient::new(http, true); | ||
|
||
let default_keys = node_layer.instance().keys().to_vec(); | ||
let (default_key, remaining_keys) = default_keys | ||
.split_first() | ||
.ok_or(NoKeysAvailable)?; | ||
|
||
let default_signer = LocalSigner::from(default_key.clone()) | ||
.with_chain_id(Some(node_layer.instance().chain_id())); | ||
let mut wallet = ZksyncWallet::from(default_signer); | ||
|
||
for key in remaining_keys { | ||
let signer = LocalSigner::from(key.clone()); | ||
wallet.register_signer(signer) | ||
} | ||
|
||
let provider = zksync_provider() | ||
.with_recommended_fillers() | ||
.wallet(wallet) | ||
.layer(node_layer) | ||
.on_client(rpc_client); | ||
|
||
// Grab default rich accounts right after init. Note that subsequent calls to this method | ||
// might return different value as wallet's signers are dynamic and can be changed by the user. | ||
let rich_accounts = provider.signer_addresses().collect::<Vec<_>>(); | ||
// Wait for anvil-zksync to get up and be able to respond | ||
// Ignore error response (should not fail here if provider is used with intentionally wrong origin for testing purposes) | ||
let _ = provider.get_chain_id().await; | ||
// Explicitly unlock the port to showcase why we waited above | ||
drop(locked_port); | ||
|
||
Ok(TestingProvider { | ||
inner: provider, | ||
rich_accounts, | ||
_pd: Default::default(), | ||
}) | ||
} | ||
|
||
impl<P, T> TestingProvider<P, T> | ||
where | ||
P: FullZksyncProvider<T>, | ||
|
@@ -383,13 +451,7 @@ where | |
self | ||
} | ||
|
||
/// Builder-pattern method for setting the chain id. | ||
pub fn with_chain_id(mut self, id: u64) -> Self { | ||
self.inner = self.inner.with_chain_id(id); | ||
self | ||
} | ||
|
||
/// Builder-pattern method for setting the recipient. | ||
/// Builder-pattern method for setting the receiver. | ||
pub fn with_to(mut self, to: Address) -> Self { | ||
self.inner = self.inner.with_to(to); | ||
self | ||
|
@@ -401,6 +463,12 @@ where | |
self | ||
} | ||
|
||
/// Builder-pattern method for setting the chain id. | ||
pub fn with_chain_id(mut self, id: u64) -> Self { | ||
self.inner = self.inner.with_chain_id(id); | ||
self | ||
} | ||
|
||
/// Submits transaction to the node. | ||
/// | ||
/// This does not wait for the transaction to be confirmed, but returns a [`PendingTransactionFinalizable`] | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we solve it by using
Box<dyn FullZksyncProvider<T>>
instead of template parameters?Transport can also be erased by using
Box<dyn Transport + Clone>
.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Possibly, but we already have the default init_testing_provider function which I copied. Can be refactored though.