Skip to content

Commit

Permalink
finish the unit test for bridge forwarder
Browse files Browse the repository at this point in the history
  • Loading branch information
Freddy Li authored and Freddy Li committed Jan 23, 2024
1 parent 0459044 commit ac9ec82
Show file tree
Hide file tree
Showing 3 changed files with 242 additions and 8 deletions.
243 changes: 238 additions & 5 deletions bridge-forwarder/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -99,19 +99,26 @@ pub mod pallet {

#[cfg(test)]
mod test {
use frame_support::assert_ok;
use codec::Encode;
use frame_support::{
assert_noop, assert_ok, traits::tokens::fungibles::Create as FungibleCerate,
};
use hex_literal::hex;
use xcm::latest::{Junction, XcmContext};
use xcm::prelude::{AccountId32, Concrete, Fungible, Here, Parachain, X1, X2};
use xcm::prelude::{
AccountId32, Concrete, Fungible, GeneralKey, Here, Parachain, XcmError, X1, X2, X5,
};
use xcm::v3::Junction::GeneralIndex;
use xcm::v3::{MultiAsset, MultiLocation};
use xcm_executor::traits::TransactAsset;

use sygma_traits::{AssetTypeIdentifier, TransactorForwarder};

use crate::mock::{
assert_events, new_test_ext, Assets, Balances, CurrencyTransactor,
ForwarderImplRuntime, FungiblesTransactor, ParachainInfo, RuntimeEvent,
SygmaBridgeForwarder, UsdtAssetId, UsdtLocation, ALICE, BOB,
assert_events, new_test_ext, slice_to_generalkey, Assets, Balances, CurrencyTransactor,
ForwarderImplRuntime, FungiblesTransactor, ParachainInfo, Runtime, RuntimeEvent,
RuntimeOrigin, SygmaBridgeForwarder, UsdtAssetId, UsdtLocation, ALICE, ASSET_OWNER,
BOB, ENDOWED_BALANCE,
};
use crate::{
xcm_asset_transactor::XCMAssetTransactor, Event as SygmaBridgeForwarderEvent,
Expand Down Expand Up @@ -211,6 +218,11 @@ pub mod pallet {
));
assert_eq!(Balances::free_balance(BOB), 10u128);

// Register foreign asset (USDT) with asset id 1
assert_ok!(<pallet_assets::pallet::Pallet<Runtime> as FungibleCerate<
<Runtime as frame_system::Config>::AccountId,
>>::create(UsdtAssetId::get(), ASSET_OWNER, true, 1,));

// send foreign asset to local parachain
let local_foreign_asset: MultiAsset =
(Concrete(UsdtLocation::get()), Fungible(10u128)).into();
Expand All @@ -227,5 +239,226 @@ pub mod pallet {
assert_eq!(Assets::balance(UsdtAssetId::get(), &BOB), 10u128);
})
}

#[test]
fn test_xcm_asset_transactor_outer() {
new_test_ext().execute_with(|| {
let dest_domain_id = 1;
let outer_recipient: MultiLocation = MultiLocation::new(
1,
X5(
Parachain(1000),
GeneralKey {
length: 5,
data: hex![
"7379676d61000000000000000000000000000000000000000000000000000000"
],
},
GeneralKey {
length: 12,
data: hex![
"7379676d612d6272696467650000000000000000000000000000000000000000"
],
},
GeneralIndex(dest_domain_id),
slice_to_generalkey(b"ethereum recipient"),
),
);

// send native asset to the outer world
let native_asset: MultiAsset =
(Concrete(MultiLocation::new(0, Here)), Fungible(10u128)).into();
assert_ok!(XCMAssetTransactor::<
CurrencyTransactor,
FungiblesTransactor,
NativeAssetTypeIdentifier<ParachainInfo>,
ForwarderImplRuntime,
>::deposit_asset(
&native_asset,
&outer_recipient,
&XcmContext::with_message_id([0; 32])
));
// asset tmp holder for outer world transfer
let tmp_account = sp_io::hashing::blake2_256(
&MultiLocation::new(0, X1(GeneralKey { length: 8, data: [1u8; 32] })).encode(),
);
assert_eq!(
Balances::free_balance(sp_runtime::AccountId32::from(tmp_account)),
10u128
);

// Register foreign asset (USDT) with asset id 1
assert_ok!(<pallet_assets::pallet::Pallet<Runtime> as FungibleCerate<
<Runtime as frame_system::Config>::AccountId,
>>::create(UsdtAssetId::get(), ASSET_OWNER, true, 1,));

// send foreign asset to the outer world
let foreign_asset: MultiAsset =
(Concrete(UsdtLocation::get()), Fungible(10u128)).into();
assert_ok!(XCMAssetTransactor::<
CurrencyTransactor,
FungiblesTransactor,
NativeAssetTypeIdentifier<ParachainInfo>,
ForwarderImplRuntime,
>::deposit_asset(
&foreign_asset,
&outer_recipient,
&XcmContext::with_message_id([0; 32])
));
// asset tmp holder for outer world transfer
let tmp_account = sp_io::hashing::blake2_256(
&MultiLocation::new(0, X1(GeneralKey { length: 8, data: [1u8; 32] })).encode(),
);
assert_eq!(
Assets::balance(UsdtAssetId::get(), sp_runtime::AccountId32::from(tmp_account)),
10u128
);
})
}

#[test]
fn test_xcm_asset_transactor_substrate() {
new_test_ext().execute_with(|| {
let substrate_recipient: MultiLocation = MultiLocation::new(
1,
X2(Parachain(2005), slice_to_generalkey(b"substrate recipient")),
);

// send native asset to the substrate world
let native_asset: MultiAsset =
(Concrete(MultiLocation::new(0, Here)), Fungible(10u128)).into();
assert_ok!(XCMAssetTransactor::<
CurrencyTransactor,
FungiblesTransactor,
NativeAssetTypeIdentifier<ParachainInfo>,
ForwarderImplRuntime,
>::deposit_asset(
&native_asset,
&substrate_recipient,
&XcmContext::with_message_id([0; 32])
));
// asset tmp holder for substrate world transfer
let tmp_account = sp_io::hashing::blake2_256(
&MultiLocation::new(0, X1(GeneralKey { length: 8, data: [2u8; 32] })).encode(),
);
assert_eq!(
Balances::free_balance(sp_runtime::AccountId32::from(tmp_account)),
10u128
);

// Register foreign asset (USDT) with asset id 1
assert_ok!(<pallet_assets::pallet::Pallet<Runtime> as FungibleCerate<
<Runtime as frame_system::Config>::AccountId,
>>::create(UsdtAssetId::get(), ASSET_OWNER, true, 1,));

// send foreign asset to the outer world
let foreign_asset: MultiAsset =
(Concrete(UsdtLocation::get()), Fungible(10u128)).into();
assert_ok!(XCMAssetTransactor::<
CurrencyTransactor,
FungiblesTransactor,
NativeAssetTypeIdentifier<ParachainInfo>,
ForwarderImplRuntime,
>::deposit_asset(
&foreign_asset,
&substrate_recipient,
&XcmContext::with_message_id([0; 32])
));
// asset tmp holder for substrate world transfer
let tmp_account = sp_io::hashing::blake2_256(
&MultiLocation::new(0, X1(GeneralKey { length: 8, data: [2u8; 32] })).encode(),
);
assert_eq!(
Assets::balance(UsdtAssetId::get(), sp_runtime::AccountId32::from(tmp_account)),
10u128
);
})
}

#[test]
fn test_xcm_asset_transactor_not_supported_dest() {
new_test_ext().execute_with(|| {
let none_supported_recipient: MultiLocation = MultiLocation::new(
2,
X2(Parachain(2005), slice_to_generalkey(b"substrate recipient")),
);

// send native asset to non-supported world
let native_asset: MultiAsset =
(Concrete(MultiLocation::new(0, Here)), Fungible(10u128)).into();
assert_noop!(
XCMAssetTransactor::<
CurrencyTransactor,
FungiblesTransactor,
NativeAssetTypeIdentifier<ParachainInfo>,
ForwarderImplRuntime,
>::deposit_asset(
&native_asset,
&none_supported_recipient,
&XcmContext::with_message_id([0; 32])
),
XcmError::DestinationUnsupported
);

// asset tmp holder for substrate world and outer world transfer, should not receive any token
let tmp_account_outer = sp_io::hashing::blake2_256(
&MultiLocation::new(0, X1(GeneralKey { length: 8, data: [1u8; 32] })).encode(),
);
assert_eq!(
Balances::free_balance(sp_runtime::AccountId32::from(tmp_account_outer)),
0u128
);
let tmp_account_substrate = sp_io::hashing::blake2_256(
&MultiLocation::new(0, X1(GeneralKey { length: 8, data: [2u8; 32] })).encode(),
);
assert_eq!(
Balances::free_balance(sp_runtime::AccountId32::from(tmp_account_substrate)),
0u128
);
})
}

#[test]
fn test_xcm_asset_transactor_withdraw() {
new_test_ext().execute_with(|| {
let from_account: MultiLocation =
MultiLocation::new(0, X1(AccountId32 { network: None, id: ALICE.into() }));

// withdraw native asset from Alice
let native_asset: MultiAsset =
(Concrete(MultiLocation::new(0, Here)), Fungible(10u128)).into();
assert_ok!(XCMAssetTransactor::<
CurrencyTransactor,
FungiblesTransactor,
NativeAssetTypeIdentifier<ParachainInfo>,
ForwarderImplRuntime,
>::withdraw_asset(&native_asset, &from_account, None));
assert_eq!(Balances::free_balance(ALICE), ENDOWED_BALANCE - 10u128);

// Register foreign asset (USDT) with asset id 1
assert_ok!(<pallet_assets::pallet::Pallet<Runtime> as FungibleCerate<
<Runtime as frame_system::Config>::AccountId,
>>::create(UsdtAssetId::get(), ASSET_OWNER, true, 1,));
// Mint some USDT to ALICE for test
assert_ok!(Assets::mint(
RuntimeOrigin::signed(ASSET_OWNER),
codec::Compact(1),
ALICE,
ENDOWED_BALANCE,
));
assert_eq!(Assets::balance(UsdtAssetId::get(), &ALICE), ENDOWED_BALANCE);

// withdraw foreign asset from Alice
let foreign_asset: MultiAsset =
(Concrete(UsdtLocation::get()), Fungible(10u128)).into();
assert_ok!(XCMAssetTransactor::<
CurrencyTransactor,
FungiblesTransactor,
NativeAssetTypeIdentifier<ParachainInfo>,
ForwarderImplRuntime,
>::withdraw_asset(&foreign_asset, &from_account, None));
assert_eq!(Assets::balance(UsdtAssetId::get(), &ALICE), ENDOWED_BALANCE - 10u128);
})
}
}
}
5 changes: 3 additions & 2 deletions bridge-forwarder/src/xcm_asset_transactor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,10 @@ impl<
match who.interior {
// sygma: 7379676d61000000000000000000000000000000000000000000000000000000
// sygma-bridge: 7379676d612d6272696467650000000000000000000000000000000000000000
// outer world multilocation pattern: { Parachain(1000), GeneralKey { length: 5, data: b"sygma"}, GeneralKey { length: 12, data: b"sygma-bridge"}, GeneralIndex(domainID), GeneralKey { length: length_of_recipient_address, data: recipient_address} }
X5(Parachain(1000), GeneralKey { length: 5, data: hex!["7379676d61000000000000000000000000000000000000000000000000000000"]}, GeneralKey { length: 12, data: hex!["7379676d612d6272696467650000000000000000000000000000000000000000"]}, GeneralIndex(..), GeneralKey { .. }) => {
// check if the asset is native or foreign, and deposit the asset to a tmp account first
let tmp_account = sp_io::hashing::blake2_256(&MultiLocation::new(0, X1(GeneralKey { length: 8, data: [2u8; 32] })).encode());
// check if the asset is native or foreign, and deposit the asset to a tmp account first
let tmp_account = sp_io::hashing::blake2_256(&MultiLocation::new(0, X1(GeneralKey { length: 8, data: [1u8; 32] })).encode());
if AssetTypeChecker::is_native_asset(what) {
CurrencyTransactor::deposit_asset(&what.clone(), &Junction::AccountId32 { network: None, id: tmp_account }.into(), context)?;
} else {
Expand Down
2 changes: 1 addition & 1 deletion deny.toml
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ targets = [
# (https://doc.rust-lang.org/cargo/reference/pkgid-spec.html)
# these are the unlicensed dependencies
exclude = ["xcm", "xcm-executor", "xcm-builder", "cumulus-primitives-core", "cumulus-primitives-utility", "parachains-common",
"polkadot-core-primitives", "polkadot-parachain-primitives", "polkadot-primitives", "ring"]
"polkadot-core-primitives", "polkadot-parachain-primitives", "polkadot-primitives", "ring", "cumulus-pallet-xcm"]
# If true, metadata will be collected with `--all-features`. Note that this can't
# be toggled off if true, if you want to conditionally enable `--all-features` it
# is recommended to pass `--all-features` on the cmd line instead
Expand Down

0 comments on commit ac9ec82

Please sign in to comment.