Skip to content

Commit

Permalink
Add bind existing sidechin asset function (#84)
Browse files Browse the repository at this point in the history
* add bind function, tests and benchmarks
  • Loading branch information
N1ghtStorm authored Sep 17, 2024
1 parent 2269286 commit f38ef9d
Show file tree
Hide file tree
Showing 5 changed files with 256 additions and 94 deletions.
8 changes: 8 additions & 0 deletions pallets/parachain-app/src/benchmarking.rs
Original file line number Diff line number Diff line change
Expand Up @@ -83,6 +83,14 @@ benchmarks! {
assert_eq!(SidechainPrecision::<T>::iter_prefix(BASE_NETWORK_ID).count(), 1);
}

bind_sidechain_asset {
let a in 1..100;
let asset_id = <T as Config>::AssetRegistry::register_asset(GenericNetworkId::Sub(Default::default()), Default::default(), Default::default())?;
}: _(RawOrigin::Root, BASE_NETWORK_ID, asset_id.clone(), [0u8; 32].into(), 6, (0..a).collect::<Vec<_>>(), 1u32.into())
verify {
assert_eq!(SidechainPrecision::<T>::get(BASE_NETWORK_ID, asset_id).unwrap(), 6);
}

add_assetid_paraid {
let asset_id = <T as Config>::AssetRegistry::register_asset(GenericNetworkId::Sub(Default::default()), Default::default(), Default::default())?;
ParachainApp::<T>::register_thischain_asset(RawOrigin::Root.into(), BASE_NETWORK_ID, asset_id.clone(), PARENT_PARACHAIN_ASSET, Default::default(), 1u32.into())?;
Expand Down
39 changes: 39 additions & 0 deletions pallets/parachain-app/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -522,6 +522,45 @@ pub mod pallet {
)?;
Ok(())
}

#[pallet::call_index(9)]
#[pallet::weight(<T as Config>::WeightInfo::bind_sidechain_asset(allowed_parachains.len() as u32))]
pub fn bind_sidechain_asset(
origin: OriginFor<T>,
network_id: SubNetworkId,
asset_id: AssetIdOf<T>,
sidechain_asset: ParachainAssetId,
sidechain_precision: u8,
allowed_parachains: Vec<u32>,
minimal_xcm_amount: BalanceOf<T>,
) -> DispatchResult {
ensure_root(origin)?;
ensure!(
!AssetKinds::<T>::contains_key(network_id, &asset_id),
Error::<T>::TokenAlreadyRegistered
);

let (_, minimal_xcm_amount) = T::BalancePrecisionConverter::to_sidechain(
&asset_id,
sidechain_precision,
minimal_xcm_amount,
)
.ok_or(Error::<T>::WrongAmount)?;

ensure!(minimal_xcm_amount > 0, Error::<T>::WrongAmount);

Self::register_asset_inner(
network_id,
asset_id,
sidechain_asset,
AssetKind::Sidechain,
sidechain_precision,
allowed_parachains,
minimal_xcm_amount,
)?;

Ok(())
}
}

impl<T: Config> Pallet<T> {
Expand Down
14 changes: 10 additions & 4 deletions pallets/parachain-app/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ use xcm::v3::Junction::Parachain;
use xcm::v3::Junctions::X2;
use xcm::v3::MultiLocation;

use crate as substrate_app;
use crate as parachain_app;

type UncheckedExtrinsic = frame_system::mocking::MockUncheckedExtrinsic<Test>;
type Block = frame_system::mocking::MockBlock<Test>;
Expand All @@ -86,6 +86,7 @@ pub enum AssetId {
Xor,
Eth,
Dai,
Usdt,
Custom(u8),
}

Expand All @@ -105,7 +106,7 @@ frame_support::construct_runtime!(
Balances: pallet_balances::{Pallet, Call, Storage, Event<T>},
Dispatch: dispatch::{Pallet, Call, Storage, Origin<T>, Event<T>},
BridgeOutboundChannel: substrate_bridge_channel::outbound::{Pallet, Config<T>, Storage, Event<T>},
ParachainApp: substrate_app::{Pallet, Call, Config<T>, Storage, Event<T>},
ParachainApp: parachain_app::{Pallet, Call, Config<T>, Storage, Event<T>},
}
);

Expand Down Expand Up @@ -280,6 +281,11 @@ impl BridgeAssetRegistry<AccountId, AssetId> for AssetRegistryImpl {
symbol: "XOR".to_owned().into(),
precision: 18,
},
AssetId::Usdt => bridge_types::types::RawAssetInfo {
name: "USDT".to_owned().into(),
symbol: "USDT".to_owned().into(),
precision: 6,
},
AssetId::Custom(1) => bridge_types::types::RawAssetInfo {
name: "KSM".to_owned().into(),
symbol: "KSM".to_owned().into(),
Expand Down Expand Up @@ -326,7 +332,7 @@ impl BalancePrecisionConverter<AssetId, Balance, Balance> for BalancePrecisionCo
}
}

impl substrate_app::Config for Test {
impl parachain_app::Config for Test {
type RuntimeEvent = RuntimeEvent;
type MessageStatusNotifier = ();
type CallOrigin =
Expand Down Expand Up @@ -413,7 +419,7 @@ pub fn new_tester() -> sp_io::TestExternalities {
AssetKind::Thischain,
)
.expect("XOR registration finalization failed");
let kusama_asset = substrate_app::RelaychainAsset::<Test>::get(SubNetworkId::Kusama);
let kusama_asset = parachain_app::RelaychainAsset::<Test>::get(SubNetworkId::Kusama);
ParachainApp::finalize_asset_registration(
origin_kusama,
kusama_asset.unwrap(),
Expand Down
33 changes: 32 additions & 1 deletion pallets/parachain-app/src/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -559,7 +559,7 @@ fn it_fails_burn_outbound_channel_submit() {

#[test]
fn it_works_register_thischain_asset() {
new_tester_no_registered_assets().execute_with(|| {
new_tester().execute_with(|| {
let origin = Origin::<Test>::Root;
let network_id = SubNetworkId::Mainnet;
let asset_id = AssetId::Xor;
Expand Down Expand Up @@ -587,6 +587,37 @@ fn it_works_register_thischain_asset() {
});
}

#[test]
fn it_works_bind_sidechain_asset() {
new_tester_no_registered_assets().execute_with(|| {
let origin = Origin::<Test>::Root;
let network_id = SubNetworkId::Mainnet;
let asset_id = AssetId::Usdt;
let sidechain_asset = ParachainAssetId::Concrete(MultiLocation::new(
1,
X2(
Parachain(PARA_A),
Junction::AccountId32 {
network: None,
id: Keyring::Bob.into(),
},
),
));
let allowed_parachains = vec![1000];
let minimal_xcm_amount = 10;

assert_ok!(ParachainApp::bind_sidechain_asset(
origin.into(),
network_id,
asset_id,
sidechain_asset,
6,
allowed_parachains,
minimal_xcm_amount
));
});
}

#[test]
fn it_works_register_asset_inner() {
new_tester_no_registered_assets().execute_with(|| {
Expand Down
Loading

0 comments on commit f38ef9d

Please sign in to comment.