Skip to content

Commit

Permalink
Merge pull request darkforestry#70 from darkforestry/0xkitsune/propag…
Browse files Browse the repository at this point in the history
…ate-errors

Propagate errors, remove unwraps, expects and panics
  • Loading branch information
0xKitsune authored Jul 27, 2023
2 parents 04c6166 + 7dfdd45 commit 14545d6
Show file tree
Hide file tree
Showing 28 changed files with 492 additions and 478 deletions.
2 changes: 2 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ uniswap_v3_math = "0.4.0"
regex = "1.9.1"
spinoff = "0.7.0"
arraydeque = {version = "0.5.1", optional = true}
eyre = "0.6.8"
lazy_static = "1.4.0"


[features]
Expand Down
9 changes: 4 additions & 5 deletions examples/discover-erc-4626-vaults.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,12 @@
use amms::discovery;
use ethers::providers::{Http, Provider};
use std::{error::Error, sync::Arc};
use std::sync::Arc;

#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
async fn main() -> eyre::Result<()> {
//Add rpc endpoint here:
let rpc_endpoint =
std::env::var("ETHEREUM_RPC_ENDPOINT").expect("Could not get ETHEREUM_RPC_ENDPOINT");
let provider = Arc::new(Provider::<Http>::try_from(rpc_endpoint).unwrap());
let rpc_endpoint = std::env::var("ETHEREUM_RPC_ENDPOINT")?;
let provider = Arc::new(Provider::<Http>::try_from(rpc_endpoint)?);

//discover vaults
let _vaults = discovery::erc_4626::discover_erc_4626_vaults(provider, 30000).await?;
Expand Down
9 changes: 4 additions & 5 deletions examples/discover-factories.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,12 @@
use amms::discovery::factory::{discover_factories, DiscoverableFactory};
use ethers::providers::{Http, Provider};
use std::{error::Error, sync::Arc};
use std::sync::Arc;

#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
let rpc_endpoint =
std::env::var("ETHEREUM_RPC_ENDPOINT").expect("Could not get ETHEREUM_RPC_ENDPOINT");
async fn main() -> eyre::Result<()> {
let rpc_endpoint = std::env::var("ETHEREUM_RPC_ENDPOINT")?;

let provider = Arc::new(Provider::<Http>::try_from(rpc_endpoint).unwrap());
let provider = Arc::new(Provider::<Http>::try_from(rpc_endpoint)?);

// Find all UniswapV2 and UniswapV3 compatible factories and filter out matches with less than 1000 AMMs
let number_of_amms_threshold = 1000;
Expand Down
26 changes: 12 additions & 14 deletions examples/filter-value.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,25 +10,24 @@ use ethers::{
providers::{Http, Provider},
types::{H160, U256},
};
use std::{error::Error, str::FromStr, sync::Arc};
use std::{str::FromStr, sync::Arc};

#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
let rpc_endpoint =
std::env::var("ETHEREUM_RPC_ENDPOINT").expect("Could not get ETHEREUM_RPC_ENDPOINT");
let provider = Arc::new(Provider::<Http>::try_from(rpc_endpoint).unwrap());
async fn main() -> eyre::Result<()> {
let rpc_endpoint = std::env::var("ETHEREUM_RPC_ENDPOINT")?;
let provider = Arc::new(Provider::<Http>::try_from(rpc_endpoint)?);

// Initialize factories
let factories = vec![
//UniswapV2
Factory::UniswapV2Factory(UniswapV2Factory::new(
H160::from_str("0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f").unwrap(),
H160::from_str("0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f")?,
2638438,
300,
)),
//Add Sushiswap
Factory::UniswapV2Factory(UniswapV2Factory::new(
H160::from_str("0xC0AEe478e3658e2610c5F7A4A2E1777cE9e4f2Ac").unwrap(),
H160::from_str("0xC0AEe478e3658e2610c5F7A4A2E1777cE9e4f2Ac")?,
10794229,
300,
)),
Expand All @@ -39,19 +38,18 @@ async fn main() -> Result<(), Box<dyn Error>> {
sync::sync_amms(factories.clone(), provider.clone(), None, 10000).await?;

//Filter out blacklisted tokens
let blacklisted_tokens =
vec![H160::from_str("0x1f9840a85d5aF5bf1D1762F925BDADdC4201F984").unwrap()];
let blacklisted_tokens = vec![H160::from_str(
"0x1f9840a85d5aF5bf1D1762F925BDADdC4201F984",
)?];
let filtered_amms = filters::address::filter_blacklisted_tokens(pools, blacklisted_tokens);

// Filter out pools below usd threshold
let weth_address = H160::from_str("0x0d500B1d8E8eF31E21C99d1Db9A6444d3ADf1270").unwrap();
let usd_weth_pair_address =
H160::from_str("0xcd353F79d9FADe311fC3119B841e1f456b54e858").unwrap();
let weth_address = H160::from_str("0x0d500B1d8E8eF31E21C99d1Db9A6444d3ADf1270")?;
let usd_weth_pair_address = H160::from_str("0xcd353F79d9FADe311fC3119B841e1f456b54e858")?;
let usd_weth_pool = AMM::UniswapV2Pool(
UniswapV2Pool::new_from_address(usd_weth_pair_address, 300, provider.clone()).await?,
);
let weth_value_in_token_to_weth_pool_threshold =
U256::from_dec_str("100000000000000000").unwrap(); // 10 weth
let weth_value_in_token_to_weth_pool_threshold = U256::from_dec_str("100000000000000000")?; // 10 weth

println!("Filtering pools below usd threshold");

Expand Down
9 changes: 4 additions & 5 deletions examples/simulate-swap.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,12 @@ use ethers::{
providers::{Http, Provider},
types::{H160, U256},
};
use std::{error::Error, str::FromStr, sync::Arc};
use std::{str::FromStr, sync::Arc};

#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
let rpc_endpoint =
std::env::var("ETHEREUM_RPC_ENDPOINT").expect("Could not get ETHEREUM_RPC_ENDPOINT");
let middleware = Arc::new(Provider::<Http>::try_from(rpc_endpoint).unwrap());
async fn main() -> eyre::Result<()> {
let rpc_endpoint = std::env::var("ETHEREUM_RPC_ENDPOINT")?;
let middleware = Arc::new(Provider::<Http>::try_from(rpc_endpoint)?);

// Initialize the pool
let pool_address = H160::from_str("0xB4e16d0168e52d35CaCD2c6185b44281Ec28C9Dc")?;
Expand Down
14 changes: 6 additions & 8 deletions examples/state-space.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,12 @@ use ethers::{
providers::{Http, Provider, Ws},
types::H160,
};
use std::{error::Error, str::FromStr, sync::Arc};
use std::{str::FromStr, sync::Arc};

#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
let rpc_endpoint =
std::env::var("ETHEREUM_RPC_ENDPOINT").expect("Could not get ETHEREUM_RPC_ENDPOINT");
let ws_endpoint =
std::env::var("ETHEREUM_WS_ENDPOINT").expect("Could not get ETHEREUM_WS_ENDPOINT");
async fn main() -> eyre::Result<()> {
let rpc_endpoint = std::env::var("ETHEREUM_RPC_ENDPOINT")?;
let ws_endpoint = std::env::var("ETHEREUM_WS_ENDPOINT")?;

// Initialize middleware
let middleware = Arc::new(Provider::<Http>::try_from(rpc_endpoint)?);
Expand All @@ -24,13 +22,13 @@ async fn main() -> Result<(), Box<dyn Error>> {
let factories = vec![
//UniswapV2
Factory::UniswapV2Factory(UniswapV2Factory::new(
H160::from_str("0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f").unwrap(),
H160::from_str("0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f")?,
2638438,
300,
)),
//Add Sushiswap
Factory::UniswapV2Factory(UniswapV2Factory::new(
H160::from_str("0xC0AEe478e3658e2610c5F7A4A2E1777cE9e4f2Ac").unwrap(),
H160::from_str("0xC0AEe478e3658e2610c5F7A4A2E1777cE9e4f2Ac")?,
10794229,
300,
)),
Expand Down
9 changes: 4 additions & 5 deletions examples/swap-calldata.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,12 @@ use ethers::{
providers::{Http, Provider},
types::{H160, U256},
};
use std::{error::Error, str::FromStr, sync::Arc};
use std::{str::FromStr, sync::Arc};

#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
let rpc_endpoint =
std::env::var("ETHEREUM_RPC_ENDPOINT").expect("Could not get ETHEREUM_RPC_ENDPOINT");
let middleware = Arc::new(Provider::<Http>::try_from(rpc_endpoint).unwrap());
async fn main() -> eyre::Result<()> {
let rpc_endpoint = std::env::var("ETHEREUM_RPC_ENDPOINT")?;
let middleware = Arc::new(Provider::<Http>::try_from(rpc_endpoint)?);

// Initialize the pool
let pool_address = H160::from_str("0xB4e16d0168e52d35CaCD2c6185b44281Ec28C9Dc")?;
Expand Down
15 changes: 7 additions & 8 deletions examples/sync-amms.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,31 +9,30 @@ use ethers::{
providers::{Http, Provider},
types::H160,
};
use std::{error::Error, str::FromStr, sync::Arc};
use std::{str::FromStr, sync::Arc};

#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
async fn main() -> eyre::Result<()> {
//Add rpc endpoint here:
let rpc_endpoint =
std::env::var("ETHEREUM_RPC_ENDPOINT").expect("Could not get ETHEREUM_RPC_ENDPOINT");
let provider = Arc::new(Provider::<Http>::try_from(rpc_endpoint).unwrap());
let rpc_endpoint = std::env::var("ETHEREUM_RPC_ENDPOINT")?;
let provider = Arc::new(Provider::<Http>::try_from(rpc_endpoint)?);

let factories = vec![
//UniswapV2
Factory::UniswapV2Factory(UniswapV2Factory::new(
H160::from_str("0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f").unwrap(),
H160::from_str("0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f")?,
2638438,
300,
)),
// //Add Sushiswap
Factory::UniswapV2Factory(UniswapV2Factory::new(
H160::from_str("0xC0AEe478e3658e2610c5F7A4A2E1777cE9e4f2Ac").unwrap(),
H160::from_str("0xC0AEe478e3658e2610c5F7A4A2E1777cE9e4f2Ac")?,
10794229,
300,
)),
//Add UniswapV3
Factory::UniswapV3Factory(UniswapV3Factory::new(
H160::from_str("0x1F98431c8aD98523631AE4a59f267346ea31F984").unwrap(),
H160::from_str("0x1F98431c8aD98523631AE4a59f267346ea31F984")?,
185,
)),
];
Expand Down
104 changes: 54 additions & 50 deletions src/amm/erc_4626/batch_request/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ use ethers::{
};
use std::sync::Arc;

use crate::errors::AMMError;
use crate::{amm::AutomatedMarketMaker, errors::AMMError};

use ethers::prelude::abigen;

Expand All @@ -16,15 +16,61 @@ abigen!(
"src/amm/erc_4626/batch_request/GetERC4626VaultDataBatchRequestABI.json";
);

fn populate_vault_data_from_tokens(
mut vault: ERC4626Vault,
tokens: Vec<Token>,
) -> Option<ERC4626Vault> {
vault.vault_token = tokens[0].to_owned().into_address()?;
vault.vault_token_decimals = tokens[1].to_owned().into_uint()?.as_u32() as u8;
vault.asset_token = tokens[2].to_owned().into_address()?;
vault.asset_token_decimals = tokens[3].to_owned().into_uint()?.as_u32() as u8;
vault.vault_reserve = tokens[4].to_owned().into_uint()?;
vault.asset_reserve = tokens[5].to_owned().into_uint()?;

let deposit_fee_delta_1 = tokens[6].to_owned().into_uint()?;
let deposit_fee_delta_2 = tokens[7].to_owned().into_uint()?;
let deposit_no_fee = tokens[8].to_owned().into_uint()?;
let withdraw_fee_delta_1 = tokens[9].to_owned().into_uint()?;
let withdraw_fee_delta_2 = tokens[10].to_owned().into_uint()?;
let withdraw_no_fee = tokens[11].to_owned().into_uint()?;

// If both deltas are zero, the fee is zero
if deposit_fee_delta_1.is_zero() && deposit_fee_delta_2.is_zero() {
vault.deposit_fee = 0;
// Assuming 18 decimals, if the delta of 1e20 is half the delta of 2e20, relative fee.
// Delta / (amount without fee / 10000) to give us the fee in basis points
} else if deposit_fee_delta_1 * 2 == deposit_fee_delta_2 {
vault.deposit_fee =
(deposit_fee_delta_1 / (deposit_no_fee / U256::from("0x2710"))).as_u32();
} else {
// If not a relative fee or zero, ignore vault
return None;
}

// If both deltas are zero, the fee is zero
if withdraw_fee_delta_1.is_zero() && withdraw_fee_delta_2.is_zero() {
vault.withdraw_fee = 0;
// Assuming 18 decimals, if the delta of 1e20 is half the delta of 2e20, relative fee.
// Delta / (amount without fee / 10000) to give us the fee in basis points
} else if withdraw_fee_delta_1 * 2 == withdraw_fee_delta_2 {
vault.withdraw_fee =
(withdraw_fee_delta_1 / (withdraw_no_fee / U256::from("0x2710"))).as_u32();
} else {
// If not a relative fee or zero, ignore vault
return None;
}

Some(vault)
}

pub async fn get_4626_vault_data_batch_request<M: Middleware>(
vault: &mut ERC4626Vault,
middleware: Arc<M>,
) -> Result<(), AMMError<M>> {
let constructor_args =
Token::Tuple(vec![Token::Array(vec![Token::Address(vault.vault_token)])]);

let deployer =
IGetERC4626VaultDataBatchRequest::deploy(middleware.clone(), constructor_args).unwrap();
let deployer = IGetERC4626VaultDataBatchRequest::deploy(middleware.clone(), constructor_args)?;

let return_data: Bytes = deployer.call_raw().await?;
let return_data_tokens = ethers::abi::decode(
Expand All @@ -48,54 +94,12 @@ pub async fn get_4626_vault_data_batch_request<M: Middleware>(
for tokens in return_data_tokens {
if let Some(tokens_arr) = tokens.into_array() {
for tup in tokens_arr {
if let Some(vault_data) = tup.into_tuple() {
// If the vault token is not zero, signalling that the vault data was populated
if !vault_data[0].to_owned().into_address().unwrap().is_zero() {
vault.vault_token = vault_data[0].to_owned().into_address().unwrap();
vault.vault_token_decimals =
vault_data[1].to_owned().into_uint().unwrap().as_u32() as u8;
vault.asset_token = vault_data[2].to_owned().into_address().unwrap();
vault.asset_token_decimals =
vault_data[3].to_owned().into_uint().unwrap().as_u32() as u8;
vault.vault_reserve = vault_data[4].to_owned().into_uint().unwrap();
vault.asset_reserve = vault_data[5].to_owned().into_uint().unwrap();

let deposit_fee_delta_1 = vault_data[6].to_owned().into_uint().unwrap();
let deposit_fee_delta_2 = vault_data[7].to_owned().into_uint().unwrap();
let deposit_no_fee = vault_data[8].to_owned().into_uint().unwrap();
let withdraw_fee_delta_1 = vault_data[9].to_owned().into_uint().unwrap();
let withdraw_fee_delta_2 = vault_data[10].to_owned().into_uint().unwrap();
let withdraw_no_fee = vault_data[11].to_owned().into_uint().unwrap();

// If both deltas are zero, the fee is zero
if deposit_fee_delta_1.is_zero() && deposit_fee_delta_2.is_zero() {
vault.deposit_fee = 0;
// Assuming 18 decimals, if the delta of 1e20 is half the delta of 2e20, relative fee.
// Delta / (amount without fee / 10000) to give us the fee in basis points
} else if deposit_fee_delta_1 * 2 == deposit_fee_delta_2 {
vault.deposit_fee = (deposit_fee_delta_1
/ (deposit_no_fee / U256::from("0x2710")))
.as_u32();
} else {
// If not a relative fee or zero, ignore vault
return Err(AMMError::InvalidERC4626Fee);
}
let vault_data = tup
.into_tuple()
.ok_or(AMMError::BatchRequestError(vault.address()))?;

// If both deltas are zero, the fee is zero
if withdraw_fee_delta_1.is_zero() && withdraw_fee_delta_2.is_zero() {
vault.withdraw_fee = 0;
// Assuming 18 decimals, if the delta of 1e20 is half the delta of 2e20, relative fee.
// Delta / (amount without fee / 10000) to give us the fee in basis points
} else if withdraw_fee_delta_1 * 2 == withdraw_fee_delta_2 {
vault.withdraw_fee = (withdraw_fee_delta_1
/ (withdraw_no_fee / U256::from("0x2710")))
.as_u32();
} else {
// If not a relative fee or zero, ignore vault
return Err(AMMError::InvalidERC4626Fee);
}
}
}
*vault = populate_vault_data_from_tokens(vault.to_owned(), vault_data)
.ok_or(AMMError::BatchRequestError(vault.address()))?;
}
}
}
Expand Down
Loading

0 comments on commit 14545d6

Please sign in to comment.