Skip to content

Commit

Permalink
change trade intrusctions calculation
Browse files Browse the repository at this point in the history
  • Loading branch information
enthusiastmartin committed Oct 31, 2024
1 parent d44a659 commit bbfaf8b
Show file tree
Hide file tree
Showing 2 changed files with 47 additions and 67 deletions.
34 changes: 10 additions & 24 deletions integration-tests/src/ice/omni.rs
Original file line number Diff line number Diff line change
Expand Up @@ -64,32 +64,18 @@ fn solver_should_find_solution_with_one_intent() {

assert_eq!(
trades,
vec![
pallet_ice::types::TradeInstruction::SwapExactIn {
vec![pallet_ice::types::TradeInstruction::SwapExactIn {
asset_in: 0,
asset_out: 27,
amount_in: 99853645824127,
amount_out: 1148028627591,
route: pallet_ice::types::BoundedRoute::try_from(vec![Trade {
pool: PoolType::Omnipool,
asset_in: 0,
asset_out: 1,
amount_in: 99853645824127,
amount_out: 17567099869,
route: pallet_ice::types::BoundedRoute::try_from(vec![Trade {
pool: PoolType::Omnipool,
asset_in: 0,
asset_out: 1,
}])
.unwrap()
},
pallet_ice::types::TradeInstruction::SwapExactOut {
asset_in: 1,
asset_out: 27,
amount_in: 16161402305,
amount_out: 1148028627591,
route: pallet_ice::types::BoundedRoute::try_from(vec![Trade {
pool: PoolType::Omnipool,
asset_in: 1,
asset_out: 27,
}])
.unwrap()
}
]
}])
.unwrap()
},]
);

assert_eq!(score, 1000000);
Expand Down
80 changes: 37 additions & 43 deletions pallets/ice/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -520,53 +520,47 @@ impl<T: Config> Pallet<T> {
let mut matched_amounts = Vec::new();
let mut trades_instructions = Vec::new();

// Sell all for lrna
for (asset_id, amount) in amounts_in.iter() {
let amount_out = *amounts_out.get(asset_id).unwrap_or(&0u128);

matched_amounts.push((*asset_id, (*amount).min(amount_out)));

if *amount > amount_out {
let route = T::RoutingSupport::get_route(*asset_id, T::HubAssetId::get());
let diff = amount.saturating_sub(amount_out);

let lrna_bought = T::RoutingSupport::calculate_amount_out(&route, diff)?;
lrna_aquired.saturating_accrue(lrna_bought);
trades_instructions.push(TradeInstruction::SwapExactIn {
asset_in: *asset_id,
asset_out: T::HubAssetId::get(),
amount_in: amount.saturating_sub(amount_out), //Swap only difference
amount_out: lrna_bought,
route: BoundedRoute::try_from(route).unwrap(),
});
let mut delta_in: BTreeMap<T::AssetId, Balance> = amounts_in.clone();
let mut delta_out: BTreeMap<T::AssetId, Balance> = amounts_out.clone();

// Calculate deltas to trade
for (asset_id, amount_out) in amounts_out.iter() {
if let Some((_, amount_in)) = amounts_in.get_key_value(asset_id) {
if *amount_out == *amount_in {
// nothing to trade here, all matched
matched_amounts.push((*asset_id, *amount_out));
} else if *amount_out > *amount_in {
// there is something left to buy
matched_amounts.push((*asset_id, *amount_out - *amount_in));
delta_out.insert(*asset_id, *amount_out - *amount_in);
} else {
// there is something left to sell
matched_amounts.push((*asset_id, *amount_in - *amount_out));
delta_in.insert(*asset_id, *amount_in - *amount_out);
}
} else {
// there is no sell of this asset, only buy
delta_out.insert(*asset_id, *amount_out);
}
}

let mut lrna_sold = 0u128;

for (asset_id, amount) in amounts_out {
let amount_in = *amounts_in.get(&asset_id).unwrap_or(&0u128);

if amount > amount_in {
let route = T::RoutingSupport::get_route(T::HubAssetId::get(), asset_id);
let diff = amount.saturating_sub(amount_in);
let lrna_in = T::RoutingSupport::calculate_amount_in(&route, diff)?;
lrna_sold.saturating_accrue(lrna_in);
trades_instructions.push(TradeInstruction::SwapExactOut {
asset_in: T::HubAssetId::get(),
asset_out: asset_id,
amount_in: lrna_in,
amount_out: amount.saturating_sub(amount_in), //Swap only difference
route: BoundedRoute::try_from(route).unwrap(),
});
}
// delta_in count should equal to delta_out count.
debug_assert_eq!(delta_in.len(), delta_out.len());

// Try to figure out what trades to do for deltas
// TODO: this might need some adjustments, as it might no be possible to sell exact amount of asset in for asset out - might try different pair if more assets
for ((asset_out, amount_out), (asset_in, amount_in)) in delta_out.iter().zip(delta_in.iter()) {
let route = T::RoutingSupport::get_route(*asset_in, *asset_out);
let amount_bought = T::RoutingSupport::calculate_amount_out(&route, *amount_in)?;
debug_assert!(amount_bought >= *amount_out);
trades_instructions.push(TradeInstruction::SwapExactIn {
asset_in: *asset_in,
asset_out: *asset_out,
amount_in: *amount_in,
amount_out: *amount_out,
route: BoundedRoute::try_from(route).unwrap(),
});
}
assert!(
lrna_aquired >= lrna_sold,
"lrna_aquired < lrna_sold ({} < {})",
lrna_aquired,
lrna_sold
);

let score = Self::score_solution(resolved_intents.len() as u128, matched_amounts).map_err(|_| ())?;
Ok((trades_instructions, score))
Expand Down

0 comments on commit bbfaf8b

Please sign in to comment.