From 6625ebbe829dd19f58a94154bc77dbc1f2c52898 Mon Sep 17 00:00:00 2001 From: Shaun Wang Date: Mon, 15 Mar 2021 14:51:17 +1300 Subject: [PATCH 1/2] Replace XcmError::Undefined usage. --- xcm-support/src/currency_adapter.rs | 80 +++++++++++++++++++++++++++++ xcm-support/src/lib.rs | 67 +++--------------------- 2 files changed, 87 insertions(+), 60 deletions(-) create mode 100644 xcm-support/src/currency_adapter.rs diff --git a/xcm-support/src/currency_adapter.rs b/xcm-support/src/currency_adapter.rs new file mode 100644 index 000000000..0489361cc --- /dev/null +++ b/xcm-support/src/currency_adapter.rs @@ -0,0 +1,80 @@ +use codec::FullCodec; +use sp_runtime::traits::{MaybeSerializeDeserialize, SaturatedConversion}; +use sp_std::{ + cmp::{Eq, PartialEq}, + fmt::Debug, + marker::PhantomData, + prelude::*, + result, +}; + +use xcm::v0::{Error as XcmError, MultiAsset, MultiLocation, Result}; +use xcm_executor::traits::{LocationConversion, MatchesFungible, TransactAsset}; + +use crate::CurrencyIdConversion; + +/// Asset transaction errors. +enum Error { + /// Asset not found. + AssetNotFound, + /// `MultiLocation` to `AccountId` Conversion failed. + AccountIdConversionFailed, + /// `CurrencyId` conversion failed. + CurrencyIdConversionFailed, +} + +impl From for XcmError { + fn from(e: Error) -> Self { + match e { + Error::AssetNotFound => XcmError::FailedToTransactAsset("AssetNotFound"), + Error::AccountIdConversionFailed => XcmError::FailedToTransactAsset("AccountIdConversionFailed"), + Error::CurrencyIdConversionFailed => XcmError::FailedToTransactAsset("CurrencyIdConversionFailed"), + } + } +} + +pub struct MultiCurrencyAdapter( + PhantomData<( + MultiCurrency, + Matcher, + AccountIdConverter, + AccountId, + CurrencyIdConverter, + CurrencyId, + )>, +); + +impl< + MultiCurrency: orml_traits::MultiCurrency, + Matcher: MatchesFungible, + AccountIdConverter: LocationConversion, + AccountId: sp_std::fmt::Debug, + CurrencyIdConverter: CurrencyIdConversion, + CurrencyId: FullCodec + Eq + PartialEq + Copy + MaybeSerializeDeserialize + Debug, + > TransactAsset + for MultiCurrencyAdapter +{ + fn deposit_asset(asset: &MultiAsset, location: &MultiLocation) -> Result { + let who = + AccountIdConverter::from_location(location).ok_or(XcmError::from(Error::AccountIdConversionFailed))?; + let currency_id = + CurrencyIdConverter::from_asset(asset).ok_or(XcmError::from(Error::CurrencyIdConversionFailed))?; + let amount: MultiCurrency::Balance = Matcher::matches_fungible(&asset) + .ok_or(XcmError::from(Error::AssetNotFound))? + .saturated_into(); + MultiCurrency::deposit(currency_id, &who, amount).map_err(|e| XcmError::FailedToTransactAsset(e.into()))?; + Ok(()) + } + + fn withdraw_asset(asset: &MultiAsset, location: &MultiLocation) -> result::Result { + let who = + AccountIdConverter::from_location(location).ok_or(XcmError::from(Error::AccountIdConversionFailed))?; + let currency_id = + CurrencyIdConverter::from_asset(asset).ok_or(XcmError::from(Error::CurrencyIdConversionFailed))?; + let amount: MultiCurrency::Balance = Matcher::matches_fungible(&asset) + .ok_or(XcmError::from(Error::AssetNotFound))? + .saturated_into(); + MultiCurrency::withdraw(currency_id, &who, amount).map_err(|e| XcmError::FailedToTransactAsset(e.into()))?; + Ok(asset.clone()) + } +} diff --git a/xcm-support/src/lib.rs b/xcm-support/src/lib.rs index 656968748..890744d97 100644 --- a/xcm-support/src/lib.rs +++ b/xcm-support/src/lib.rs @@ -1,21 +1,20 @@ #![cfg_attr(not(feature = "std"), no_std)] -use codec::FullCodec; -use sp_runtime::traits::{CheckedConversion, Convert, MaybeSerializeDeserialize, SaturatedConversion}; +use frame_support::{dispatch::DispatchResult, traits::Get}; +use sp_runtime::traits::{CheckedConversion, Convert}; use sp_std::{ - cmp::{Eq, PartialEq}, collections::btree_set::BTreeSet, convert::{TryFrom, TryInto}, - fmt::Debug, marker::PhantomData, prelude::*, - result, }; -use xcm::v0::{Error, Junction, MultiAsset, MultiLocation, Result, Xcm}; -use xcm_executor::traits::{FilterAssetLocation, LocationConversion, MatchesFungible, NativeAsset, TransactAsset}; +use xcm::v0::{Junction, MultiAsset, MultiLocation, Xcm}; +use xcm_executor::traits::{FilterAssetLocation, MatchesFungible, NativeAsset}; -use frame_support::{dispatch::DispatchResult, log, traits::Get}; +pub use currency_adapter::MultiCurrencyAdapter; + +mod currency_adapter; pub trait XcmHandler { fn execute_xcm(origin: AccountId, xcm: Xcm) -> DispatchResult; @@ -25,58 +24,6 @@ pub trait CurrencyIdConversion { fn from_asset(asset: &MultiAsset) -> Option; } -pub struct MultiCurrencyAdapter( - PhantomData<( - MultiCurrency, - Matcher, - AccountIdConverter, - AccountId, - CurrencyIdConverter, - CurrencyId, - )>, -); - -impl< - MultiCurrency: orml_traits::MultiCurrency, - Matcher: MatchesFungible, - AccountIdConverter: LocationConversion, - AccountId: sp_std::fmt::Debug, - CurrencyIdConverter: CurrencyIdConversion, - CurrencyId: FullCodec + Eq + PartialEq + Copy + MaybeSerializeDeserialize + Debug, - > TransactAsset - for MultiCurrencyAdapter -{ - fn deposit_asset(asset: &MultiAsset, location: &MultiLocation) -> Result { - log::info!("------------------------------------------------"); - log::info!(">>> trying deposit. asset: {:?}, location: {:?}", asset, location); - let who = AccountIdConverter::from_location(location).ok_or(())?; - log::info!("who: {:?}", who); - let currency_id = CurrencyIdConverter::from_asset(asset).ok_or(())?; - log::info!("currency_id: {:?}", currency_id); - let amount: MultiCurrency::Balance = Matcher::matches_fungible(&asset).ok_or(())?.saturated_into(); - log::info!("amount: {:?}", amount); - MultiCurrency::deposit(currency_id, &who, amount).map_err(|_| ())?; - log::info!(">>> success deposit."); - log::info!("------------------------------------------------"); - Ok(()) - } - - fn withdraw_asset(asset: &MultiAsset, location: &MultiLocation) -> result::Result { - log::info!("------------------------------------------------"); - log::info!(">>> trying withdraw. asset: {:?}, location: {:?}", asset, location); - let who = AccountIdConverter::from_location(location).ok_or(())?; - log::info!("who: {:?}", who); - let currency_id = CurrencyIdConverter::from_asset(asset).ok_or(())?; - log::info!("currency_id: {:?}", currency_id); - let amount: MultiCurrency::Balance = Matcher::matches_fungible(&asset).ok_or(())?.saturated_into(); - log::info!("amount: {:?}", amount); - MultiCurrency::withdraw(currency_id, &who, amount).map_err(|_| ())?; - log::info!(">>> success withdraw."); - log::info!("------------------------------------------------"); - Ok(asset.clone()) - } -} - pub struct IsConcreteWithGeneralKey( PhantomData<(CurrencyId, FromRelayChainBalance)>, ); From 97dc7c6d3e5a844f08e270f88241d711f8212c9b Mon Sep 17 00:00:00 2001 From: Shaun Wang Date: Mon, 15 Mar 2021 14:59:30 +1300 Subject: [PATCH 2/2] make clippy happy --- xcm-support/src/currency_adapter.rs | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/xcm-support/src/currency_adapter.rs b/xcm-support/src/currency_adapter.rs index 0489361cc..5eb76945f 100644 --- a/xcm-support/src/currency_adapter.rs +++ b/xcm-support/src/currency_adapter.rs @@ -55,24 +55,24 @@ impl< for MultiCurrencyAdapter { fn deposit_asset(asset: &MultiAsset, location: &MultiLocation) -> Result { - let who = - AccountIdConverter::from_location(location).ok_or(XcmError::from(Error::AccountIdConversionFailed))?; + let who = AccountIdConverter::from_location(location) + .ok_or_else(|| XcmError::from(Error::AccountIdConversionFailed))?; let currency_id = - CurrencyIdConverter::from_asset(asset).ok_or(XcmError::from(Error::CurrencyIdConversionFailed))?; + CurrencyIdConverter::from_asset(asset).ok_or_else(|| XcmError::from(Error::CurrencyIdConversionFailed))?; let amount: MultiCurrency::Balance = Matcher::matches_fungible(&asset) - .ok_or(XcmError::from(Error::AssetNotFound))? + .ok_or_else(|| XcmError::from(Error::AssetNotFound))? .saturated_into(); MultiCurrency::deposit(currency_id, &who, amount).map_err(|e| XcmError::FailedToTransactAsset(e.into()))?; Ok(()) } fn withdraw_asset(asset: &MultiAsset, location: &MultiLocation) -> result::Result { - let who = - AccountIdConverter::from_location(location).ok_or(XcmError::from(Error::AccountIdConversionFailed))?; + let who = AccountIdConverter::from_location(location) + .ok_or_else(|| XcmError::from(Error::AccountIdConversionFailed))?; let currency_id = - CurrencyIdConverter::from_asset(asset).ok_or(XcmError::from(Error::CurrencyIdConversionFailed))?; + CurrencyIdConverter::from_asset(asset).ok_or_else(|| XcmError::from(Error::CurrencyIdConversionFailed))?; let amount: MultiCurrency::Balance = Matcher::matches_fungible(&asset) - .ok_or(XcmError::from(Error::AssetNotFound))? + .ok_or_else(|| XcmError::from(Error::AssetNotFound))? .saturated_into(); MultiCurrency::withdraw(currency_id, &who, amount).map_err(|e| XcmError::FailedToTransactAsset(e.into()))?; Ok(asset.clone())