mirror of
https://github.com/pezkuwichain/pezkuwi-subxt.git
synced 2026-04-26 21:37:56 +00:00
Pallet: Atomic Swap (#6349)
* Init atomic swap pallet * Implement module swap operations * Add successful swap test * Bump node spec_version * Fix storage name * Add ProofLimit parameter to prevent proof size being too large * Add missing events * Basic weight support * Add basic docs * Mark swap on claim This handles the additional case if `repatriate_reserved` fails. * Add additional expire handler * Update frame/atomic-swap/src/lib.rs Co-authored-by: Shawn Tabrizi <shawntabrizi@gmail.com> * Add docs on ProofLimit * Fix test * Return Ok(()) even when the transfer fails Because we need to mark the swap as claimed no matter what. * Remove retry logic It's overkill. Swap is about something being executed, not necessarily successful. Although there should be logic (reserve and unreserve) to make it so that both parties *believes* that the execution is successful. * succeed -> succeeded * Add docs on duration -- revealer should use duration shorter than counterparty * Missing trait type Co-authored-by: Shawn Tabrizi <shawntabrizi@gmail.com>
This commit is contained in:
@@ -0,0 +1,155 @@
|
||||
#![cfg(test)]
|
||||
|
||||
use super::*;
|
||||
|
||||
use frame_support::{
|
||||
impl_outer_origin, parameter_types, weights::Weight,
|
||||
};
|
||||
use sp_core::H256;
|
||||
// The testing primitives are very useful for avoiding having to work with signatures
|
||||
// or public keys. `u64` is used as the `AccountId` and no `Signature`s are required.
|
||||
use sp_runtime::{
|
||||
Perbill,
|
||||
testing::Header,
|
||||
traits::{BlakeTwo256, IdentityLookup},
|
||||
};
|
||||
|
||||
impl_outer_origin! {
|
||||
pub enum Origin for Test where system = frame_system {}
|
||||
}
|
||||
|
||||
// For testing the pallet, we construct most of a mock runtime. This means
|
||||
// first constructing a configuration type (`Test`) which `impl`s each of the
|
||||
// configuration traits of pallets we want to use.
|
||||
#[derive(Clone, Eq, PartialEq)]
|
||||
pub struct Test;
|
||||
parameter_types! {
|
||||
pub const BlockHashCount: u64 = 250;
|
||||
pub const MaximumBlockWeight: Weight = 1024;
|
||||
pub const MaximumBlockLength: u32 = 2 * 1024;
|
||||
pub const AvailableBlockRatio: Perbill = Perbill::one();
|
||||
}
|
||||
impl frame_system::Trait for Test {
|
||||
type BaseCallFilter = ();
|
||||
type Origin = Origin;
|
||||
type Index = u64;
|
||||
type BlockNumber = u64;
|
||||
type Hash = H256;
|
||||
type Call = ();
|
||||
type Hashing = BlakeTwo256;
|
||||
type AccountId = u64;
|
||||
type Lookup = IdentityLookup<Self::AccountId>;
|
||||
type Header = Header;
|
||||
type Event = ();
|
||||
type BlockHashCount = BlockHashCount;
|
||||
type MaximumBlockWeight = MaximumBlockWeight;
|
||||
type DbWeight = ();
|
||||
type BlockExecutionWeight = ();
|
||||
type ExtrinsicBaseWeight = ();
|
||||
type MaximumExtrinsicWeight = MaximumBlockWeight;
|
||||
type MaximumBlockLength = MaximumBlockLength;
|
||||
type AvailableBlockRatio = AvailableBlockRatio;
|
||||
type Version = ();
|
||||
type ModuleToIndex = ();
|
||||
type AccountData = pallet_balances::AccountData<u64>;
|
||||
type OnNewAccount = ();
|
||||
type OnKilledAccount = ();
|
||||
}
|
||||
parameter_types! {
|
||||
pub const ExistentialDeposit: u64 = 1;
|
||||
}
|
||||
impl pallet_balances::Trait for Test {
|
||||
type Balance = u64;
|
||||
type DustRemoval = ();
|
||||
type Event = ();
|
||||
type ExistentialDeposit = ExistentialDeposit;
|
||||
type AccountStore = System;
|
||||
}
|
||||
parameter_types! {
|
||||
pub const ProofLimit: u32 = 1024;
|
||||
pub const ExpireDuration: u64 = 100;
|
||||
}
|
||||
impl Trait for Test {
|
||||
type Event = ();
|
||||
type Currency = Balances;
|
||||
type ProofLimit = ProofLimit;
|
||||
}
|
||||
type System = frame_system::Module<Test>;
|
||||
type Balances = pallet_balances::Module<Test>;
|
||||
type AtomicSwap = Module<Test>;
|
||||
|
||||
const A: u64 = 1;
|
||||
const B: u64 = 2;
|
||||
|
||||
pub fn new_test_ext() -> sp_io::TestExternalities {
|
||||
let mut t = frame_system::GenesisConfig::default().build_storage::<Test>().unwrap();
|
||||
let genesis = pallet_balances::GenesisConfig::<Test> {
|
||||
balances: vec![
|
||||
(A, 100),
|
||||
(B, 200),
|
||||
],
|
||||
};
|
||||
genesis.assimilate_storage(&mut t).unwrap();
|
||||
t.into()
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn two_party_successful_swap() {
|
||||
let mut chain1 = new_test_ext();
|
||||
let mut chain2 = new_test_ext();
|
||||
|
||||
// A generates a random proof. Keep it secret.
|
||||
let proof: [u8; 2] = [4, 2];
|
||||
// The hashed proof is the blake2_256 hash of the proof. This is public.
|
||||
let hashed_proof = blake2_256(&proof);
|
||||
|
||||
// A creates the swap on chain1.
|
||||
chain1.execute_with(|| {
|
||||
AtomicSwap::create_swap(
|
||||
Origin::signed(A),
|
||||
B,
|
||||
hashed_proof.clone(),
|
||||
50,
|
||||
1000,
|
||||
).unwrap();
|
||||
|
||||
assert_eq!(Balances::free_balance(A), 100 - 50);
|
||||
assert_eq!(Balances::free_balance(B), 200);
|
||||
});
|
||||
|
||||
// B creates the swap on chain2.
|
||||
chain2.execute_with(|| {
|
||||
AtomicSwap::create_swap(
|
||||
Origin::signed(B),
|
||||
A,
|
||||
hashed_proof.clone(),
|
||||
75,
|
||||
1000,
|
||||
).unwrap();
|
||||
|
||||
assert_eq!(Balances::free_balance(A), 100);
|
||||
assert_eq!(Balances::free_balance(B), 200 - 75);
|
||||
});
|
||||
|
||||
// A reveals the proof and claims the swap on chain2.
|
||||
chain2.execute_with(|| {
|
||||
AtomicSwap::claim_swap(
|
||||
Origin::signed(A),
|
||||
proof.to_vec(),
|
||||
).unwrap();
|
||||
|
||||
assert_eq!(Balances::free_balance(A), 100 + 75);
|
||||
assert_eq!(Balances::free_balance(B), 200 - 75);
|
||||
});
|
||||
|
||||
// B use the revealed proof to claim the swap on chain1.
|
||||
chain1.execute_with(|| {
|
||||
AtomicSwap::claim_swap(
|
||||
Origin::signed(B),
|
||||
proof.to_vec(),
|
||||
).unwrap();
|
||||
|
||||
assert_eq!(Balances::free_balance(A), 100 - 50);
|
||||
assert_eq!(Balances::free_balance(B), 200 + 50);
|
||||
});
|
||||
}
|
||||
Reference in New Issue
Block a user