Migrate pallet-transaction-payment to new pallet attribute macro (#9087)

* Migrate pallet-transaciont-payment to new pallet attribute macro

Signed-off-by: koushiro <koushiro.cqx@gmail.com>

* remove generic from genesis config

* fix test

* fix tests

* fix deprecated

* fix tests

Signed-off-by: koushiro <koushiro.cqx@gmail.com>

Co-authored-by: thiolliere <gui.thiolliere@gmail.com>
Co-authored-by: Keith Yeung <kungfukeith11@gmail.com>
This commit is contained in:
Qinxuan Chen
2021-06-25 11:23:36 +08:00
committed by GitHub
parent 20347c2edb
commit bc0520913d
16 changed files with 187 additions and 130 deletions
+1 -1
View File
@@ -821,7 +821,7 @@ impl pallet_contracts::Config for Runtime {
type RentFraction = RentFraction;
type SurchargeReward = SurchargeReward;
type CallStack = [pallet_contracts::Frame<Self>; 31];
type WeightPrice = pallet_transaction_payment::Module<Self>;
type WeightPrice = pallet_transaction_payment::Pallet<Self>;
type WeightInfo = pallet_contracts::weights::SubstrateWeight<Self>;
type ChainExtension = ();
type DeletionQueueDepth = DeletionQueueDepth;
+4 -2
View File
@@ -26,7 +26,7 @@ macro_rules! decl_tests {
use crate::*;
use sp_runtime::{ArithmeticError, FixedPointNumber, traits::{SignedExtension, BadOrigin}};
use frame_support::{
assert_noop, assert_storage_noop, assert_ok, assert_err, StorageValue,
assert_noop, assert_storage_noop, assert_ok, assert_err,
traits::{
LockableCurrency, LockIdentifier, WithdrawReasons,
Currency, ReservableCurrency, ExistenceRequirement::AllowDeath
@@ -148,7 +148,9 @@ macro_rules! decl_tests {
.monied(true)
.build()
.execute_with(|| {
pallet_transaction_payment::NextFeeMultiplier::put(Multiplier::saturating_from_integer(1));
pallet_transaction_payment::NextFeeMultiplier::<$test>::put(
Multiplier::saturating_from_integer(1)
);
Balances::set_lock(ID_1, &1, 10, WithdrawReasons::RESERVE);
assert_noop!(
<Balances as Currency<_>>::transfer(&1, &2, 1, AllowDeath),
@@ -43,6 +43,7 @@ frame_support::construct_runtime!(
{
System: frame_system::{Pallet, Call, Config, Storage, Event<T>},
Balances: pallet_balances::{Pallet, Call, Storage, Config<T>, Event<T>},
TransactionPayment: pallet_transaction_payment::{Pallet, Storage},
}
);
@@ -45,6 +45,7 @@ frame_support::construct_runtime!(
{
System: frame_system::{Pallet, Call, Config, Storage, Event<T>},
Balances: pallet_balances::{Pallet, Call, Storage, Config<T>, Event<T>},
TransactionPayment: pallet_transaction_payment::{Pallet, Storage},
}
);
+2 -1
View File
@@ -667,6 +667,7 @@ mod tests {
{
System: frame_system::{Pallet, Call, Config, Storage, Event<T>},
Balances: pallet_balances::{Pallet, Call, Storage, Config<T>, Event<T>},
TransactionPayment: pallet_transaction_payment::{Pallet, Storage},
Custom: custom::{Pallet, Call, ValidateUnsigned, Inherent},
}
);
@@ -835,7 +836,7 @@ mod tests {
header: Header {
parent_hash: [69u8; 32].into(),
number: 1,
state_root: hex!("ec6bb58b0e4bc7fdf0151a0f601eb825f529fbf90b5be5b2024deba30c5cbbcb").into(),
state_root: hex!("1039e1a4bd0cf5deefe65f313577e70169c41c7773d6acf31ca8d671397559f5").into(),
extrinsics_root: hex!("03170a2e7597b7b7e3d84c05391d139a62b157e78786d8c082f29dcf4c111314").into(),
digest: Digest { logs: vec![], },
},
+10 -8
View File
@@ -15,29 +15,31 @@ targets = ["x86_64-unknown-linux-gnu"]
[dependencies]
codec = { package = "parity-scale-codec", version = "2.0.0", default-features = false, features = ["derive"] }
serde = { version = "1.0.101", optional = true }
sp-std = { version = "3.0.0", default-features = false, path = "../../primitives/std" }
smallvec = "1.4.1"
sp-core = { version = "3.0.0", path = "../../primitives/core", default-features = false }
sp-io = { version = "3.0.0", path = "../../primitives/io", default-features = false }
sp-runtime = { version = "3.0.0", default-features = false, path = "../../primitives/runtime" }
sp-std = { version = "3.0.0", default-features = false, path = "../../primitives/std" }
frame-support = { version = "3.0.0", default-features = false, path = "../support" }
frame-system = { version = "3.0.0", default-features = false, path = "../system" }
smallvec = "1.4.1"
sp-io = { version = "3.0.0", path = "../../primitives/io", default-features = false }
sp-core = { version = "3.0.0", path = "../../primitives/core", default-features = false }
[dev-dependencies]
serde_json = "1.0.41"
pallet-balances = { version = "3.0.0", path = "../balances" }
sp-storage = { version = "3.0.0", path = "../../primitives/storage" }
pallet-balances = { version = "3.0.0", path = "../balances" }
[features]
default = ["std"]
std = [
"serde",
"codec/std",
"sp-std/std",
"sp-core/std",
"sp-io/std",
"sp-runtime/std",
"sp-std/std",
"frame-support/std",
"frame-system/std",
"sp-io/std",
"sp-core/std",
]
try-runtime = ["frame-support/try-runtime"]
@@ -1,16 +1,16 @@
# Transaction Payment Module
# Transaction Payment Pallet
This module provides the basic logic needed to pay the absolute minimum amount needed for a
This pallet provides the basic logic needed to pay the absolute minimum amount needed for a
transaction to be included. This includes:
- _weight fee_: A fee proportional to amount of weight a transaction consumes.
- _length fee_: A fee proportional to the encoded length of the transaction.
- _tip_: An optional tip. Tip increases the priority of the transaction, giving it a higher
chance to be included by the transaction queue.
Additionally, this module allows one to configure:
Additionally, this pallet allows one to configure:
- The mapping between one unit of weight to one unit of fee via [`Config::WeightToFee`].
- A means of updating the fee for the next block, via defining a multiplier, based on the
final state of the chain at the end of the previous block. This can be configured via
[`Config::FeeMultiplierUpdate`]
License: Apache-2.0
License: Apache-2.0
@@ -6,7 +6,7 @@ edition = "2018"
license = "Apache-2.0"
homepage = "https://substrate.dev"
repository = "https://github.com/paritytech/substrate/"
description = "RPC interface for the transaction payment module."
description = "RPC interface for the transaction payment pallet."
readme = "README.md"
[package.metadata.docs.rs]
@@ -17,9 +17,10 @@ codec = { package = "parity-scale-codec", version = "2.0.0" }
jsonrpc-core = "15.1.0"
jsonrpc-core-client = "15.1.0"
jsonrpc-derive = "15.1.0"
sp-api = { version = "3.0.0", path = "../../../primitives/api" }
sp-blockchain = { version = "3.0.0", path = "../../../primitives/blockchain" }
sp-core = { version = "3.0.0", path = "../../../primitives/core" }
sp-rpc = { version = "3.0.0", path = "../../../primitives/rpc" }
sp-runtime = { version = "3.0.0", path = "../../../primitives/runtime" }
sp-api = { version = "3.0.0", path = "../../../primitives/api" }
sp-blockchain = { version = "3.0.0", path = "../../../primitives/blockchain" }
pallet-transaction-payment-rpc-runtime-api = { version = "3.0.0", path = "./runtime-api" }
@@ -1,3 +1,3 @@
RPC interface for the transaction payment module.
RPC interface for the transaction payment pallet.
License: Apache-2.0
License: Apache-2.0
@@ -13,16 +13,16 @@ readme = "README.md"
targets = ["x86_64-unknown-linux-gnu"]
[dependencies]
sp-api = { version = "3.0.0", default-features = false, path = "../../../../primitives/api" }
codec = { package = "parity-scale-codec", version = "2.0.0", default-features = false, features = ["derive"] }
sp-api = { version = "3.0.0", default-features = false, path = "../../../../primitives/api" }
sp-runtime = { version = "3.0.0", default-features = false, path = "../../../../primitives/runtime" }
pallet-transaction-payment = { version = "3.0.0", default-features = false, path = "../../../transaction-payment" }
[features]
default = ["std"]
std = [
"sp-api/std",
"codec/std",
"sp-api/std",
"sp-runtime/std",
"pallet-transaction-payment/std",
]
@@ -1,3 +1,3 @@
Runtime API definition for transaction payment module.
Runtime API definition for transaction payment pallet.
License: Apache-2.0
License: Apache-2.0
@@ -15,7 +15,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
//! Runtime API definition for transaction payment module.
//! Runtime API definition for transaction payment pallet.
#![cfg_attr(not(feature = "std"), no_std)]
@@ -15,7 +15,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
//! RPC interface for the transaction payment module.
//! RPC interface for the transaction payment pallet.
use std::sync::Arc;
use std::convert::TryInto;
+140 -96
View File
@@ -15,9 +15,9 @@
// See the License for the specific language governing permissions and
// limitations under the License.
//! # Transaction Payment Module
//! # Transaction Payment Pallet
//!
//! This module provides the basic logic needed to pay the absolute minimum amount needed for a
//! This pallet provides the basic logic needed to pay the absolute minimum amount needed for a
//! transaction to be included. This includes:
//! - _base fee_: This is the minimum amount a user pays for a transaction. It is declared
//! as a base _weight_ in the runtime and converted to a fee using `WeightToFee`.
@@ -38,7 +38,7 @@
//! - `targeted_fee_adjustment`: This is a multiplier that can tune the final fee based on
//! the congestion of the network.
//!
//! Additionally, this module allows one to configure:
//! Additionally, this pallet allows one to configure:
//! - The mapping between one unit of weight to one unit of fee via [`Config::WeightToFee`].
//! - A means of updating the fee for the next block, via defining a multiplier, based on the
//! final state of the chain at the end of the previous block. This can be configured via
@@ -47,17 +47,8 @@
#![cfg_attr(not(feature = "std"), no_std)]
use sp_std::prelude::*;
use codec::{Encode, Decode};
use frame_support::{
decl_storage, decl_module,
traits::Get,
weights::{
Weight, DispatchInfo, PostDispatchInfo, GetDispatchInfo, Pays, WeightToFeePolynomial,
WeightToFeeCoefficient, DispatchClass,
},
dispatch::DispatchResult,
};
use sp_runtime::{
FixedU128, FixedPointNumber, FixedPointOperand, Perquintill, RuntimeDebug,
transaction_validity::{
@@ -68,23 +59,33 @@ use sp_runtime::{
DispatchInfoOf, PostDispatchInfoOf,
},
};
use sp_std::prelude::*;
use frame_support::{
traits::Get,
weights::{
Weight, DispatchInfo, PostDispatchInfo, GetDispatchInfo, Pays, WeightToFeePolynomial,
WeightToFeeCoefficient, DispatchClass,
},
dispatch::DispatchResult,
};
mod payment;
mod types;
pub use pallet::*;
pub use payment::*;
pub use types::{InclusionFee, FeeDetails, RuntimeDispatchInfo};
/// Fee multiplier.
pub type Multiplier = FixedU128;
type BalanceOf<T> =
<<T as Config>::OnChargeTransaction as OnChargeTransaction<T>>::Balance;
type BalanceOf<T> = <<T as Config>::OnChargeTransaction as OnChargeTransaction<T>>::Balance;
/// A struct to update the weight multiplier per block. It implements `Convert<Multiplier,
/// Multiplier>`, meaning that it can convert the previous multiplier to the next one. This should
/// be called on `on_finalize` of a block, prior to potentially cleaning the weight data from the
/// system module.
/// system pallet.
///
/// given:
/// s = previous block weight
@@ -214,10 +215,10 @@ impl<T, S, V, M> Convert<Multiplier, Multiplier> for TargetedFeeAdjustment<T, S,
}
}
/// Storage releases of the module.
/// Storage releases of the pallet.
#[derive(Encode, Decode, Clone, Copy, PartialEq, Eq, RuntimeDebug)]
enum Releases {
/// Original version of the module.
/// Original version of the pallet.
V1Ancient,
/// One that bumps the usage to FixedU128 from FixedI128.
V2,
@@ -229,44 +230,83 @@ impl Default for Releases {
}
}
pub trait Config: frame_system::Config {
/// Handler for withdrawing, refunding and depositing the transaction fee.
/// Transaction fees are withdrawn before the transaction is executed.
/// After the transaction was executed the transaction weight can be
/// adjusted, depending on the used resources by the transaction. If the
/// transaction weight is lower than expected, parts of the transaction fee
/// might be refunded. In the end the fees can be deposited.
type OnChargeTransaction: OnChargeTransaction<Self>;
#[frame_support::pallet]
pub mod pallet {
use frame_support::pallet_prelude::*;
use frame_system::pallet_prelude::*;
use super::*;
/// The fee to be paid for making a transaction; the per-byte portion.
type TransactionByteFee: Get<BalanceOf<Self>>;
#[pallet::pallet]
#[pallet::generate_store(pub(super) trait Store)]
pub struct Pallet<T>(_);
/// Convert a weight value into a deductible fee based on the currency type.
type WeightToFee: WeightToFeePolynomial<Balance=BalanceOf<Self>>;
#[pallet::config]
pub trait Config: frame_system::Config {
/// Handler for withdrawing, refunding and depositing the transaction fee.
/// Transaction fees are withdrawn before the transaction is executed.
/// After the transaction was executed the transaction weight can be
/// adjusted, depending on the used resources by the transaction. If the
/// transaction weight is lower than expected, parts of the transaction fee
/// might be refunded. In the end the fees can be deposited.
type OnChargeTransaction: OnChargeTransaction<Self>;
/// Update the multiplier of the next block, based on the previous block's weight.
type FeeMultiplierUpdate: MultiplierUpdate;
}
decl_storage! {
trait Store for Module<T: Config> as TransactionPayment {
pub NextFeeMultiplier get(fn next_fee_multiplier): Multiplier = Multiplier::saturating_from_integer(1);
StorageVersion build(|_: &GenesisConfig| Releases::V2): Releases;
}
}
decl_module! {
pub struct Module<T: Config> for enum Call where origin: T::Origin {
/// The fee to be paid for making a transaction; the per-byte portion.
const TransactionByteFee: BalanceOf<T> = T::TransactionByteFee::get();
#[pallet::constant]
type TransactionByteFee: Get<BalanceOf<Self>>;
/// Convert a weight value into a deductible fee based on the currency type.
type WeightToFee: WeightToFeePolynomial<Balance = BalanceOf<Self>>;
/// Update the multiplier of the next block, based on the previous block's weight.
type FeeMultiplierUpdate: MultiplierUpdate;
}
#[pallet::extra_constants]
impl<T: Config> Pallet<T> {
//TODO: rename to snake case after https://github.com/paritytech/substrate/issues/8826 fixed.
#[allow(non_snake_case)]
/// The polynomial that is applied in order to derive fee from weight.
const WeightToFee: Vec<WeightToFeeCoefficient<BalanceOf<T>>> =
T::WeightToFee::polynomial().to_vec();
fn WeightToFee() -> Vec<WeightToFeeCoefficient<BalanceOf<T>>> {
T::WeightToFee::polynomial().to_vec()
}
}
fn on_finalize() {
NextFeeMultiplier::mutate(|fm| {
#[pallet::type_value]
pub fn NextFeeMultiplierOnEmpty() -> Multiplier { Multiplier::saturating_from_integer(1) }
#[pallet::storage]
#[pallet::getter(fn next_fee_multiplier)]
pub type NextFeeMultiplier<T: Config> = StorageValue<
_,
Multiplier,
ValueQuery,
NextFeeMultiplierOnEmpty
>;
#[pallet::storage]
pub(super) type StorageVersion<T: Config> = StorageValue<_, Releases, ValueQuery>;
#[pallet::genesis_config]
pub struct GenesisConfig;
#[cfg(feature = "std")]
impl Default for GenesisConfig {
fn default() -> Self {
Self
}
}
#[pallet::genesis_build]
impl<T: Config> GenesisBuild<T> for GenesisConfig {
fn build(&self) {
StorageVersion::<T>::put(Releases::V2);
}
}
#[pallet::hooks]
impl<T: Config> Hooks<BlockNumberFor<T>> for Pallet<T> {
fn on_finalize(_: T::BlockNumber) {
<NextFeeMultiplier<T>>::mutate(|fm| {
*fm = T::FeeMultiplierUpdate::convert(*fm);
});
}
@@ -293,7 +333,6 @@ decl_module! {
"Setting `max_total` for `Normal` dispatch class is not compatible with \
`transaction-payment` pallet."
);
// add 1 percent;
let addition = target / 100;
if addition == 0 {
@@ -302,6 +341,7 @@ decl_module! {
}
target += addition;
#[cfg(any(feature = "std", test))]
sp_io::TestExternalities::new_empty().execute_with(|| {
<frame_system::Pallet<T>>::set_block_consumed_resources(target, 0);
let next = T::FeeMultiplierUpdate::convert(min_value);
@@ -309,17 +349,17 @@ decl_module! {
block saturation is more than target by 1% and multiplier is minimal then \
the multiplier doesn't increase."
);
})
});
}
}
}
impl<T: Config> Module<T> where
impl<T: Config> Pallet<T> where
BalanceOf<T>: FixedPointOperand
{
/// Query the data that we know about the fee of a given `call`.
///
/// This module is not and cannot be aware of the internals of a signed extension, for example
/// This pallet is not and cannot be aware of the internals of a signed extension, for example
/// a tip. It only interprets the extrinsic as some encoded value and accounts for its weight
/// and length, the runtime's extrinsic base weight, and the current fee multiplier.
///
@@ -330,7 +370,7 @@ impl<T: Config> Module<T> where
len: u32,
) -> RuntimeDispatchInfo<BalanceOf<T>>
where
T::Call: Dispatchable<Info=DispatchInfo>,
T::Call: Dispatchable<Info = DispatchInfo>,
{
// NOTE: we can actually make it understand `ChargeTransactionPayment`, but would be some
// hassle for sure. We have to make it aware of the index of `ChargeTransactionPayment` in
@@ -351,7 +391,7 @@ impl<T: Config> Module<T> where
len: u32,
) -> FeeDetails<BalanceOf<T>>
where
T::Call: Dispatchable<Info=DispatchInfo>,
T::Call: Dispatchable<Info = DispatchInfo>,
{
let dispatch_info = <Extrinsic as GetDispatchInfo>::get_dispatch_info(&unchecked_extrinsic);
Self::compute_fee_details(len, &dispatch_info, 0u32.into())
@@ -363,7 +403,7 @@ impl<T: Config> Module<T> where
info: &DispatchInfoOf<T::Call>,
tip: BalanceOf<T>,
) -> BalanceOf<T> where
T::Call: Dispatchable<Info=DispatchInfo>,
T::Call: Dispatchable<Info = DispatchInfo>,
{
Self::compute_fee_details(len, info, tip).final_fee()
}
@@ -374,7 +414,7 @@ impl<T: Config> Module<T> where
info: &DispatchInfoOf<T::Call>,
tip: BalanceOf<T>,
) -> FeeDetails<BalanceOf<T>> where
T::Call: Dispatchable<Info=DispatchInfo>,
T::Call: Dispatchable<Info = DispatchInfo>,
{
Self::compute_fee_raw(len, info.weight, tip, info.pays_fee, info.class)
}
@@ -389,7 +429,7 @@ impl<T: Config> Module<T> where
post_info: &PostDispatchInfoOf<T::Call>,
tip: BalanceOf<T>,
) -> BalanceOf<T> where
T::Call: Dispatchable<Info=DispatchInfo,PostInfo=PostDispatchInfo>,
T::Call: Dispatchable<Info = DispatchInfo, PostInfo = PostDispatchInfo>,
{
Self::compute_actual_fee_details(len, info, post_info, tip).final_fee()
}
@@ -401,7 +441,7 @@ impl<T: Config> Module<T> where
post_info: &PostDispatchInfoOf<T::Call>,
tip: BalanceOf<T>,
) -> FeeDetails<BalanceOf<T>> where
T::Call: Dispatchable<Info=DispatchInfo,PostInfo=PostDispatchInfo>,
T::Call: Dispatchable<Info = DispatchInfo, PostInfo = PostDispatchInfo>,
{
Self::compute_fee_raw(
len,
@@ -457,7 +497,7 @@ impl<T: Config> Module<T> where
}
}
impl<T> Convert<Weight, BalanceOf<T>> for Module<T> where
impl<T> Convert<Weight, BalanceOf<T>> for Pallet<T> where
T: Config,
BalanceOf<T>: FixedPointOperand,
{
@@ -467,7 +507,7 @@ impl<T> Convert<Weight, BalanceOf<T>> for Module<T> where
/// share that the weight contributes to the overall fee of a transaction. It is mainly
/// for informational purposes and not used in the actual fee calculation.
fn convert(weight: Weight) -> BalanceOf<T> {
NextFeeMultiplier::get().saturating_mul_int(Self::weight_to_fee(weight))
<NextFeeMultiplier<T>>::get().saturating_mul_int(Self::weight_to_fee(weight))
}
}
@@ -477,7 +517,7 @@ impl<T> Convert<Weight, BalanceOf<T>> for Module<T> where
pub struct ChargeTransactionPayment<T: Config>(#[codec(compact)] BalanceOf<T>);
impl<T: Config> ChargeTransactionPayment<T> where
T::Call: Dispatchable<Info=DispatchInfo, PostInfo=PostDispatchInfo>,
T::Call: Dispatchable<Info = DispatchInfo, PostInfo = PostDispatchInfo>,
BalanceOf<T>: Send + Sync + FixedPointOperand,
{
/// utility constructor. Used only in client/factory code.
@@ -499,7 +539,7 @@ impl<T: Config> ChargeTransactionPayment<T> where
TransactionValidityError,
> {
let tip = self.0;
let fee = Module::<T>::compute_fee(len as u32, info, tip);
let fee = Pallet::<T>::compute_fee(len as u32, info, tip);
<<T as Config>::OnChargeTransaction as OnChargeTransaction<T>>::withdraw_fee(who, call, info, fee, tip)
.map(|i| (fee, i))
@@ -537,7 +577,7 @@ impl<T: Config> sp_std::fmt::Debug for ChargeTransactionPayment<T> {
impl<T: Config> SignedExtension for ChargeTransactionPayment<T> where
BalanceOf<T>: Send + Sync + From<u64> + FixedPointOperand,
T::Call: Dispatchable<Info=DispatchInfo, PostInfo=PostDispatchInfo>,
T::Call: Dispatchable<Info = DispatchInfo, PostInfo = PostDispatchInfo>,
{
const IDENTIFIER: &'static str = "ChargeTransactionPayment";
type AccountId = T::AccountId;
@@ -586,7 +626,7 @@ impl<T: Config> SignedExtension for ChargeTransactionPayment<T> where
_result: &DispatchResult,
) -> Result<(), TransactionValidityError> {
let (tip, who, imbalance) = pre;
let actual_fee = Module::<T>::compute_actual_fee(
let actual_fee = Pallet::<T>::compute_actual_fee(
len as u32,
info,
post_info,
@@ -601,8 +641,20 @@ impl<T: Config> SignedExtension for ChargeTransactionPayment<T> where
mod tests {
use super::*;
use crate as pallet_transaction_payment;
use frame_system as system;
use std::cell::RefCell;
use codec::Encode;
use smallvec::smallvec;
use sp_core::H256;
use sp_runtime::{
testing::{Header, TestXt},
traits::{BlakeTwo256, IdentityLookup, One},
transaction_validity::InvalidTransaction,
Perbill,
};
use frame_support::{
assert_noop, assert_ok, parameter_types,
weights::{
@@ -611,16 +663,8 @@ mod tests {
},
traits::{Currency, OnUnbalanced, Imbalance},
};
use frame_system as system;
use pallet_balances::Call as BalancesCall;
use sp_core::H256;
use sp_runtime::{
testing::{Header, TestXt},
traits::{BlakeTwo256, IdentityLookup, One},
transaction_validity::InvalidTransaction,
Perbill,
};
use std::cell::RefCell;
use smallvec::smallvec;
type UncheckedExtrinsic = frame_system::mocking::MockUncheckedExtrinsic<Runtime>;
type Block = frame_system::mocking::MockBlock<Runtime>;
@@ -728,7 +772,7 @@ mod tests {
pub struct DealWithFees;
impl OnUnbalanced<pallet_balances::NegativeImbalance<Runtime>> for DealWithFees {
fn on_unbalanceds<B>(
mut fees_then_tips: impl Iterator<Item=pallet_balances::NegativeImbalance<Runtime>>
mut fees_then_tips: impl Iterator<Item = pallet_balances::NegativeImbalance<Runtime>>
) {
if let Some(fees) = fees_then_tips.next() {
FEE_UNBALANCED_AMOUNT.with(|a| *a.borrow_mut() += fees.peek());
@@ -882,7 +926,7 @@ mod tests {
.execute_with(||
{
let len = 10;
NextFeeMultiplier::put(Multiplier::saturating_from_rational(3, 2));
<NextFeeMultiplier<Runtime>>::put(Multiplier::saturating_from_rational(3, 2));
let pre = ChargeTransactionPayment::<Runtime>::from(5 /* tipped */)
.pre_dispatch(&2, CALL, &info_from_weight(100), len)
@@ -967,7 +1011,7 @@ mod tests {
.execute_with(||
{
// all fees should be x1.5
NextFeeMultiplier::put(Multiplier::saturating_from_rational(3, 2));
<NextFeeMultiplier<Runtime>>::put(Multiplier::saturating_from_rational(3, 2));
let len = 10;
assert_ok!(
@@ -1001,7 +1045,7 @@ mod tests {
.execute_with(||
{
// all fees should be x1.5
NextFeeMultiplier::put(Multiplier::saturating_from_rational(3, 2));
<NextFeeMultiplier<Runtime>>::put(Multiplier::saturating_from_rational(3, 2));
assert_eq!(
TransactionPayment::query_info(xt, len),
@@ -1028,7 +1072,7 @@ mod tests {
.execute_with(||
{
// Next fee multiplier is zero
assert_eq!(NextFeeMultiplier::get(), Multiplier::one());
assert_eq!(<NextFeeMultiplier<Runtime>>::get(), Multiplier::one());
// Tip only, no fees works
let dispatch_info = DispatchInfo {
@@ -1036,25 +1080,25 @@ mod tests {
class: DispatchClass::Operational,
pays_fee: Pays::No,
};
assert_eq!(Module::<Runtime>::compute_fee(0, &dispatch_info, 10), 10);
assert_eq!(Pallet::<Runtime>::compute_fee(0, &dispatch_info, 10), 10);
// No tip, only base fee works
let dispatch_info = DispatchInfo {
weight: 0,
class: DispatchClass::Operational,
pays_fee: Pays::Yes,
};
assert_eq!(Module::<Runtime>::compute_fee(0, &dispatch_info, 0), 100);
assert_eq!(Pallet::<Runtime>::compute_fee(0, &dispatch_info, 0), 100);
// Tip + base fee works
assert_eq!(Module::<Runtime>::compute_fee(0, &dispatch_info, 69), 169);
assert_eq!(Pallet::<Runtime>::compute_fee(0, &dispatch_info, 69), 169);
// Len (byte fee) + base fee works
assert_eq!(Module::<Runtime>::compute_fee(42, &dispatch_info, 0), 520);
assert_eq!(Pallet::<Runtime>::compute_fee(42, &dispatch_info, 0), 520);
// Weight fee + base fee works
let dispatch_info = DispatchInfo {
weight: 1000,
class: DispatchClass::Operational,
pays_fee: Pays::Yes,
};
assert_eq!(Module::<Runtime>::compute_fee(0, &dispatch_info, 0), 1100);
assert_eq!(Pallet::<Runtime>::compute_fee(0, &dispatch_info, 0), 1100);
});
}
@@ -1068,14 +1112,14 @@ mod tests {
.execute_with(||
{
// Add a next fee multiplier. Fees will be x3/2.
NextFeeMultiplier::put(Multiplier::saturating_from_rational(3, 2));
<NextFeeMultiplier<Runtime>>::put(Multiplier::saturating_from_rational(3, 2));
// Base fee is unaffected by multiplier
let dispatch_info = DispatchInfo {
weight: 0,
class: DispatchClass::Operational,
pays_fee: Pays::Yes,
};
assert_eq!(Module::<Runtime>::compute_fee(0, &dispatch_info, 0), 100);
assert_eq!(Pallet::<Runtime>::compute_fee(0, &dispatch_info, 0), 100);
// Everything works together :)
let dispatch_info = DispatchInfo {
@@ -1085,7 +1129,7 @@ mod tests {
};
// 123 weight, 456 length, 100 base
assert_eq!(
Module::<Runtime>::compute_fee(456, &dispatch_info, 789),
Pallet::<Runtime>::compute_fee(456, &dispatch_info, 789),
100 + (3 * 123 / 2) + 4560 + 789,
);
});
@@ -1101,7 +1145,7 @@ mod tests {
.execute_with(||
{
// Add a next fee multiplier. All fees will be x1/2.
NextFeeMultiplier::put(Multiplier::saturating_from_rational(1, 2));
<NextFeeMultiplier<Runtime>>::put(Multiplier::saturating_from_rational(1, 2));
// Base fee is unaffected by multiplier.
let dispatch_info = DispatchInfo {
@@ -1109,7 +1153,7 @@ mod tests {
class: DispatchClass::Operational,
pays_fee: Pays::Yes,
};
assert_eq!(Module::<Runtime>::compute_fee(0, &dispatch_info, 0), 100);
assert_eq!(Pallet::<Runtime>::compute_fee(0, &dispatch_info, 0), 100);
// Everything works together.
let dispatch_info = DispatchInfo {
@@ -1119,7 +1163,7 @@ mod tests {
};
// 123 weight, 456 length, 100 base
assert_eq!(
Module::<Runtime>::compute_fee(456, &dispatch_info, 789),
Pallet::<Runtime>::compute_fee(456, &dispatch_info, 789),
100 + (123 / 2) + 4560 + 789,
);
});
@@ -1141,7 +1185,7 @@ mod tests {
pays_fee: Pays::Yes,
};
assert_eq!(
Module::<Runtime>::compute_fee(
Pallet::<Runtime>::compute_fee(
u32::MAX,
&dispatch_info,
u64::MAX
@@ -1250,7 +1294,7 @@ mod tests {
let len = 10;
let tip = 5;
NextFeeMultiplier::put(Multiplier::saturating_from_rational(5, 4));
<NextFeeMultiplier<Runtime>>::put(Multiplier::saturating_from_rational(5, 4));
let pre = ChargeTransactionPayment::<Runtime>::from(tip)
.pre_dispatch(&2, CALL, &info, len)
@@ -1261,7 +1305,7 @@ mod tests {
.unwrap();
let refund_based_fee = prev_balance - Balances::free_balance(2);
let actual_fee = Module::<Runtime>
let actual_fee = Pallet::<Runtime>
::compute_actual_fee(len as u32, &info, &post_info, tip);
// 33 weight, 10 length, 7 base, 5 tip
@@ -1284,7 +1328,7 @@ mod tests {
let len = 10;
let tip = 5;
NextFeeMultiplier::put(Multiplier::saturating_from_rational(5, 4));
<NextFeeMultiplier<Runtime>>::put(Multiplier::saturating_from_rational(5, 4));
let pre = ChargeTransactionPayment::<Runtime>::from(tip)
.pre_dispatch(&2, CALL, &info, len)
@@ -1295,7 +1339,7 @@ mod tests {
.unwrap();
let refund_based_fee = prev_balance - Balances::free_balance(2);
let actual_fee = Module::<Runtime>
let actual_fee = Pallet::<Runtime>
::compute_actual_fee(len as u32, &info, &post_info, tip);
// Only 5 tip is paid
@@ -1,16 +1,19 @@
///! Traits and default implementation for paying transaction fees.
use crate::Config;
use codec::FullCodec;
use frame_support::{
traits::{Currency, ExistenceRequirement, Get, Imbalance, OnUnbalanced, WithdrawReasons},
unsigned::TransactionValidityError,
};
use sp_runtime::{
traits::{AtLeast32BitUnsigned, DispatchInfoOf, MaybeSerializeDeserialize, PostDispatchInfoOf, Saturating, Zero},
transaction_validity::InvalidTransaction,
};
use sp_std::{fmt::Debug, marker::PhantomData};
use frame_support::{
traits::{Currency, ExistenceRequirement, Get, Imbalance, OnUnbalanced, WithdrawReasons},
unsigned::TransactionValidityError,
};
type NegativeImbalanceOf<C, T> =
<C as Currency<<T as frame_system::Config>::AccountId>>::NegativeImbalance;
@@ -47,7 +50,7 @@ pub trait OnChargeTransaction<T: Config> {
) -> Result<(), TransactionValidityError>;
}
/// Implements the transaction payment for a module implementing the `Currency`
/// Implements the transaction payment for a pallet implementing the `Currency`
/// trait (eg. the pallet_balances) using an unbalance handler (implementing
/// `OnUnbalanced`).
///
@@ -17,12 +17,14 @@
//! Types for transaction-payment RPC.
use sp_std::prelude::*;
use frame_support::weights::{Weight, DispatchClass};
use codec::{Encode, Decode};
#[cfg(feature = "std")]
use serde::{Serialize, Deserialize};
use sp_runtime::traits::{AtLeast32BitUnsigned, Zero};
use sp_std::prelude::*;
use frame_support::weights::{Weight, DispatchClass};
/// The base fee and adjusted weight and length fees constitute the _inclusion fee_.
#[derive(Encode, Decode, Clone, Eq, PartialEq)]