tempo_bench/cmd/
signer_providers.rs1use std::sync::Arc;
2
3use alloy::{
4 providers::{
5 DynProvider, Provider, ProviderBuilder, RootProvider,
6 fillers::{CachedNonceManager, FillProvider, TxFiller},
7 },
8 signers::local::{MnemonicBuilder, Secp256k1Signer},
9 transports::http::reqwest::Url,
10};
11use indicatif::ProgressIterator;
12use rand::seq::IndexedRandom;
13use tempo_alloy::TempoNetwork;
14
15type BenchProvider<F> = FillProvider<F, RootProvider<TempoNetwork>, TempoNetwork>;
16type UnsignedProviderFactory<F> =
17 Box<dyn Fn(Url, CachedNonceManager) -> BenchProvider<F> + Send + Sync>;
18type SignedProviderFactory = Box<
19 dyn Fn(Secp256k1Signer, Url, CachedNonceManager) -> DynProvider<TempoNetwork> + Send + Sync,
20>;
21
22#[derive(Debug, Clone)]
24pub(crate) struct SignerProviderManager<F: TxFiller<TempoNetwork>>(
25 Arc<SignerProviderManagerInner<F>>,
26);
27
28#[derive(Debug)]
29struct SignerProviderManagerInner<F: TxFiller<TempoNetwork>> {
30 signers: Vec<Secp256k1Signer>,
32 target_urls: Vec<Url>,
34 unsigned_providers: Vec<BenchProvider<F>>,
36 signer_providers: Vec<(Secp256k1Signer, DynProvider<TempoNetwork>)>,
38}
39
40impl<F: TxFiller<TempoNetwork> + 'static> SignerProviderManager<F> {
41 pub fn new(
48 mnemonic: String,
49 from_mnemonic_index: u32,
50 accounts: u64,
51 target_urls: Vec<Url>,
52 unsigned_provider_factory: UnsignedProviderFactory<F>,
53 signed_provider_factory: SignedProviderFactory,
54 ) -> Self {
55 let cached_nonce_manager = CachedNonceManager::default();
56 let signers: Vec<Secp256k1Signer> = (from_mnemonic_index..)
58 .take(accounts as usize)
59 .progress_count(accounts)
60 .map(|i| MnemonicBuilder::from_phrase_nth(&mnemonic, i).into_secp256k1())
61 .collect();
62 let unsigned_providers = target_urls
63 .iter()
64 .cloned()
65 .map(|target_url| (unsigned_provider_factory)(target_url, cached_nonce_manager.clone()))
66 .collect();
67 let signer_providers = signers
68 .iter()
69 .progress()
70 .cloned()
71 .map(|signer| {
72 let target_url = target_urls.choose(&mut rand::rng()).unwrap().clone();
73 let provider = (signed_provider_factory)(
74 signer.clone(),
75 target_url,
76 cached_nonce_manager.clone(),
77 );
78 (signer, provider)
79 })
80 .collect();
81 Self(Arc::new(SignerProviderManagerInner {
82 signers,
83 target_urls,
84 unsigned_providers,
85 signer_providers,
86 }))
87 }
88
89 pub fn target_url_providers(&self) -> Vec<(&Url, DynProvider<TempoNetwork>)> {
91 self.0
92 .target_urls
93 .iter()
94 .map(|target_url| {
95 let provider = ProviderBuilder::default()
96 .connect_http(target_url.clone())
97 .erased();
98 (target_url, provider)
99 })
100 .collect()
101 }
102
103 pub fn signer_providers(&self) -> &[(Secp256k1Signer, DynProvider<TempoNetwork>)] {
105 &self.0.signer_providers
106 }
107
108 pub fn random_unsigned_provider(&self) -> BenchProvider<F> {
110 self.0
111 .unsigned_providers
112 .choose(&mut rand::rng())
113 .unwrap()
114 .clone()
115 }
116
117 pub fn random_signer(&self) -> &Secp256k1Signer {
119 self.0.signers.choose(&mut rand::rng()).unwrap()
120 }
121}