use super::*;
#[test]
fn exchange_asset_should_work() {
AllowUnpaidFrom::set(vec![Parent.into()]);
add_asset(Parent, (Parent, 1000u128));
set_exchange_assets(vec![(Here, 100u128).into()]);
let message = Xcm(vec![
WithdrawAsset((Parent, 100u128).into()),
SetAppendix(
vec![DepositAsset { assets: AllCounted(2).into(), beneficiary: Parent.into() }].into(),
),
ExchangeAsset {
give: Definite((Parent, 50u128).into()),
want: (Here, 50u128).into(),
maximal: true,
},
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Parent,
message,
&mut hash,
Weight::from_parts(50, 50),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(40, 40) });
assert_eq!(asset_list(Parent), vec![(Here, 100u128).into(), (Parent, 950u128).into()]);
assert_eq!(exchange_assets(), vec![(Parent, 50u128).into()].into());
}
#[test]
fn exchange_asset_without_maximal_should_work() {
AllowUnpaidFrom::set(vec![Parent.into()]);
add_asset(Parent, (Parent, 1000u128));
set_exchange_assets(vec![(Here, 100u128).into()]);
let message = Xcm(vec![
WithdrawAsset((Parent, 100u128).into()),
SetAppendix(
vec![DepositAsset { assets: AllCounted(2).into(), beneficiary: Parent.into() }].into(),
),
ExchangeAsset {
give: Definite((Parent, 50).into()),
want: (Here, 50u128).into(),
maximal: false,
},
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Parent,
message,
&mut hash,
Weight::from_parts(50, 50),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(40, 40) });
assert_eq!(asset_list(Parent), vec![(Here, 50u128).into(), (Parent, 950u128).into()]);
assert_eq!(exchange_assets(), vec![(Here, 50u128).into(), (Parent, 50u128).into()].into());
}
#[test]
fn exchange_asset_should_fail_when_no_deal_possible() {
AllowUnpaidFrom::set(vec![Parent.into()]);
add_asset(Parent, (Parent, 1000u128));
set_exchange_assets(vec![(Here, 100u128).into()]);
let message = Xcm(vec![
WithdrawAsset((Parent, 150u128).into()),
SetAppendix(
vec![DepositAsset { assets: AllCounted(2).into(), beneficiary: Parent.into() }].into(),
),
ExchangeAsset {
give: Definite((Parent, 150u128).into()),
want: (Here, 150u128).into(),
maximal: false,
},
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Parent,
message,
&mut hash,
Weight::from_parts(50, 50),
Weight::zero(),
);
assert_eq!(
r,
Outcome::Incomplete {
used: Weight::from_parts(40, 40),
error: InstructionError { index: 2, error: XcmError::NoDeal },
}
);
assert_eq!(asset_list(Parent), vec![(Parent, 1000u128).into()]);
assert_eq!(exchange_assets(), vec![(Here, 100u128).into()].into());
}
#[test]
fn paying_reserve_deposit_should_work() {
AllowPaidFrom::set(vec![Parent.into()]);
add_reserve(Parent.into(), (Parent, WildFungible).into());
WeightPrice::set((Parent.into(), 1_000_000_000_000, 1024 * 1024));
let fees = (Parent, 60u128).into();
let message = Xcm(vec![
ReserveAssetDeposited((Parent, 100u128).into()),
BuyExecution { fees, weight_limit: Limited(Weight::from_parts(30, 30)) },
DepositAsset { assets: AllCounted(1).into(), beneficiary: Here.into() },
]);
let mut hash = fake_message_hash(&message);
let weight_limit = Weight::from_parts(50, 50);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Parent,
message,
&mut hash,
weight_limit,
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(30, 30) });
assert_eq!(asset_list(Here), vec![(Parent, 40u128).into()]);
}
#[test]
fn transfer_should_work() {
AllowUnpaidFrom::set(vec![[Teyrchain(1)].into()]);
add_asset(Teyrchain(1), (Here, 1000));
let message = Xcm(vec![TransferAsset {
assets: (Here, 100u128).into(),
beneficiary: [AccountIndex64 { index: 3, network: None }].into(),
}]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(50, 50),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(10, 10) });
assert_eq!(
asset_list(AccountIndex64 { index: 3, network: None }),
vec![(Here, 100u128).into()]
);
assert_eq!(asset_list(Teyrchain(1)), vec![(Here, 900u128).into()]);
assert_eq!(sent_xcm(), vec![]);
}
#[test]
fn reserve_transfer_should_work() {
AllowUnpaidFrom::set(vec![[Teyrchain(1)].into()]);
add_asset(Teyrchain(1), (Here, 1000));
let three: Location = [AccountIndex64 { index: 3, network: None }].into();
let message = Xcm(vec![TransferReserveAsset {
assets: (Here, 100u128).into(),
dest: Teyrchain(2).into(),
xcm: Xcm::<()>(vec![DepositAsset {
assets: AllCounted(1).into(),
beneficiary: three.clone(),
}]),
}]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(50, 50),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(10, 10) });
let expected_msg = Xcm::<()>(vec![
ReserveAssetDeposited((Parent, 100u128).into()),
ClearOrigin,
DepositAsset { assets: AllCounted(1).into(), beneficiary: three },
SetTopic(hash),
]);
assert_eq!(asset_list(Teyrchain(2)), vec![(Here, 100).into()]);
assert_eq!(sent_xcm(), vec![(Teyrchain(2).into(), expected_msg, hash)]);
}
#[test]
fn burn_should_work() {
AllowUnpaidFrom::set(vec![[Teyrchain(1)].into()]);
add_asset(Teyrchain(1), (Here, 1000));
let message = Xcm(vec![
WithdrawAsset((Here, 1000u128).into()),
BurnAsset((Here, 100u128).into()),
DepositAsset { assets: Wild(AllCounted(1)), beneficiary: Teyrchain(1).into() },
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(50, 50),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(30, 30) });
assert_eq!(asset_list(Teyrchain(1)), vec![(Here, 900u128).into()]);
assert_eq!(sent_xcm(), vec![]);
let message = Xcm(vec![
WithdrawAsset((Here, 900u128).into()),
BurnAsset((Here, 1000u128).into()),
DepositAsset { assets: Wild(AllCounted(1)), beneficiary: Teyrchain(1).into() },
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(50, 50),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(30, 30) });
assert_eq!(asset_list(Teyrchain(1)), vec![]);
assert_eq!(sent_xcm(), vec![]);
}
#[test]
fn basic_asset_trap_should_work() {
AllowUnpaidFrom::set(vec![[Teyrchain(1)].into(), [Teyrchain(2)].into()]);
add_asset(Teyrchain(1), (Here, 1000));
let message = Xcm(vec![
WithdrawAsset((Here, 100u128).into()),
DepositAsset {
assets: Wild(AllCounted(0)), beneficiary: AccountIndex64 { index: 3, network: None }.into(),
},
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(20, 20),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(25, 25) });
assert_eq!(asset_list(Teyrchain(1)), vec![(Here, 900u128).into()]);
assert_eq!(asset_list(AccountIndex64 { index: 3, network: None }), vec![]);
let message = Xcm(vec![
ClaimAsset { assets: (Here, 100u128).into(), ticket: GeneralIndex(1).into() },
DepositAsset {
assets: Wild(AllCounted(1)),
beneficiary: AccountIndex64 { index: 3, network: None }.into(),
},
]);
let mut hash = fake_message_hash(&message);
let old_trapped_assets = TrappedAssets::get();
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(20, 20),
Weight::zero(),
);
assert_eq!(
r,
Outcome::Incomplete {
used: Weight::from_parts(10, 10),
error: InstructionError { index: 0, error: XcmError::UnknownClaim },
}
);
assert_eq!(asset_list(Teyrchain(1)), vec![(Here, 900u128).into()]);
assert_eq!(asset_list(AccountIndex64 { index: 3, network: None }), vec![]);
assert_eq!(old_trapped_assets, TrappedAssets::get());
let message = Xcm(vec![
ClaimAsset { assets: (Here, 100u128).into(), ticket: GeneralIndex(0).into() },
DepositAsset {
assets: Wild(AllCounted(1)),
beneficiary: AccountIndex64 { index: 3, network: None }.into(),
},
]);
let mut hash = fake_message_hash(&message);
let old_trapped_assets = TrappedAssets::get();
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(2),
message,
&mut hash,
Weight::from_parts(20, 20),
Weight::zero(),
);
assert_eq!(
r,
Outcome::Incomplete {
used: Weight::from_parts(10, 10),
error: InstructionError { index: 0, error: XcmError::UnknownClaim },
}
);
assert_eq!(asset_list(Teyrchain(1)), vec![(Here, 900u128).into()]);
assert_eq!(asset_list(AccountIndex64 { index: 3, network: None }), vec![]);
assert_eq!(old_trapped_assets, TrappedAssets::get());
let message = Xcm(vec![
ClaimAsset { assets: (Here, 101u128).into(), ticket: GeneralIndex(0).into() },
DepositAsset {
assets: Wild(AllCounted(1)),
beneficiary: AccountIndex64 { index: 3, network: None }.into(),
},
]);
let mut hash = fake_message_hash(&message);
let old_trapped_assets = TrappedAssets::get();
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(20, 20),
Weight::zero(),
);
assert_eq!(
r,
Outcome::Incomplete {
used: Weight::from_parts(10, 10),
error: InstructionError { index: 0, error: XcmError::UnknownClaim },
}
);
assert_eq!(asset_list(Teyrchain(1)), vec![(Here, 900u128).into()]);
assert_eq!(asset_list(AccountIndex64 { index: 3, network: None }), vec![]);
assert_eq!(old_trapped_assets, TrappedAssets::get());
let message = Xcm(vec![
ClaimAsset { assets: (Here, 100u128).into(), ticket: GeneralIndex(0).into() },
DepositAsset {
assets: Wild(AllCounted(1)),
beneficiary: AccountIndex64 { index: 3, network: None }.into(),
},
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(20, 20),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(20, 20) });
assert_eq!(asset_list(Teyrchain(1)), vec![(Here, 900u128).into()]);
assert_eq!(
asset_list(AccountIndex64 { index: 3, network: None }),
vec![(Here, 100u128).into()]
);
let message = Xcm(vec![
ClaimAsset { assets: (Here, 100u128).into(), ticket: GeneralIndex(0).into() },
DepositAsset {
assets: Wild(AllCounted(1)),
beneficiary: AccountIndex64 { index: 3, network: None }.into(),
},
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(20, 20),
Weight::zero(),
);
assert_eq!(
r,
Outcome::Incomplete {
used: Weight::from_parts(10, 10),
error: InstructionError { index: 0, error: XcmError::UnknownClaim },
}
);
}
#[test]
fn max_assets_limit_should_work() {
AllowUnpaidFrom::set(vec![[Teyrchain(1)].into()]);
add_asset(Teyrchain(1), (Junctions::from([GeneralIndex(0)]), 1000u128));
add_asset(Teyrchain(1), (Junctions::from([GeneralIndex(1)]), 1000u128));
add_asset(Teyrchain(1), (Junctions::from([GeneralIndex(2)]), 1000u128));
add_asset(Teyrchain(1), (Junctions::from([GeneralIndex(3)]), 1000u128));
add_asset(Teyrchain(1), (Junctions::from([GeneralIndex(4)]), 1000u128));
add_asset(Teyrchain(1), (Junctions::from([GeneralIndex(5)]), 1000u128));
add_asset(Teyrchain(1), (Junctions::from([GeneralIndex(6)]), 1000u128));
add_asset(Teyrchain(1), (Junctions::from([GeneralIndex(7)]), 1000u128));
add_asset(Teyrchain(1), (Junctions::from([GeneralIndex(8)]), 1000u128));
let message = Xcm(vec![
WithdrawAsset((Junctions::from([GeneralIndex(0)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(1)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(2)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(3)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(4)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(5)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(6)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(7)]), 100u128).into()),
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(100, 100),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(85, 85) });
let message = Xcm(vec![
WithdrawAsset((Junctions::from([GeneralIndex(0)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(1)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(2)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(3)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(4)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(5)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(6)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(7)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(8)]), 100u128).into()),
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(100, 100),
Weight::zero(),
);
assert_eq!(
r,
Outcome::Incomplete {
used: Weight::from_parts(95, 95),
error: InstructionError { index: 8, error: XcmError::HoldingWouldOverflow },
}
);
let message = Xcm(vec![
WithdrawAsset((Junctions::from([GeneralIndex(0)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(1)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(2)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(3)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(0)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(1)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(2)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(3)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(4)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(5)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(6)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(7)]), 100u128).into()),
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(200, 200),
Weight::zero(),
);
assert_eq!(r, Outcome::Complete { used: Weight::from_parts(125, 125) });
let message = Xcm(vec![
WithdrawAsset((Junctions::from([GeneralIndex(0)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(1)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(2)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(3)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(4)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(5)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(6)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(7)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(0)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(1)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(2)]), 100u128).into()),
WithdrawAsset((Junctions::from([GeneralIndex(3)]), 100u128).into()),
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(200, 200),
Weight::zero(),
);
assert_eq!(
r,
Outcome::Incomplete {
used: Weight::from_parts(95, 95),
error: InstructionError { index: 8, error: XcmError::HoldingWouldOverflow },
}
);
let message = Xcm(vec![
WithdrawAsset(Assets::from(vec![
(Junctions::from([GeneralIndex(0)]), 100u128).into(),
(Junctions::from([GeneralIndex(1)]), 100u128).into(),
(Junctions::from([GeneralIndex(2)]), 100u128).into(),
(Junctions::from([GeneralIndex(3)]), 100u128).into(),
(Junctions::from([GeneralIndex(4)]), 100u128).into(),
(Junctions::from([GeneralIndex(5)]), 100u128).into(),
(Junctions::from([GeneralIndex(6)]), 100u128).into(),
(Junctions::from([GeneralIndex(7)]), 100u128).into(),
])),
WithdrawAsset((Junctions::from([GeneralIndex(0)]), 100u128).into()),
]);
let mut hash = fake_message_hash(&message);
let r = XcmExecutor::<TestConfig>::prepare_and_execute(
Teyrchain(1),
message,
&mut hash,
Weight::from_parts(200, 200),
Weight::zero(),
);
assert_eq!(
r,
Outcome::Incomplete {
used: Weight::from_parts(25, 25),
error: InstructionError { index: 1, error: XcmError::HoldingWouldOverflow },
}
);
}