From 4dc76030c4fa8df1704d074c74950dac0398e09c Mon Sep 17 00:00:00 2001 From: Svyatoslav Nikolsky Date: Mon, 30 Aug 2021 12:19:20 +0300 Subject: [PATCH] upgrade currency exchange pallet to frame v2 (#1097) --- .../currency-exchange/src/benchmarking.rs | 12 +- bridges/modules/currency-exchange/src/lib.rs | 152 ++++++++++-------- 2 files changed, 89 insertions(+), 75 deletions(-) diff --git a/bridges/modules/currency-exchange/src/benchmarking.rs b/bridges/modules/currency-exchange/src/benchmarking.rs index 574ae93f6e..db8b2256c8 100644 --- a/bridges/modules/currency-exchange/src/benchmarking.rs +++ b/bridges/modules/currency-exchange/src/benchmarking.rs @@ -18,12 +18,10 @@ //! So we are giving runtime opportunity to prepare environment and construct proof //! before invoking module calls. -use super::{ - Call, Config as CurrencyExchangeConfig, InclusionProofVerifier, Instance, Pallet as CurrencyExchangePallet, -}; +use super::{Call, Config as CurrencyExchangeConfig, InclusionProofVerifier, Pallet as CurrencyExchangePallet}; use sp_std::prelude::*; -use frame_benchmarking::{account, benchmarks_instance}; +use frame_benchmarking::{account, benchmarks_instance_pallet}; use frame_system::RawOrigin; const SEED: u32 = 0; @@ -31,7 +29,7 @@ const WORST_TX_SIZE_FACTOR: u32 = 1000; const WORST_PROOF_SIZE_FACTOR: u32 = 1000; /// Pallet we're benchmarking here. -pub struct Pallet, I: Instance>(CurrencyExchangePallet); +pub struct Pallet, I: 'static>(CurrencyExchangePallet); /// Proof benchmarking parameters. pub struct ProofParams { @@ -48,14 +46,14 @@ pub struct ProofParams { } /// Config that must be implemented by runtime. -pub trait Config: CurrencyExchangeConfig { +pub trait Config: CurrencyExchangeConfig { /// Prepare proof for importing exchange transaction. fn make_proof( proof_params: ProofParams, ) -> <>::PeerBlockchain as InclusionProofVerifier>::TransactionInclusionProof; } -benchmarks_instance! { +benchmarks_instance_pallet! { // Benchmark `import_peer_transaction` extrinsic with the best possible conditions: // * Proof is the transaction itself. // * Transaction has minimal size. diff --git a/bridges/modules/currency-exchange/src/lib.rs b/bridges/modules/currency-exchange/src/lib.rs index 9a8af5ba50..290e1a9bc9 100644 --- a/bridges/modules/currency-exchange/src/lib.rs +++ b/bridges/modules/currency-exchange/src/lib.rs @@ -22,8 +22,7 @@ use bp_currency_exchange::{ CurrencyConverter, DepositInto, Error as ExchangeError, MaybeLockFundsTransaction, RecipientsMap, }; use bp_header_chain::InclusionProofVerifier; -use frame_support::{decl_error, decl_module, decl_storage, ensure}; -use sp_runtime::DispatchResult; +use frame_support::ensure; #[cfg(feature = "runtime-benchmarks")] pub mod benchmarking; @@ -34,61 +33,53 @@ pub trait OnTransactionSubmitted { fn on_valid_transaction_submitted(submitter: AccountId); } -/// The module configuration trait -pub trait Config: frame_system::Config { - /// Handler for transaction submission result. - type OnTransactionSubmitted: OnTransactionSubmitted; - /// Represents the blockchain that we'll be exchanging currency with. - type PeerBlockchain: InclusionProofVerifier; - /// Peer blockchain transaction parser. - type PeerMaybeLockFundsTransaction: MaybeLockFundsTransaction< - Transaction = ::Transaction, - >; - /// Map between blockchains recipients. - type RecipientsMap: RecipientsMap< - PeerRecipient = ::Recipient, - Recipient = Self::AccountId, - >; - /// This blockchain currency amount type. - type Amount; - /// Converter from peer blockchain currency type into current blockchain currency type. - type CurrencyConverter: CurrencyConverter< - SourceAmount = ::Amount, - TargetAmount = Self::Amount, - >; - /// Something that could grant money. - type DepositInto: DepositInto; -} +pub use pallet::*; -decl_error! { - pub enum Error for Pallet, I: Instance> { - /// Invalid peer blockchain transaction provided. - InvalidTransaction, - /// Peer transaction has invalid amount. - InvalidAmount, - /// Peer transaction has invalid recipient. - InvalidRecipient, - /// Cannot map from peer recipient to this blockchain recipient. - FailedToMapRecipients, - /// Failed to convert from peer blockchain currency to this blockchain currency. - FailedToConvertCurrency, - /// Deposit has failed. - DepositFailed, - /// Deposit has partially failed (changes to recipient account were made). - DepositPartiallyFailed, - /// Transaction is not finalized. - UnfinalizedTransaction, - /// Transaction funds are already claimed. - AlreadyClaimed, +#[frame_support::pallet] +pub mod pallet { + use super::*; + use frame_support::pallet_prelude::*; + use frame_system::pallet_prelude::*; + + #[pallet::config] + pub trait Config: frame_system::Config { + /// Handler for transaction submission result. + type OnTransactionSubmitted: OnTransactionSubmitted; + /// Represents the blockchain that we'll be exchanging currency with. + type PeerBlockchain: InclusionProofVerifier; + /// Peer blockchain transaction parser. + type PeerMaybeLockFundsTransaction: MaybeLockFundsTransaction< + Transaction = ::Transaction, + >; + /// Map between blockchains recipients. + type RecipientsMap: RecipientsMap< + PeerRecipient = ::Recipient, + Recipient = Self::AccountId, + >; + /// This blockchain currency amount type. + type Amount; + /// Converter from peer blockchain currency type into current blockchain currency type. + type CurrencyConverter: CurrencyConverter< + SourceAmount = ::Amount, + TargetAmount = Self::Amount, + >; + /// Something that could grant money. + type DepositInto: DepositInto; } -} -decl_module! { - pub struct Module, I: Instance = DefaultInstance> for enum Call where origin: T::Origin { + #[pallet::pallet] + #[pallet::generate_store(pub(super) trait Store)] + pub struct Pallet(PhantomData<(T, I)>); + + #[pallet::hooks] + impl, I: 'static> Hooks> for Pallet {} + + #[pallet::call] + impl, I: 'static> Pallet { /// Imports lock fund transaction of the peer blockchain. - #[weight = 0] // TODO: update me (https://github.com/paritytech/parity-bridges-common/issues/78) + #[pallet::weight(0)] // TODO: update me (https://github.com/paritytech/parity-bridges-common/issues/78) pub fn import_peer_transaction( - origin, + origin: OriginFor, proof: <>::PeerBlockchain as InclusionProofVerifier>::TransactionInclusionProof, ) -> DispatchResult { let submitter = frame_system::ensure_signed(origin)?; @@ -122,16 +113,41 @@ decl_module! { Ok(()) } } -} -decl_storage! { - trait Store for Pallet, I: Instance = DefaultInstance> as Bridge { - /// All transfers that have already been claimed. - Transfers: map hasher(blake2_128_concat) ::Id => (); + #[pallet::error] + pub enum Error { + /// Invalid peer blockchain transaction provided. + InvalidTransaction, + /// Peer transaction has invalid amount. + InvalidAmount, + /// Peer transaction has invalid recipient. + InvalidRecipient, + /// Cannot map from peer recipient to this blockchain recipient. + FailedToMapRecipients, + /// Failed to convert from peer blockchain currency to this blockchain currency. + FailedToConvertCurrency, + /// Deposit has failed. + DepositFailed, + /// Deposit has partially failed (changes to recipient account were made). + DepositPartiallyFailed, + /// Transaction is not finalized. + UnfinalizedTransaction, + /// Transaction funds are already claimed. + AlreadyClaimed, } + + /// All transfers that have already been claimed. + #[pallet::storage] + pub(super) type Transfers, I: 'static = ()> = StorageMap< + _, + Blake2_128Concat, + ::Id, + (), + ValueQuery, + >; } -impl, I: Instance> Pallet { +impl, I: 'static> Pallet { /// Returns true if currency exchange module is able to import given transaction proof in /// its current state. pub fn filter_transaction_proof( @@ -151,7 +167,7 @@ impl, I: Instance> Pallet { } } -impl, I: Instance> From for Error { +impl, I: 'static> From for Error { fn from(error: ExchangeError) -> Self { match error { ExchangeError::InvalidTransaction => Error::InvalidTransaction, @@ -170,7 +186,7 @@ impl OnTransactionSubmitted for () { } /// Exchange deposit details. -struct DepositDetails, I: Instance> { +struct DepositDetails, I: 'static> { /// Transfer id. pub transfer_id: ::Id, /// Transfer recipient. @@ -181,7 +197,7 @@ struct DepositDetails, I: Instance> { /// Verify and parse transaction proof, preparing everything required for importing /// this transaction proof. -fn prepare_deposit_details, I: Instance>( +fn prepare_deposit_details, I: 'static>( proof: &<>::PeerBlockchain as InclusionProofVerifier>::TransactionInclusionProof, ) -> Result, Error> { // ensure that transaction is included in finalized block that we know of @@ -238,7 +254,7 @@ mod tests { impl OnTransactionSubmitted for DummyTransactionSubmissionHandler { fn on_valid_transaction_submitted(submitter: AccountId) { - Transfers::::insert(submitter, ()); + Transfers::::insert(submitter, ()); } } @@ -394,7 +410,7 @@ mod tests { new_test_ext().execute_with(|| { assert_noop!( Exchange::import_peer_transaction(Origin::signed(SUBMITTER), (false, transaction(0))), - Error::::UnfinalizedTransaction, + Error::::UnfinalizedTransaction, ); }); } @@ -407,7 +423,7 @@ mod tests { Origin::signed(SUBMITTER), (true, transaction(INVALID_TRANSACTION_ID)), ), - Error::::InvalidTransaction, + Error::::InvalidTransaction, ); }); } @@ -421,7 +437,7 @@ mod tests { Origin::signed(SUBMITTER), (true, transaction(ALREADY_CLAIMED_TRANSACTION_ID)), ), - Error::::AlreadyClaimed, + Error::::AlreadyClaimed, ); }); } @@ -433,7 +449,7 @@ mod tests { transaction.recipient = UNKNOWN_RECIPIENT_ID; assert_noop!( Exchange::import_peer_transaction(Origin::signed(SUBMITTER), (true, transaction)), - Error::::FailedToMapRecipients, + Error::::FailedToMapRecipients, ); }); } @@ -445,7 +461,7 @@ mod tests { transaction.amount = INVALID_AMOUNT; assert_noop!( Exchange::import_peer_transaction(Origin::signed(SUBMITTER), (true, transaction)), - Error::::FailedToConvertCurrency, + Error::::FailedToConvertCurrency, ); }); } @@ -457,7 +473,7 @@ mod tests { transaction.amount = MAX_DEPOSIT_AMOUNT + 1; assert_noop!( Exchange::import_peer_transaction(Origin::signed(SUBMITTER), (true, transaction)), - Error::::DepositFailed, + Error::::DepositFailed, ); }); }