From 147d798d54e15396879ec047b591099786e100ec Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Sat, 24 Dec 2022 09:30:22 +0100 Subject: [PATCH 01/10] initialize --- pallets/rmrk-equip/Cargo.toml | 5 +- pallets/rmrk-equip/src/benchmarking.rs | 73 ++++++++++++++++++++++++++ pallets/rmrk-equip/src/functions.rs | 2 +- pallets/rmrk-equip/src/lib.rs | 5 +- 4 files changed, 81 insertions(+), 4 deletions(-) create mode 100644 pallets/rmrk-equip/src/benchmarking.rs diff --git a/pallets/rmrk-equip/Cargo.toml b/pallets/rmrk-equip/Cargo.toml index 8cd22692..aac5e990 100644 --- a/pallets/rmrk-equip/Cargo.toml +++ b/pallets/rmrk-equip/Cargo.toml @@ -51,5 +51,8 @@ std = [ "pallet-balances/std", ] -runtime-benchmarks = ["frame-benchmarking/runtime-benchmarks"] +runtime-benchmarks = [ + "frame-benchmarking/runtime-benchmarks", + "pallet-rmrk-core/runtime-benchmarks" +] try-runtime = ["frame-support/try-runtime"] diff --git a/pallets/rmrk-equip/src/benchmarking.rs b/pallets/rmrk-equip/src/benchmarking.rs new file mode 100644 index 00000000..639b5816 --- /dev/null +++ b/pallets/rmrk-equip/src/benchmarking.rs @@ -0,0 +1,73 @@ +#![cfg(feature = "runtime-benchmarks")] + +// Benchmarks for rmrk-equip pallet + +use super::*; + +use frame_benchmarking::{account, benchmarks, whitelisted_caller}; +use frame_support::traits::Currency; +use frame_system::RawOrigin; +use sp_runtime::traits::Bounded; + +use crate::Pallet as RmrkEquip; + +pub type BalanceOf = <::Currency as Currency< + ::AccountId, +>>::Balance; + +const SEED: u32 = 0; + +macro_rules! bvec { + ($( $x:tt )*) => { + vec![$( $x )*].try_into().unwrap() + } +} + +/// Assert that the last event equals the provided one. +fn assert_last_event(generic_event: ::Event) { + frame_system::Pallet::::assert_last_event(generic_event.into()); +} + +fn funded_account(name: &'static str, index: u32) -> T::AccountId { + let caller: T::AccountId = account(name, index, SEED); + T::Currency::make_free_balance_be(&caller, BalanceOf::::max_value()); + caller +} + +/// Creates a base +fn create_base(creator: T::AccountId) { + let _ = RmrkEquip::::create_base( + RawOrigin::Signed(creator).into(), // origin + bvec![0u8; 20], // base_type + bvec![0u8; 20], // symbol + bvec![], // parts + ); +} + +benchmarks! { + change_base_issuer { + let caller: T::AccountId = whitelisted_caller(); + let new_issuer = funded_account::("new_issuer", 0); + let new_issuer_lookup = T::Lookup::unlookup(new_issuer.clone()); + create_base::(caller.clone()); + }: _(RawOrigin::Signed(caller.clone()), 0u32, new_issuer_lookup) + verify { + assert_last_event::(Event::BaseIssuerChanged { + old_issuer: caller, + new_issuer: new_issuer, + base_id: 0u32, + }.into()); + } + + impl_benchmark_test_suite!(RmrkEquip, crate::benchmarking::tests::new_test_ext(), crate::mock::Test); +} + +#[cfg(test)] +mod tests { + use crate::mock; + use sp_io::TestExternalities; + + pub fn new_test_ext() -> TestExternalities { + mock::ExtBuilder::default().build() + } +} diff --git a/pallets/rmrk-equip/src/functions.rs b/pallets/rmrk-equip/src/functions.rs index a8cd450f..8b97de65 100644 --- a/pallets/rmrk-equip/src/functions.rs +++ b/pallets/rmrk-equip/src/functions.rs @@ -142,7 +142,7 @@ impl } /// Implementation of the base_change_issuer function for the Base trait - /// Called by the change_base_issuer extrinsic to change the issuer of a base + /// called by the change_base_issuer extrinsic to change the issuer of a base /// /// Parameters: /// - base_id: The Base ID to change the issuer of diff --git a/pallets/rmrk-equip/src/lib.rs b/pallets/rmrk-equip/src/lib.rs index cff7f063..1da7c482 100644 --- a/pallets/rmrk-equip/src/lib.rs +++ b/pallets/rmrk-equip/src/lib.rs @@ -30,6 +30,9 @@ mod mock; #[cfg(test)] mod tests; +#[cfg(any(feature = "runtime-benchmarks"))] +pub mod benchmarking; + // Re-export pallet items so that they can be accessed from the crate namespace. pub use pallet::*; @@ -250,8 +253,6 @@ pub mod pallet { ensure!(base.issuer == sender, Error::::PermissionError); let new_owner = T::Lookup::lookup(new_issuer)?; - ensure!(Bases::::contains_key(base_id), Error::::NoAvailableBaseId); - let (new_owner, base_id) = Self::base_change_issuer(base_id, new_owner)?; Self::deposit_event(Event::BaseIssuerChanged { From 95693c04b3c38d9625213a2fddbfb38b508ba20d Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Mon, 26 Dec 2022 12:02:34 +0100 Subject: [PATCH 02/10] works - but messy --- pallets/rmrk-equip/src/benchmarking.rs | 174 ++++++++++++++++++++++++- pallets/rmrk-equip/src/functions.rs | 2 +- pallets/rmrk-equip/src/lib.rs | 9 +- pallets/rmrk-equip/src/mock.rs | 2 + 4 files changed, 181 insertions(+), 6 deletions(-) diff --git a/pallets/rmrk-equip/src/benchmarking.rs b/pallets/rmrk-equip/src/benchmarking.rs index 639b5816..6eb63deb 100644 --- a/pallets/rmrk-equip/src/benchmarking.rs +++ b/pallets/rmrk-equip/src/benchmarking.rs @@ -7,7 +7,12 @@ use super::*; use frame_benchmarking::{account, benchmarks, whitelisted_caller}; use frame_support::traits::Currency; use frame_system::RawOrigin; -use sp_runtime::traits::Bounded; +use pallet_rmrk_core::Pallet as RmrkCore; +use rmrk_traits::{ + primitives::{BaseId, SlotId}, + ComposableResource, FixedPart, SlotPart, SlotResource, +}; +use sp_runtime::{traits::Bounded, Permill}; use crate::Pallet as RmrkEquip; @@ -17,6 +22,11 @@ pub type BalanceOf = <::Currency as Currency< const SEED: u32 = 0; +/// Turns a string into a BoundedVec +fn stb(s: &str) -> BoundedVec::StringLimit> { + s.as_bytes().to_vec().try_into().unwrap() +} + macro_rules! bvec { ($( $x:tt )*) => { vec![$( $x )*].try_into().unwrap() @@ -34,22 +44,104 @@ fn funded_account(name: &'static str, index: u32) -> T::AccountId { caller } +/// Creates a collection +fn create_test_collection( + caller: T::AccountId, + collection_index: u32, +) -> T::CollectionId { + let collection_id = ::Helper::collection(collection_index); + let metadata = bvec![0u8; 20]; + let max = None; + let symbol = bvec![0u8; 15]; + ::Currency::make_free_balance_be( + &caller, + BalanceOf::::max_value(), + ); + let _ = RmrkCore::::create_collection( + (RawOrigin::Signed(caller.clone())).into(), + collection_id.clone(), + metadata, + max, + symbol, + ); + + collection_id +} + +fn mint_test_nft( + owner: T::AccountId, + mint_for: Option, + collection_id: T::CollectionId, + nft_index: u32, +) -> T::ItemId { + let nft_id = ::Helper::item(nft_index); + let royalty_recipient = owner.clone(); + let royalty = Permill::from_percent(1); + let nft_metadata = bvec![0u8; 20]; + let resource = None; + let _ = RmrkCore::::mint_nft( + RawOrigin::Signed(owner.clone()).into(), + mint_for, + nft_id, + collection_id, + Some(royalty_recipient), + Some(royalty), + nft_metadata, + true, + resource, + ); + nft_id +} + +fn mint_test_nft_directly_to( + owner: T::AccountId, + mint_to: (T::CollectionId, T::ItemId), + collection_id: T::CollectionId, + nft_index: u32, +) -> T::ItemId { + let nft_id = ::Helper::item(nft_index); + let royalty_recipient = owner.clone(); + let royalty = Permill::from_percent(1); + let nft_metadata = bvec![0u8; 20]; + let resource = None; + let _ = RmrkCore::::mint_nft_directly_to_nft( + RawOrigin::Signed(owner.clone()).into(), + mint_to, + nft_id, + collection_id, + Some(royalty_recipient), + Some(royalty), + nft_metadata, + true, + resource, + ); + nft_id +} + /// Creates a base -fn create_base(creator: T::AccountId) { +fn create_base( + creator: T::AccountId, + parts: BoundedVec< + PartType, BoundedVec>, + T::PartsLimit, + >, +) { let _ = RmrkEquip::::create_base( RawOrigin::Signed(creator).into(), // origin bvec![0u8; 20], // base_type bvec![0u8; 20], // symbol - bvec![], // parts + parts, // parts ); } +fn test_slot_part() {} + benchmarks! { change_base_issuer { let caller: T::AccountId = whitelisted_caller(); let new_issuer = funded_account::("new_issuer", 0); let new_issuer_lookup = T::Lookup::unlookup(new_issuer.clone()); - create_base::(caller.clone()); + create_base::(caller.clone(), bvec![]); }: _(RawOrigin::Signed(caller.clone()), 0u32, new_issuer_lookup) verify { assert_last_event::(Event::BaseIssuerChanged { @@ -59,6 +151,80 @@ benchmarks! { }.into()); } + equip { + let caller: T::AccountId = whitelisted_caller(); + let collection_id = create_test_collection::(caller.clone(), 1); + + // create the slot parts. + let fixed_part_body = FixedPart { + id: 101, + z: 0, + src: Some(stb::("body")), + }; + + let slot_part_hand = SlotPart { + id: 201, + z: 0, + src: Some(stb::("hand")), + equippable: EquippableList::Custom(bvec![ + collection_id + ]), + }; + + let _ = RmrkEquip::::create_base( + RawOrigin::Signed(caller.clone()).into(), + bvec![42, 5], + bvec![42, 5], + bvec![ + //PartType::FixedPart(fixed_part_body), + PartType::SlotPart(slot_part_hand), + ], + ); + + let character = mint_test_nft::(caller.clone(), None, collection_id, 0); + let sword = mint_test_nft_directly_to::( + caller.clone(), + (collection_id, character), + collection_id, + 1 + ); + + let composable_resource = ComposableResource { + parts: bvec![101, 201], + base: 0, + metadata: None, + slot: None, + }; + + let _ = RmrkCore::::add_composable_resource( + RawOrigin::Signed(caller.clone()).into(), + collection_id, + character, + composable_resource, + 0, // base id + ); + + let sword_slot_resource = SlotResource { + base: 0, + metadata: None, + slot: 201 + }; + + let _ = RmrkCore::::add_slot_resource( + RawOrigin::Signed(caller.clone()).into(), + collection_id, + sword, + sword_slot_resource, + 0 // base id + ); + + let item = (collection_id, sword); + let equipper = (collection_id, character); + }: _(RawOrigin::Signed(caller.clone()), item, equipper, 0u32, 0, 201) + verify { + + } + impl_benchmark_test_suite!(RmrkEquip, crate::benchmarking::tests::new_test_ext(), crate::mock::Test); } diff --git a/pallets/rmrk-equip/src/functions.rs b/pallets/rmrk-equip/src/functions.rs index 8b97de65..34806ae8 100644 --- a/pallets/rmrk-equip/src/functions.rs +++ b/pallets/rmrk-equip/src/functions.rs @@ -275,7 +275,7 @@ impl Error::::NoResourceForThisBaseFoundOnNft ); - // The item being equipped must be have a resource that is equippable into that base.slot + // The item being equipped must have a resource that is equippable into that base.slot ensure!( pallet_rmrk_core::Pallet::::equippable_slots(( item_collection_id, diff --git a/pallets/rmrk-equip/src/lib.rs b/pallets/rmrk-equip/src/lib.rs index 1da7c482..e70472be 100644 --- a/pallets/rmrk-equip/src/lib.rs +++ b/pallets/rmrk-equip/src/lib.rs @@ -30,9 +30,12 @@ mod mock; #[cfg(test)] mod tests; -#[cfg(any(feature = "runtime-benchmarks"))] +#[cfg(feature = "runtime-benchmarks")] pub mod benchmarking; +#[cfg(feature = "runtime-benchmarks")] +use pallet_rmrk_core::BenchmarkHelper; + // Re-export pallet items so that they can be accessed from the crate namespace. pub use pallet::*; @@ -74,6 +77,9 @@ pub mod pallet { /// Maximum number of Properties allowed for any Theme #[pallet::constant] type MaxCollectionsEquippablePerPart: Get; + + #[cfg(feature = "runtime-benchmarks")] + type Helper: BenchmarkHelper; } #[pallet::storage] @@ -262,6 +268,7 @@ pub mod pallet { }); Ok(()) } + /// Equips a child NFT's resource to a parent's slot, if all are available. /// Equipping operations are maintained inside the Equippings storage. /// Modeled after [equip interaction](https://github.com/rmrk-team/rmrk-spec/blob/master/standards/rmrk2.0.0/interactions/equip.md) diff --git a/pallets/rmrk-equip/src/mock.rs b/pallets/rmrk-equip/src/mock.rs index 63109ba5..71a662a5 100644 --- a/pallets/rmrk-equip/src/mock.rs +++ b/pallets/rmrk-equip/src/mock.rs @@ -50,6 +50,8 @@ impl pallet_rmrk_equip::Config for Test { type Event = Event; type MaxPropertiesPerTheme = MaxPropertiesPerTheme; type MaxCollectionsEquippablePerPart = MaxCollectionsEquippablePerPart; + #[cfg(feature = "runtime-benchmarks")] + type Helper = RmrkBenchmark; } parameter_types! { From 43e5e409ca2d1fd27a70cca477bf0d01853e4f9e Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Mon, 26 Dec 2022 14:17:43 +0100 Subject: [PATCH 03/10] cleanup --- pallets/rmrk-equip/src/benchmarking.rs | 136 ++++++++++++------------- 1 file changed, 66 insertions(+), 70 deletions(-) diff --git a/pallets/rmrk-equip/src/benchmarking.rs b/pallets/rmrk-equip/src/benchmarking.rs index 6eb63deb..6566f7fc 100644 --- a/pallets/rmrk-equip/src/benchmarking.rs +++ b/pallets/rmrk-equip/src/benchmarking.rs @@ -8,10 +8,7 @@ use frame_benchmarking::{account, benchmarks, whitelisted_caller}; use frame_support::traits::Currency; use frame_system::RawOrigin; use pallet_rmrk_core::Pallet as RmrkCore; -use rmrk_traits::{ - primitives::{BaseId, SlotId}, - ComposableResource, FixedPart, SlotPart, SlotResource, -}; +use rmrk_traits::{ComposableResource, SlotPart, SlotResource}; use sp_runtime::{traits::Bounded, Permill}; use crate::Pallet as RmrkEquip; @@ -23,7 +20,7 @@ pub type BalanceOf = <::Currency as Currency< const SEED: u32 = 0; /// Turns a string into a BoundedVec -fn stb(s: &str) -> BoundedVec::StringLimit> { +fn stb(s: &str) -> BoundedVec { s.as_bytes().to_vec().try_into().unwrap() } @@ -127,14 +124,68 @@ fn create_base( >, ) { let _ = RmrkEquip::::create_base( - RawOrigin::Signed(creator).into(), // origin - bvec![0u8; 20], // base_type - bvec![0u8; 20], // symbol - parts, // parts + RawOrigin::Signed(creator).into(), + bvec![0u8; 20], + bvec![0u8; 20], + parts, ); } -fn test_slot_part() {} +fn hand_slot_part( + collection_id: T::CollectionId, + id: u32, +) -> SlotPart< + BoundedVec, + BoundedVec, +> { + SlotPart { + id, + z: 0, + src: Some(stb::("hand")), + equippable: EquippableList::Custom(bvec![collection_id]), + } +} + +fn add_composable_resource( + caller: T::AccountId, + collection_id: T::CollectionId, + item: T::ItemId, + base_id: BaseId, + parts: Vec, +) { + let composable_resource = ComposableResource { + parts: parts.try_into().unwrap(), + base: base_id, + metadata: None, + slot: None, + }; + + let _ = RmrkCore::::add_composable_resource( + RawOrigin::Signed(caller.clone()).into(), + collection_id, + item, + composable_resource, + 0, + ); +} + +fn add_slot_resource( + caller: T::AccountId, + collection_id: T::CollectionId, + item: T::ItemId, + base_id: BaseId, + slot: u32, +) { + let slot_resource = SlotResource { base: base_id, metadata: None, slot }; + + let _ = RmrkCore::::add_slot_resource( + RawOrigin::Signed(caller.clone()).into(), + collection_id, + item, + slot_resource, + 0, + ); +} benchmarks! { change_base_issuer { @@ -155,69 +206,14 @@ benchmarks! { let caller: T::AccountId = whitelisted_caller(); let collection_id = create_test_collection::(caller.clone(), 1); - // create the slot parts. - let fixed_part_body = FixedPart { - id: 101, - z: 0, - src: Some(stb::("body")), - }; - - let slot_part_hand = SlotPart { - id: 201, - z: 0, - src: Some(stb::("hand")), - equippable: EquippableList::Custom(bvec![ - collection_id - ]), - }; - - let _ = RmrkEquip::::create_base( - RawOrigin::Signed(caller.clone()).into(), - bvec![42, 5], - bvec![42, 5], - bvec![ - //PartType::FixedPart(fixed_part_body), - PartType::SlotPart(slot_part_hand), - ], - ); + let slot_part_hand = hand_slot_part::(collection_id, 201); + create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); let character = mint_test_nft::(caller.clone(), None, collection_id, 0); - let sword = mint_test_nft_directly_to::( - caller.clone(), - (collection_id, character), - collection_id, - 1 - ); - - let composable_resource = ComposableResource { - parts: bvec![101, 201], - base: 0, - metadata: None, - slot: None, - }; - - let _ = RmrkCore::::add_composable_resource( - RawOrigin::Signed(caller.clone()).into(), - collection_id, - character, - composable_resource, - 0, // base id - ); - - let sword_slot_resource = SlotResource { - base: 0, - metadata: None, - slot: 201 - }; - - let _ = RmrkCore::::add_slot_resource( - RawOrigin::Signed(caller.clone()).into(), - collection_id, - sword, - sword_slot_resource, - 0 // base id - ); + let sword = mint_test_nft_directly_to::(caller.clone(), (collection_id, character), collection_id, 1); + add_composable_resource::(caller.clone(), collection_id, character, 0, vec![201]); + add_slot_resource::(caller.clone(), collection_id, sword, 0, 201); let item = (collection_id, sword); let equipper = (collection_id, character); }: _(RawOrigin::Signed(caller.clone()), item, equipper, 0u32, 0, 201) From 24b3f4540fbc457f4ab0752ab3e2d6aea139af41 Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Mon, 26 Dec 2022 14:23:35 +0100 Subject: [PATCH 04/10] shorten the code --- pallets/rmrk-equip/src/benchmarking.rs | 30 ++++++++++---------------- 1 file changed, 11 insertions(+), 19 deletions(-) diff --git a/pallets/rmrk-equip/src/benchmarking.rs b/pallets/rmrk-equip/src/benchmarking.rs index 6566f7fc..25130851 100644 --- a/pallets/rmrk-equip/src/benchmarking.rs +++ b/pallets/rmrk-equip/src/benchmarking.rs @@ -90,29 +90,19 @@ fn mint_test_nft( nft_id } -fn mint_test_nft_directly_to( +// Send nft to Account or to another nft +fn send_test_nft( owner: T::AccountId, - mint_to: (T::CollectionId, T::ItemId), collection_id: T::CollectionId, - nft_index: u32, -) -> T::ItemId { - let nft_id = ::Helper::item(nft_index); - let royalty_recipient = owner.clone(); - let royalty = Permill::from_percent(1); - let nft_metadata = bvec![0u8; 20]; - let resource = None; - let _ = RmrkCore::::mint_nft_directly_to_nft( + nft_id: T::ItemId, + new_owner_enum: AccountIdOrCollectionNftTuple, +) { + let _ = RmrkCore::::send( RawOrigin::Signed(owner.clone()).into(), - mint_to, - nft_id, collection_id, - Some(royalty_recipient), - Some(royalty), - nft_metadata, - true, - resource, + nft_id, + new_owner_enum, ); - nft_id } /// Creates a base @@ -210,7 +200,9 @@ benchmarks! { create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); let character = mint_test_nft::(caller.clone(), None, collection_id, 0); - let sword = mint_test_nft_directly_to::(caller.clone(), (collection_id, character), collection_id, 1); + let sword = mint_test_nft::(caller.clone(), None, collection_id, 1); + let new_owner = AccountIdOrCollectionNftTuple::CollectionAndNftTuple(collection_id, character); + send_test_nft::(caller.clone(), collection_id, sword, new_owner); add_composable_resource::(caller.clone(), collection_id, character, 0, vec![201]); add_slot_resource::(caller.clone(), collection_id, sword, 0, 201); From 443339b62ca8cb3258c7f1df52c04876f28c6336 Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Mon, 26 Dec 2022 15:03:28 +0100 Subject: [PATCH 05/10] unequip --- pallets/rmrk-equip/src/benchmarking.rs | 33 ++++++++++++++++++++++++++ 1 file changed, 33 insertions(+) diff --git a/pallets/rmrk-equip/src/benchmarking.rs b/pallets/rmrk-equip/src/benchmarking.rs index 25130851..457a8d2c 100644 --- a/pallets/rmrk-equip/src/benchmarking.rs +++ b/pallets/rmrk-equip/src/benchmarking.rs @@ -210,7 +210,40 @@ benchmarks! { let equipper = (collection_id, character); }: _(RawOrigin::Signed(caller.clone()), item, equipper, 0u32, 0, 201) verify { + assert_last_event::(Event::SlotEquipped { + item_collection: collection_id, + item_nft: item.1, + base_id: 0, + slot_id: 201, + }.into()) + } + unequip { + let caller: T::AccountId = whitelisted_caller(); + let collection_id = create_test_collection::(caller.clone(), 1); + + let slot_part_hand = hand_slot_part::(collection_id, 201); + create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); + + let character = mint_test_nft::(caller.clone(), None, collection_id, 0); + let sword = mint_test_nft::(caller.clone(), None, collection_id, 1); + let new_owner = AccountIdOrCollectionNftTuple::CollectionAndNftTuple(collection_id, character); + send_test_nft::(caller.clone(), collection_id, sword, new_owner); + + add_composable_resource::(caller.clone(), collection_id, character, 0, vec![201]); + add_slot_resource::(caller.clone(), collection_id, sword, 0, 201); + let item = (collection_id, sword); + // the equipper is going to be the unequipper. + let equipper = (collection_id, character); + let _ = RmrkEquip::::equip(RawOrigin::Signed(caller.clone()).into(), item, equipper, 0u32, 0, 201); + }: _(RawOrigin::Signed(caller.clone()), item, equipper, 0, 201) + verify { + assert_last_event::(Event::SlotUnequipped { + item_collection: collection_id, + item_nft: item.1, + base_id: 0, + slot_id: 201, + }.into()) } impl_benchmark_test_suite!(RmrkEquip, crate::benchmarking::tests::new_test_ext(), crate::mock::Test); From 69a3770162adf7d4960251c491b7ca6524f4acd5 Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Mon, 26 Dec 2022 15:13:42 +0100 Subject: [PATCH 06/10] equippable & equippable_* --- pallets/rmrk-equip/src/benchmarking.rs | 37 ++++++++++++++++++++++++++ 1 file changed, 37 insertions(+) diff --git a/pallets/rmrk-equip/src/benchmarking.rs b/pallets/rmrk-equip/src/benchmarking.rs index 457a8d2c..6abbc7f6 100644 --- a/pallets/rmrk-equip/src/benchmarking.rs +++ b/pallets/rmrk-equip/src/benchmarking.rs @@ -246,6 +246,43 @@ benchmarks! { }.into()) } + equippable { + let caller: T::AccountId = whitelisted_caller(); + let collection_0 = ::Helper::collection(0); + + let slot_part_hand = hand_slot_part::(collection_0, 201); + create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); + + let collection_1 = ::Helper::collection(1); + }: _(RawOrigin::Signed(caller.clone()), 0, 201, EquippableList::Custom(bvec![collection_1])) + verify { + assert_last_event::(Event::EquippablesUpdated { base_id: 0, slot_id: 201 }.into()) + } + + equippable_add { + let caller: T::AccountId = whitelisted_caller(); + let collection_0 = ::Helper::collection(0); + + let slot_part_hand = hand_slot_part::(collection_0, 201); + create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); + + let collection_1 = ::Helper::collection(1); + }: _(RawOrigin::Signed(caller.clone()), 0, 201, collection_1) + verify { + assert_last_event::(Event::EquippablesUpdated { base_id: 0, slot_id: 201 }.into()) + } + + equippable_remove { + let caller: T::AccountId = whitelisted_caller(); + let collection_0 = ::Helper::collection(0); + + let slot_part_hand = hand_slot_part::(collection_0, 201); + create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); + }: _(RawOrigin::Signed(caller.clone()), 0, 201, collection_0) + verify { + assert_last_event::(Event::EquippablesUpdated { base_id: 0, slot_id: 201 }.into()) + } + impl_benchmark_test_suite!(RmrkEquip, crate::benchmarking::tests::new_test_ext(), crate::mock::Test); } From 7d81f55e8c42b036000c53bb6bb0000819956593 Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Mon, 26 Dec 2022 15:40:42 +0100 Subject: [PATCH 07/10] theme_add & create_base --- pallets/rmrk-equip/src/benchmarking.rs | 45 ++++++++++++++++++-------- 1 file changed, 32 insertions(+), 13 deletions(-) diff --git a/pallets/rmrk-equip/src/benchmarking.rs b/pallets/rmrk-equip/src/benchmarking.rs index 6abbc7f6..32508c46 100644 --- a/pallets/rmrk-equip/src/benchmarking.rs +++ b/pallets/rmrk-equip/src/benchmarking.rs @@ -97,16 +97,12 @@ fn send_test_nft( nft_id: T::ItemId, new_owner_enum: AccountIdOrCollectionNftTuple, ) { - let _ = RmrkCore::::send( - RawOrigin::Signed(owner.clone()).into(), - collection_id, - nft_id, - new_owner_enum, - ); + let _ = + RmrkCore::::send(RawOrigin::Signed(owner).into(), collection_id, nft_id, new_owner_enum); } /// Creates a base -fn create_base( +fn base_create( creator: T::AccountId, parts: BoundedVec< PartType, BoundedVec>, @@ -182,7 +178,7 @@ benchmarks! { let caller: T::AccountId = whitelisted_caller(); let new_issuer = funded_account::("new_issuer", 0); let new_issuer_lookup = T::Lookup::unlookup(new_issuer.clone()); - create_base::(caller.clone(), bvec![]); + base_create::(caller.clone(), bvec![]); }: _(RawOrigin::Signed(caller.clone()), 0u32, new_issuer_lookup) verify { assert_last_event::(Event::BaseIssuerChanged { @@ -197,7 +193,7 @@ benchmarks! { let collection_id = create_test_collection::(caller.clone(), 1); let slot_part_hand = hand_slot_part::(collection_id, 201); - create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); + base_create::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); let character = mint_test_nft::(caller.clone(), None, collection_id, 0); let sword = mint_test_nft::(caller.clone(), None, collection_id, 1); @@ -223,7 +219,7 @@ benchmarks! { let collection_id = create_test_collection::(caller.clone(), 1); let slot_part_hand = hand_slot_part::(collection_id, 201); - create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); + base_create::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); let character = mint_test_nft::(caller.clone(), None, collection_id, 0); let sword = mint_test_nft::(caller.clone(), None, collection_id, 1); @@ -251,7 +247,7 @@ benchmarks! { let collection_0 = ::Helper::collection(0); let slot_part_hand = hand_slot_part::(collection_0, 201); - create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); + base_create::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); let collection_1 = ::Helper::collection(1); }: _(RawOrigin::Signed(caller.clone()), 0, 201, EquippableList::Custom(bvec![collection_1])) @@ -264,7 +260,7 @@ benchmarks! { let collection_0 = ::Helper::collection(0); let slot_part_hand = hand_slot_part::(collection_0, 201); - create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); + base_create::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); let collection_1 = ::Helper::collection(1); }: _(RawOrigin::Signed(caller.clone()), 0, 201, collection_1) @@ -277,12 +273,35 @@ benchmarks! { let collection_0 = ::Helper::collection(0); let slot_part_hand = hand_slot_part::(collection_0, 201); - create_base::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); + base_create::(caller.clone(), bvec![PartType::SlotPart(slot_part_hand)]); }: _(RawOrigin::Signed(caller.clone()), 0, 201, collection_0) verify { assert_last_event::(Event::EquippablesUpdated { base_id: 0, slot_id: 201 }.into()) } + theme_add { + let caller: T::AccountId = whitelisted_caller(); + let default_theme = Theme { + name: stb::("default"), + properties: bvec![ + ThemeProperty { key: stb::("primary_color"), value: stb::("red") }, + ThemeProperty { key: stb::("secondary_color"), value: stb::("blue") }, + ], + inherit: false, + }; + base_create::(caller.clone(), bvec![]); + }: _(RawOrigin::Signed(caller.clone()), 0, default_theme) + verify { + + } + + create_base { + let caller: T::AccountId = whitelisted_caller(); + }: _(RawOrigin::Signed(caller.clone()), bvec![42u8; 20], bvec![25u8; 20], bvec![]) + verify { + assert_last_event::(Event::BaseCreated { issuer: caller, base_id: 0 }.into()) + } + impl_benchmark_test_suite!(RmrkEquip, crate::benchmarking::tests::new_test_ext(), crate::mock::Test); } From 03a6dd01ea269b20d51bccebe3731c73cfc98bd8 Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Mon, 26 Dec 2022 17:05:50 +0100 Subject: [PATCH 08/10] add weight --- pallets/rmrk-equip/src/benchmarking.rs | 1 + pallets/rmrk-equip/src/lib.rs | 22 +++-- pallets/rmrk-equip/src/mock.rs | 1 + pallets/rmrk-equip/src/weights.rs | 111 +++++++++++++++++++++++++ runtime/Cargo.toml | 1 + runtime/src/lib.rs | 3 + 6 files changed, 131 insertions(+), 8 deletions(-) create mode 100644 pallets/rmrk-equip/src/weights.rs diff --git a/pallets/rmrk-equip/src/benchmarking.rs b/pallets/rmrk-equip/src/benchmarking.rs index 32508c46..b947cbbd 100644 --- a/pallets/rmrk-equip/src/benchmarking.rs +++ b/pallets/rmrk-equip/src/benchmarking.rs @@ -10,6 +10,7 @@ use frame_system::RawOrigin; use pallet_rmrk_core::Pallet as RmrkCore; use rmrk_traits::{ComposableResource, SlotPart, SlotResource}; use sp_runtime::{traits::Bounded, Permill}; +use sp_std::vec; use crate::Pallet as RmrkEquip; diff --git a/pallets/rmrk-equip/src/lib.rs b/pallets/rmrk-equip/src/lib.rs index e70472be..08f06b24 100644 --- a/pallets/rmrk-equip/src/lib.rs +++ b/pallets/rmrk-equip/src/lib.rs @@ -14,6 +14,9 @@ use sp_runtime::traits::StaticLookup; pub use pallet::*; +pub mod weights; +pub use weights::WeightInfo; + use rmrk_traits::{ base::EquippableOperation, primitives::{BaseId, PartId, ResourceId, SlotId}, @@ -78,6 +81,9 @@ pub mod pallet { #[pallet::constant] type MaxCollectionsEquippablePerPart: Get; + /// Weight information for extrinsics in this pallet. + type WeightInfo: WeightInfo; + #[cfg(feature = "runtime-benchmarks")] type Helper: BenchmarkHelper; } @@ -248,7 +254,7 @@ pub mod pallet { /// - `origin`: sender of the transaction /// - `base_id`: base_id to change issuer of /// - `new_issuer`: Base's new issuer - #[pallet::weight(10_000 + T::DbWeight::get().reads_writes(1,1).ref_time())] + #[pallet::weight(::WeightInfo::change_base_issuer())] pub fn change_base_issuer( origin: OriginFor, base_id: BaseId, @@ -279,7 +285,7 @@ pub mod pallet { /// - equipper: Parent NFT which will equip the item /// - base: ID of the base which the item and equipper must each have a resource referencing /// - slot: ID of the slot which the item and equipper must each have a resource referencing - #[pallet::weight(10_000 + T::DbWeight::get().reads_writes(1,1).ref_time())] + #[pallet::weight(::WeightInfo::equip())] pub fn equip( origin: OriginFor, item: (T::CollectionId, T::ItemId), @@ -318,7 +324,7 @@ pub mod pallet { /// - unequipper: Parent NFT which will unequip the item /// - base: ID of the base which the item and equipper must each have a resource referencing /// - slot: ID of the slot which the item and equipper must each have a resource referencing - #[pallet::weight(10_000 + T::DbWeight::get().reads_writes(1,1).ref_time())] + #[pallet::weight(::WeightInfo::unequip())] pub fn unequip( origin: OriginFor, item: (T::CollectionId, T::ItemId), @@ -349,7 +355,7 @@ pub mod pallet { /// - base_id: The Base containing the Slot Part to be updated /// - part_id: The Slot Part whose Equippable List is being updated /// - equippables: The list of equippables that will override the current Equippaables list - #[pallet::weight(10_000 + T::DbWeight::get().reads_writes(1,1).ref_time())] + #[pallet::weight(::WeightInfo::equippable())] pub fn equippable( origin: OriginFor, base_id: BaseId, @@ -378,7 +384,7 @@ pub mod pallet { /// - base_id: The Base containing the Slot Part to be updated /// - part_id: The Slot Part whose Equippable List is being updated /// - equippable: The equippable that will be added to the current Equippaables list - #[pallet::weight(10_000 + T::DbWeight::get().reads_writes(1,1).ref_time())] + #[pallet::weight(::WeightInfo::equippable_add())] pub fn equippable_add( origin: OriginFor, base_id: BaseId, @@ -405,7 +411,7 @@ pub mod pallet { /// - base_id: The Base containing the Slot Part to be updated /// - part_id: The Slot Part whose Equippable List is being updated /// - equippable: The equippable that will be removed from the current Equippaables list - #[pallet::weight(10_000 + T::DbWeight::get().reads_writes(1,1).ref_time())] + #[pallet::weight(::WeightInfo::equippable_remove())] pub fn equippable_remove( origin: OriginFor, base_id: BaseId, @@ -438,7 +444,7 @@ pub mod pallet { /// - key: arbitrary BoundedString, defined by client /// - value: arbitrary BoundedString, defined by client /// - inherit: optional bool - #[pallet::weight(10_000 + T::DbWeight::get().reads_writes(1,1).ref_time())] + #[pallet::weight(::WeightInfo::theme_add())] pub fn theme_add( origin: OriginFor, base_id: BaseId, @@ -471,7 +477,7 @@ pub mod pallet { /// - symbol: arbitrary client-chosen symbol, e.g. "kanaria_superbird" /// - parts: array of Fixed and Slot parts composing the base, confined in length by /// PartsLimit - #[pallet::weight(10_000 + T::DbWeight::get().reads_writes(1,1).ref_time())] + #[pallet::weight(::WeightInfo::create_base())] pub fn create_base( origin: OriginFor, base_type: BoundedVec, diff --git a/pallets/rmrk-equip/src/mock.rs b/pallets/rmrk-equip/src/mock.rs index 71a662a5..d9eb696b 100644 --- a/pallets/rmrk-equip/src/mock.rs +++ b/pallets/rmrk-equip/src/mock.rs @@ -50,6 +50,7 @@ impl pallet_rmrk_equip::Config for Test { type Event = Event; type MaxPropertiesPerTheme = MaxPropertiesPerTheme; type MaxCollectionsEquippablePerPart = MaxCollectionsEquippablePerPart; + type WeightInfo = crate::weights::SubstrateWeight; #[cfg(feature = "runtime-benchmarks")] type Helper = RmrkBenchmark; } diff --git a/pallets/rmrk-equip/src/weights.rs b/pallets/rmrk-equip/src/weights.rs new file mode 100644 index 00000000..dc5ca694 --- /dev/null +++ b/pallets/rmrk-equip/src/weights.rs @@ -0,0 +1,111 @@ + +//! Autogenerated weights for `pallet_rmrk_equip` +//! +//! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 4.0.0-dev +//! DATE: 2022-12-26, STEPS: `50`, REPEAT: 20, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! HOSTNAME: `Sergejs-MacBook-Air.local`, CPU: `` +//! EXECUTION: Some(Wasm), WASM-EXECUTION: Compiled, CHAIN: Some("dev"), DB CACHE: 1024 + +// Executed Command: +// ./target/release/rmrk-substrate +// benchmark +// pallet +// --chain +// dev +// --execution=wasm +// --wasm-execution=compiled +// --pallet +// pallet_rmrk_equip +// --extrinsic=* +// --steps +// 50 +// --repeat +// 20 +// --output +// pallets/rmrk-equip/src/weights.rs + +#![cfg_attr(rustfmt, rustfmt_skip)] +#![allow(unused_parens)] +#![allow(unused_imports)] + +use frame_support::{traits::Get, weights::{Weight}}; +use sp_std::marker::PhantomData; + +/// Weight functions needed for `pallet_rmrk_equip`. +pub trait WeightInfo { + fn change_base_issuer() -> Weight; + fn equip() -> Weight; + fn unequip() -> Weight; + fn equippable() -> Weight; + fn equippable_add() -> Weight; + fn equippable_remove() -> Weight; + fn theme_add() -> Weight; + fn create_base() -> Weight; +} + +/// Weight functions for `pallet_rmrk_equip`. +pub struct SubstrateWeight(PhantomData); +impl WeightInfo for SubstrateWeight { + // Storage: RmrkEquip Bases (r:1 w:1) + fn change_base_issuer() -> Weight { + Weight::from_ref_time(16_000_000 as u64) + .saturating_add(T::DbWeight::get().reads(1 as u64)) + .saturating_add(T::DbWeight::get().writes(1 as u64)) + } + // Storage: RmrkCore Nfts (r:2 w:1) + // Storage: RmrkCore Lock (r:2 w:0) + // Storage: RmrkEquip Equippings (r:1 w:1) + // Storage: Uniques Asset (r:2 w:0) + // Storage: RmrkCore EquippableBases (r:1 w:0) + // Storage: RmrkCore EquippableSlots (r:1 w:0) + // Storage: RmrkEquip Parts (r:1 w:0) + fn equip() -> Weight { + Weight::from_ref_time(47_000_000 as u64) + .saturating_add(T::DbWeight::get().reads(10 as u64)) + .saturating_add(T::DbWeight::get().writes(2 as u64)) + } + // Storage: RmrkCore Lock (r:2 w:0) + // Storage: RmrkEquip Equippings (r:1 w:1) + // Storage: RmrkCore Nfts (r:1 w:1) + // Storage: Uniques Asset (r:2 w:0) + fn unequip() -> Weight { + Weight::from_ref_time(35_000_000 as u64) + .saturating_add(T::DbWeight::get().reads(6 as u64)) + .saturating_add(T::DbWeight::get().writes(2 as u64)) + } + // Storage: RmrkEquip Bases (r:1 w:0) + // Storage: RmrkEquip Parts (r:1 w:1) + fn equippable() -> Weight { + Weight::from_ref_time(16_000_000 as u64) + .saturating_add(T::DbWeight::get().reads(2 as u64)) + .saturating_add(T::DbWeight::get().writes(1 as u64)) + } + // Storage: RmrkEquip Bases (r:1 w:0) + // Storage: RmrkEquip Parts (r:1 w:1) + fn equippable_add() -> Weight { + Weight::from_ref_time(16_000_000 as u64) + .saturating_add(T::DbWeight::get().reads(2 as u64)) + .saturating_add(T::DbWeight::get().writes(1 as u64)) + } + // Storage: RmrkEquip Bases (r:1 w:0) + // Storage: RmrkEquip Parts (r:1 w:1) + fn equippable_remove() -> Weight { + Weight::from_ref_time(17_000_000 as u64) + .saturating_add(T::DbWeight::get().reads(2 as u64)) + .saturating_add(T::DbWeight::get().writes(1 as u64)) + } + // Storage: RmrkEquip Bases (r:1 w:0) + // Storage: RmrkEquip Themes (r:1 w:2) + fn theme_add() -> Weight { + Weight::from_ref_time(16_000_000 as u64) + .saturating_add(T::DbWeight::get().reads(2 as u64)) + .saturating_add(T::DbWeight::get().writes(2 as u64)) + } + // Storage: RmrkEquip NextBaseId (r:1 w:1) + // Storage: RmrkEquip Bases (r:0 w:1) + fn create_base() -> Weight { + Weight::from_ref_time(13_000_000 as u64) + .saturating_add(T::DbWeight::get().reads(1 as u64)) + .saturating_add(T::DbWeight::get().writes(2 as u64)) + } +} diff --git a/runtime/Cargo.toml b/runtime/Cargo.toml index d2846bd4..2fcadd73 100644 --- a/runtime/Cargo.toml +++ b/runtime/Cargo.toml @@ -105,6 +105,7 @@ runtime-benchmarks = [ "hex-literal", "pallet-balances/runtime-benchmarks", "pallet-rmrk-core/runtime-benchmarks", + "pallet-rmrk-equip/runtime-benchmarks", "pallet-template/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "sp-runtime/runtime-benchmarks", diff --git a/runtime/src/lib.rs b/runtime/src/lib.rs index baef26f8..3e64dabd 100644 --- a/runtime/src/lib.rs +++ b/runtime/src/lib.rs @@ -399,6 +399,7 @@ impl pallet_rmrk_equip::Config for Runtime { type Event = Event; type MaxPropertiesPerTheme = MaxPropertiesPerTheme; type MaxCollectionsEquippablePerPart = MaxCollectionsEquippablePerPart; + type Helper = RmrkBenchmark; } impl pallet_uniques::Config for Runtime { @@ -750,6 +751,7 @@ impl_runtime_apis! { list_benchmark!(list, extra, pallet_timestamp, Timestamp); list_benchmark!(list, extra, pallet_template, TemplateModule); list_benchmark!(list, extra, pallet_rmrk_core, RmrkCore); + list_benchmark!(list, extra, pallet_rmrk_equip, RmrkEquip); let storage_info = AllPalletsWithSystem::storage_info(); @@ -789,6 +791,7 @@ impl_runtime_apis! { add_benchmark!(params, batches, pallet_timestamp, Timestamp); add_benchmark!(params, batches, pallet_template, TemplateModule); add_benchmark!(params, batches, pallet_rmrk_core, RmrkCore); + add_benchmark!(params, batches, pallet_rmrk_equip, RmrkEquip); Ok(batches) } From a389f08b2fc6655ec7452b3fe6aca55a0efa0bcf Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Tue, 27 Dec 2022 10:00:09 +0100 Subject: [PATCH 09/10] fix --- runtime/src/lib.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/runtime/src/lib.rs b/runtime/src/lib.rs index 3e64dabd..f43eb758 100644 --- a/runtime/src/lib.rs +++ b/runtime/src/lib.rs @@ -399,6 +399,7 @@ impl pallet_rmrk_equip::Config for Runtime { type Event = Event; type MaxPropertiesPerTheme = MaxPropertiesPerTheme; type MaxCollectionsEquippablePerPart = MaxCollectionsEquippablePerPart; + type WeightInfo = pallet_rmrk_equip::weights::SubstrateWeight; type Helper = RmrkBenchmark; } From da927e3f3cc1baede538fcb6ea1d60744770148b Mon Sep 17 00:00:00 2001 From: Sergej Sakac Date: Tue, 10 Jan 2023 07:51:59 +0100 Subject: [PATCH 10/10] fix in benchmarking.rs --- pallets/rmrk-equip/src/benchmarking.rs | 2 +- pallets/rmrk-equip/src/lib.rs | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/pallets/rmrk-equip/src/benchmarking.rs b/pallets/rmrk-equip/src/benchmarking.rs index b947cbbd..031de843 100644 --- a/pallets/rmrk-equip/src/benchmarking.rs +++ b/pallets/rmrk-equip/src/benchmarking.rs @@ -32,7 +32,7 @@ macro_rules! bvec { } /// Assert that the last event equals the provided one. -fn assert_last_event(generic_event: ::Event) { +fn assert_last_event(generic_event: ::RuntimeEvent) { frame_system::Pallet::::assert_last_event(generic_event.into()); } diff --git a/pallets/rmrk-equip/src/lib.rs b/pallets/rmrk-equip/src/lib.rs index 931b934b..fcad042f 100644 --- a/pallets/rmrk-equip/src/lib.rs +++ b/pallets/rmrk-equip/src/lib.rs @@ -254,7 +254,7 @@ pub mod pallet { /// - `origin`: sender of the transaction /// - `base_id`: base_id to change issuer of /// - `new_issuer`: Base's new issuer - #[pallet::call_index(0)] + #[pallet::call_index(0)] #[pallet::weight(::WeightInfo::change_base_issuer())] pub fn change_base_issuer( origin: OriginFor, @@ -286,7 +286,7 @@ pub mod pallet { /// - equipper: Parent NFT which will equip the item /// - base: ID of the base which the item and equipper must each have a resource referencing /// - slot: ID of the slot which the item and equipper must each have a resource referencing - #[pallet::call_index(1)] + #[pallet::call_index(1)] #[pallet::weight(::WeightInfo::equip())] pub fn equip( origin: OriginFor, @@ -326,7 +326,7 @@ pub mod pallet { /// - unequipper: Parent NFT which will unequip the item /// - base: ID of the base which the item and equipper must each have a resource referencing /// - slot: ID of the slot which the item and equipper must each have a resource referencing - #[pallet::call_index(2)] + #[pallet::call_index(2)] #[pallet::weight(::WeightInfo::unequip())] pub fn unequip( origin: OriginFor,