feat(tycho-router-encoder): Select strategy depending on the solution

- The tycho router address default is set at the EncoderBuilder level (not inside the strategies)
- Rename TychoCoreChain to TychoCommonChain
- Only take TychoCommonChain as an argument at the outermost level: EncoderBuilder. Everywhere else we use the execution Chain right away

--- don't change below this line ---
ENG-4332 Took 1 hour 10 minutes
This commit is contained in:
Diana Carvalho
2025-04-08 15:55:55 +01:00
parent 6fd0ab54c1
commit f5e712e0ff
6 changed files with 150 additions and 147 deletions

View File

@@ -175,7 +175,7 @@ mod tests {
use alloy_primitives::Uint; use alloy_primitives::Uint;
use num_bigint::BigUint; use num_bigint::BigUint;
use tycho_common::models::Chain as TychoCoreChain; use tycho_common::models::Chain as TychoCommonChain;
use super::*; use super::*;
@@ -211,7 +211,7 @@ mod tests {
} }
fn eth_chain() -> Chain { fn eth_chain() -> Chain {
TychoCoreChain::Ethereum.into() TychoCommonChain::Ethereum.into()
} }
#[test] #[test]

View File

@@ -1,13 +1,15 @@
use tycho_common::{models::Chain, Bytes}; use std::collections::HashMap;
use tycho_common::{models::Chain as TychoCommonChain, Bytes};
use crate::encoding::{ use crate::encoding::{
errors::EncodingError, errors::EncodingError,
evm::{ evm::{
strategy_encoder::strategy_encoders::SplitSwapStrategyEncoder, constants::DEFAULT_ROUTERS_JSON,
swap_encoder::swap_encoder_registry::SwapEncoderRegistry, swap_encoder::swap_encoder_registry::SwapEncoderRegistry,
tycho_encoders::{TychoExecutorEncoder, TychoRouterEncoder}, tycho_encoders::{TychoExecutorEncoder, TychoRouterEncoder},
}, },
strategy_encoder::StrategyEncoder, models::Chain,
tycho_encoder::TychoEncoder, tycho_encoder::TychoEncoder,
}; };
@@ -16,7 +18,6 @@ use crate::encoding::{
/// This struct allows setting a chain and strategy encoder before building the final encoder. /// This struct allows setting a chain and strategy encoder before building the final encoder.
pub struct TychoRouterEncoderBuilder { pub struct TychoRouterEncoderBuilder {
swapper_pk: Option<String>, swapper_pk: Option<String>,
strategy: Option<Box<dyn StrategyEncoder>>,
chain: Option<Chain>, chain: Option<Chain>,
executors_file_path: Option<String>, executors_file_path: Option<String>,
router_address: Option<Bytes>, router_address: Option<Bytes>,
@@ -33,13 +34,12 @@ impl TychoRouterEncoderBuilder {
TychoRouterEncoderBuilder { TychoRouterEncoderBuilder {
swapper_pk: None, swapper_pk: None,
chain: None, chain: None,
strategy: None,
executors_file_path: None, executors_file_path: None,
router_address: None, router_address: None,
} }
} }
pub fn chain(mut self, chain: Chain) -> Self { pub fn chain(mut self, chain: TychoCommonChain) -> Self {
self.chain = Some(chain); self.chain = Some(chain.into());
self self
} }
@@ -62,32 +62,36 @@ impl TychoRouterEncoderBuilder {
self self
} }
/// Sets the `strategy_encoder` manually. /// Builds the `TychoRouterEncoder` instance using the configured chain.
/// /// Returns an error if either the chain has not been set.
/// **Note**: This method should not be used in combination with `tycho_router` or
/// `direct_execution`.
pub fn strategy_encoder(mut self, strategy: Box<dyn StrategyEncoder>) -> Self {
self.strategy = Some(strategy);
self
}
/// Builds the `TychoRouterEncoder` instance using the configured chain and strategy.
/// Returns an error if either the chain or strategy has not been set.
pub fn build(self) -> Result<Box<dyn TychoEncoder>, EncodingError> { pub fn build(self) -> Result<Box<dyn TychoEncoder>, EncodingError> {
if let Some(chain) = self.chain { if let Some(chain) = self.chain {
let swap_encoder_registry = let tycho_router_address;
SwapEncoderRegistry::new(self.executors_file_path.clone(), chain)?; if let Some(address) = self.router_address {
tycho_router_address = address;
} else {
let default_routers: HashMap<String, Bytes> =
serde_json::from_str(DEFAULT_ROUTERS_JSON)?;
tycho_router_address = default_routers
.get(&chain.name)
.ok_or(EncodingError::FatalError(
"No default router address found for chain".to_string(),
))?
.to_owned();
}
let strategy = Box::new(SplitSwapStrategyEncoder::new( let swap_encoder_registry =
SwapEncoderRegistry::new(self.executors_file_path.clone(), chain.clone())?;
Ok(Box::new(TychoRouterEncoder::new(
chain, chain,
swap_encoder_registry, swap_encoder_registry,
self.swapper_pk, self.swapper_pk,
self.router_address.clone(), tycho_router_address,
)?); )?))
Ok(Box::new(TychoRouterEncoder::new(chain, strategy)?))
} else { } else {
Err(EncodingError::FatalError( Err(EncodingError::FatalError(
"Please set the chain and strategy before building the encoder".to_string(), "Please set the chain and router address before building the encoder".to_string(),
)) ))
} }
} }
@@ -109,8 +113,8 @@ impl TychoExecutorEncoderBuilder {
pub fn new() -> Self { pub fn new() -> Self {
TychoExecutorEncoderBuilder { chain: None, executors_file_path: None } TychoExecutorEncoderBuilder { chain: None, executors_file_path: None }
} }
pub fn chain(mut self, chain: Chain) -> Self { pub fn chain(mut self, chain: TychoCommonChain) -> Self {
self.chain = Some(chain); self.chain = Some(chain.into());
self self
} }
@@ -126,7 +130,7 @@ impl TychoExecutorEncoderBuilder {
pub fn build(self) -> Result<Box<dyn TychoEncoder>, EncodingError> { pub fn build(self) -> Result<Box<dyn TychoEncoder>, EncodingError> {
if let Some(chain) = self.chain { if let Some(chain) = self.chain {
let swap_encoder_registry = let swap_encoder_registry =
SwapEncoderRegistry::new(self.executors_file_path.clone(), chain)?; SwapEncoderRegistry::new(self.executors_file_path.clone(), chain.clone())?;
Ok(Box::new(TychoExecutorEncoder::new(chain, swap_encoder_registry)?)) Ok(Box::new(TychoExecutorEncoder::new(chain, swap_encoder_registry)?))
} else { } else {
Err(EncodingError::FatalError( Err(EncodingError::FatalError(

View File

@@ -1,7 +1,4 @@
use std::{ use std::{collections::HashSet, str::FromStr};
collections::{HashMap, HashSet},
str::FromStr,
};
use alloy_primitives::{aliases::U24, U256, U8}; use alloy_primitives::{aliases::U24, U256, U8};
use alloy_sol_types::SolValue; use alloy_sol_types::SolValue;
@@ -11,7 +8,6 @@ use crate::encoding::{
errors::EncodingError, errors::EncodingError,
evm::{ evm::{
approvals::permit2::Permit2, approvals::permit2::Permit2,
constants::DEFAULT_ROUTERS_JSON,
group_swaps::group_swaps, group_swaps::group_swaps,
strategy_encoder::strategy_validators::{ strategy_encoder::strategy_validators::{
SequentialSwapValidator, SplitSwapValidator, SwapValidator, SequentialSwapValidator, SplitSwapValidator, SwapValidator,
@@ -47,12 +43,11 @@ pub struct SingleSwapStrategyEncoder {
impl SingleSwapStrategyEncoder { impl SingleSwapStrategyEncoder {
pub fn new( pub fn new(
blockchain: tycho_common::models::Chain, chain: Chain,
swap_encoder_registry: SwapEncoderRegistry, swap_encoder_registry: SwapEncoderRegistry,
swapper_pk: Option<String>, swapper_pk: Option<String>,
router_address: Bytes, router_address: Bytes,
) -> Result<Self, EncodingError> { ) -> Result<Self, EncodingError> {
let chain = Chain::from(blockchain);
let (permit2, selector) = if let Some(swapper_pk) = swapper_pk { let (permit2, selector) = if let Some(swapper_pk) = swapper_pk {
(Some(Permit2::new(swapper_pk, chain.clone())?), "singleSwapPermit2(uint256,address,address,uint256,bool,bool,address,((address,uint160,uint48,uint48),address,uint256),bytes,bytes)".to_string()) (Some(Permit2::new(swapper_pk, chain.clone())?), "singleSwapPermit2(uint256,address,address,uint256,bool,bool,address,((address,uint160,uint48,uint48),address,uint256),bytes,bytes)".to_string())
} else { } else {
@@ -206,12 +201,11 @@ pub struct SequentialSwapStrategyEncoder {
impl SequentialSwapStrategyEncoder { impl SequentialSwapStrategyEncoder {
pub fn new( pub fn new(
blockchain: tycho_common::models::Chain, chain: Chain,
swap_encoder_registry: SwapEncoderRegistry, swap_encoder_registry: SwapEncoderRegistry,
swapper_pk: Option<String>, swapper_pk: Option<String>,
router_address: Bytes, router_address: Bytes,
) -> Result<Self, EncodingError> { ) -> Result<Self, EncodingError> {
let chain = Chain::from(blockchain);
let (permit2, selector) = if let Some(swapper_pk) = swapper_pk { let (permit2, selector) = if let Some(swapper_pk) = swapper_pk {
(Some(Permit2::new(swapper_pk, chain.clone())?), "sequentialSwapPermit2(uint256,address,address,uint256,bool,bool,address,((address,uint160,uint48,uint48),address,uint256),bytes,bytes)".to_string()) (Some(Permit2::new(swapper_pk, chain.clone())?), "sequentialSwapPermit2(uint256,address,address,uint256,bool,bool,address,((address,uint160,uint48,uint48),address,uint256),bytes,bytes)".to_string())
} else { } else {
@@ -375,12 +369,11 @@ pub struct SplitSwapStrategyEncoder {
impl SplitSwapStrategyEncoder { impl SplitSwapStrategyEncoder {
pub fn new( pub fn new(
blockchain: tycho_common::models::Chain, chain: Chain,
swap_encoder_registry: SwapEncoderRegistry, swap_encoder_registry: SwapEncoderRegistry,
swapper_pk: Option<String>, swapper_pk: Option<String>,
router_address: Option<Bytes>, router_address: Bytes,
) -> Result<Self, EncodingError> { ) -> Result<Self, EncodingError> {
let chain = Chain::from(blockchain);
let (permit2, selector) = if let Some(swapper_pk) = swapper_pk { let (permit2, selector) = if let Some(swapper_pk) = swapper_pk {
(Some(Permit2::new(swapper_pk, chain.clone())?), "splitSwapPermit2(uint256,address,address,uint256,bool,bool,uint256,address,((address,uint160,uint48,uint48),address,uint256),bytes,bytes)".to_string()) (Some(Permit2::new(swapper_pk, chain.clone())?), "splitSwapPermit2(uint256,address,address,uint256,bool,bool,uint256,address,((address,uint160,uint48,uint48),address,uint256),bytes,bytes)".to_string())
} else { } else {
@@ -391,20 +384,6 @@ impl SplitSwapStrategyEncoder {
) )
}; };
let tycho_router_address;
if let Some(address) = router_address {
tycho_router_address = address;
} else {
let default_routers: HashMap<String, Bytes> =
serde_json::from_str(DEFAULT_ROUTERS_JSON)?;
tycho_router_address = default_routers
.get(&chain.name)
.ok_or(EncodingError::FatalError(
"No default router address found for chain".to_string(),
))?
.to_owned();
}
Ok(Self { Ok(Self {
permit2, permit2,
selector, selector,
@@ -412,7 +391,7 @@ impl SplitSwapStrategyEncoder {
native_address: chain.native_token()?, native_address: chain.native_token()?,
wrapped_address: chain.wrapped_token()?, wrapped_address: chain.wrapped_token()?,
split_swap_validator: SplitSwapValidator, split_swap_validator: SplitSwapValidator,
router_address: tycho_router_address, router_address,
}) })
} }
@@ -601,15 +580,15 @@ mod tests {
use num_bigint::{BigInt, BigUint}; use num_bigint::{BigInt, BigUint};
use rstest::rstest; use rstest::rstest;
use tycho_common::{ use tycho_common::{
models::{protocol::ProtocolComponent, Chain as TychoCoreChain}, models::{protocol::ProtocolComponent, Chain as TychoCommonChain},
Bytes, Bytes,
}; };
use super::*; use super::*;
use crate::encoding::models::Swap; use crate::encoding::models::Swap;
fn eth_chain() -> TychoCoreChain { fn eth_chain() -> Chain {
TychoCoreChain::Ethereum TychoCommonChain::Ethereum.into()
} }
fn eth() -> Bytes { fn eth() -> Bytes {
@@ -675,7 +654,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key), Some(private_key),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
let solution = Solution { let solution = Solution {
@@ -882,7 +861,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key), Some(private_key),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
let solution = Solution { let solution = Solution {
@@ -934,7 +913,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key), Some(private_key),
Some(Bytes::from_str("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395").unwrap()), Bytes::from_str("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395").unwrap(),
) )
.unwrap(); .unwrap();
let solution = Solution { let solution = Solution {
@@ -986,7 +965,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key), Some(private_key),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
let solution = Solution { let solution = Solution {
@@ -1079,7 +1058,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key), Some(private_key),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
let solution = Solution { let solution = Solution {
@@ -1291,7 +1270,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key), Some(private_key),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
let solution = Solution { let solution = Solution {
@@ -1411,7 +1390,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
None, None,
Some(Bytes::from_str("0x1d1499e622D69689cdf9004d05Ec547d650Ff211").unwrap()), Bytes::from_str("0x1d1499e622D69689cdf9004d05Ec547d650Ff211").unwrap(),
) )
.unwrap(); .unwrap();
@@ -1544,7 +1523,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
None, None,
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
let solution = Solution { let solution = Solution {
@@ -1637,7 +1616,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key), Some(private_key),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
@@ -1704,7 +1683,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key), Some(private_key),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
@@ -1791,7 +1770,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key), Some(private_key),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
@@ -1943,7 +1922,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key.clone()), Some(private_key.clone()),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();
@@ -2101,7 +2080,7 @@ mod tests {
eth_chain(), eth_chain(),
swap_encoder_registry, swap_encoder_registry,
Some(private_key.clone()), Some(private_key.clone()),
Some(Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395")), Bytes::from("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395"),
) )
.unwrap(); .unwrap();

View File

@@ -17,11 +17,7 @@ pub struct SwapEncoderRegistry {
impl SwapEncoderRegistry { impl SwapEncoderRegistry {
/// Populates the registry with the `SwapEncoders` for the given blockchain by parsing the /// Populates the registry with the `SwapEncoders` for the given blockchain by parsing the
/// executors' addresses in the file at the given path. /// executors' addresses in the file at the given path.
pub fn new( pub fn new(executors_file_path: Option<String>, chain: Chain) -> Result<Self, EncodingError> {
executors_file_path: Option<String>,
blockchain: tycho_common::models::Chain,
) -> Result<Self, EncodingError> {
let chain = Chain::from(blockchain);
let config_str = if let Some(ref path) = executors_file_path { let config_str = if let Some(ref path) = executors_file_path {
fs::read_to_string(path).map_err(|e| { fs::read_to_string(path).map_err(|e| {
EncodingError::FatalError(format!( EncodingError::FatalError(format!(

View File

@@ -5,7 +5,13 @@ use tycho_common::Bytes;
use crate::encoding::{ use crate::encoding::{
errors::EncodingError, errors::EncodingError,
evm::{group_swaps::group_swaps, swap_encoder::swap_encoder_registry::SwapEncoderRegistry}, evm::{
group_swaps::group_swaps,
strategy_encoder::strategy_encoders::{
SequentialSwapStrategyEncoder, SingleSwapStrategyEncoder, SplitSwapStrategyEncoder,
},
swap_encoder::swap_encoder_registry::SwapEncoderRegistry,
},
models::{Chain, EncodingContext, NativeAction, Solution, Transaction}, models::{Chain, EncodingContext, NativeAction, Solution, Transaction},
strategy_encoder::StrategyEncoder, strategy_encoder::StrategyEncoder,
tycho_encoder::TychoEncoder, tycho_encoder::TychoEncoder,
@@ -14,24 +20,50 @@ use crate::encoding::{
/// Encodes solutions to be used by the TychoRouter. /// Encodes solutions to be used by the TychoRouter.
/// ///
/// # Fields /// # Fields
/// * `strategy_encoder`: Strategy encoder to follow for encoding the solution /// * `single_swap_strategy`: Encoder for single swaps
/// * `sequential_swap_strategy`: Encoder for sequential swaps
/// * `split_swap_strategy`: Encoder for split swaps
/// * `native_address`: Address of the chain's native token /// * `native_address`: Address of the chain's native token
/// * `wrapped_address`: Address of the chain's wrapped native token /// * `wrapped_address`: Address of the chain's wrapped native token
pub struct TychoRouterEncoder { pub struct TychoRouterEncoder {
strategy_encoder: Box<dyn StrategyEncoder>, single_swap_strategy: SingleSwapStrategyEncoder,
sequential_swap_strategy: SequentialSwapStrategyEncoder,
split_swap_strategy: SplitSwapStrategyEncoder,
native_address: Bytes, native_address: Bytes,
wrapped_address: Bytes, wrapped_address: Bytes,
} }
impl TychoRouterEncoder { impl TychoRouterEncoder {
pub fn new( pub fn new(
chain: tycho_common::models::Chain, chain: Chain,
strategy_encoder: Box<dyn StrategyEncoder>, swap_encoder_registry: SwapEncoderRegistry,
swapper_pk: Option<String>,
router_address: Bytes,
) -> Result<Self, EncodingError> { ) -> Result<Self, EncodingError> {
let chain: Chain = Chain::from(chain);
let native_address = chain.native_token()?; let native_address = chain.native_token()?;
let wrapped_address = chain.wrapped_token()?; let wrapped_address = chain.wrapped_token()?;
Ok(TychoRouterEncoder { strategy_encoder, native_address, wrapped_address }) Ok(TychoRouterEncoder {
single_swap_strategy: SingleSwapStrategyEncoder::new(
chain.clone(),
swap_encoder_registry.clone(),
swapper_pk.clone(),
router_address.clone(),
)?,
sequential_swap_strategy: SequentialSwapStrategyEncoder::new(
chain.clone(),
swap_encoder_registry.clone(),
swapper_pk.clone(),
router_address.clone(),
)?,
split_swap_strategy: SplitSwapStrategyEncoder::new(
chain,
swap_encoder_registry,
None,
router_address.clone(),
)?,
native_address,
wrapped_address,
})
} }
} }
@@ -40,10 +72,20 @@ impl TychoEncoder for TychoRouterEncoder {
let mut transactions: Vec<Transaction> = Vec::new(); let mut transactions: Vec<Transaction> = Vec::new();
for solution in solutions.iter() { for solution in solutions.iter() {
self.validate_solution(solution)?; self.validate_solution(solution)?;
let (contract_interaction, target_address) = if solution.swaps.len() == 1 {
let (contract_interaction, target_address) = self self.single_swap_strategy
.strategy_encoder .encode_strategy(solution.clone())?
.encode_strategy(solution.clone())?; } else if solution
.swaps
.iter()
.all(|swap| swap.split == 0.0)
{
self.sequential_swap_strategy
.encode_strategy(solution.clone())?
} else {
self.split_swap_strategy
.encode_strategy(solution.clone())?
};
let value = if solution.given_token == self.native_address { let value = if solution.given_token == self.native_address {
solution.given_amount.clone() solution.given_amount.clone()
@@ -173,10 +215,9 @@ pub struct TychoExecutorEncoder {
impl TychoExecutorEncoder { impl TychoExecutorEncoder {
pub fn new( pub fn new(
chain: tycho_common::models::Chain, chain: Chain,
swap_encoder_registry: SwapEncoderRegistry, swap_encoder_registry: SwapEncoderRegistry,
) -> Result<Self, EncodingError> { ) -> Result<Self, EncodingError> {
let chain: Chain = Chain::from(chain);
let native_address = chain.native_token()?; let native_address = chain.native_token()?;
Ok(TychoExecutorEncoder { swap_encoder_registry, native_address }) Ok(TychoExecutorEncoder { swap_encoder_registry, native_address })
} }
@@ -269,12 +310,10 @@ impl TychoEncoder for TychoExecutorEncoder {
mod tests { mod tests {
use std::str::FromStr; use std::str::FromStr;
use tycho_common::models::{protocol::ProtocolComponent, Chain as TychoCoreChain}; use tycho_common::models::{protocol::ProtocolComponent, Chain as TychoCommonChain};
use super::*; use super::*;
use crate::encoding::{ use crate::encoding::models::Swap;
models::Swap, strategy_encoder::StrategyEncoder, swap_encoder::SwapEncoder,
};
fn dai() -> Bytes { fn dai() -> Bytes {
Bytes::from_str("0x6b175474e89094c44da98b954eedeac495271d0f").unwrap() Bytes::from_str("0x6b175474e89094c44da98b954eedeac495271d0f").unwrap()
@@ -296,36 +335,25 @@ mod tests {
Bytes::from_str("0x2260FAC5E5542a773Aa44fBCfeDf7C193bc2C599").unwrap() Bytes::from_str("0x2260FAC5E5542a773Aa44fBCfeDf7C193bc2C599").unwrap()
} }
fn get_swap_encoder_registry() -> SwapEncoderRegistry {
SwapEncoderRegistry::new(
Some("config/test_executor_addresses.json".to_string()),
TychoCommonChain::Ethereum.into(),
)
.unwrap()
}
mod router_encoder { mod router_encoder {
use super::*; use super::*;
#[derive(Clone)]
struct MockStrategy;
impl StrategyEncoder for MockStrategy {
fn encode_strategy(
&self,
_solution: Solution,
) -> Result<(Vec<u8>, Bytes), EncodingError> {
Ok((
Bytes::from_str("0x1234")
.unwrap()
.to_vec(),
Bytes::from_str("0xabcd").unwrap(),
))
}
fn get_swap_encoder(&self, _protocol_system: &str) -> Option<&Box<dyn SwapEncoder>> {
None
}
fn clone_box(&self) -> Box<dyn StrategyEncoder> {
Box::new(self.clone())
}
}
fn get_mocked_tycho_router_encoder() -> TychoRouterEncoder { fn get_mocked_tycho_router_encoder() -> TychoRouterEncoder {
let strategy_encoder = Box::new(MockStrategy {}); TychoRouterEncoder::new(
TychoRouterEncoder::new(TychoCoreChain::Ethereum, strategy_encoder).unwrap() TychoCommonChain::Ethereum.into(),
get_swap_encoder_registry(),
None,
Bytes::from_str("0x3Ede3eCa2a72B3aeCC820E955B36f38437D01395").unwrap(),
)
.unwrap()
} }
#[test] #[test]
fn test_encode_router_calldata() { fn test_encode_router_calldata() {
@@ -346,7 +374,9 @@ mod tests {
exact_out: false, exact_out: false,
given_amount: eth_amount_in.clone(), given_amount: eth_amount_in.clone(),
given_token: eth(), given_token: eth(),
checked_token: dai(),
swaps: vec![swap], swaps: vec![swap],
receiver: Bytes::from_str("0xcd09f75E2BF2A4d11F3AB23f1389FcC1621c0cc2").unwrap(),
native_action: Some(NativeAction::Wrap), native_action: Some(NativeAction::Wrap),
..Default::default() ..Default::default()
}; };
@@ -357,8 +387,10 @@ mod tests {
let transactions = transactions.unwrap(); let transactions = transactions.unwrap();
assert_eq!(transactions.len(), 1); assert_eq!(transactions.len(), 1);
assert_eq!(transactions[0].value, eth_amount_in); assert_eq!(transactions[0].value, eth_amount_in);
assert_eq!(transactions[0].data, Bytes::from_str("0x1234").unwrap()); assert_eq!(
assert_eq!(transactions[0].to, Bytes::from_str("0xabcd").unwrap()); transactions[0].to,
Bytes::from_str("0x3ede3eca2a72b3aecc820e955b36f38437d01395").unwrap()
);
} }
#[test] #[test]
@@ -824,24 +856,14 @@ mod tests {
use tycho_common::{models::protocol::ProtocolComponent, Bytes}; use tycho_common::{models::protocol::ProtocolComponent, Bytes};
use super::*; use super::*;
use crate::encoding::{ use crate::encoding::models::{Solution, Swap};
evm::swap_encoder::swap_encoder_registry::SwapEncoderRegistry,
models::{Solution, Swap},
};
fn get_swap_encoder_registry() -> SwapEncoderRegistry {
SwapEncoderRegistry::new(
Some("config/test_executor_addresses.json".to_string()),
TychoCoreChain::Ethereum,
)
.unwrap()
}
#[test] #[test]
fn test_executor_encoder_encode() { fn test_executor_encoder_encode() {
let swap_encoder_registry = get_swap_encoder_registry(); let swap_encoder_registry = get_swap_encoder_registry();
let encoder = let encoder =
TychoExecutorEncoder::new(TychoCoreChain::Ethereum, swap_encoder_registry).unwrap(); TychoExecutorEncoder::new(TychoCommonChain::Ethereum.into(), swap_encoder_registry)
.unwrap();
let token_in = weth(); let token_in = weth();
let token_out = dai(); let token_out = dai();
@@ -902,7 +924,8 @@ mod tests {
fn test_executor_encoder_too_many_swaps() { fn test_executor_encoder_too_many_swaps() {
let swap_encoder_registry = get_swap_encoder_registry(); let swap_encoder_registry = get_swap_encoder_registry();
let encoder = let encoder =
TychoExecutorEncoder::new(TychoCoreChain::Ethereum, swap_encoder_registry).unwrap(); TychoExecutorEncoder::new(TychoCommonChain::Ethereum.into(), swap_encoder_registry)
.unwrap();
let token_in = weth(); let token_in = weth();
let token_out = dai(); let token_out = dai();
@@ -939,7 +962,8 @@ mod tests {
fn test_executor_encoder_grouped_swaps() { fn test_executor_encoder_grouped_swaps() {
let swap_encoder_registry = get_swap_encoder_registry(); let swap_encoder_registry = get_swap_encoder_registry();
let encoder = let encoder =
TychoExecutorEncoder::new(TychoCoreChain::Ethereum, swap_encoder_registry).unwrap(); TychoExecutorEncoder::new(TychoCommonChain::Ethereum.into(), swap_encoder_registry)
.unwrap();
let eth = eth(); let eth = eth();
let usdc = usdc(); let usdc = usdc();

View File

@@ -2,7 +2,7 @@ use hex;
use num_bigint::BigUint; use num_bigint::BigUint;
use serde::{Deserialize, Serialize}; use serde::{Deserialize, Serialize};
use tycho_common::{ use tycho_common::{
models::{protocol::ProtocolComponent, Chain as TychoCoreChain}, models::{protocol::ProtocolComponent, Chain as TychoCommonChain},
Bytes, Bytes,
}; };
@@ -121,15 +121,15 @@ pub struct Chain {
pub name: String, pub name: String,
} }
impl From<TychoCoreChain> for Chain { impl From<TychoCommonChain> for Chain {
fn from(chain: TychoCoreChain) -> Self { fn from(chain: TychoCommonChain) -> Self {
match chain { match chain {
TychoCoreChain::Ethereum => Chain { id: 1, name: chain.to_string() }, TychoCommonChain::Ethereum => Chain { id: 1, name: chain.to_string() },
TychoCoreChain::ZkSync => Chain { id: 324, name: chain.to_string() }, TychoCommonChain::ZkSync => Chain { id: 324, name: chain.to_string() },
TychoCoreChain::Arbitrum => Chain { id: 42161, name: chain.to_string() }, TychoCommonChain::Arbitrum => Chain { id: 42161, name: chain.to_string() },
TychoCoreChain::Starknet => Chain { id: 0, name: chain.to_string() }, TychoCommonChain::Starknet => Chain { id: 0, name: chain.to_string() },
TychoCoreChain::Base => Chain { id: 8453, name: chain.to_string() }, TychoCommonChain::Base => Chain { id: 8453, name: chain.to_string() },
TychoCoreChain::Unichain => Chain { id: 130, name: chain.to_string() }, TychoCommonChain::Unichain => Chain { id: 130, name: chain.to_string() },
} }
} }
} }