pallet-asset-conversion: Decoupling Native Currency Dependancy (#2031)

closes https://github.com/paritytech/polkadot-sdk/issues/1842

Decoupling Pallet from the Concept of Native Currency

Currently, the pallet is intrinsically linked with the concept of native
currency, requiring users to provide implementations of the
`fungible::*` and `fungibles::*` traits to interact with native and non
native assets. This incapsulates some non-related to the pallet
complexity and makes it less adaptable in contexts where the native
currency concept is absent.

With this PR, the dependence on `fungible::*` for liquidity-supplying
assets has been removed. Instead, the native and non-native currencies'
handling is now overseen by a single type that implements the
`fungibles::*` traits. To simplify this integration, types have been
introduced to facilitate the creation of a union between `fungible::*`
and `fungibles::*` implementations, producing a unified `fungibles::*`
type.

One of the reasons driving these changes is the ambition to create a
more user-friendly API for the `SwapCredit` implementation. Given that
it interacts with two distinct credit types from `fungible` and
`fungibles`, a unified type was introduced. Clients now manage potential
conversion failures for those credit types. In certain contexts, it's
vital to guarantee that operations are fail-safe, like in this impl -
[PR](https://github.com/paritytech/polkadot-sdk/pull/1845), place in
[code](https://github.com/paritytech/polkadot-sdk/blob/20b85a5fada8f55c98ba831964f5866ffeadf4da/cumulus/primitives/utility/src/lib.rs#L429).

Additional Updates:
- abstracted the pool ID and its account derivation logic via trait
bounds, along with common implementation offerings;
- removed `inc_providers` on a pool creation for the pool account;
- benchmarks:
-- swap complexity is N, not const;
-- removed `From<u128> + Into<u128>` bound from `T::Balance`;
-- removed swap/liquidity/.. amount constants, resolve them dynamically
based on pallet configuration;
-- migrated to v2 API;
- `OnUnbalanced` handler for the pool creation fee, replacing direct
transfers to a specified account ID;
- renamed `MultiAssetId` to `AssetKind` aligning with naming across
frame crates;

related PRs:
- (depends) https://github.com/paritytech/polkadot-sdk/pull/1677
- (caused) https://github.com/paritytech/polkadot-sdk/pull/2033
- (caused) https://github.com/paritytech/polkadot-sdk/pull/1876

---------

Co-authored-by: joe petrowski <25483142+joepetrowski@users.noreply.github.com>
Co-authored-by: Liam Aharon <liam.aharon@hotmail.com>
This commit is contained in:
Muharem
2023-12-20 13:57:26 +01:00
committed by GitHub
parent d32f66fb8f
commit 4f832ea865
26 changed files with 1750 additions and 4571 deletions
@@ -20,14 +20,13 @@ use frame_support::{
dispatch::{DispatchInfo, PostDispatchInfo},
pallet_prelude::*,
traits::{
fungible::Inspect,
fungible::{Inspect, NativeOrWithId},
fungibles::{Inspect as FungiblesInspect, Mutate},
},
weights::Weight,
};
use frame_system as system;
use mock::{ExtrinsicBaseWeight, *};
use pallet_asset_conversion::NativeOrAssetId;
use pallet_balances::Call as BalancesCall;
use sp_runtime::{traits::StaticLookup, BuildStorage};
@@ -127,12 +126,12 @@ fn setup_lp(asset_id: u32, balance_factor: u64) {
10_000 * balance_factor + ed_asset
));
let token_1 = NativeOrAssetId::Native;
let token_2 = NativeOrAssetId::Asset(asset_id);
let token_1 = NativeOrWithId::Native;
let token_2 = NativeOrWithId::WithId(asset_id);
assert_ok!(AssetConversion::create_pool(
RuntimeOrigin::signed(lp_provider),
Box::new(token_1),
Box::new(token_2)
Box::new(token_1.clone()),
Box::new(token_2.clone())
));
assert_ok!(AssetConversion::add_liquidity(
@@ -228,8 +227,8 @@ fn transaction_payment_in_asset_possible() {
let fee_in_native = base_weight + tx_weight + len as u64;
let input_quote = AssetConversion::quote_price_tokens_for_exact_tokens(
NativeOrAssetId::Asset(asset_id),
NativeOrAssetId::Native,
NativeOrWithId::WithId(asset_id),
NativeOrWithId::Native,
fee_in_native,
true,
);
@@ -337,8 +336,8 @@ fn transaction_payment_without_fee() {
let len = 10;
let fee_in_native = base_weight + weight + len as u64;
let input_quote = AssetConversion::quote_price_tokens_for_exact_tokens(
NativeOrAssetId::Asset(asset_id),
NativeOrAssetId::Native,
NativeOrWithId::WithId(asset_id),
NativeOrWithId::Native,
fee_in_native,
true,
);
@@ -355,8 +354,8 @@ fn transaction_payment_without_fee() {
assert_eq!(Assets::balance(asset_id, caller), balance - fee_in_asset);
let refund = AssetConversion::quote_price_exact_tokens_for_tokens(
NativeOrAssetId::Native,
NativeOrAssetId::Asset(asset_id),
NativeOrWithId::Native,
NativeOrWithId::WithId(asset_id),
fee_in_native,
true,
)
@@ -412,8 +411,8 @@ fn asset_transaction_payment_with_tip_and_refund() {
let len = 10;
let fee_in_native = base_weight + weight + len as u64 + tip;
let input_quote = AssetConversion::quote_price_tokens_for_exact_tokens(
NativeOrAssetId::Asset(asset_id),
NativeOrAssetId::Native,
NativeOrWithId::WithId(asset_id),
NativeOrWithId::Native,
fee_in_native,
true,
);
@@ -428,8 +427,8 @@ fn asset_transaction_payment_with_tip_and_refund() {
let final_weight = 50;
let expected_fee = fee_in_native - final_weight - tip;
let expected_token_refund = AssetConversion::quote_price_exact_tokens_for_tokens(
NativeOrAssetId::Native,
NativeOrAssetId::Asset(asset_id),
NativeOrWithId::Native,
NativeOrWithId::WithId(asset_id),
fee_in_native - expected_fee - tip,
true,
)
@@ -493,8 +492,8 @@ fn payment_from_account_with_only_assets() {
let fee_in_native = base_weight + weight + len as u64;
let ed = Balances::minimum_balance();
let fee_in_asset = AssetConversion::quote_price_tokens_for_exact_tokens(
NativeOrAssetId::Asset(asset_id),
NativeOrAssetId::Native,
NativeOrWithId::WithId(asset_id),
NativeOrWithId::Native,
fee_in_native + ed,
true,
)
@@ -509,8 +508,8 @@ fn payment_from_account_with_only_assets() {
assert_eq!(Assets::balance(asset_id, caller), balance - fee_in_asset);
let refund = AssetConversion::quote_price_exact_tokens_for_tokens(
NativeOrAssetId::Native,
NativeOrAssetId::Asset(asset_id),
NativeOrWithId::Native,
NativeOrWithId::WithId(asset_id),
ed,
true,
)
@@ -585,8 +584,8 @@ fn converted_fee_is_never_zero_if_input_fee_is_not() {
// validate even a small fee gets converted to asset.
let fee_in_native = base_weight + weight + len as u64;
let fee_in_asset = AssetConversion::quote_price_tokens_for_exact_tokens(
NativeOrAssetId::Asset(asset_id),
NativeOrAssetId::Native,
NativeOrWithId::WithId(asset_id),
NativeOrWithId::Native,
fee_in_native,
true,
)