// This file is part of Bizinikiwi. // Copyright (C) Parity Technologies (UK) Ltd. // SPDX-License-Identifier: Apache-2.0 // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. //! # Staking Async Teyrchain Runtime #![cfg_attr(not(feature = "std"), no_std)] #![allow(non_local_definitions)] #![recursion_limit = "512"] // Make the WASM binary available. #[cfg(feature = "std")] include!(concat!(env!("OUT_DIR"), "/wasm_binary.rs")); mod genesis_config_presets; mod weights; pub mod xcm_config; // Configurations for next functionality. mod bag_thresholds; pub mod governance; mod staking; extern crate alloc; use alloc::{vec, vec::Vec}; use assets_common::{ foreign_creators::ForeignCreators, local_and_foreign_assets::{ForeignAssetReserveData, LocalFromLeft, TargetFromLeft}, matching::{FromNetwork, FromSiblingTeyrchain}, AssetIdForPoolAssets, AssetIdForPoolAssetsConvert, AssetIdForTrustBackedAssetsConvert, }; use codec::{Decode, DecodeWithMemTracking, Encode, MaxEncodedLen}; use governance::{ pezpallet_custom_origins, FellowshipAdmin, GeneralAdmin, StakingAdmin, Treasurer, }; use pezcumulus_pezpallet_teyrchain_system::{ RelayNumberMonotonicallyIncreases, RelaychainDataProvider, }; use pezcumulus_primitives_core::{AggregateMessageOrigin, ParaId}; use pezframe_support::{ construct_runtime, derive_impl, dispatch::DispatchClass, genesis_builder_helper::{build_state, get_preset}, ord_parameter_types, parameter_types, traits::{ fungible, fungible::HoldConsideration, fungibles, tokens::{imbalance::ResolveAssetTo, nonfungibles_v2::Inspect}, AsEnsureOriginWithArg, ConstBool, ConstU128, ConstU32, ConstU64, ConstU8, ConstantStoragePrice, Equals, InstanceFilter, TransformOrigin, WithdrawReasons, }, weights::{ConstantMultiplier, Weight, WeightToFee as _}, BoundedVec, PalletId, }; use pezframe_system::{ limits::{BlockLength, BlockWeights}, EnsureRoot, EnsureSigned, EnsureSignedBy, }; use pezkuwi_runtime_common::{BlockHashCount, SlowAdjustingFeeUpdate}; use pezpallet_asset_conversion_tx_payment::SwapAssetAdapter; use pezpallet_nfts::PalletFeatures; use pezpallet_nomination_pools::PoolId; use pezpallet_xcm::EnsureXcm; use pezsp_api::impl_runtime_apis; use pezsp_core::{crypto::KeyTypeId, OpaqueMetadata}; #[cfg(any(feature = "std", test))] pub use pezsp_runtime::BuildStorage; use pezsp_runtime::{ generic, impl_opaque_keys, traits::{AccountIdConversion, BlakeTwo256, Block as BlockT, ConvertInto, Verify}, transaction_validity::{TransactionSource, TransactionValidity}, ApplyExtrinsicResult, Perbill, Permill, RuntimeDebug, }; #[cfg(feature = "std")] use pezsp_version::NativeVersion; use pezsp_version::RuntimeVersion; use testnet_teyrchains_constants::zagros::{ consensus::*, currency::*, fee::WeightToFee, snowbridge::EthereumNetwork, time::*, }; use teyrchains_common::{ impls::DealWithFees, message_queue::*, AccountId, AssetIdForTrustBackedAssets, AuraId, Balance, BlockNumber, CollectionId, Hash, Header, ItemId, Nonce, Signature, AVERAGE_ON_INITIALIZE_RATIO, NORMAL_DISPATCH_RATIO, }; use weights::{BlockExecutionWeight, ExtrinsicBaseWeight, RocksDbWeight}; use xcm::{ latest::prelude::AssetId, prelude::{VersionedAsset, VersionedAssetId, VersionedAssets, VersionedLocation, VersionedXcm}, }; use xcm_config::{ ForeignAssetsConvertedConcreteId, LocationToAccountId, PoolAssetsConvertedConcreteId, PoolAssetsPalletLocation, TrustBackedAssetsConvertedConcreteId, TrustBackedAssetsPalletLocation, XcmOriginToTransactDispatchOrigin, ZagrosLocation, }; #[cfg(feature = "runtime-benchmarks")] use pezframe_support::traits::PalletInfoAccess; #[cfg(feature = "runtime-benchmarks")] use xcm::latest::prelude::{ Asset, Assets as XcmAssets, Fungible, Here, InteriorLocation, Junction, Junction::*, Location, NetworkId, NonFungible, Parent, ParentThen, Response, XCM_VERSION, }; use xcm_runtime_pezapis::{ dry_run::{CallDryRunEffects, Error as XcmDryRunApiError, XcmDryRunEffects}, fees::Error as XcmPaymentApiError, }; impl_opaque_keys! { pub struct SessionKeys { pub aura: Aura, } } #[pezsp_version::runtime_version] pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("staking-async-teyrchain"), impl_name: alloc::borrow::Cow::Borrowed("staking-async-teyrchain"), authoring_version: 1, spec_version: 1_000_000, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 16, system_version: 1, }; /// The version information used to identify this runtime when compiled natively. #[cfg(feature = "std")] pub fn native_version() -> NativeVersion { NativeVersion { runtime_version: VERSION, can_author_with: Default::default() } } type RelayChainBlockNumberProvider = RelaychainDataProvider; parameter_types! { pub const Version: RuntimeVersion = VERSION; pub RuntimeBlockLength: BlockLength = BlockLength::max_with_normal_ratio(5 * 1024 * 1024, NORMAL_DISPATCH_RATIO); pub RuntimeBlockWeights: BlockWeights = BlockWeights::builder() .base_block(BlockExecutionWeight::get()) .for_class(DispatchClass::all(), |weights| { weights.base_extrinsic = ExtrinsicBaseWeight::get(); }) .for_class(DispatchClass::Normal, |weights| { weights.max_total = Some(NORMAL_DISPATCH_RATIO * MAXIMUM_BLOCK_WEIGHT); }) .for_class(DispatchClass::Operational, |weights| { weights.max_total = Some(MAXIMUM_BLOCK_WEIGHT); // Operational transactions have some extra reserved space, so that they // are included even if block reached `MAXIMUM_BLOCK_WEIGHT`. weights.reserved = Some( MAXIMUM_BLOCK_WEIGHT - NORMAL_DISPATCH_RATIO * MAXIMUM_BLOCK_WEIGHT ); }) .avg_block_initialization(AVERAGE_ON_INITIALIZE_RATIO) .build_or_panic(); pub const SS58Prefix: u8 = 42; } // Configure FRAME pallets to include in runtime. #[derive_impl(pezframe_system::config_preludes::TeyrchainDefaultConfig)] impl pezframe_system::Config for Runtime { type BlockWeights = RuntimeBlockWeights; type BlockLength = RuntimeBlockLength; type AccountId = AccountId; type Nonce = Nonce; type Hash = Hash; type Block = Block; type BlockHashCount = BlockHashCount; type DbWeight = RocksDbWeight; type Version = Version; type AccountData = pezpallet_balances::AccountData; type SystemWeightInfo = weights::pezframe_system::WeightInfo; type ExtensionsWeightInfo = weights::pezframe_system_extensions::WeightInfo; type SS58Prefix = SS58Prefix; type OnSetCode = pezcumulus_pezpallet_teyrchain_system::TeyrchainSetCode; type MaxConsumers = pezframe_support::traits::ConstU32<16>; type MultiBlockMigrator = MultiBlockMigrations; type SingleBlockMigrations = Migrations; } impl pezcumulus_pezpallet_weight_reclaim::Config for Runtime { type WeightInfo = weights::pezcumulus_pezpallet_weight_reclaim::WeightInfo; } impl pezpallet_timestamp::Config for Runtime { /// A timestamp: milliseconds since the unix epoch. type Moment = u64; type OnTimestampSet = Aura; type MinimumPeriod = ConstU64<0>; type WeightInfo = weights::pezpallet_timestamp::WeightInfo; } impl pezpallet_authorship::Config for Runtime { type FindAuthor = pezpallet_session::FindAccountFromAuthorIndex; type EventHandler = (CollatorSelection,); } parameter_types! { pub const ExistentialDeposit: Balance = EXISTENTIAL_DEPOSIT; } impl pezpallet_balances::Config for Runtime { type MaxLocks = ConstU32<50>; /// The type for recording an account's balance. type Balance = Balance; /// The ubiquitous event type. type RuntimeEvent = RuntimeEvent; type DustRemoval = (); type ExistentialDeposit = ExistentialDeposit; type AccountStore = System; type WeightInfo = weights::pezpallet_balances::WeightInfo; type MaxReserves = ConstU32<50>; type ReserveIdentifier = [u8; 8]; type RuntimeHoldReason = RuntimeHoldReason; type RuntimeFreezeReason = RuntimeFreezeReason; type FreezeIdentifier = RuntimeFreezeReason; type MaxFreezes = pezframe_support::traits::VariantCountOf; type DoneSlashHandler = (); } parameter_types! { /// Relay Chain `TransactionByteFee` / 10 pub const TransactionByteFee: Balance = MILLICENTS; } impl pezpallet_transaction_payment::Config for Runtime { type RuntimeEvent = RuntimeEvent; type OnChargeTransaction = pezpallet_transaction_payment::FungibleAdapter>; type WeightToFee = WeightToFee; type LengthToFee = ConstantMultiplier; type FeeMultiplierUpdate = SlowAdjustingFeeUpdate; type OperationalFeeMultiplier = ConstU8<5>; type WeightInfo = weights::pezpallet_transaction_payment::WeightInfo; } parameter_types! { pub const AssetDeposit: Balance = UNITS / 10; // 1 / 10 ZGR deposit to create asset pub const AssetAccountDeposit: Balance = deposit(1, 16); pub const ApprovalDeposit: Balance = EXISTENTIAL_DEPOSIT; pub const AssetsStringLimit: u32 = 50; /// Key = 32 bytes, Value = 36 bytes (32+1+1+1+1) // https://github.com/pezkuwichain/pezkuwi-sdk/blob/main/bizinikiwi/pezframe/assets/src/lib.rs#L257L271 pub const MetadataDepositBase: Balance = deposit(1, 68); pub const MetadataDepositPerByte: Balance = deposit(0, 1); } pub type AssetsForceOrigin = EnsureRoot; // Called "Trust Backed" assets because these are generally registered by some account, and users of // the asset assume it has some claimed backing. The pezpallet is called `Assets` in // `construct_runtime` to avoid breaking changes on storage reads. pub type TrustBackedAssetsInstance = pezpallet_assets::Instance1; type TrustBackedAssetsCall = pezpallet_assets::Call; impl pezpallet_assets::Config for Runtime { type RuntimeEvent = RuntimeEvent; type Balance = Balance; type AssetId = AssetIdForTrustBackedAssets; type AssetIdParameter = codec::Compact; type ReserveData = (); type Currency = Balances; type CreateOrigin = AsEnsureOriginWithArg>; type ForceOrigin = AssetsForceOrigin; type AssetDeposit = AssetDeposit; type MetadataDepositBase = MetadataDepositBase; type MetadataDepositPerByte = MetadataDepositPerByte; type ApprovalDeposit = ApprovalDeposit; type StringLimit = AssetsStringLimit; type Holder = (); type Freezer = AssetsFreezer; type Extra = (); type WeightInfo = weights::pezpallet_assets_local::WeightInfo; type CallbackHandle = pezpallet_assets::AutoIncAssetId; type AssetAccountDeposit = AssetAccountDeposit; type RemoveItemsLimit = ConstU32<1000>; #[cfg(feature = "runtime-benchmarks")] type BenchmarkHelper = (); } // Allow Freezes for the `Assets` pezpallet pub type AssetsFreezerInstance = pezpallet_assets_freezer::Instance1; impl pezpallet_assets_freezer::Config for Runtime { type RuntimeFreezeReason = RuntimeFreezeReason; type RuntimeEvent = RuntimeEvent; } parameter_types! { pub const AssetConversionPalletId: PalletId = PalletId(*b"py/ascon"); pub const LiquidityWithdrawalFee: Permill = Permill::from_percent(0); } ord_parameter_types! { pub const AssetConversionOrigin: pezsp_runtime::AccountId32 = AccountIdConversion::::into_account_truncating(&AssetConversionPalletId::get()); } pub type PoolAssetsInstance = pezpallet_assets::Instance3; impl pezpallet_assets::Config for Runtime { type RuntimeEvent = RuntimeEvent; type Balance = Balance; type RemoveItemsLimit = ConstU32<1000>; type AssetId = u32; type AssetIdParameter = u32; type ReserveData = (); type Currency = Balances; type CreateOrigin = AsEnsureOriginWithArg>; type ForceOrigin = AssetsForceOrigin; type AssetDeposit = ConstU128<0>; type AssetAccountDeposit = ConstU128<0>; type MetadataDepositBase = ConstU128<0>; type MetadataDepositPerByte = ConstU128<0>; type ApprovalDeposit = ConstU128<0>; type StringLimit = ConstU32<50>; type Holder = (); type Freezer = PoolAssetsFreezer; type Extra = (); type WeightInfo = weights::pezpallet_assets_pool::WeightInfo; type CallbackHandle = (); #[cfg(feature = "runtime-benchmarks")] type BenchmarkHelper = (); } // Allow Freezes for the `PoolAssets` pezpallet pub type PoolAssetsFreezerInstance = pezpallet_assets_freezer::Instance3; impl pezpallet_assets_freezer::Config for Runtime { type RuntimeFreezeReason = RuntimeFreezeReason; type RuntimeEvent = RuntimeEvent; } /// Union fungibles implementation for `Assets` and `ForeignAssets`. pub type LocalAndForeignAssets = fungibles::UnionOf< Assets, ForeignAssets, LocalFromLeft< AssetIdForTrustBackedAssetsConvert, AssetIdForTrustBackedAssets, xcm::v5::Location, >, xcm::v5::Location, AccountId, >; /// Union fungibles implementation for `AssetsFreezer` and `ForeignAssetsFreezer`. pub type LocalAndForeignAssetsFreezer = fungibles::UnionOf< AssetsFreezer, ForeignAssetsFreezer, LocalFromLeft< AssetIdForTrustBackedAssetsConvert, AssetIdForTrustBackedAssets, xcm::v5::Location, >, xcm::v5::Location, AccountId, >; /// Union fungibles implementation for [`LocalAndForeignAssets`] and `Balances`. pub type NativeAndNonPoolAssets = fungible::UnionOf< Balances, LocalAndForeignAssets, TargetFromLeft, xcm::v5::Location, AccountId, >; /// Union fungibles implementation for [`LocalAndForeignAssetsFreezer`] and [`Balances`]. pub type NativeAndNonPoolAssetsFreezer = fungible::UnionOf< Balances, LocalAndForeignAssetsFreezer, TargetFromLeft, xcm::v5::Location, AccountId, >; /// Union fungibles implementation for [`PoolAssets`] and [`NativeAndNonPoolAssets`]. /// /// NOTE: Should be kept updated to include ALL balances and assets in the runtime. pub type NativeAndAllAssets = fungibles::UnionOf< PoolAssets, NativeAndNonPoolAssets, LocalFromLeft< AssetIdForPoolAssetsConvert, AssetIdForPoolAssets, xcm::v5::Location, >, xcm::v5::Location, AccountId, >; /// Union fungibles implementation for [`PoolAssetsFreezer`] and [`NativeAndNonPoolAssetsFreezer`]. /// /// NOTE: Should be kept updated to include ALL balances and assets in the runtime. pub type NativeAndAllAssetsFreezer = fungibles::UnionOf< PoolAssetsFreezer, NativeAndNonPoolAssetsFreezer, LocalFromLeft< AssetIdForPoolAssetsConvert, AssetIdForPoolAssets, xcm::v5::Location, >, xcm::v5::Location, AccountId, >; pub type PoolIdToAccountId = pezpallet_asset_conversion::AccountIdConverter< AssetConversionPalletId, (xcm::v5::Location, xcm::v5::Location), >; impl pezpallet_asset_conversion::Config for Runtime { type RuntimeEvent = RuntimeEvent; type Balance = Balance; type HigherPrecisionBalance = pezsp_core::U256; type AssetKind = xcm::v5::Location; type Assets = NativeAndNonPoolAssets; type PoolId = (Self::AssetKind, Self::AssetKind); type PoolLocator = pezpallet_asset_conversion::WithFirstAsset< ZagrosLocation, AccountId, Self::AssetKind, PoolIdToAccountId, >; type PoolAssetId = u32; type PoolAssets = PoolAssets; type PoolSetupFee = ConstU128<0>; // Asset class deposit fees are sufficient to prevent spam type PoolSetupFeeAsset = ZagrosLocation; type PoolSetupFeeTarget = ResolveAssetTo; type LiquidityWithdrawalFee = LiquidityWithdrawalFee; type LPFee = ConstU32<3>; type PalletId = AssetConversionPalletId; type MaxSwapPathLength = ConstU32<3>; type MintMinLiquidity = ConstU128<100>; type WeightInfo = weights::pezpallet_asset_conversion::WeightInfo; #[cfg(feature = "runtime-benchmarks")] type BenchmarkHelper = assets_common::benchmarks::AssetPairFactory< ZagrosLocation, teyrchain_info::Pezpallet, xcm_config::TrustBackedAssetsPalletIndex, xcm::v5::Location, >; } #[cfg(feature = "runtime-benchmarks")] pub struct PalletAssetRewardsBenchmarkHelper; #[cfg(feature = "runtime-benchmarks")] impl pezpallet_asset_rewards::benchmarking::BenchmarkHelper for PalletAssetRewardsBenchmarkHelper { fn staked_asset() -> Location { Location::new( 0, [PalletInstance(::index() as u8), GeneralIndex(100)], ) } fn reward_asset() -> Location { Location::new( 0, [PalletInstance(::index() as u8), GeneralIndex(101)], ) } } parameter_types! { pub const MinVestedTransfer: Balance = 100 * CENTS; pub UnvestedFundsAllowedWithdrawReasons: WithdrawReasons = WithdrawReasons::except(WithdrawReasons::TRANSFER | WithdrawReasons::RESERVE); } impl pezpallet_vesting::Config for Runtime { const MAX_VESTING_SCHEDULES: u32 = 100; type BlockNumberProvider = RelayChainBlockNumberProvider; type BlockNumberToBalance = ConvertInto; type Currency = Balances; type MinVestedTransfer = MinVestedTransfer; type RuntimeEvent = RuntimeEvent; type WeightInfo = weights::pezpallet_vesting::WeightInfo; type UnvestedFundsAllowedWithdrawReasons = UnvestedFundsAllowedWithdrawReasons; } parameter_types! { pub const AssetRewardsPalletId: PalletId = PalletId(*b"py/astrd"); pub const RewardsPoolCreationHoldReason: RuntimeHoldReason = RuntimeHoldReason::AssetRewards(pezpallet_asset_rewards::HoldReason::PoolCreation); // 1 item, 135 bytes into the storage on pool creation. pub const StakePoolCreationDeposit: Balance = deposit(1, 135); } impl pezpallet_asset_rewards::Config for Runtime { type RuntimeEvent = RuntimeEvent; type PalletId = AssetRewardsPalletId; type Balance = Balance; type Assets = NativeAndAllAssets; type AssetsFreezer = NativeAndAllAssetsFreezer; type AssetId = xcm::v5::Location; type CreatePoolOrigin = EnsureSigned; type RuntimeFreezeReason = RuntimeFreezeReason; type Consideration = HoldConsideration< AccountId, Balances, RewardsPoolCreationHoldReason, ConstantStoragePrice, >; type WeightInfo = weights::pezpallet_asset_rewards::WeightInfo; type BlockNumberProvider = pezframe_system::Pezpallet; #[cfg(feature = "runtime-benchmarks")] type BenchmarkHelper = PalletAssetRewardsBenchmarkHelper; } impl pezpallet_asset_conversion_ops::Config for Runtime { type RuntimeEvent = RuntimeEvent; type PriorAccountIdConverter = pezpallet_asset_conversion::AccountIdConverterNoSeed< ::PoolId, >; type AssetsRefund = ::Assets; type PoolAssetsRefund = ::PoolAssets; type PoolAssetsTeam = ::PoolAssets; type DepositAsset = Balances; type WeightInfo = weights::pezpallet_asset_conversion_ops::WeightInfo; } parameter_types! { // we just reuse the same deposits pub const ForeignAssetsAssetDeposit: Balance = AssetDeposit::get(); pub const ForeignAssetsAssetAccountDeposit: Balance = AssetAccountDeposit::get(); pub const ForeignAssetsApprovalDeposit: Balance = ApprovalDeposit::get(); pub const ForeignAssetsAssetsStringLimit: u32 = AssetsStringLimit::get(); pub const ForeignAssetsMetadataDepositBase: Balance = MetadataDepositBase::get(); pub const ForeignAssetsMetadataDepositPerByte: Balance = MetadataDepositPerByte::get(); } /// Assets managed by some foreign location. Note: we do not declare a `ForeignAssetsCall` type, as /// this type is used in proxy definitions. We assume that a foreign location would not want to set /// an individual, local account as a proxy for the issuance of their assets. This issuance should /// be managed by the foreign location's governance. pub type ForeignAssetsInstance = pezpallet_assets::Instance2; impl pezpallet_assets::Config for Runtime { type RuntimeEvent = RuntimeEvent; type Balance = Balance; type AssetId = xcm::v5::Location; type AssetIdParameter = xcm::v5::Location; type ReserveData = ForeignAssetReserveData; type Currency = Balances; type CreateOrigin = ForeignCreators< ( FromSiblingTeyrchain, xcm::v5::Location>, FromNetwork, xcm_config::bridging::to_pezkuwichain::PezkuwichainAssetFromAssetHubPezkuwichain, ), LocationToAccountId, AccountId, xcm::v5::Location, >; type ForceOrigin = AssetsForceOrigin; type AssetDeposit = ForeignAssetsAssetDeposit; type MetadataDepositBase = ForeignAssetsMetadataDepositBase; type MetadataDepositPerByte = ForeignAssetsMetadataDepositPerByte; type ApprovalDeposit = ForeignAssetsApprovalDeposit; type StringLimit = ForeignAssetsAssetsStringLimit; type Holder = (); type Freezer = ForeignAssetsFreezer; type Extra = (); type WeightInfo = weights::pezpallet_assets_foreign::WeightInfo; type CallbackHandle = (); type AssetAccountDeposit = ForeignAssetsAssetAccountDeposit; type RemoveItemsLimit = pezframe_support::traits::ConstU32<1000>; #[cfg(feature = "runtime-benchmarks")] type BenchmarkHelper = assets_common::benchmarks::LocationAssetsBenchmarkHelper; } // Allow Freezes for the `ForeignAssets` pezpallet pub type ForeignAssetsFreezerInstance = pezpallet_assets_freezer::Instance2; impl pezpallet_assets_freezer::Config for Runtime { type RuntimeFreezeReason = RuntimeFreezeReason; type RuntimeEvent = RuntimeEvent; } parameter_types! { // One storage item; key size is 32; value is size 4+4+16+32 bytes = 56 bytes. pub const DepositBase: Balance = deposit(1, 88); // Additional storage item size of 32 bytes. pub const DepositFactor: Balance = deposit(0, 32); pub const MaxSignatories: u32 = 100; } impl pezpallet_multisig::Config for Runtime { type RuntimeEvent = RuntimeEvent; type RuntimeCall = RuntimeCall; type Currency = Balances; type DepositBase = DepositBase; type DepositFactor = DepositFactor; type MaxSignatories = MaxSignatories; type WeightInfo = weights::pezpallet_multisig::WeightInfo; // TODO add migration. type BlockNumberProvider = RelayChainBlockNumberProvider; } impl pezpallet_utility::Config for Runtime { type RuntimeEvent = RuntimeEvent; type RuntimeCall = RuntimeCall; type PalletsOrigin = OriginCaller; type WeightInfo = weights::pezpallet_utility::WeightInfo; } parameter_types! { // One storage item; key size 32, value size 8; . pub const ProxyDepositBase: Balance = deposit(1, 40); // Additional storage item size of 33 bytes. pub const ProxyDepositFactor: Balance = deposit(0, 33); pub const MaxProxies: u16 = 32; // One storage item; key size 32, value size 16 pub const AnnouncementDepositBase: Balance = deposit(1, 48); pub const AnnouncementDepositFactor: Balance = deposit(0, 66); pub const MaxPending: u16 = 32; } /// The type used to represent the kinds of proxying allowed. #[derive( Copy, Clone, Eq, PartialEq, Ord, PartialOrd, Encode, Decode, DecodeWithMemTracking, RuntimeDebug, MaxEncodedLen, scale_info::TypeInfo, )] pub enum ProxyType { /// Fully permissioned proxy. Can execute any call on behalf of _proxied_. Any, /// Can execute any call that does not transfer funds or assets. NonTransfer, /// Proxy with the ability to reject time-delay proxy announcements. CancelProxy, /// Assets proxy. Can execute any call from `assets`, **including asset transfers**. Assets, /// Owner proxy. Can execute calls related to asset ownership. AssetOwner, /// Asset manager. Can execute calls related to asset management. AssetManager, /// Collator selection proxy. Can execute calls related to collator selection mechanism. Collator, } impl Default for ProxyType { fn default() -> Self { Self::Any } } impl InstanceFilter for ProxyType { fn filter(&self, c: &RuntimeCall) -> bool { match self { ProxyType::Any => true, ProxyType::NonTransfer => !matches!( c, RuntimeCall::Balances { .. } | RuntimeCall::Assets { .. } | RuntimeCall::NftFractionalization { .. } | RuntimeCall::Nfts { .. } | RuntimeCall::Uniques { .. } ), ProxyType::CancelProxy => matches!( c, RuntimeCall::Proxy(pezpallet_proxy::Call::reject_announcement { .. }) | RuntimeCall::Utility { .. } | RuntimeCall::Multisig { .. } ), ProxyType::Assets => { matches!( c, RuntimeCall::Assets { .. } | RuntimeCall::Utility { .. } | RuntimeCall::Multisig { .. } | RuntimeCall::NftFractionalization { .. } | RuntimeCall::Nfts { .. } | RuntimeCall::Uniques { .. } ) }, ProxyType::AssetOwner => matches!( c, RuntimeCall::Assets(TrustBackedAssetsCall::create { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::start_destroy { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::destroy_accounts { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::destroy_approvals { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::finish_destroy { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::transfer_ownership { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::set_team { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::set_metadata { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::clear_metadata { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::set_min_balance { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::create { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::destroy { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::redeposit { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::transfer_ownership { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::set_team { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::set_collection_max_supply { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::lock_collection { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::create { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::destroy { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::transfer_ownership { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::set_team { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::set_metadata { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::set_attribute { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::set_collection_metadata { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::clear_metadata { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::clear_attribute { .. }) | RuntimeCall::Uniques( pezpallet_uniques::Call::clear_collection_metadata { .. } ) | RuntimeCall::Uniques(pezpallet_uniques::Call::set_collection_max_supply { .. }) | RuntimeCall::Utility { .. } | RuntimeCall::Multisig { .. } ), ProxyType::AssetManager => matches!( c, RuntimeCall::Assets(TrustBackedAssetsCall::mint { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::burn { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::freeze { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::block { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::thaw { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::freeze_asset { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::thaw_asset { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::touch_other { .. }) | RuntimeCall::Assets(TrustBackedAssetsCall::refund_other { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::force_mint { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::update_mint_settings { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::mint_pre_signed { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::set_attributes_pre_signed { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::lock_item_transfer { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::unlock_item_transfer { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::lock_item_properties { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::set_metadata { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::clear_metadata { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::set_collection_metadata { .. }) | RuntimeCall::Nfts(pezpallet_nfts::Call::clear_collection_metadata { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::mint { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::burn { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::freeze { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::thaw { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::freeze_collection { .. }) | RuntimeCall::Uniques(pezpallet_uniques::Call::thaw_collection { .. }) | RuntimeCall::Utility { .. } | RuntimeCall::Multisig { .. } ), ProxyType::Collator => matches!( c, RuntimeCall::CollatorSelection { .. } | RuntimeCall::Utility { .. } | RuntimeCall::Multisig { .. } ), } } fn is_superset(&self, o: &Self) -> bool { match (self, o) { (x, y) if x == y => true, (ProxyType::Any, _) => true, (_, ProxyType::Any) => false, (ProxyType::Assets, ProxyType::AssetOwner) => true, (ProxyType::Assets, ProxyType::AssetManager) => true, (ProxyType::NonTransfer, ProxyType::Collator) => true, _ => false, } } } impl pezpallet_proxy::Config for Runtime { type RuntimeEvent = RuntimeEvent; type RuntimeCall = RuntimeCall; type Currency = Balances; type ProxyType = ProxyType; type ProxyDepositBase = ProxyDepositBase; type ProxyDepositFactor = ProxyDepositFactor; type MaxProxies = MaxProxies; type WeightInfo = weights::pezpallet_proxy::WeightInfo; type MaxPending = MaxPending; type CallHasher = BlakeTwo256; type AnnouncementDepositBase = AnnouncementDepositBase; type AnnouncementDepositFactor = AnnouncementDepositFactor; // TODO add migration. type BlockNumberProvider = RelayChainBlockNumberProvider; } parameter_types! { pub const ReservedXcmpWeight: Weight = MAXIMUM_BLOCK_WEIGHT.saturating_div(4); pub const ReservedDmpWeight: Weight = MAXIMUM_BLOCK_WEIGHT.saturating_div(4); } impl pezcumulus_pezpallet_teyrchain_system::Config for Runtime { type WeightInfo = weights::pezcumulus_pezpallet_teyrchain_system::WeightInfo; type RuntimeEvent = RuntimeEvent; type OnSystemEvent = (); type SelfParaId = teyrchain_info::Pezpallet; type DmpQueue = pezframe_support::traits::EnqueueWithOrigin; type ReservedDmpWeight = ReservedDmpWeight; type OutboundXcmpMessageSource = XcmpQueue; type XcmpMessageHandler = XcmpQueue; type ReservedXcmpWeight = ReservedXcmpWeight; type CheckAssociatedRelayNumber = RelayNumberMonotonicallyIncreases; type ConsensusHook = ConsensusHook; type RelayParentOffset = ConstU32<0>; } type ConsensusHook = pezcumulus_pezpallet_aura_ext::FixedVelocityConsensusHook< Runtime, RELAY_CHAIN_SLOT_DURATION_MILLIS, BLOCK_PROCESSING_VELOCITY, UNINCLUDED_SEGMENT_CAPACITY, >; impl teyrchain_info::Config for Runtime {} parameter_types! { // TODO: note that this value is different from most system chains, and is changed here only // until lazy era pruning is implemented. The actual weight of the era pruning is not huge due // to the fact that deletion is not expensive in `state_version: 1`. pub MessageQueueServiceWeight: Weight = Perbill::from_percent(70) * RuntimeBlockWeights::get().max_block; } impl pezpallet_message_queue::Config for Runtime { type RuntimeEvent = RuntimeEvent; type WeightInfo = weights::pezpallet_message_queue::WeightInfo; #[cfg(feature = "runtime-benchmarks")] type MessageProcessor = pezpallet_message_queue::mock_helpers::NoopMessageProcessor< pezcumulus_primitives_core::AggregateMessageOrigin, >; #[cfg(not(feature = "runtime-benchmarks"))] type MessageProcessor = xcm_builder::ProcessXcmMessage< AggregateMessageOrigin, xcm_executor::XcmExecutor, RuntimeCall, >; type Size = u32; // The XCMP queue pezpallet is only ever able to handle the `Sibling(ParaId)` origin: type QueueChangeHandler = NarrowOriginToSibling; type QueuePausedQuery = NarrowOriginToSibling; type HeapSize = pezsp_core::ConstU32<{ 103 * 1024 }>; type MaxStale = pezsp_core::ConstU32<8>; type ServiceWeight = MessageQueueServiceWeight; type IdleMaxServiceWeight = MessageQueueServiceWeight; } impl pezcumulus_pezpallet_aura_ext::Config for Runtime {} parameter_types! { /// The asset ID for the asset that we use to pay for message delivery fees. pub FeeAssetId: AssetId = AssetId(xcm_config::ZagrosLocation::get()); /// The base fee for the message delivery fees. pub const BaseDeliveryFee: u128 = CENTS.saturating_mul(3); } pub type PriceForSiblingTeyrchainDelivery = pezkuwi_runtime_common::xcm_sender::ExponentialPrice< FeeAssetId, BaseDeliveryFee, TransactionByteFee, XcmpQueue, >; impl pezcumulus_pezpallet_xcmp_queue::Config for Runtime { type RuntimeEvent = RuntimeEvent; type ChannelInfo = TeyrchainSystem; type VersionWrapper = PezkuwiXcm; // Enqueue XCMP messages from siblings for later processing. type XcmpQueue = TransformOrigin; type MaxInboundSuspended = ConstU32<1_000>; type MaxActiveOutboundChannels = ConstU32<128>; // Most on-chain HRMP channels are configured to use 102400 bytes of max message size, so we // need to set the page size larger than that until we reduce the channel size on-chain. type MaxPageSize = ConstU32<{ 103 * 1024 }>; type ControllerOrigin = EnsureRoot; type ControllerOriginConverter = XcmOriginToTransactDispatchOrigin; type WeightInfo = weights::pezcumulus_pezpallet_xcmp_queue::WeightInfo; type PriceForSiblingDelivery = PriceForSiblingTeyrchainDelivery; } impl pezcumulus_pezpallet_xcmp_queue::migration::v5::V5Config for Runtime { // This must be the same as the `ChannelInfo` from the `Config`: type ChannelList = TeyrchainSystem; } parameter_types! { pub const RelayOrigin: AggregateMessageOrigin = AggregateMessageOrigin::Parent; } parameter_types! { pub const Period: u32 = 6 * HOURS; pub const Offset: u32 = 0; } impl pezpallet_session::Config for Runtime { type RuntimeEvent = RuntimeEvent; type ValidatorId = ::AccountId; // we don't have stash and controller, thus we don't need the convert as well. type ValidatorIdOf = pezpallet_collator_selection::IdentityCollator; type ShouldEndSession = pezpallet_session::PeriodicSessions; type NextSessionRotation = pezpallet_session::PeriodicSessions; type SessionManager = CollatorSelection; // Essentially just Aura, but let's be pedantic. type SessionHandler = ::KeyTypeIdProviders; type Keys = SessionKeys; type DisablingStrategy = (); type WeightInfo = weights::pezpallet_session::WeightInfo; type Currency = Balances; type KeyDeposit = (); } impl pezpallet_aura::Config for Runtime { type AuthorityId = AuraId; type DisabledValidators = (); type MaxAuthorities = ConstU32<100_000>; type AllowMultipleBlocksPerSlot = ConstBool; type SlotDuration = ConstU64; } parameter_types! { pub const PotId: PalletId = PalletId(*b"PotStake"); pub const SessionLength: BlockNumber = 6 * HOURS; } pub type CollatorSelectionUpdateOrigin = EnsureRoot; impl pezpallet_collator_selection::Config for Runtime { type RuntimeEvent = RuntimeEvent; type Currency = Balances; type UpdateOrigin = CollatorSelectionUpdateOrigin; type PotId = PotId; type MaxCandidates = ConstU32<100>; type MinEligibleCollators = ConstU32<4>; type MaxInvulnerables = ConstU32<20>; // should be a multiple of session or things will get inconsistent type KickThreshold = Period; type ValidatorId = ::AccountId; type ValidatorIdOf = pezpallet_collator_selection::IdentityCollator; type ValidatorRegistration = Session; type WeightInfo = weights::pezpallet_collator_selection::WeightInfo; } parameter_types! { pub StakingPot: AccountId = CollatorSelection::account_id(); } impl pezpallet_asset_conversion_tx_payment::Config for Runtime { type RuntimeEvent = RuntimeEvent; type AssetId = xcm::v5::Location; type OnChargeAssetTransaction = SwapAssetAdapter< ZagrosLocation, NativeAndNonPoolAssets, AssetConversion, ResolveAssetTo, >; type WeightInfo = weights::pezpallet_asset_conversion_tx_payment::WeightInfo; #[cfg(feature = "runtime-benchmarks")] type BenchmarkHelper = AssetConversionTxHelper; } parameter_types! { pub const UniquesCollectionDeposit: Balance = UNITS / 10; // 1 / 10 UNIT deposit to create a collection pub const UniquesItemDeposit: Balance = UNITS / 1_000; // 1 / 1000 UNIT deposit to mint an item pub const UniquesMetadataDepositBase: Balance = deposit(1, 129); pub const UniquesAttributeDepositBase: Balance = deposit(1, 0); pub const UniquesDepositPerByte: Balance = deposit(0, 1); } impl pezpallet_uniques::Config for Runtime { type RuntimeEvent = RuntimeEvent; type CollectionId = CollectionId; type ItemId = ItemId; type Currency = Balances; type ForceOrigin = AssetsForceOrigin; type CollectionDeposit = UniquesCollectionDeposit; type ItemDeposit = UniquesItemDeposit; type MetadataDepositBase = UniquesMetadataDepositBase; type AttributeDepositBase = UniquesAttributeDepositBase; type DepositPerByte = UniquesDepositPerByte; type StringLimit = ConstU32<128>; type KeyLimit = ConstU32<32>; type ValueLimit = ConstU32<64>; type WeightInfo = weights::pezpallet_uniques::WeightInfo; #[cfg(feature = "runtime-benchmarks")] type Helper = (); type CreateOrigin = AsEnsureOriginWithArg>; type Locker = (); } parameter_types! { pub const NftFractionalizationPalletId: PalletId = PalletId(*b"fraction"); pub NewAssetSymbol: BoundedVec = (*b"FRAC").to_vec().try_into().unwrap(); pub NewAssetName: BoundedVec = (*b"Frac").to_vec().try_into().unwrap(); } impl pezpallet_nft_fractionalization::Config for Runtime { type RuntimeEvent = RuntimeEvent; type Deposit = AssetDeposit; type Currency = Balances; type NewAssetSymbol = NewAssetSymbol; type NewAssetName = NewAssetName; type StringLimit = AssetsStringLimit; type NftCollectionId = ::CollectionId; type NftId = ::ItemId; type AssetBalance = ::Balance; type AssetId = >::AssetId; type Assets = Assets; type Nfts = Nfts; type PalletId = NftFractionalizationPalletId; type WeightInfo = weights::pezpallet_nft_fractionalization::WeightInfo; type RuntimeHoldReason = RuntimeHoldReason; #[cfg(feature = "runtime-benchmarks")] type BenchmarkHelper = (); } parameter_types! { pub NftsPalletFeatures: PalletFeatures = PalletFeatures::all_enabled(); pub const NftsMaxDeadlineDuration: BlockNumber = 12 * 30 * DAYS; // re-use the Uniques deposits pub const NftsCollectionDeposit: Balance = UniquesCollectionDeposit::get(); pub const NftsItemDeposit: Balance = UniquesItemDeposit::get(); pub const NftsMetadataDepositBase: Balance = UniquesMetadataDepositBase::get(); pub const NftsAttributeDepositBase: Balance = UniquesAttributeDepositBase::get(); pub const NftsDepositPerByte: Balance = UniquesDepositPerByte::get(); } impl pezpallet_nfts::Config for Runtime { type RuntimeEvent = RuntimeEvent; type CollectionId = CollectionId; type ItemId = ItemId; type Currency = Balances; type CreateOrigin = AsEnsureOriginWithArg>; type ForceOrigin = AssetsForceOrigin; type Locker = (); type CollectionDeposit = NftsCollectionDeposit; type ItemDeposit = NftsItemDeposit; type MetadataDepositBase = NftsMetadataDepositBase; type AttributeDepositBase = NftsAttributeDepositBase; type DepositPerByte = NftsDepositPerByte; type StringLimit = ConstU32<256>; type KeyLimit = ConstU32<64>; type ValueLimit = ConstU32<256>; type ApprovalsLimit = ConstU32<20>; type ItemAttributesApprovalsLimit = ConstU32<30>; type MaxTips = ConstU32<10>; type MaxDeadlineDuration = NftsMaxDeadlineDuration; type MaxAttributesPerCall = ConstU32<10>; type Features = NftsPalletFeatures; type OffchainSignature = Signature; type OffchainPublic = ::Signer; type WeightInfo = weights::pezpallet_nfts::WeightInfo; #[cfg(feature = "runtime-benchmarks")] type Helper = (); type BlockNumberProvider = System; } /// XCM router instance to BridgeHub with bridging capabilities for `Pezkuwichain` global /// consensus with dynamic fees and back-pressure. pub type ToPezkuwichainXcmRouterInstance = pezpallet_xcm_bridge_hub_router::Instance1; impl pezpallet_xcm_bridge_hub_router::Config for Runtime { type RuntimeEvent = RuntimeEvent; type WeightInfo = weights::pezpallet_xcm_bridge_hub_router::WeightInfo; type UniversalLocation = xcm_config::UniversalLocation; type SiblingBridgeHubLocation = xcm_config::bridging::SiblingBridgeHub; type BridgedNetworkId = xcm_config::bridging::to_pezkuwichain::PezkuwichainNetwork; type Bridges = xcm_config::bridging::NetworkExportTable; type DestinationVersion = PezkuwiXcm; type BridgeHubOrigin = pezframe_support::traits::EitherOfDiverse< EnsureRoot, EnsureXcm>, >; type ToBridgeHubSender = XcmpQueue; type LocalXcmChannelManager = pezcumulus_pezpallet_xcmp_queue::bridging::InAndOutXcmpChannelStatusProvider; type ByteFee = xcm_config::bridging::XcmBridgeHubRouterByteFee; type FeeAsset = xcm_config::bridging::XcmBridgeHubRouterFeeAssetId; } parameter_types! { pub MbmServiceWeight: Weight = Perbill::from_percent(80) * RuntimeBlockWeights::get().max_block; } impl pezpallet_migrations::Config for Runtime { type RuntimeEvent = RuntimeEvent; #[cfg(not(feature = "runtime-benchmarks"))] type Migrations = (); // Benchmarks need mocked migrations to guarantee that they succeed. #[cfg(feature = "runtime-benchmarks")] type Migrations = pezpallet_migrations::mock_helpers::MockedMigrations; type CursorMaxLen = ConstU32<65_536>; type IdentifierMaxLen = ConstU32<256>; type MigrationStatusHandler = (); type FailedMigrationHandler = pezframe_support::migrations::FreezeChainOnFailedMigration; type MaxServiceWeight = MbmServiceWeight; type WeightInfo = weights::pezpallet_migrations::WeightInfo; } impl pezpallet_sudo::Config for Runtime { type RuntimeCall = RuntimeCall; type RuntimeEvent = RuntimeEvent; type WeightInfo = pezpallet_sudo::weights::BizinikiwiWeight; } impl pezpallet_staking_async_preset_store::Config for Runtime {} // Create the runtime by composing the FRAME pallets that were previously configured. construct_runtime!( pub enum Runtime { // System support stuff. System: pezframe_system = 0, TeyrchainSystem: pezcumulus_pezpallet_teyrchain_system = 1, // RandomnessCollectiveFlip = 2 removed Timestamp: pezpallet_timestamp = 3, TeyrchainInfo: teyrchain_info = 4, WeightReclaim: pezcumulus_pezpallet_weight_reclaim = 5, MultiBlockMigrations: pezpallet_migrations = 6, // Monetary stuff. Balances: pezpallet_balances = 10, TransactionPayment: pezpallet_transaction_payment = 11, // AssetTxPayment: pezpallet_asset_tx_payment = 12, AssetTxPayment: pezpallet_asset_conversion_tx_payment = 13, // Collator support. the order of these 5 are important and shall not change. Authorship: pezpallet_authorship = 20, CollatorSelection: pezpallet_collator_selection = 21, Session: pezpallet_session = 22, Aura: pezpallet_aura = 23, AuraExt: pezcumulus_pezpallet_aura_ext = 24, // XCM helpers. XcmpQueue: pezcumulus_pezpallet_xcmp_queue = 30, PezkuwiXcm: pezpallet_xcm = 31, CumulusXcm: pezcumulus_pezpallet_xcm = 32, // Bridge utilities. ToPezkuwichainXcmRouter: pezpallet_xcm_bridge_hub_router:: = 34, MessageQueue: pezpallet_message_queue = 35, // Handy utilities. Utility: pezpallet_utility = 40, Multisig: pezpallet_multisig = 41, Proxy: pezpallet_proxy = 42, // The main stage. Assets: pezpallet_assets:: = 50, Uniques: pezpallet_uniques = 51, Nfts: pezpallet_nfts = 52, ForeignAssets: pezpallet_assets:: = 53, NftFractionalization: pezpallet_nft_fractionalization = 54, PoolAssets: pezpallet_assets:: = 55, AssetConversion: pezpallet_asset_conversion = 56, AssetsFreezer: pezpallet_assets_freezer:: = 57, ForeignAssetsFreezer: pezpallet_assets_freezer:: = 58, PoolAssetsFreezer: pezpallet_assets_freezer:: = 59, AssetRewards: pezpallet_asset_rewards = 61, StateTrieMigration: pezpallet_state_trie_migration = 70, // Staking. Staking: pezpallet_staking_async = 80, NominationPools: pezpallet_nomination_pools = 81, FastUnstake: pezpallet_fast_unstake = 82, VoterList: pezpallet_bags_list:: = 83, DelegatedStaking: pezpallet_delegated_staking = 84, StakingRcClient: pezpallet_staking_async_rc_client = 89, // Election apparatus. MultiBlockElection: pezpallet_election_provider_multi_block = 85, MultiBlockElectionVerifier: pezpallet_election_provider_multi_block::verifier = 86, MultiBlockElectionUnsigned: pezpallet_election_provider_multi_block::unsigned = 87, MultiBlockElectionSigned: pezpallet_election_provider_multi_block::signed = 88, // Governance. Preimage: pezpallet_preimage = 90, Scheduler: pezpallet_scheduler = 91, ConvictionVoting: pezpallet_conviction_voting = 92, Referenda: pezpallet_referenda = 93, Origins: pezpallet_custom_origins = 94, Whitelist: pezpallet_whitelist = 95, Treasury: pezpallet_treasury = 96, AssetRate: pezpallet_asset_rate = 97, // Balances. Vesting: pezpallet_vesting = 100, // AHN specific. Sudo: pezpallet_sudo = 110, PresetStore: pezpallet_staking_async_preset_store = 111, // TODO: the pezpallet instance should be removed once all pools have migrated // to the new account IDs. AssetConversionMigration: pezpallet_asset_conversion_ops = 200, } ); /// The address format for describing accounts. pub type Address = pezsp_runtime::MultiAddress; /// Block type as expected by this runtime. pub type Block = generic::Block; /// A Block signed with a Justification pub type SignedBlock = generic::SignedBlock; /// BlockId type as expected by this runtime. pub type BlockId = generic::BlockId; /// The extension to the basic transaction logic. pub type TxExtension = pezcumulus_pezpallet_weight_reclaim::StorageWeightReclaim< Runtime, ( pezframe_system::CheckNonZeroSender, pezframe_system::CheckSpecVersion, pezframe_system::CheckTxVersion, pezframe_system::CheckGenesis, pezframe_system::CheckEra, pezframe_system::CheckNonce, pezframe_system::CheckWeight, pezpallet_asset_conversion_tx_payment::ChargeAssetTxPayment, pezframe_metadata_hash_extension::CheckMetadataHash, ), >; pub type UncheckedExtrinsic = generic::UncheckedExtrinsic; /// Migrations to apply on runtime upgrade. pub type Migrations = ( // permanent pezpallet_xcm::migration::MigrateToLatestXcmVersion, ); /// Executive: handles dispatch to the various modules. pub type Executive = pezframe_executive::Executive< Runtime, Block, pezframe_system::ChainContext, Runtime, AllPalletsWithSystem, >; #[cfg(feature = "runtime-benchmarks")] pub struct AssetConversionTxHelper; #[cfg(feature = "runtime-benchmarks")] impl pezpallet_asset_conversion_tx_payment::BenchmarkHelperTrait< AccountId, pezcumulus_primitives_core::Location, pezcumulus_primitives_core::Location, > for AssetConversionTxHelper { fn create_asset_id_parameter( seed: u32, ) -> (pezcumulus_primitives_core::Location, pezcumulus_primitives_core::Location) { // Use a different teyrchain' foreign assets pezpallet so that the asset is indeed foreign. let asset_id = pezcumulus_primitives_core::Location::new( 1, [ pezcumulus_primitives_core::Junction::Teyrchain(3000), pezcumulus_primitives_core::Junction::PalletInstance(53), pezcumulus_primitives_core::Junction::GeneralIndex(seed.into()), ], ); (asset_id.clone(), asset_id) } fn setup_balances_and_pool(asset_id: pezcumulus_primitives_core::Location, account: AccountId) { use pezframe_support::{assert_ok, traits::fungibles::Mutate}; assert_ok!(ForeignAssets::force_create( RuntimeOrigin::root(), asset_id.clone().into(), account.clone().into(), /* owner */ true, /* is_sufficient */ 1, )); let lp_provider = account.clone(); use pezframe_support::traits::Currency; let _ = Balances::deposit_creating(&lp_provider, u64::MAX.into()); assert_ok!(ForeignAssets::mint_into( asset_id.clone().into(), &lp_provider, u64::MAX.into() )); let token_native = alloc::boxed::Box::new(pezcumulus_primitives_core::Location::new( 1, pezcumulus_primitives_core::Junctions::Here, )); let token_second = alloc::boxed::Box::new(asset_id); assert_ok!(AssetConversion::create_pool( RuntimeOrigin::signed(lp_provider.clone()), token_native.clone(), token_second.clone() )); assert_ok!(AssetConversion::add_liquidity( RuntimeOrigin::signed(lp_provider.clone()), token_native, token_second, (u32::MAX / 2).into(), // 1 desired u32::MAX.into(), // 2 desired 1, // 1 min 1, // 2 min lp_provider, )); } } #[cfg(feature = "runtime-benchmarks")] mod benches { pezframe_benchmarking::define_benchmarks!( [pezframe_system, SystemBench::] [pezframe_system_extensions, SystemExtensionsBench::] [pezpallet_asset_conversion_ops, AssetConversionMigration] [pezpallet_asset_rate, AssetRate] [pezpallet_assets, Local] [pezpallet_assets, Foreign] [pezpallet_assets, Pool] [pezpallet_asset_conversion, AssetConversion] [pezpallet_asset_rewards, AssetRewards] [pezpallet_asset_conversion_tx_payment, AssetTxPayment] [pezpallet_staking_async, Staking] [pezpallet_bags_list, VoterList] [pezpallet_balances, Balances] [pezpallet_conviction_voting, ConvictionVoting] [pezpallet_election_provider_multi_block, MultiBlockElection] [pezpallet_election_provider_multi_block_verifier, MultiBlockElectionVerifier] [pezpallet_election_provider_multi_block_unsigned, MultiBlockElectionUnsigned] [pezpallet_election_provider_multi_block_signed, MultiBlockElectionSigned] [pezpallet_fast_unstake, FastUnstake] [pezpallet_message_queue, MessageQueue] [pezpallet_migrations, MultiBlockMigrations] [pezpallet_multisig, Multisig] [pezpallet_nft_fractionalization, NftFractionalization] [pezpallet_nfts, Nfts] [pezpallet_proxy, Proxy] [pezpallet_session, SessionBench::] [pezpallet_sudo, Sudo] [pezpallet_uniques, Uniques] [pezpallet_utility, Utility] [pezpallet_timestamp, Timestamp] [pezpallet_transaction_payment, TransactionPayment] [pezpallet_collator_selection, CollatorSelection] [pezcumulus_pezpallet_teyrchain_system, TeyrchainSystem] [pezcumulus_pezpallet_xcmp_queue, XcmpQueue] [pezpallet_treasury, Treasury] [pezpallet_vesting, Vesting] [pezpallet_whitelist, Whitelist] [pezpallet_xcm_bridge_hub_router, ToPezkuwichain] [pezpallet_asset_conversion_ops, AssetConversionMigration] // XCM [pezpallet_xcm, PalletXcmExtrinsicsBenchmark::] // NOTE: Make sure you point to the individual modules below. [pezpallet_xcm_benchmarks::fungible, XcmBalances] [pezpallet_xcm_benchmarks::generic, XcmGeneric] [pezcumulus_pezpallet_weight_reclaim, WeightReclaim] ); } impl_runtime_apis! { impl pezsp_consensus_aura::AuraApi for Runtime { fn slot_duration() -> pezsp_consensus_aura::SlotDuration { pezsp_consensus_aura::SlotDuration::from_millis(SLOT_DURATION) } fn authorities() -> Vec { pezpallet_aura::Authorities::::get().into_inner() } } impl pezcumulus_primitives_core::RelayParentOffsetApi for Runtime { fn relay_parent_offset() -> u32 { 0 } } impl pezcumulus_primitives_aura::AuraUnincludedSegmentApi for Runtime { fn can_build_upon( included_hash: ::Hash, slot: pezcumulus_primitives_aura::Slot, ) -> bool { ConsensusHook::can_build_upon(included_hash, slot) } } impl pezsp_api::Core for Runtime { fn version() -> RuntimeVersion { VERSION } fn execute_block(block: ::LazyBlock) { Executive::execute_block(block) } fn initialize_block(header: &::Header) -> pezsp_runtime::ExtrinsicInclusionMode { Executive::initialize_block(header) } } impl pezsp_api::Metadata for Runtime { fn metadata() -> OpaqueMetadata { OpaqueMetadata::new(Runtime::metadata().into()) } fn metadata_at_version(version: u32) -> Option { Runtime::metadata_at_version(version) } fn metadata_versions() -> alloc::vec::Vec { Runtime::metadata_versions() } } impl pezsp_block_builder::BlockBuilder for Runtime { fn apply_extrinsic(extrinsic: ::Extrinsic) -> ApplyExtrinsicResult { Executive::apply_extrinsic(extrinsic) } fn finalize_block() -> ::Header { Executive::finalize_block() } fn inherent_extrinsics(data: pezsp_inherents::InherentData) -> Vec<::Extrinsic> { data.create_extrinsics() } fn check_inherents( block: ::LazyBlock, data: pezsp_inherents::InherentData, ) -> pezsp_inherents::CheckInherentsResult { data.check_extrinsics(&block) } } impl pezsp_transaction_pool::runtime_api::TaggedTransactionQueue for Runtime { fn validate_transaction( source: TransactionSource, tx: ::Extrinsic, block_hash: ::Hash, ) -> TransactionValidity { Executive::validate_transaction(source, tx, block_hash) } } impl pezsp_offchain::OffchainWorkerApi for Runtime { fn offchain_worker(header: &::Header) { Executive::offchain_worker(header) } } impl pezsp_session::SessionKeys for Runtime { fn generate_session_keys(seed: Option>) -> Vec { SessionKeys::generate(seed) } fn decode_session_keys( encoded: Vec, ) -> Option, KeyTypeId)>> { SessionKeys::decode_into_raw_public_keys(&encoded) } } impl pezframe_system_rpc_runtime_api::AccountNonceApi for Runtime { fn account_nonce(account: AccountId) -> Nonce { System::account_nonce(account) } } impl pezpallet_nfts_runtime_api::NftsApi for Runtime { fn owner(collection: u32, item: u32) -> Option { >::owner(&collection, &item) } fn collection_owner(collection: u32) -> Option { >::collection_owner(&collection) } fn attribute( collection: u32, item: u32, key: Vec, ) -> Option> { >::attribute(&collection, &item, &key) } fn custom_attribute( account: AccountId, collection: u32, item: u32, key: Vec, ) -> Option> { >::custom_attribute( &account, &collection, &item, &key, ) } fn system_attribute( collection: u32, item: Option, key: Vec, ) -> Option> { >::system_attribute(&collection, item.as_ref(), &key) } fn collection_attribute(collection: u32, key: Vec) -> Option> { >::collection_attribute(&collection, &key) } } impl pezpallet_asset_conversion::AssetConversionApi< Block, Balance, xcm::v5::Location, > for Runtime { fn quote_price_exact_tokens_for_tokens(asset1: xcm::v5::Location, asset2: xcm::v5::Location, amount: Balance, include_fee: bool) -> Option { AssetConversion::quote_price_exact_tokens_for_tokens(asset1, asset2, amount, include_fee) } fn quote_price_tokens_for_exact_tokens(asset1: xcm::v5::Location, asset2: xcm::v5::Location, amount: Balance, include_fee: bool) -> Option { AssetConversion::quote_price_tokens_for_exact_tokens(asset1, asset2, amount, include_fee) } fn get_reserves(asset1: xcm::v5::Location, asset2: xcm::v5::Location) -> Option<(Balance, Balance)> { AssetConversion::get_reserves(asset1, asset2).ok() } } impl pezpallet_transaction_payment_rpc_runtime_api::TransactionPaymentApi for Runtime { fn query_info( uxt: ::Extrinsic, len: u32, ) -> pezpallet_transaction_payment_rpc_runtime_api::RuntimeDispatchInfo { TransactionPayment::query_info(uxt, len) } fn query_fee_details( uxt: ::Extrinsic, len: u32, ) -> pezpallet_transaction_payment::FeeDetails { TransactionPayment::query_fee_details(uxt, len) } fn query_weight_to_fee(weight: Weight) -> Balance { TransactionPayment::weight_to_fee(weight) } fn query_length_to_fee(length: u32) -> Balance { TransactionPayment::length_to_fee(length) } } impl xcm_runtime_pezapis::fees::XcmPaymentApi for Runtime { fn query_acceptable_payment_assets(xcm_version: xcm::Version) -> Result, XcmPaymentApiError> { let native_token = xcm_config::ZagrosLocation::get(); // We accept the native token to pay fees. let mut acceptable_assets = vec![AssetId(native_token.clone())]; // We also accept all assets in a pool with the native token. acceptable_assets.extend( assets_common::PoolAdapter::::get_assets_in_pool_with(native_token) .map_err(|()| XcmPaymentApiError::VersionedConversionFailed)? ); PezkuwiXcm::query_acceptable_payment_assets(xcm_version, acceptable_assets) } fn query_weight_to_asset_fee(weight: Weight, asset: VersionedAssetId) -> Result { let native_asset = xcm_config::ZagrosLocation::get(); let fee_in_native = WeightToFee::weight_to_fee(&weight); let latest_asset_id: Result = asset.clone().try_into(); match latest_asset_id { Ok(asset_id) if asset_id.0 == native_asset => { // for native asset Ok(fee_in_native) }, Ok(asset_id) => { // Try to get current price of `asset_id` in `native_asset`. if let Ok(Some(swapped_in_native)) = assets_common::PoolAdapter::::quote_price_tokens_for_exact_tokens( asset_id.0.clone(), native_asset, fee_in_native, true, // We include the fee. ) { Ok(swapped_in_native) } else { log::trace!(target: "xcm::xcm_runtime_pezapis", "query_weight_to_asset_fee - unhandled asset_id: {asset_id:?}!"); Err(XcmPaymentApiError::AssetNotFound) } }, Err(_) => { log::trace!(target: "xcm::xcm_runtime_pezapis", "query_weight_to_asset_fee - failed to convert asset: {asset:?}!"); Err(XcmPaymentApiError::VersionedConversionFailed) } } } fn query_xcm_weight(message: VersionedXcm<()>) -> Result { PezkuwiXcm::query_xcm_weight(message) } fn query_delivery_fees(destination: VersionedLocation, message: VersionedXcm<()>, asset_id: VersionedAssetId) -> Result { type AssetExchanger = ::AssetExchanger; PezkuwiXcm::query_delivery_fees::(destination, message, asset_id) } } impl xcm_runtime_pezapis::dry_run::DryRunApi for Runtime { fn dry_run_call(origin: OriginCaller, call: RuntimeCall, result_xcms_version: xcm::prelude::XcmVersion) -> Result, XcmDryRunApiError> { PezkuwiXcm::dry_run_call::(origin, call, result_xcms_version) } fn dry_run_xcm(origin_location: VersionedLocation, xcm: VersionedXcm) -> Result, XcmDryRunApiError> { PezkuwiXcm::dry_run_xcm::(origin_location, xcm) } } impl xcm_runtime_pezapis::conversions::LocationToAccountApi for Runtime { fn convert_location(location: VersionedLocation) -> Result< AccountId, xcm_runtime_pezapis::conversions::Error > { xcm_runtime_pezapis::conversions::LocationToAccountHelper::< AccountId, xcm_config::LocationToAccountId, >::convert_location(location) } } impl pezpallet_transaction_payment_rpc_runtime_api::TransactionPaymentCallApi for Runtime { fn query_call_info( call: RuntimeCall, len: u32, ) -> pezpallet_transaction_payment::RuntimeDispatchInfo { TransactionPayment::query_call_info(call, len) } fn query_call_fee_details( call: RuntimeCall, len: u32, ) -> pezpallet_transaction_payment::FeeDetails { TransactionPayment::query_call_fee_details(call, len) } fn query_weight_to_fee(weight: Weight) -> Balance { TransactionPayment::weight_to_fee(weight) } fn query_length_to_fee(length: u32) -> Balance { TransactionPayment::length_to_fee(length) } } impl assets_common::runtime_api::FungiblesApi< Block, AccountId, > for Runtime { fn query_account_balances(account: AccountId) -> Result { use assets_common::fungible_conversion::{convert, convert_balance}; Ok([ // collect pezpallet_balance { let balance = Balances::free_balance(account.clone()); if balance > 0 { vec![convert_balance::(balance)?] } else { vec![] } }, // collect pezpallet_assets (TrustBackedAssets) convert::<_, _, _, _, TrustBackedAssetsConvertedConcreteId>( Assets::account_balances(account.clone()) .iter() .filter(|(_, balance)| balance > &0) )?, // collect pezpallet_assets (ForeignAssets) convert::<_, _, _, _, ForeignAssetsConvertedConcreteId>( ForeignAssets::account_balances(account.clone()) .iter() .filter(|(_, balance)| balance > &0) )?, // collect pezpallet_assets (PoolAssets) convert::<_, _, _, _, PoolAssetsConvertedConcreteId>( PoolAssets::account_balances(account) .iter() .filter(|(_, balance)| balance > &0) )?, // collect ... e.g. other tokens ].concat().into()) } } impl pezcumulus_primitives_core::CollectCollationInfo for Runtime { fn collect_collation_info(header: &::Header) -> pezcumulus_primitives_core::CollationInfo { TeyrchainSystem::collect_collation_info(header) } } impl pezpallet_asset_rewards::AssetRewards for Runtime { fn pool_creation_cost() -> Balance { StakePoolCreationDeposit::get() } } #[cfg(feature = "try-runtime")] impl pezframe_try_runtime::TryRuntime for Runtime { fn on_runtime_upgrade(checks: pezframe_try_runtime::UpgradeCheckSelect) -> (Weight, Weight) { let weight = Executive::try_runtime_upgrade(checks).unwrap(); (weight, RuntimeBlockWeights::get().max_block) } fn execute_block( block: ::LazyBlock, state_root_check: bool, signature_check: bool, select: pezframe_try_runtime::TryStateSelect, ) -> Weight { // NOTE: intentional unwrap: we don't want to propagate the error backwards, and want to // have a backtrace here. Executive::try_execute_block(block, state_root_check, signature_check, select).unwrap() } } impl pezpallet_nomination_pools_runtime_api::NominationPoolsApi< Block, AccountId, Balance, > for Runtime { fn pending_rewards(member: AccountId) -> Balance { NominationPools::api_pending_rewards(member).unwrap_or_default() } fn points_to_balance(pool_id: PoolId, points: Balance) -> Balance { NominationPools::api_points_to_balance(pool_id, points) } fn balance_to_points(pool_id: PoolId, new_funds: Balance) -> Balance { NominationPools::api_balance_to_points(pool_id, new_funds) } fn pool_pending_slash(pool_id: PoolId) -> Balance { NominationPools::api_pool_pending_slash(pool_id) } fn member_pending_slash(member: AccountId) -> Balance { NominationPools::api_member_pending_slash(member) } fn pool_needs_delegate_migration(pool_id: PoolId) -> bool { NominationPools::api_pool_needs_delegate_migration(pool_id) } fn member_needs_delegate_migration(member: AccountId) -> bool { NominationPools::api_member_needs_delegate_migration(member) } fn member_total_balance(member: AccountId) -> Balance { NominationPools::api_member_total_balance(member) } fn pool_balance(pool_id: PoolId) -> Balance { NominationPools::api_pool_balance(pool_id) } fn pool_accounts(pool_id: PoolId) -> (AccountId, AccountId) { NominationPools::api_pool_accounts(pool_id) } } impl pezpallet_staking_async_runtime_api::StakingApi for Runtime { fn nominations_quota(balance: Balance) -> u32 { Staking::api_nominations_quota(balance) } fn eras_stakers_page_count(era: pezsp_staking::EraIndex, account: AccountId) -> pezsp_staking::Page { Staking::api_eras_stakers_page_count(era, account) } fn pending_rewards(era: pezsp_staking::EraIndex, account: AccountId) -> bool { Staking::api_pending_rewards(era, account) } } #[cfg(feature = "runtime-benchmarks")] impl pezframe_benchmarking::Benchmark for Runtime { fn benchmark_metadata(extra: bool) -> ( Vec, Vec, ) { use pezframe_benchmarking::BenchmarkList; use pezframe_support::traits::StorageInfoTrait; use pezframe_system_benchmarking::Pezpallet as SystemBench; use pezframe_system_benchmarking::extensions::Pezpallet as SystemExtensionsBench; use pezcumulus_pezpallet_session_benchmarking::Pezpallet as SessionBench; use pezpallet_xcm::benchmarking::Pezpallet as PalletXcmExtrinsicsBenchmark; use pezpallet_xcm_bridge_hub_router::benchmarking::Pezpallet as XcmBridgeHubRouterBench; // This is defined once again in dispatch_benchmark, because list_benchmarks! // and add_benchmarks! are macros exported by define_benchmarks! macros and those types // are referenced in that call. type XcmBalances = pezpallet_xcm_benchmarks::fungible::Pezpallet::; type XcmGeneric = pezpallet_xcm_benchmarks::generic::Pezpallet::; // Benchmark files generated for `Assets/ForeignAssets` instances are by default // `pezpallet_assets_assets.rs / pezpallet_assets_foreign_assets`, which is not really nice, // so with this redefinition we can change names to nicer: // `pezpallet_assets_local.rs / pezpallet_assets_foreign.rs`. type Local = pezpallet_assets::Pezpallet::; type Foreign = pezpallet_assets::Pezpallet::; type Pool = pezpallet_assets::Pezpallet::; type ToPezkuwichain = XcmBridgeHubRouterBench; let mut list = Vec::::new(); list_benchmarks!(list, extra); let storage_info = AllPalletsWithSystem::storage_info(); (list, storage_info) } fn dispatch_benchmark( config: pezframe_benchmarking::BenchmarkConfig ) -> Result, alloc::string::String> { use pezframe_benchmarking::{BenchmarkBatch, BenchmarkError}; use pezsp_storage::TrackedStorageKey; use pezframe_system_benchmarking::Pezpallet as SystemBench; use pezframe_system_benchmarking::extensions::Pezpallet as SystemExtensionsBench; use xcm::prelude::WeightLimit; // add a few custom keys to benchmarks. pezframe_benchmarking::benchmarking::add_to_whitelist( crate::staking::MaxElectingVoters::key().to_vec().into() ); pezframe_benchmarking::benchmarking::add_to_whitelist( crate::staking::Pages::key().to_vec().into() ); pezframe_benchmarking::benchmarking::add_to_whitelist( crate::staking::SignedPhase::key().to_vec().into() ); pezframe_benchmarking::benchmarking::add_to_whitelist( crate::staking::UnsignedPhase::key().to_vec().into() ); pezframe_benchmarking::benchmarking::add_to_whitelist( crate::staking::SignedValidationPhase::key().to_vec().into() ); impl pezframe_system_benchmarking::Config for Runtime { fn setup_set_code_requirements(code: &alloc::vec::Vec) -> Result<(), BenchmarkError> { TeyrchainSystem::initialize_for_set_code_benchmark(code.len() as u32); Ok(()) } fn verify_set_code() { System::assert_last_event(pezcumulus_pezpallet_teyrchain_system::Event::::ValidationFunctionStored.into()); } } use pezcumulus_pezpallet_session_benchmarking::Pezpallet as SessionBench; impl pezcumulus_pezpallet_session_benchmarking::Config for Runtime {} parameter_types! { pub ExistentialDepositAsset: Option = Some(( ZagrosLocation::get(), ExistentialDeposit::get() ).into()); pub const RandomParaId: ParaId = ParaId::new(43211234); } use pezpallet_xcm::benchmarking::Pezpallet as PalletXcmExtrinsicsBenchmark; impl pezpallet_xcm::benchmarking::Config for Runtime { type DeliveryHelper = ( pezcumulus_primitives_utility::ToParentDeliveryHelper< xcm_config::XcmConfig, ExistentialDepositAsset, xcm_config::PriceForParentDelivery, >, pezkuwi_runtime_common::xcm_sender::ToTeyrchainDeliveryHelper< xcm_config::XcmConfig, ExistentialDepositAsset, PriceForSiblingTeyrchainDelivery, RandomParaId, TeyrchainSystem, > ); fn reachable_dest() -> Option { Some(Parent.into()) } fn teleportable_asset_and_dest() -> Option<(Asset, Location)> { // Relay/native token can be teleported between AH and Relay. Some(( Asset { fun: Fungible(ExistentialDeposit::get()), id: AssetId(Parent.into()) }, Parent.into(), )) } fn reserve_transferable_asset_and_dest() -> Option<(Asset, Location)> { Some(( Asset { fun: Fungible(ExistentialDeposit::get()), id: AssetId(Parent.into()) }, // AH can reserve transfer native token to some random teyrchain. ParentThen(Teyrchain(RandomParaId::get().into()).into()).into(), )) } fn set_up_complex_asset_transfer( ) -> Option<(XcmAssets, AssetId, Location, alloc::boxed::Box)> { // Transfer to Relay some local AH asset (local-reserve-transfer) while paying // fees using teleported native token. // (We don't care that Relay doesn't accept incoming unknown AH local asset) let dest = Parent.into(); let fee_amount = EXISTENTIAL_DEPOSIT; let fee_asset: Asset = (Location::parent(), fee_amount).into(); let who = pezframe_benchmarking::whitelisted_caller(); // Give some multiple of the existential deposit let balance = fee_amount + EXISTENTIAL_DEPOSIT * 1000; let _ = >::make_free_balance_be( &who, balance, ); // verify initial balance assert_eq!(Balances::free_balance(&who), balance); // set up local asset let asset_amount = 10u128; let initial_asset_amount = asset_amount * 10; let (asset_id, _, _) = pezpallet_assets::benchmarking::create_default_minted_asset::< Runtime, pezpallet_assets::Instance1 >(true, initial_asset_amount); let asset_location = Location::new( 0, [PalletInstance(50), GeneralIndex(u32::from(asset_id).into())] ); let transfer_asset: Asset = (asset_location, asset_amount).into(); let assets: XcmAssets = vec![fee_asset.clone(), transfer_asset].into(); // verify transferred successfully let verify = alloc::boxed::Box::new(move || { // verify native balance after transfer, decreased by transferred fee amount // (plus transport fees) assert!(Balances::free_balance(&who) <= balance - fee_amount); // verify asset balance decreased by exactly transferred amount assert_eq!( Assets::balance(asset_id.into(), &who), initial_asset_amount - asset_amount, ); }); Some((assets, fee_asset.id, dest, verify)) } fn get_asset() -> Asset { Asset { id: AssetId(Location::parent()), fun: Fungible(ExistentialDeposit::get()), } } } use pezpallet_xcm_bridge_hub_router::benchmarking::{ Pezpallet as XcmBridgeHubRouterBench, Config as XcmBridgeHubRouterConfig, }; impl XcmBridgeHubRouterConfig for Runtime { fn make_congested() { pezcumulus_pezpallet_xcmp_queue::bridging::suspend_channel_for_benchmarks::( xcm_config::bridging::SiblingBridgeHubParaId::get().into() ); } fn ensure_bridged_target_destination() -> Result { TeyrchainSystem::open_outbound_hrmp_channel_for_benchmarks_or_tests( xcm_config::bridging::SiblingBridgeHubParaId::get().into() ); let bridged_asset_hub = xcm_config::bridging::to_pezkuwichain::AssetHubPezkuwichain::get(); let _ = PezkuwiXcm::force_xcm_version( RuntimeOrigin::root(), alloc::boxed::Box::new(bridged_asset_hub.clone()), XCM_VERSION, ).map_err(|e| { log::error!( "Failed to dispatch `force_xcm_version({:?}, {:?}, {:?})`, error: {:?}", RuntimeOrigin::root(), bridged_asset_hub, XCM_VERSION, e ); BenchmarkError::Stop("XcmVersion was not stored!") })?; Ok(bridged_asset_hub) } } use xcm_config::{MaxAssetsIntoHolding, ZagrosLocation}; use pezpallet_xcm_benchmarks::asset_instance_from; impl pezpallet_xcm_benchmarks::Config for Runtime { type XcmConfig = xcm_config::XcmConfig; type AccountIdConverter = xcm_config::LocationToAccountId; type DeliveryHelper = pezcumulus_primitives_utility::ToParentDeliveryHelper< xcm_config::XcmConfig, ExistentialDepositAsset, xcm_config::PriceForParentDelivery, >; fn valid_destination() -> Result { Ok(ZagrosLocation::get()) } fn worst_case_holding(depositable_count: u32) -> XcmAssets { // A mix of fungible, non-fungible, and concrete assets. let holding_non_fungibles = MaxAssetsIntoHolding::get() / 2 - depositable_count; let holding_fungibles = holding_non_fungibles - 2; // -2 for two `iter::once` bellow let fungibles_amount: u128 = 100; (0..holding_fungibles) .map(|i| { Asset { id: AssetId(GeneralIndex(i as u128).into()), fun: Fungible(fungibles_amount * (i + 1) as u128), // non-zero amount } }) .chain(core::iter::once(Asset { id: AssetId(Here.into()), fun: Fungible(u128::MAX) })) .chain(core::iter::once(Asset { id: AssetId(ZagrosLocation::get()), fun: Fungible(1_000_000 * UNITS) })) .chain((0..holding_non_fungibles).map(|i| Asset { id: AssetId(GeneralIndex(i as u128).into()), fun: NonFungible(asset_instance_from(i)), })) .collect::>() .into() } } parameter_types! { pub const TrustedTeleporter: Option<(Location, Asset)> = Some(( ZagrosLocation::get(), Asset { fun: Fungible(UNITS), id: AssetId(ZagrosLocation::get()) }, )); pub const CheckedAccount: Option<(AccountId, xcm_builder::MintLocation)> = None; // AssetHubNextZagros trusts AssetHubPezkuwichain as reserve for TYRs pub TrustedReserve: Option<(Location, Asset)> = Some( ( xcm_config::bridging::to_pezkuwichain::AssetHubPezkuwichain::get(), Asset::from((xcm_config::bridging::to_pezkuwichain::RocLocation::get(), 1000000000000 as u128)) ) ); } impl pezpallet_xcm_benchmarks::fungible::Config for Runtime { type TransactAsset = Balances; type CheckedAccount = CheckedAccount; type TrustedTeleporter = TrustedTeleporter; type TrustedReserve = TrustedReserve; fn get_asset() -> Asset { Asset { id: AssetId(ZagrosLocation::get()), fun: Fungible(UNITS), } } } impl pezpallet_xcm_benchmarks::generic::Config for Runtime { type TransactAsset = Balances; type RuntimeCall = RuntimeCall; fn worst_case_response() -> (u64, Response) { (0u64, Response::Version(Default::default())) } fn worst_case_asset_exchange() -> Result<(XcmAssets, XcmAssets), BenchmarkError> { Err(BenchmarkError::Skip) } fn universal_alias() -> Result<(Location, Junction), BenchmarkError> { xcm_config::bridging::BridgingBenchmarksHelper::prepare_universal_alias() .ok_or(BenchmarkError::Skip) } fn transact_origin_and_runtime_call() -> Result<(Location, RuntimeCall), BenchmarkError> { Ok((ZagrosLocation::get(), pezframe_system::Call::remark_with_event { remark: vec![] }.into())) } fn subscribe_origin() -> Result { Ok(ZagrosLocation::get()) } fn claimable_asset() -> Result<(Location, Location, XcmAssets), BenchmarkError> { let origin = ZagrosLocation::get(); let assets: XcmAssets = (AssetId(ZagrosLocation::get()), 1_000 * UNITS).into(); let ticket = Location { parents: 0, interior: Here }; Ok((origin, ticket, assets)) } fn worst_case_for_trader() -> Result<(Asset, WeightLimit), BenchmarkError> { Ok((Asset { id: AssetId(ZagrosLocation::get()), fun: Fungible(1_000 * UNITS), }, WeightLimit::Limited(Weight::from_parts(5000, 5000)))) } fn unlockable_asset() -> Result<(Location, Location, Asset), BenchmarkError> { Err(BenchmarkError::Skip) } fn export_message_origin_and_destination( ) -> Result<(Location, NetworkId, InteriorLocation), BenchmarkError> { Err(BenchmarkError::Skip) } fn alias_origin() -> Result<(Location, Location), BenchmarkError> { // Any location can alias to an internal location. // Here teyrchain 1001 aliases to an internal account. Ok(( Location::new(1, [Teyrchain(1001)]), Location::new(1, [Teyrchain(1001), AccountId32 { id: [111u8; 32], network: None }]), )) } } type XcmBalances = pezpallet_xcm_benchmarks::fungible::Pezpallet::; type XcmGeneric = pezpallet_xcm_benchmarks::generic::Pezpallet::; type Local = pezpallet_assets::Pezpallet::; type Foreign = pezpallet_assets::Pezpallet::; type Pool = pezpallet_assets::Pezpallet::; type ToPezkuwichain = XcmBridgeHubRouterBench; use pezframe_support::traits::WhitelistedStorageKeys; let whitelist: Vec = AllPalletsWithSystem::whitelisted_storage_keys(); let mut batches = Vec::::new(); let params = (&config, &whitelist); add_benchmarks!(params, batches); Ok(batches) } } impl pezsp_genesis_builder::GenesisBuilder for Runtime { fn build_state(config: Vec) -> pezsp_genesis_builder::Result { let res = build_state::(config); match PresetStore::preset().unwrap().as_str() { "real-s" => { log::info!(target: "runtime", "detected a real-s preset"); // used for slashing, better make it faster. crate::staking::SignedPhase::set(&0); crate::staking::SignedValidationPhase::set(&0); }, "real-m" => { log::info!(target: "runtime", "detected a real-m preset"); crate::staking::SignedPhase::set(&0); crate::staking::SignedValidationPhase::set(&0); } "fake-dev" => { log::info!(target: "runtime", "detected a fake-dev preset"); // noop, default values are for dev. }, "fake-ksm" => { log::info!(target: "runtime", "detected fake-ksm preset"); crate::staking::enable_ksm_preset(true); }, "fake-hez" => { log::info!(target: "runtime", "detected fake-hez preset"); crate::staking::enable_hez_preset(true); }, _ => { panic!("Unrecognized preset to build"); } } res } fn get_preset(id: &Option) -> Option> { get_preset::(id, &genesis_config_presets::get_preset) } fn preset_names() -> Vec { genesis_config_presets::preset_names() } } impl xcm_runtime_pezapis::trusted_query::TrustedQueryApi for Runtime { fn is_trusted_reserve(asset: VersionedAsset, location: VersionedLocation) -> xcm_runtime_pezapis::trusted_query::XcmTrustedQueryResult { PezkuwiXcm::is_trusted_reserve(asset, location) } fn is_trusted_teleporter(asset: VersionedAsset, location: VersionedLocation) -> xcm_runtime_pezapis::trusted_query::XcmTrustedQueryResult { PezkuwiXcm::is_trusted_teleporter(asset, location) } } impl pezcumulus_primitives_core::GetTeyrchainInfo for Runtime { fn teyrchain_id() -> ParaId { TeyrchainInfo::teyrchain_id() } } } pezcumulus_pezpallet_teyrchain_system::register_validate_block! { Runtime = Runtime, BlockExecutor = pezcumulus_pezpallet_aura_ext::BlockExecutor::, } parameter_types! { // The deposit configuration for the singed migration. Specially if you want to allow any signed account to do the migration (see `SignedFilter`, these deposits should be high) pub const MigrationSignedDepositPerItem: Balance = CENTS; pub const MigrationSignedDepositBase: Balance = 2_000 * CENTS; pub const MigrationMaxKeyLen: u32 = 512; } impl pezpallet_state_trie_migration::Config for Runtime { type RuntimeEvent = RuntimeEvent; type Currency = Balances; type RuntimeHoldReason = RuntimeHoldReason; type SignedDepositPerItem = MigrationSignedDepositPerItem; type SignedDepositBase = MigrationSignedDepositBase; // An origin that can control the whole pezpallet: should be Root, or a part of your council. type ControlOrigin = pezframe_system::EnsureSignedBy; // specific account for the migration, can trigger the signed migrations. type SignedFilter = pezframe_system::EnsureSignedBy; // Replace this with weight based on your runtime. type WeightInfo = pezpallet_state_trie_migration::weights::BizinikiwiWeight; type MaxKeyLen = MigrationMaxKeyLen; } pezframe_support::ord_parameter_types! { pub const MigController: AccountId = AccountId::from(hex_literal::hex!("8458ed39dc4b6f6c7255f7bc42be50c2967db126357c999d44e12ca7ac80dc52")); pub const RootMigController: AccountId = AccountId::from(hex_literal::hex!("8458ed39dc4b6f6c7255f7bc42be50c2967db126357c999d44e12ca7ac80dc52")); } #[test] fn ensure_key_ss58() { use pezframe_support::traits::SortedMembers; use pezsp_core::crypto::Ss58Codec; let acc = AccountId::from_ss58check("5F4EbSkZz18X36xhbsjvDNs6NuZ82HyYtq5UiJ1h9SBHJXZD").unwrap(); assert_eq!(acc, MigController::sorted_members()[0]); let acc = AccountId::from_ss58check("5F4EbSkZz18X36xhbsjvDNs6NuZ82HyYtq5UiJ1h9SBHJXZD").unwrap(); assert_eq!(acc, RootMigController::sorted_members()[0]); }