use std::{collections::HashMap, str::FromStr, sync::LazyLock};
use alloy::{
primitives::B256,
rpc::client::{ClientBuilder, ReqwestClient},
};
use tycho_common::{
models::{blockchain::Block, Address, Chain},
Bytes,
};
use crate::BytesCodec;
pub const TEST_BLOCK_NUMBER: u64 = 23475728;
pub const TEST_BLOCK_HASH: &str =
"0x7f70ac678819e24c4947a3a95fdab886083892a18ba1a962ebaac31455584042";
pub const BALANCER_VAULT_STR: &str = "0xba12222222228d8ba445958a75a0704d566bf2c8";
pub const STETH_STR: &str = "0xae7ab96520de3a18e5e111b5eaab095312d7fe84";
pub const DAI_STR: &str = "0x6b175474e89094c44da98b954eedeac495271d0f";
pub const WBTC_STR: &str = "0x2260fac5e5542a773aa44fbcfedf7c193bc2c599";
pub const USDC_STR: &str = "0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48";
pub const USDT_STR: &str = "0xdAC17F958D2ee523a2206206994597C13D831ec7";
pub const WETH_STR: &str = "0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2";
pub const ARB_USDC_STR: &str = "0xaf88d065e77c8cC2239327C5EDb3A432268e5831";
pub const ARB_WETH_STR: &str = "0x82aF49447D8a07e3bd95BD0d56f35241523fBab1";
pub const ARB_ARB_STR: &str = "0x912CE59144191C1204E64559FE8253a0e49E6548";
pub const ARB_USDC_HOLDER_ADDR: &str = "0xC6962004f452bE9203591991D15f6b388e09E8D0"; pub const ARB_WETH_HOLDER_ADDR: &str = "0xC6962004f452bE9203591991D15f6b388e09E8D0"; pub const ARB_ARB_HOLDER_ADDR: &str = "0x92c63d0e701CAAe670C9415d91C474F686298f00";
pub const TOKEN_ADDRESSES: [&str; 5] = [BALANCER_VAULT_STR, STETH_STR, DAI_STR, WBTC_STR, USDC_STR];
pub const BALANCER_VAULT_EXPECTED_SLOTS: usize = 47690;
pub const STETH_EXPECTED_SLOTS: usize = 789526;
pub const USDC_HOLDER_ADDR: &str = "0x000000000004444c5dc75cB358380D2e3dE08A90";
pub const USDC_HOLDER_BALANCE: u64 = 74743132960379_u64;
pub const WETH_HOLDER_ADDR: &str = "0xB4e16d0168e52d35CaCD2c6185b44281Ec28C9Dc";
pub static TOKEN_HOLDERS: LazyLock<HashMap<Address, (Bytes, Bytes)>> = LazyLock::new(|| {
HashMap::from([
(
Address::from_str(USDC_STR).unwrap(),
(
Bytes::from_str(USDC_HOLDER_ADDR).unwrap(),
Bytes::from_str("0x43f6e8f16703").unwrap(),
),
),
(
Address::from_str(WETH_STR).unwrap(),
(
Bytes::from_str(WETH_HOLDER_ADDR).unwrap(),
Bytes::from_str("0x2386f26fc10000").unwrap(), ),
),
])
});
pub static ARB_TOKEN_HOLDERS: LazyLock<HashMap<Address, (Bytes, Bytes)>> = LazyLock::new(|| {
HashMap::from([
(
Address::from_str(ARB_USDC_STR).unwrap(),
(
Bytes::from_str(ARB_USDC_HOLDER_ADDR).unwrap(),
Bytes::from_str("0x09184e72a000").unwrap(), ),
),
(
Address::from_str(ARB_WETH_STR).unwrap(),
(
Bytes::from_str(ARB_WETH_HOLDER_ADDR).unwrap(),
Bytes::from_str("0x3635c9adc5dea00000").unwrap(), ),
),
(
Address::from_str(ARB_ARB_STR).unwrap(),
(
Bytes::from_str(ARB_ARB_HOLDER_ADDR).unwrap(),
Bytes::from_str("0x3635c9adc5dea00000").unwrap(), ),
),
])
});
pub static TEST_SLOTS: LazyLock<HashMap<B256, B256>> = LazyLock::new(|| {
HashMap::from([
(
B256::from_str("0000000000000000000000000000000000000000000000000000000000000000")
.unwrap(),
B256::from_str("0000000000000000000000000000000000000000000000000000000000000001")
.unwrap(),
),
(
B256::from_str("0000000000000000000000000000000000000000000000000000000000000003")
.unwrap(),
B256::from_str("00000000000000000000006048a8c631fb7e77eca533cf9c29784e482391e700")
.unwrap(),
),
(
B256::from_str("00015ea75c6f99b2e8663793de8ab1ce7c52e3295bf307bbf9990d4af56f7035")
.unwrap(),
B256::from_str("0000000000000000000000000000000000000000000000000000000000000001")
.unwrap(),
),
])
});
static RPC_CLIENT: LazyLock<ReqwestClient> = LazyLock::new(|| {
let url = std::env::var("RPC_URL")
.expect("RPC_URL must be set for testing")
.parse()
.expect("Invalid RPC_URL");
ClientBuilder::default().http(url)
});
pub struct TestFixture {
pub block: Block,
pub inner_rpc: ReqwestClient,
pub url: String,
}
impl TestFixture {
pub fn new() -> Self {
let chain = Chain::Ethereum;
let inner_rpc = RPC_CLIENT.clone();
let block_hash = B256::from_str(TEST_BLOCK_HASH).expect("expected valid block hash");
let block = Block::new(
TEST_BLOCK_NUMBER,
chain,
block_hash.to_bytes(),
Default::default(),
Default::default(),
);
let url = std::env::var("RPC_URL").expect("RPC_URL must be set for testing");
Self { block, inner_rpc, url }
}
pub fn new_arbitrum() -> Self {
let url = std::env::var("ARB_RPC_URL").expect("ARB_RPC_URL must be set for Arbitrum tests");
let inner_rpc = ClientBuilder::default().http(
url.parse()
.expect("Invalid ARB_RPC_URL"),
);
let block = Block::new(
0,
Chain::Arbitrum,
Default::default(),
Default::default(),
Default::default(),
);
Self { block, inner_rpc, url }
}
}
impl Default for TestFixture {
fn default() -> Self {
Self::new()
}
}