FRAME: Unity Balance Conversion for Different IDs of Native Asset (#3659)

Introduce types to define 1:1 balance conversion for different relative
asset ids/locations of native asset.

Examples:
native asset on Asset Hub presented as `VersionedLocatableAsset` type in
the context of Relay Chain is
```
{
  `location`: (0, Parachain(1000)),
  `asset_id`: (1, Here),
}
```
and it's balance should be converted 1:1 by implementations of
`ConversionToAssetBalance` trait.

---------

Co-authored-by: Branislav Kontur <bkontur@gmail.com>
This commit is contained in:
Muharem
2024-04-16 18:11:14 +02:00
committed by GitHub
parent 753bf2d860
commit 6f3d890ed3
21 changed files with 790 additions and 26 deletions
+1 -1
View File
@@ -36,7 +36,7 @@ mod members;
pub use members::{AllowAll, DenyAll, Filter};
pub use members::{
AsContains, ChangeMembers, Contains, ContainsLengthBound, ContainsPair, Equals, Everything,
EverythingBut, FromContainsPair, InitializeMembers, InsideBoth, IsInVec, Nothing,
EverythingBut, FromContains, FromContainsPair, InitializeMembers, InsideBoth, IsInVec, Nothing,
RankedMembers, RankedMembersSwapHandler, SortedMembers, TheseExcept,
};
@@ -66,6 +66,15 @@ impl<A, B, CP: ContainsPair<A, B>> Contains<(A, B)> for FromContainsPair<CP> {
}
}
/// A [`ContainsPair`] implementation that has a `Contains` implementation for each member of the
/// pair.
pub struct FromContains<CA, CB>(PhantomData<(CA, CB)>);
impl<A, B, CA: Contains<A>, CB: Contains<B>> ContainsPair<A, B> for FromContains<CA, CB> {
fn contains(a: &A, b: &B) -> bool {
CA::contains(a) && CB::contains(b)
}
}
/// A [`Contains`] implementation that contains every value.
pub enum Everything {}
impl<T> Contains<T> for Everything {
+2 -2
View File
@@ -31,7 +31,7 @@ pub mod pay;
pub use misc::{
AssetId, Balance, BalanceStatus, ConversionFromAssetBalance, ConversionToAssetBalance,
ConvertRank, DepositConsequence, ExistenceRequirement, Fortitude, GetSalary, Locker, Precision,
Preservation, Provenance, Restriction, UnityAssetBalanceConversion, WithdrawConsequence,
WithdrawReasons,
Preservation, Provenance, Restriction, UnityAssetBalanceConversion, UnityOrOuterConversion,
WithdrawConsequence, WithdrawReasons,
};
pub use pay::{Pay, PayFromAccount, PaymentStatus};
@@ -17,6 +17,7 @@
//! Miscellaneous types.
use crate::traits::Contains;
use codec::{Decode, Encode, FullCodec, MaxEncodedLen};
use sp_arithmetic::traits::{AtLeast32BitUnsigned, Zero};
use sp_core::RuntimeDebug;
@@ -299,6 +300,33 @@ where
fn ensure_successful(_: AssetId) {}
}
/// Implements [`ConversionFromAssetBalance`], allowing for a 1:1 balance conversion of the asset
/// when it meets the conditions specified by `C`. If the conditions are not met, the conversion is
/// delegated to `O`.
pub struct UnityOrOuterConversion<C, O>(core::marker::PhantomData<(C, O)>);
impl<AssetBalance, AssetId, OutBalance, C, O>
ConversionFromAssetBalance<AssetBalance, AssetId, OutBalance> for UnityOrOuterConversion<C, O>
where
C: Contains<AssetId>,
O: ConversionFromAssetBalance<AssetBalance, AssetId, OutBalance>,
AssetBalance: Into<OutBalance>,
{
type Error = O::Error;
fn from_asset_balance(
balance: AssetBalance,
asset_id: AssetId,
) -> Result<OutBalance, Self::Error> {
if C::contains(&asset_id) {
return Ok(balance.into());
}
O::from_asset_balance(balance, asset_id)
}
#[cfg(feature = "runtime-benchmarks")]
fn ensure_successful(asset_id: AssetId) {
O::ensure_successful(asset_id)
}
}
/// Trait to handle NFT locking mechanism to ensure interactions with the asset can be implemented
/// downstream to extend logic of Uniques/Nfts current functionality.
pub trait Locker<CollectionId, ItemId> {