From 7f09e495982a7ce7397dfa23f951a04f494329e8 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Fri, 21 Jul 2023 12:45:32 +0200 Subject: [PATCH 01/28] add docs for impl_codec_bitflags --- frame/nfts/src/macros.rs | 47 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 47 insertions(+) diff --git a/frame/nfts/src/macros.rs b/frame/nfts/src/macros.rs index db560cfbc33f0..b1c6cda00bf09 100644 --- a/frame/nfts/src/macros.rs +++ b/frame/nfts/src/macros.rs @@ -15,6 +15,53 @@ // See the License for the specific language governing permissions and // limitations under the License. +/// Implements encoding and decoding traits for a wrapper type that represents +/// bitflags. The wrapper type should contain a field of type `$size`, where +/// `$size` is an integer type (e.g., u8, u16, u32) that can represent the bitflags. +/// The `$bitflag_enum` type is the enumeration type that defines the individual bitflags. +/// +/// This macro provides implementations for the following traits: +/// - `MaxEncodedLen`: Calculates the maximum encoded length for the wrapper type. +/// - `Encode`: Encodes the wrapper type using the provided encoding function. +/// - `EncodeLike`: Trait indicating the type can be encoded as is. +/// - `Decode`: Decodes the wrapper type from the input. +/// - `TypeInfo`: Provides type information for the wrapper type. +/// +/// # Example +/// +/// ``` +/// # use codec::{Encode, Decode, MaxEncodedLen, TypeInfo}; +/// # use sp_std::prelude::BitFlags; +/// # use sp_core::Bytes; +/// +/// // Assume `MyBitflagEnum` is defined here. +/// # #[derive(Debug, Encode, Decode)] +/// # enum MyBitflagEnum { +/// # A = 0b0001, +/// # B = 0b0010, +/// # C = 0b0100, +/// # D = 0b1000, +/// # } +/// +/// // Define a newtype wrapper to hold the bitflags. +/// #[derive(Debug, Encode, Decode)] +/// struct MyBitflagsWrapper(BitFlags); +/// +/// // Implement the `impl_codec_bitflags` macro for the newtype wrapper. +/// impl_codec_bitflags!(MyBitflagsWrapper, u8, MyBitflagEnum); +/// +/// // Now you can use the `MyBitflagsWrapper` with the codec library for encoding/decoding. +/// let bitflags = MyBitflagsWrapper(BitFlags::from(MyBitflagEnum::A | MyBitflagEnum::C)); +/// let encoded_bytes = bitflags.using_encoded(|bytes| Bytes::from(bytes.to_vec())); +/// +/// // ... do something with `encoded_bytes` ... +/// +/// // Decode the bytes back to the wrapper type. +/// let decoded_bitflags = MyBitflagsWrapper::decode(&mut &encoded_bytes[..]) +/// .expect("Decoding failed"); +/// +/// assert_eq!(decoded_bitflags, bitflags); +/// ``` macro_rules! impl_codec_bitflags { ($wrapper:ty, $size:ty, $bitflag_enum:ty) => { impl MaxEncodedLen for $wrapper { From c0e549a5a638b74e413042353d0993dee3177d65 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Fri, 21 Jul 2023 17:10:50 +0200 Subject: [PATCH 02/28] add missing docs for type aliases --- frame/nfts/src/lib.rs | 1 + frame/nfts/src/types.rs | 16 +++++++++++++++- 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/frame/nfts/src/lib.rs b/frame/nfts/src/lib.rs index 8124c71682451..4f498668fa81c 100644 --- a/frame/nfts/src/lib.rs +++ b/frame/nfts/src/lib.rs @@ -63,6 +63,7 @@ pub use weights::WeightInfo; /// The log target of this pallet. pub const LOG_TARGET: &'static str = "runtime::nfts"; +/// A type alias for the account ID type used in the dispatchable functions of this pallet. type AccountIdLookupOf = <::Lookup as StaticLookup>::Source; #[frame_support::pallet] diff --git a/frame/nfts/src/types.rs b/frame/nfts/src/types.rs index e4e6165774627..f083b116fe938 100644 --- a/frame/nfts/src/types.rs +++ b/frame/nfts/src/types.rs @@ -15,7 +15,7 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! Various basic types for use in the Nfts pallet. +//! This module contains various basic types and data structures used in the NFTs pallet. use super::*; use crate::macros::*; @@ -29,36 +29,49 @@ use frame_support::{ use frame_system::pallet_prelude::BlockNumberFor; use scale_info::{build::Fields, meta_type, Path, Type, TypeInfo, TypeParameter}; +/// A type alias for handling balance deposits. pub(super) type DepositBalanceOf = <>::Currency as Currency<::AccountId>>::Balance; +/// A type alias representing the details of a collection. pub(super) type CollectionDetailsFor = CollectionDetails<::AccountId, DepositBalanceOf>; +/// A type alias for keeping track of approvals used by a single item. pub(super) type ApprovalsOf = BoundedBTreeMap< ::AccountId, Option>, >::ApprovalsLimit, >; +/// A type alias for keeping track of approvals for an item's attributes. pub(super) type ItemAttributesApprovals = BoundedBTreeSet<::AccountId, >::ItemAttributesApprovalsLimit>; +/// A type that holds the deposit for a single item. pub(super) type ItemDepositOf = ItemDeposit, ::AccountId>; +/// A type that holds the deposit amount for an item's attribute. pub(super) type AttributeDepositOf = AttributeDeposit, ::AccountId>; +/// A type that holds the deposit amount for an item's metadata. pub(super) type ItemMetadataDepositOf = ItemMetadataDeposit, ::AccountId>; +/// A type that holds the details of a single item. pub(super) type ItemDetailsFor = ItemDetails<::AccountId, ItemDepositOf, ApprovalsOf>; +/// A type alias for an accounts balance. pub(super) type BalanceOf = <>::Currency as Currency<::AccountId>>::Balance; +/// A type alias to represent the price of an item. pub(super) type ItemPrice = BalanceOf; +/// A type alias for the tips held by a single item. pub(super) type ItemTipOf = ItemTip< >::CollectionId, >::ItemId, ::AccountId, BalanceOf, >; +/// A type alias for the settings configuration of a collection. pub(super) type CollectionConfigFor = CollectionConfig, BlockNumberFor, >::CollectionId>; +/// A type alias for the pre-signed minting configuration for a specified collection. pub(super) type PreSignedMintOf = PreSignedMint< >::CollectionId, >::ItemId, @@ -66,6 +79,7 @@ pub(super) type PreSignedMintOf = PreSignedMint< BlockNumberFor, BalanceOf, >; +/// A type alias for the pre-signed minting configuration on the attribute level of an item. pub(super) type PreSignedAttributesOf = PreSignedAttributes< >::CollectionId, >::ItemId, From 3bf32c405d150fccfff56c022794c14600a2561f Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Fri, 21 Jul 2023 17:35:01 +0200 Subject: [PATCH 03/28] add docs to transfer module --- frame/nfts/src/features/transfer.rs | 83 +++++++++++++++++++++++++---- 1 file changed, 74 insertions(+), 9 deletions(-) diff --git a/frame/nfts/src/features/transfer.rs b/frame/nfts/src/features/transfer.rs index 69209e1bb6c4b..4f091e911a7c9 100644 --- a/frame/nfts/src/features/transfer.rs +++ b/frame/nfts/src/features/transfer.rs @@ -15,10 +15,24 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper functions to perform the transfer functionalities +//! of the NFTs pallet. + use crate::*; use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { + /// Transfer an NFT to the specified destination account. + /// + /// - `collection`: The ID of the collection to which the NFT belongs. + /// - `item`: The ID of the NFT to transfer. + /// - `dest`: The destination account to which the NFT will be transferred. + /// - `with_details`: A closure that provides access to the collection and item details, + /// allowing customization of the transfer process. + /// + /// This function performs the actual transfer of an NFT to the destination account. + /// It checks various conditions like item lock status and transferability settings + /// for the collection and item before transferring the NFT. pub fn do_transfer( collection: T::CollectionId, item: T::ItemId, @@ -28,45 +42,58 @@ impl, I: 'static> Pallet { &mut ItemDetailsFor, ) -> DispatchResult, ) -> DispatchResult { + + // Retrieve collection details. let collection_details = Collection::::get(&collection).ok_or(Error::::UnknownCollection)?; - + + // Ensure the item is not locked. ensure!(!T::Locker::is_locked(collection, item), Error::::ItemLocked); + + // Ensure the item is not transfer disabled on the system level attribute. ensure!( !Self::has_system_attribute(&collection, &item, PalletAttributes::TransferDisabled)?, Error::::ItemLocked ); + // Retrieve collection config and check if items are transferable. let collection_config = Self::get_collection_config(&collection)?; ensure!( collection_config.is_setting_enabled(CollectionSetting::TransferableItems), Error::::ItemsNonTransferable ); - + + // Retrieve item config and check if the item is transferable. let item_config = Self::get_item_config(&collection, &item)?; ensure!( item_config.is_setting_enabled(ItemSetting::Transferable), Error::::ItemLocked ); - + + // Retrieve the item details. let mut details = Item::::get(&collection, &item).ok_or(Error::::UnknownItem)?; + + // Perform the transfer with custom details using the provided closure. with_details(&collection_details, &mut details)?; - + + // Update account ownership information. Account::::remove((&details.owner, &collection, &item)); Account::::insert((&dest, &collection, &item), ()); let origin = details.owner; details.owner = dest; - // The approved accounts have to be reset to None, because otherwise pre-approve attack + // The approved accounts have to be reset to `None`, because otherwise pre-approve attack // would be possible, where the owner can approve their second account before making the // transaction and then claiming the item back. details.approvals.clear(); - + + // Update item details. Item::::insert(&collection, &item, &details); ItemPriceOf::::remove(&collection, &item); PendingSwapOf::::remove(&collection, &item); + // Emit `Transferred` event. Self::deposit_event(Event::Transferred { collection, item, @@ -76,16 +103,29 @@ impl, I: 'static> Pallet { Ok(()) } + /// Transfer ownership of a collection to another account. + /// + /// - `origin`: The account requesting the transfer. + /// - `collection`: The ID of the collection to transfer ownership. + /// - `owner`: The new account that will become the owner of the collection. + /// + /// This function transfers the ownership of a collection to the specified account. + /// It performs checks to ensure that the `origin` is the current owner and that the + /// new owner is an acceptable account based on the collection's acceptance settings. pub(crate) fn do_transfer_ownership( origin: T::AccountId, collection: T::CollectionId, owner: T::AccountId, ) -> DispatchResult { + + // Check if the new owner is acceptable based on the collection's acceptance settings. let acceptable_collection = OwnershipAcceptance::::get(&owner); ensure!(acceptable_collection.as_ref() == Some(&collection), Error::::Unaccepted); + // Try to retrieve and mutate the collection details. Collection::::try_mutate(collection, |maybe_details| { let details = maybe_details.as_mut().ok_or(Error::::UnknownCollection)?; + // Check if the `origin` is the current owner of the collection. ensure!(origin == details.owner, Error::::NoPermission); if details.owner == owner { return Ok(()) @@ -98,17 +138,28 @@ impl, I: 'static> Pallet { details.owner_deposit, Reserved, )?; + + // Update account ownership information. CollectionAccount::::remove(&details.owner, &collection); CollectionAccount::::insert(&owner, &collection, ()); details.owner = owner.clone(); OwnershipAcceptance::::remove(&owner); - + + // Emit `OwnerChanged` event. Self::deposit_event(Event::OwnerChanged { collection, new_owner: owner }); Ok(()) }) } - + /// Set or unset the ownership acceptance for an account regarding a specific collection. + /// + /// - `who`: The account for which to set or unset the ownership acceptance. + /// - `maybe_collection`: An optional collection ID to set the ownership acceptance. + /// + /// If `maybe_collection` is `Some(collection)`, then the account `who` will accept + /// ownership transfers for the specified collection. If `maybe_collection` is `None`, + /// then the account `who` will unset the ownership acceptance, effectively refusing + /// ownership transfers for any collection. pub(crate) fn do_set_accept_ownership( who: T::AccountId, maybe_collection: Option, @@ -128,14 +179,26 @@ impl, I: 'static> Pallet { } else { OwnershipAcceptance::::remove(&who); } + + // Emit `OwnershipAcceptanceChanged` event. Self::deposit_event(Event::OwnershipAcceptanceChanged { who, maybe_collection }); Ok(()) } + /// Forcefully change the owner of a collection. + /// + /// - `collection`: The ID of the collection to change ownership. + /// - `owner`: The new account that will become the owner of the collection. + /// + /// This function allows for changing the ownership of a collection without any checks. + /// It moves the deposit to the new owner, updates the collection's owner, and emits + /// an `OwnerChanged` event. pub(crate) fn do_force_collection_owner( collection: T::CollectionId, owner: T::AccountId, ) -> DispatchResult { + + // Try to retrieve and mutate the collection details. Collection::::try_mutate(collection, |maybe_details| { let details = maybe_details.as_mut().ok_or(Error::::UnknownCollection)?; if details.owner == owner { @@ -150,10 +213,12 @@ impl, I: 'static> Pallet { Reserved, )?; + // Update collection accounts and set the new owner. CollectionAccount::::remove(&details.owner, &collection); CollectionAccount::::insert(&owner, &collection, ()); details.owner = owner.clone(); - + + // Emit `OwnerChanged` event. Self::deposit_event(Event::OwnerChanged { collection, new_owner: owner }); Ok(()) }) From 98dcbf4b610d9e46166ab4d64b2e9754a5d5910e Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Fri, 21 Jul 2023 17:47:39 +0200 Subject: [PATCH 04/28] add docs for settings module --- frame/nfts/src/features/settings.rs | 67 +++++++++++++++++++++++++++++ 1 file changed, 67 insertions(+) diff --git a/frame/nfts/src/features/settings.rs b/frame/nfts/src/features/settings.rs index 3d96a411ae708..1b87469236c3b 100644 --- a/frame/nfts/src/features/settings.rs +++ b/frame/nfts/src/features/settings.rs @@ -15,10 +15,19 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module provides helper functions to configure collection settings for the NFTs pallet. + use crate::*; use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { + /// Forcefully change the configuration of a collection. + /// + /// - `collection`: The ID of the collection for which to update the configuration. + /// - `config`: The new collection configuration to set. + /// + /// This function allows for changing the configuration of a collection without any checks. + /// It updates the collection configuration and emits a `CollectionConfigChanged` event. pub(crate) fn do_force_collection_config( collection: T::CollectionId, config: CollectionConfigFor, @@ -29,6 +38,22 @@ impl, I: 'static> Pallet { Ok(()) } + /// Set the maximum supply for a collection. + /// + /// - `maybe_check_owner`: An optional account ID used to check permissions. + /// - `collection`: The ID of the collection for which to set the maximum supply. + /// - `max_supply`: The new maximum supply to set for the collection. + /// + /// This function checks if the setting `UnlockedMaxSupply` is enabled in the collection + /// configuration. If it is not enabled, it returns an `Error::MaxSupplyLocked`. If + /// `maybe_check_owner` is `Some(owner)`, it checks if the caller of the function is the + /// owner of the collection. If the caller is not the owner and the `maybe_check_owner` + /// parameter is provided, it returns an `Error::NoPermission`. + /// + /// It also checks if the new maximum supply is greater than the current number of items in + /// the collection, and if not, it returns an `Error::MaxSupplyTooSmall`. If all checks pass, + /// it updates the collection configuration with the new maximum supply and emits a + /// `CollectionMaxSupplySet` event. pub(crate) fn do_set_collection_max_supply( maybe_check_owner: Option, collection: T::CollectionId, @@ -56,6 +81,18 @@ impl, I: 'static> Pallet { }) } + /// Update the mint settings for a collection. + /// + /// - `maybe_check_origin`: An optional account ID used to check issuer permissions. + /// - `collection`: The ID of the collection for which to update the mint settings. + /// - `mint_settings`: The new mint settings to set for the collection. + /// + /// This function updates the mint settings for a collection. If `maybe_check_origin` is + /// `Some(origin)`, it checks if the caller of the function has the `CollectionRole::Issuer` + /// for the given collection. If the caller doesn't have the required permission and + /// `maybe_check_origin` is provided, it returns an `Error::NoPermission`. If all checks + /// pass, it updates the collection configuration with the new mint settings and emits a + /// `CollectionMintSettingsUpdated` event. pub(crate) fn do_update_mint_settings( maybe_check_origin: Option, collection: T::CollectionId, @@ -80,6 +117,13 @@ impl, I: 'static> Pallet { }) } + /// Get the configuration for a specific collection. + /// + /// - `collection_id`: The ID of the collection for which to retrieve the configuration. + /// + /// This function attempts to fetch the configuration (`CollectionConfigFor`) associated + /// with the given `collection_id`. If the configuration exists, it returns `Ok(config)`, + /// otherwise, it returns a `DispatchError` with `Error::NoConfig`. pub(crate) fn get_collection_config( collection_id: &T::CollectionId, ) -> Result, DispatchError> { @@ -88,6 +132,14 @@ impl, I: 'static> Pallet { Ok(config) } + /// Get the configuration for a specific item within a collection. + /// + /// - `collection_id`: The ID of the collection to which the item belongs. + /// - `item_id`: The ID of the item for which to retrieve the configuration. + /// + /// This function attempts to fetch the configuration (`ItemConfig`) associated with the given + /// `collection_id` and `item_id`. If the configuration exists, it returns `Ok(config)`, + /// otherwise, it returns a `DispatchError` with `Error::UnknownItem`. pub(crate) fn get_item_config( collection_id: &T::CollectionId, item_id: &T::ItemId, @@ -97,6 +149,14 @@ impl, I: 'static> Pallet { Ok(config) } + /// Get the default item settings for a specific collection. + /// + /// - `collection_id`: The ID of the collection for which to retrieve the default item settings. + /// + /// This function fetches the `default_item_settings` from the collection configuration + /// associated with the given `collection_id`. If the collection configuration exists, it + /// returns `Ok(default_item_settings)`, otherwise, it returns a `DispatchError` with + /// `Error::NoConfig`. pub(crate) fn get_default_item_settings( collection_id: &T::CollectionId, ) -> Result { @@ -104,6 +164,13 @@ impl, I: 'static> Pallet { Ok(collection_config.mint_settings.default_item_settings) } + /// Check if a specified pallet feature is enabled. + /// + /// - `feature`: The feature to check. + /// + /// This function checks if the given `feature` is enabled in the runtime using the + /// pallet's `T::Features::get()` function. It returns `true` if the feature is enabled, + /// otherwise it returns `false`. pub(crate) fn is_pallet_feature_enabled(feature: PalletFeature) -> bool { let features = T::Features::get(); return features.is_enabled(feature) From 7172c2aeb7f001a45ff7bf1cdf2b211d11d5bbbf Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Fri, 21 Jul 2023 17:56:30 +0200 Subject: [PATCH 05/28] add docs to roles module --- frame/nfts/src/features/roles.rs | 25 +++++++++++++++++++------ 1 file changed, 19 insertions(+), 6 deletions(-) diff --git a/frame/nfts/src/features/roles.rs b/frame/nfts/src/features/roles.rs index 3bac002069cf3..b2b8d10aec959 100644 --- a/frame/nfts/src/features/roles.rs +++ b/frame/nfts/src/features/roles.rs @@ -15,11 +15,24 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper functions to configure account roles for existing collections. + use crate::*; use frame_support::pallet_prelude::*; use sp_std::collections::btree_map::BTreeMap; impl, I: 'static> Pallet { + /// Set the team roles for a specific collection. + /// + /// - `maybe_check_owner`: An optional account ID used to check ownership permission. If `None`, it is considered as the root. + /// - `collection`: The ID of the collection for which to set the team roles. + /// - `issuer`: An optional account ID representing the issuer role. + /// - `admin`: An optional account ID representing the admin role. + /// - `freezer`: An optional account ID representing the freezer role. + /// + /// This function allows the owner or the root (when `maybe_check_owner` is `None`) to set the team roles + /// for a specific collection. The root can change the role from `None` to `Some(account)`, but other roles + /// can only be updated by the root or an account with an existing role in the collection. pub(crate) fn do_set_team( maybe_check_owner: Option, collection: T::CollectionId, @@ -59,10 +72,10 @@ impl, I: 'static> Pallet { let account_to_role = Self::group_roles_by_account(roles); - // delete the previous records + // Delete the previous records. Self::clear_roles(&collection)?; - // insert new records + // Insert new records. for (account, roles) in account_to_role { CollectionRoleOf::::insert(&collection, &account, roles); } @@ -76,8 +89,8 @@ impl, I: 'static> Pallet { /// /// - `collection_id`: A collection to clear the roles in. /// - /// Throws an error if some of the roles were left in storage. - /// This means the `CollectionRoles::max_roles()` needs to be adjusted. + /// This function clears all the roles associated with the given `collection_id`. It throws an error + /// if some of the roles were left in storage, indicating that the maximum number of roles may need to be adjusted. pub(crate) fn clear_roles(collection_id: &T::CollectionId) -> Result<(), DispatchError> { let res = CollectionRoleOf::::clear_prefix( &collection_id, @@ -94,7 +107,7 @@ impl, I: 'static> Pallet { /// - `account_id`: An account to check the role for. /// - `role`: A role to validate. /// - /// Returns boolean. + /// Returns `true` if the account has the specified role, `false` otherwise. pub(crate) fn has_role( collection_id: &T::CollectionId, account_id: &T::AccountId, @@ -123,7 +136,7 @@ impl, I: 'static> Pallet { /// /// - `input`: A vector of (Account, Role) tuples. /// - /// Returns a grouped vector. + /// Returns a grouped vector of (Account, Roles) tuples. pub fn group_roles_by_account( input: Vec<(T::AccountId, CollectionRole)>, ) -> Vec<(T::AccountId, CollectionRoles)> { From 3de322bba58f70150dac9d6e6b30a72f5c811177 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Fri, 21 Jul 2023 18:12:14 +0200 Subject: [PATCH 06/28] add docs to metadata module --- frame/nfts/src/features/metadata.rs | 57 ++++++++++++++++++++++++++++- 1 file changed, 56 insertions(+), 1 deletion(-) diff --git a/frame/nfts/src/features/metadata.rs b/frame/nfts/src/features/metadata.rs index fde0296784d11..97b327fef8c4c 100644 --- a/frame/nfts/src/features/metadata.rs +++ b/frame/nfts/src/features/metadata.rs @@ -15,11 +15,27 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper functions to configure the metadata of collections and items. + use crate::*; use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { - /// Note: if `maybe_depositor` is None, that means the depositor will be a collection's owner + /// Sets the metadata for a specific item within a collection. + /// + /// - `maybe_check_origin`: An optional account ID that is allowed to set the metadata. If `None`, it's considered the root account. + /// - `collection`: The ID of the collection to which the item belongs. + /// - `item`: The ID of the item to set the metadata for. + /// - `data`: The metadata to set for the item. + /// - `maybe_depositor`: An optional account ID that will provide the deposit for the metadata. If `None`, the collection's owner provides the deposit. + /// + /// Emits `ItemMetadataSet` event upon successful setting of the metadata. + /// Returns `Ok(())` on success, or one of the following dispatch errors: + /// - `UnknownCollection`: The specified collection does not exist. + /// - `UnknownItem`: The specified item does not exist within the collection. + /// - `LockedItemMetadata`: The metadata for the item is locked and cannot be modified. + /// - `NoPermission`: The caller does not have the required permission to set the metadata. + /// - `DepositExceeded`: The deposit amount exceeds the maximum allowed value. pub(crate) fn do_set_item_metadata( maybe_check_origin: Option, collection: T::CollectionId, @@ -91,6 +107,18 @@ impl, I: 'static> Pallet { }) } + /// Clears the metadata for a specific item within a collection. + /// + /// - `maybe_check_origin`: An optional account ID that is allowed to clear the metadata. If `None`, it's considered the root account. + /// - `collection`: The ID of the collection to which the item belongs. + /// - `item`: The ID of the item for which to clear the metadata. + /// + /// Emits `ItemMetadataCleared` event upon successful clearing of the metadata. + /// Returns `Ok(())` on success, or one of the following dispatch errors: + /// - `UnknownCollection`: The specified collection does not exist. + /// - `MetadataNotFound`: The metadata for the specified item was not found. + /// - `LockedItemMetadata`: The metadata for the item is locked and cannot be modified. + /// - `NoPermission`: The caller does not have the required permission to clear the metadata. pub(crate) fn do_clear_item_metadata( maybe_check_origin: Option, collection: T::CollectionId, @@ -131,6 +159,17 @@ impl, I: 'static> Pallet { Ok(()) } + /// Sets the metadata for a specific collection. + /// + /// - `maybe_check_origin`: An optional account ID that is allowed to set the collection metadata. If `None`, it's considered the root account. + /// - `collection`: The ID of the collection for which to set the metadata. + /// - `data`: The metadata to set for the collection. + /// + /// Emits `CollectionMetadataSet` event upon successful setting of the metadata. + /// Returns `Ok(())` on success, or one of the following dispatch errors: + /// - `UnknownCollection`: The specified collection does not exist. + /// - `LockedCollectionMetadata`: The metadata for the collection is locked and cannot be modified. + /// - `NoPermission`: The caller does not have the required permission to set the metadata. pub(crate) fn do_set_collection_metadata( maybe_check_origin: Option, collection: T::CollectionId, @@ -179,6 +218,17 @@ impl, I: 'static> Pallet { }) } + /// Clears the metadata for a specific collection. + /// + /// - `maybe_check_origin`: An optional account ID that is allowed to clear the collection metadata. If `None`, it's considered the root account. + /// - `collection`: The ID of the collection for which to clear the metadata. + /// + /// Emits `CollectionMetadataCleared` event upon successful clearing of the metadata. + /// Returns `Ok(())` on success, or one of the following dispatch errors: + /// - `UnknownCollection`: The specified collection does not exist. + /// - `MetadataNotFound`: The metadata for the collection was not found. + /// - `LockedCollectionMetadata`: The metadata for the collection is locked and cannot be modified. + /// - `NoPermission`: The caller does not have the required permission to clear the metadata. pub(crate) fn do_clear_collection_metadata( maybe_check_origin: Option, collection: T::CollectionId, @@ -209,6 +259,11 @@ impl, I: 'static> Pallet { } /// A helper method to construct metadata. + /// + /// - `metadata`: A vector of bytes representing the metadata. + /// + /// Returns `Ok(BoundedVec)` on successful construction, or `Error::IncorrectMetadata` + /// if the metadata length exceeds the allowed limit. pub fn construct_metadata( metadata: Vec, ) -> Result, DispatchError> { From 45262349b04d20d8b35e683ed905ab9023ac21ac Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Fri, 21 Jul 2023 18:20:45 +0200 Subject: [PATCH 07/28] add docs to migration module --- frame/nfts/src/migration.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/frame/nfts/src/migration.rs b/frame/nfts/src/migration.rs index ba14492be84ca..a4529148e35b6 100644 --- a/frame/nfts/src/migration.rs +++ b/frame/nfts/src/migration.rs @@ -36,6 +36,7 @@ pub mod v1 { } impl OldCollectionDetails { + /// Migrates the old collection details to the new v1 format. fn migrate_to_v1(self, item_configs: u32) -> CollectionDetails { CollectionDetails { owner: self.owner, @@ -48,6 +49,7 @@ pub mod v1 { } } + /// A migration utility to update the storage version from v0 to v1 for the pallet. pub struct MigrateToV1(sp_std::marker::PhantomData); impl OnRuntimeUpgrade for MigrateToV1 { fn on_runtime_upgrade() -> Weight { From caf1ecfdb266bc6171fb670187904cfa90019333 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Fri, 21 Jul 2023 18:33:22 +0200 Subject: [PATCH 08/28] add missing docs to feature library --- frame/nfts/src/lib.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/frame/nfts/src/lib.rs b/frame/nfts/src/lib.rs index 4f498668fa81c..fbcc5fbc85516 100644 --- a/frame/nfts/src/lib.rs +++ b/frame/nfts/src/lib.rs @@ -37,6 +37,8 @@ pub mod mock; mod tests; mod common_functions; +/// A library providing the feature set of this pallet. It contains modules with helper methods that perform +/// storage updates and checks required by this pallet's dispatchables. mod features; mod impl_nonfungibles; mod types; From 64913d422df5d2cd351e21cc5f52b90ba0ab2f4c Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 10:57:01 +0200 Subject: [PATCH 09/28] methods not functions --- frame/nfts/src/features/metadata.rs | 2 +- frame/nfts/src/features/roles.rs | 2 +- frame/nfts/src/features/settings.rs | 2 +- frame/nfts/src/features/transfer.rs | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/frame/nfts/src/features/metadata.rs b/frame/nfts/src/features/metadata.rs index 97b327fef8c4c..f3684ff91f4fd 100644 --- a/frame/nfts/src/features/metadata.rs +++ b/frame/nfts/src/features/metadata.rs @@ -15,7 +15,7 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module contains helper functions to configure the metadata of collections and items. +//! This module contains helper methods to configure the metadata of collections and items. use crate::*; use frame_support::pallet_prelude::*; diff --git a/frame/nfts/src/features/roles.rs b/frame/nfts/src/features/roles.rs index b2b8d10aec959..37054890e43c4 100644 --- a/frame/nfts/src/features/roles.rs +++ b/frame/nfts/src/features/roles.rs @@ -15,7 +15,7 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module contains helper functions to configure account roles for existing collections. +//! This module contains helper methods to configure account roles for existing collections. use crate::*; use frame_support::pallet_prelude::*; diff --git a/frame/nfts/src/features/settings.rs b/frame/nfts/src/features/settings.rs index 1b87469236c3b..468b57c8b69d5 100644 --- a/frame/nfts/src/features/settings.rs +++ b/frame/nfts/src/features/settings.rs @@ -15,7 +15,7 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module provides helper functions to configure collection settings for the NFTs pallet. +//! This module provides helper methods to configure collection settings for the NFTs pallet. use crate::*; use frame_support::pallet_prelude::*; diff --git a/frame/nfts/src/features/transfer.rs b/frame/nfts/src/features/transfer.rs index 4f091e911a7c9..5f6d4a83ad351 100644 --- a/frame/nfts/src/features/transfer.rs +++ b/frame/nfts/src/features/transfer.rs @@ -15,7 +15,7 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module contains helper functions to perform the transfer functionalities +//! This module contains helper methods to perform the transfer functionalities //! of the NFTs pallet. use crate::*; From bfe2c3017013a73ba86f37673a741914d0940180 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 11:06:49 +0200 Subject: [PATCH 10/28] add docs to lock module --- frame/nfts/src/features/lock.rs | 45 +++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) diff --git a/frame/nfts/src/features/lock.rs b/frame/nfts/src/features/lock.rs index 8b4914baeb450..7e88141e4f1f4 100644 --- a/frame/nfts/src/features/lock.rs +++ b/frame/nfts/src/features/lock.rs @@ -15,10 +15,22 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper methods to configure locks on collections and items for the NFTs pallet. + use crate::*; use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { + /// Locks a collection with specified settings. + /// + /// The origin must be the owner of the collection to lock it. This function disables certain + /// settings on the collection, including disabling the `DepositRequired` setting to allow for + /// unlocking the collection in the future. + /// + /// - `origin`: The origin of the transaction, representing the account attempting to lock + /// the collection. + /// - `collection`: The identifier of the collection to be locked. + /// - `lock_settings`: The collection settings to be locked. pub(crate) fn do_lock_collection( origin: T::AccountId, collection: T::CollectionId, @@ -41,6 +53,16 @@ impl, I: 'static> Pallet { }) } + /// Locks the transfer of an item within a collection. + /// + /// The origin must have the `Freezer` role within the collection to lock the transfer of the item. + /// This function disables the `Transferable` setting on the item, preventing it from being + /// transferred to other accounts. + /// + /// - `origin`: The origin of the transaction, representing the account attempting to lock + /// the item transfer. + /// - `collection`: The identifier of the collection to which the item belongs. + /// - `item`: The identifier of the item to be locked for transfer. pub(crate) fn do_lock_item_transfer( origin: T::AccountId, collection: T::CollectionId, @@ -61,6 +83,16 @@ impl, I: 'static> Pallet { Ok(()) } + /// Unlocks the transfer of an item within a collection. + /// + /// The origin must have the `Freezer` role within the collection to unlock the transfer of the item. + /// This function enables the `Transferable` setting on the item, allowing it to be transferred + /// to other accounts. + /// + /// - `origin`: The origin of the transaction, representing the account attempting to unlock + /// the item transfer. + /// - `collection`: The identifier of the collection to which the item belongs. + /// - `item`: The identifier of the item to be unlocked for transfer. pub(crate) fn do_unlock_item_transfer( origin: T::AccountId, collection: T::CollectionId, @@ -81,6 +113,19 @@ impl, I: 'static> Pallet { Ok(()) } + /// Locks the metadata and attributes of an item within a collection. + /// + /// The origin must have the `Admin` role within the collection to lock the metadata and attributes + /// of the item. This function disables the `UnlockedMetadata` and `UnlockedAttributes` settings on + /// the item, preventing modifications to its metadata and attributes. + /// + /// - `maybe_check_origin`: An optional origin representing the account attempting to lock the + /// item properties. If provided, this account must have the `Admin` role within the collection. + /// If `None`, no permission check is performed, and the function can be called from any origin. + /// - `collection`: The identifier of the collection to which the item belongs. + /// - `item`: The identifier of the item to be locked for properties. + /// - `lock_metadata`: A boolean indicating whether to lock the metadata of the item. + /// - `lock_attributes`: A boolean indicating whether to lock the attributes of the item. pub(crate) fn do_lock_item_properties( maybe_check_origin: Option, collection: T::CollectionId, From 72d9256c18caca10458b824120cc48d78baedd9a Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 11:29:24 +0200 Subject: [PATCH 11/28] add docs to attributes module --- frame/nfts/src/features/attributes.rs | 96 +++++++++++++++++++++++++++ 1 file changed, 96 insertions(+) diff --git a/frame/nfts/src/features/attributes.rs b/frame/nfts/src/features/attributes.rs index 8a9bbe8a61de0..91060db669d04 100644 --- a/frame/nfts/src/features/attributes.rs +++ b/frame/nfts/src/features/attributes.rs @@ -15,10 +15,36 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper methods to configure attributes for items and collections in the NFTs pallet. + use crate::*; use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { + + /// Sets the attribute of an item or a collection. + /// + /// This function is used to set an attribute for an item or a collection. It checks the provided + /// `namespace` and verifies the permission of the caller to perform the action. The `collection` + /// and `maybe_item` parameters specify the target for the attribute. + /// + /// - `origin`: The account attempting to set the attribute. + /// - `collection`: The identifier of the collection to which the item belongs, or the collection + /// itself if setting a collection attribute. + /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if setting + /// a collection attribute. + /// - `namespace`: The namespace in which the attribute is being set. It can be either + /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined by + /// `T::KeyLimit`. + /// - `value`: The value of the attribute. It should be a vector of bytes within the limits defined by + /// `T::ValueLimit`. + /// - `depositor`: The account that is paying the deposit for the attribute. + /// + /// Note: For the `CollectionOwner` namespace, the collection must have the `UnlockedAttributes` + /// setting enabled. For the `ItemOwner` namespace, the item must not be locked for attributes. For + /// the `Account` namespace, the deposit is required based on the `T::DepositPerByte` and + /// `T::AttributeDepositBase` configuration. pub(crate) fn do_set_attribute( origin: T::AccountId, collection: T::CollectionId, @@ -128,6 +154,23 @@ impl, I: 'static> Pallet { Ok(()) } + /// Sets the attribute of an item or a collection without performing deposit checks. + /// + /// This function is used to force-set an attribute for an item or a collection without performing + /// the deposit checks. It bypasses the deposit requirement and should only be used in specific + /// situations where deposit checks are not necessary or handled separately. + /// + /// - `set_as`: The account that the attribute should be set as. + /// - `collection`: The identifier of the collection to which the item belongs, or the collection + /// itself if setting a collection attribute. + /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if setting + /// a collection attribute. + /// - `namespace`: The namespace in which the attribute is being set. It can be either + /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined by + /// `T::KeyLimit`. + /// - `value`: The value of the attribute. It should be a vector of bytes within the limits defined by + /// `T::ValueLimit`. pub(crate) fn do_force_set_attribute( set_as: Option, collection: T::CollectionId, @@ -159,6 +202,17 @@ impl, I: 'static> Pallet { Ok(()) } + /// Sets multiple attributes for an item or a collection in a single transaction. + /// + /// This function allows setting multiple attributes for an item or a collection at once. It is + /// intended to be used with pre-signed transactions for off-chain mints. The `signer` account must + /// have the `ItemOwner` or `Account` namespace permission, depending on the `namespace` provided + /// for each attribute. The transaction must be signed with the `signer` account's key. It is limited + /// by `T::MaxAttributesPerCall` to prevent excessive storage consumption in a single transaction. + /// + /// - `origin`: The account initiating the transaction. + /// - `data`: The data containing the details of the pre-signed attributes to be set. + /// - `signer`: The account of the pre-signed attributes signer. pub(crate) fn do_set_attributes_pre_signed( origin: T::AccountId, data: PreSignedAttributesOf, @@ -212,6 +266,23 @@ impl, I: 'static> Pallet { Ok(()) } + /// Clears an attribute of an item or a collection. + /// + /// This function allows clearing an attribute from an item or a collection. It verifies the + /// permission of the caller to perform the action based on the provided `namespace` and `depositor` + /// account. The deposit associated with the attribute, if any, will be unreserved or moved to the + /// collection owner's deposit based on the deposit settings and the attribute namespace. + /// + /// - `maybe_check_origin`: An optional account that acts as an additional security check when + /// clearing the attribute. This can be `None` if no additional check is required. + /// - `collection`: The identifier of the collection to which the item belongs, or the collection + /// itself if clearing a collection attribute. + /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if clearing + /// a collection attribute. + /// - `namespace`: The namespace in which the attribute is being cleared. It can be either + /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// - `key`: The key of the attribute to be cleared. It should be a vector of bytes within the limits + /// defined by `T::KeyLimit`. pub(crate) fn do_clear_attribute( maybe_check_origin: Option, collection: T::CollectionId, @@ -288,6 +359,17 @@ impl, I: 'static> Pallet { Ok(()) } + /// Approves a delegate to set attributes on behalf of the item's owner. + /// + /// This function allows the owner of an item to approve a delegate to set attributes on their + /// behalf. The delegate must have the account namespace permission, and the item must belong to + /// the specified `collection`. The maximum number of approvals is determined by the configuration + /// `T::MaxAttributesApprovals`. + /// + /// - `check_origin`: The account of the item's owner attempting to approve the delegate. + /// - `collection`: The identifier of the collection to which the item belongs. + /// - `item`: The identifier of the item for which the delegate is being approved. + /// - `delegate`: The account that is being approved to set attributes on behalf of the item's owner. pub(crate) fn do_approve_item_attributes( check_origin: T::AccountId, collection: T::CollectionId, @@ -312,6 +394,19 @@ impl, I: 'static> Pallet { }) } + /// Cancels the approval of an item's attributes by a delegate. + /// + /// This function allows the owner of an item to cancel the approval of a delegate to set attributes + /// on their behalf. The delegate's approval is removed, and any unreserved deposit associated with + /// their approved attributes is returned to them. The number of attributes that the delegate has set + /// for the item must not exceed the `account_attributes` provided in the `witness`. This function is + /// used to prevent unintended or malicious cancellations. + /// + /// - `check_origin`: The account of the item's owner attempting to cancel the delegate's approval. + /// - `collection`: The identifier of the collection to which the item belongs. + /// - `item`: The identifier of the item for which the delegate's approval is being canceled. + /// - `delegate`: The account whose approval is being canceled. + /// - `witness`: The witness containing the number of attributes set by the delegate for the item. pub(crate) fn do_cancel_item_attributes_approval( check_origin: T::AccountId, collection: T::CollectionId, @@ -355,6 +450,7 @@ impl, I: 'static> Pallet { }) } + /// A helper method to check whether a attribute namespace is valid. fn is_valid_namespace( origin: &T::AccountId, namespace: &AttributeNamespace, From 831085aa0bfd30cbdf6b93195e7cea96c2819003 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 13:02:35 +0200 Subject: [PATCH 12/28] add docs to create_delete_item module --- frame/nfts/src/features/create_delete_item.rs | 42 +++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/frame/nfts/src/features/create_delete_item.rs b/frame/nfts/src/features/create_delete_item.rs index e3d1334d48ef5..023ae32743b23 100644 --- a/frame/nfts/src/features/create_delete_item.rs +++ b/frame/nfts/src/features/create_delete_item.rs @@ -15,10 +15,29 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper methods to perform functionality associated with minting and burning items for the NFTs pallet. + use crate::*; use frame_support::{pallet_prelude::*, traits::ExistenceRequirement}; impl, I: 'static> Pallet { + /// Mints a new item in the specified collection and assigns it to the `mint_to` account. + /// + /// This function is used to mint a new item in the specified `collection` and assign it to the + /// `mint_to` account. The minting process involves creating the item, setting its attributes and + /// metadata, and reserving the required deposit amount from the `mint_to` account. The minting + /// process is configurable through the provided `item_config` parameter. The `with_details_and_config` + /// closure is called to validate the provided `collection_details` and `collection_config` before + /// minting the item. + /// + /// - `collection`: The collection ID in which the item is minted. + /// - `item`: The ID of the newly minted item. + /// - `maybe_depositor`: The optional account that deposits the required amount for the item. + /// - `mint_to`: The account that receives the newly minted item. + /// - `item_config`: The configuration settings for the newly minted item. + /// - `with_details_and_config`: A closure to perform custom validation for minting the item. It + /// is called with the `collection_details` and `collection_config`, allowing custom checks to + /// be performed. pub fn do_mint( collection: T::CollectionId, item: T::ItemId, @@ -86,6 +105,19 @@ impl, I: 'static> Pallet { Ok(()) } + /// Mints a new item using a pre-signed message. + /// + /// This function allows minting a new item using a pre-signed message. The minting process is + /// similar to the regular minting process, but it is performed by a pre-authorized account. The + /// `mint_to` account receives the newly minted item. The minting process is configurable through + /// the provided `mint_data`. The attributes, metadata, and price of the item are set according to + /// the provided `mint_data`. The `with_details_and_config` closure is called to validate the + /// provided `collection_details` and `collection_config` before minting the item. + /// + /// - `mint_to`: The account that receives the newly minted item. + /// - `mint_data`: The pre-signed minting data containing the `collection`, `item`, `attributes`, + /// `metadata`, `deadline`, `only_account`, and `mint_price`. + /// - `signer`: The account that is authorized to mint the item using the pre-signed message. pub(crate) fn do_mint_pre_signed( mint_to: T::AccountId, mint_data: PreSignedMintOf, @@ -163,6 +195,16 @@ impl, I: 'static> Pallet { Ok(()) } + /// Burns the specified item from the collection. + /// + /// This function burns the specified `item` from the specified `collection`. The item's owner + /// can call this function to remove the item permanently from the collection. Any associated + /// deposit and metadata will be cleared from the item. Custom logic can be executed using the + /// `with_details` closure to perform additional checks or actions before burning the item. + /// + /// - `collection`: The ID of the collection from which the item will be burned. + /// - `item`: The ID of the item to be burned. + /// - `with_details`: A closure to perform custom validation or actions before burning the item. pub fn do_burn( collection: T::CollectionId, item: T::ItemId, From c195c5bc730e6768987b00eaf3f3de4a6ef4fbfb Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 13:06:25 +0200 Subject: [PATCH 13/28] add docs for create_delete_collection module --- frame/nfts/src/features/create_delete_collection.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/frame/nfts/src/features/create_delete_collection.rs b/frame/nfts/src/features/create_delete_collection.rs index e9434760628ec..fb0532128c74a 100644 --- a/frame/nfts/src/features/create_delete_collection.rs +++ b/frame/nfts/src/features/create_delete_collection.rs @@ -15,6 +15,8 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper methods to perform functionality associated with creating and destroying collections for the NFTs pallet. + use crate::*; use frame_support::pallet_prelude::*; From 02ed70a8e18973c952760b18aeacade330ea11be Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 13:50:46 +0200 Subject: [PATCH 14/28] add docs to buy_sell module --- frame/nfts/src/features/buy_sell.rs | 34 +++++++++++++++++++++++++++++ 1 file changed, 34 insertions(+) diff --git a/frame/nfts/src/features/buy_sell.rs b/frame/nfts/src/features/buy_sell.rs index ad721e0748ad0..64ae326a10d00 100644 --- a/frame/nfts/src/features/buy_sell.rs +++ b/frame/nfts/src/features/buy_sell.rs @@ -22,6 +22,16 @@ use frame_support::{ }; impl, I: 'static> Pallet { + /// Pays the specified tips to the corresponding receivers. + /// + /// This function is used to pay tips from the `sender` account to multiple receivers. The tips + /// are specified as a `BoundedVec` of `ItemTipOf` with a maximum length of `T::MaxTips`. For each + /// tip, the function transfers the `amount` to the `receiver` account. The sender is responsible + /// for ensuring the validity of the provided tips. + /// + /// - `sender`: The account that pays the tips. + /// - `tips`: A `BoundedVec` containing the tips to be paid, where each tip contains the + /// `collection`, `item`, `receiver`, and `amount`. pub(crate) fn do_pay_tips( sender: T::AccountId, tips: BoundedVec, T::MaxTips>, @@ -40,6 +50,18 @@ impl, I: 'static> Pallet { Ok(()) } + /// Sets the price and whitelist information for an item in the specified collection. + /// + /// This function is used to set the price and whitelist information for an item in the specified + /// `collection`. The `sender` account must be the owner of the item. The item's price and + /// whitelist information can be set to allow trading the item. If `price` is `None`, the item will + /// be marked as not for sale. + /// + /// - `collection`: The identifier of the collection containing the item. + /// - `item`: The identifier of the item for which the price and whitelist information will be set. + /// - `sender`: The account that sets the price and whitelist information for the item. + /// - `price`: The optional price for the item. + /// - `whitelisted_buyer`: The optional account that is whitelisted to buy the item at the set price. pub(crate) fn do_set_price( collection: T::CollectionId, item: T::ItemId, @@ -83,6 +105,18 @@ impl, I: 'static> Pallet { Ok(()) } + /// Buys the specified item from the collection. + /// + /// This function is used to buy an item from the specified `collection`. The `buyer` account will + /// attempt to buy the item with the provided `bid_price`. The item's current owner will receive + /// the bid price if it is equal to or higher than the item's set price. If `whitelisted_buyer` is + /// specified in the item's price information, only that account is allowed to buy the item. If the + /// item is not for sale, or the bid price is too low, the function will return an error. + /// + /// - `collection`: The identifier of the collection containing the item to be bought. + /// - `item`: The identifier of the item to be bought. + /// - `buyer`: The account that attempts to buy the item. + /// - `bid_price`: The bid price offered by the buyer for the item. pub(crate) fn do_buy_item( collection: T::CollectionId, item: T::ItemId, From 2a89afa4556b87e091d86f95406687bcacf7f2c1 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 13:52:53 +0200 Subject: [PATCH 15/28] add missing doc for buy_sell module --- frame/nfts/src/features/buy_sell.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/frame/nfts/src/features/buy_sell.rs b/frame/nfts/src/features/buy_sell.rs index 64ae326a10d00..d59cd6c27fcc1 100644 --- a/frame/nfts/src/features/buy_sell.rs +++ b/frame/nfts/src/features/buy_sell.rs @@ -15,6 +15,8 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper functions to perform the buy and sell functionalities of the NFTs pallet. + use crate::*; use frame_support::{ pallet_prelude::*, From 4f0342c4c167708211444f271358b13b6c856dd9 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 14:00:46 +0200 Subject: [PATCH 16/28] add docs to atomic_swap module --- frame/nfts/src/features/atomic_swap.rs | 43 +++++++++++++++++++++++++- 1 file changed, 42 insertions(+), 1 deletion(-) diff --git a/frame/nfts/src/features/atomic_swap.rs b/frame/nfts/src/features/atomic_swap.rs index 5b0096d72a3d6..6d8e8baa3a2fd 100644 --- a/frame/nfts/src/features/atomic_swap.rs +++ b/frame/nfts/src/features/atomic_swap.rs @@ -22,6 +22,25 @@ use frame_support::{ }; impl, I: 'static> Pallet { + /// Creates a new swap offer for the specified item. + /// + /// This function is used to create a new swap offer for the specified item. The `caller` + /// account must be the owner of the item. The swap offer specifies the `offered_collection`, + /// `offered_item`, `desired_collection`, `maybe_desired_item`, `maybe_price`, and `duration`. + /// The `duration` specifies the deadline by which the swap must be claimed. If `maybe_desired_item` + /// is `Some`, the specified item is expected in return for the swap. If `maybe_desired_item` is + /// `None`, it indicates that any item from the `desired_collection` can be offered in return. + /// The `maybe_price` specifies an optional price for the swap. If specified, the other party must + /// offer the specified `price` or higher for the swap. After creating the swap, the function emits + /// the `SwapCreated` event. + /// + /// - `caller`: The account creating the swap offer, which must be the owner of the item. + /// - `offered_collection_id`: The collection ID containing the offered item. + /// - `offered_item_id`: The item ID offered for the swap. + /// - `desired_collection_id`: The collection ID containing the desired item (if any). + /// - `maybe_desired_item_id`: The ID of the desired item (if any). + /// - `maybe_price`: The optional price for the swap. + /// - `duration`: The duration (in block numbers) specifying the deadline for the swap claim. pub(crate) fn do_create_swap( caller: T::AccountId, offered_collection_id: T::CollectionId, @@ -77,7 +96,15 @@ impl, I: 'static> Pallet { Ok(()) } - + /// Cancels the specified swap offer. + /// + /// This function is used to cancel the specified swap offer created by the `caller` account. If the + /// swap offer's deadline has not yet passed, the `caller` must be the owner of the offered item. After + /// canceling the swap offer, the function emits the `SwapCancelled` event. + /// + /// - `caller`: The account canceling the swap offer. + /// - `offered_collection_id`: The collection ID containing the offered item. + /// - `offered_item_id`: The item ID offered for the swap. pub(crate) fn do_cancel_swap( caller: T::AccountId, offered_collection_id: T::CollectionId, @@ -107,6 +134,20 @@ impl, I: 'static> Pallet { Ok(()) } + /// Claims the specified swap offer. + /// + /// This function is used to claim a swap offer specified by the `send_collection_id`, `send_item_id`, + /// `receive_collection_id`, and `receive_item_id`. The `caller` account must be the owner of the item + /// specified by `send_collection_id` and `send_item_id`. If the claimed swap has an associated `price`, + /// it will be transferred between the owners of the two items based on the `price.direction`. After + /// the swap is completed, the function emits the `SwapClaimed` event. + /// + /// - `caller`: The account claiming the swap offer, which must be the owner of the sent item. + /// - `send_collection_id`: The identifier of the collection containing the item being sent. + /// - `send_item_id`: The identifier of the item being sent for the swap. + /// - `receive_collection_id`: The identifier of the collection containing the item being received. + /// - `receive_item_id`: The identifier of the item being received in the swap. + /// - `witness_price`: The optional witness price for the swap (price that was offered in the swap). pub(crate) fn do_claim_swap( caller: T::AccountId, send_collection_id: T::CollectionId, From facfc2270c3c04fd2eb240951160ea06a201b981 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 14:02:19 +0200 Subject: [PATCH 17/28] add docs to atomic_swap module --- frame/nfts/src/features/atomic_swap.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/frame/nfts/src/features/atomic_swap.rs b/frame/nfts/src/features/atomic_swap.rs index 6d8e8baa3a2fd..3b098d02d0829 100644 --- a/frame/nfts/src/features/atomic_swap.rs +++ b/frame/nfts/src/features/atomic_swap.rs @@ -15,6 +15,8 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper functions for performing atomic swaps implemented in the NFTs pallet. + use crate::*; use frame_support::{ pallet_prelude::*, From 742b22a5abf22cb0e30931ea1cdeb3965386de71 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 14:14:54 +0200 Subject: [PATCH 18/28] add docs for approvals module --- frame/nfts/src/features/approvals.rs | 42 ++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/frame/nfts/src/features/approvals.rs b/frame/nfts/src/features/approvals.rs index c78dd2d96b089..678e6a8e866d4 100644 --- a/frame/nfts/src/features/approvals.rs +++ b/frame/nfts/src/features/approvals.rs @@ -15,10 +15,28 @@ // See the License for the specific language governing permissions and // limitations under the License. +//! This module contains helper functions for the approval logic implemented in the NFTs pallet. + use crate::*; use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { + /// Approves the transfer of an item to a delegate. + /// + /// This function is used to approve the transfer of the specified `item` in the `collection` to a + /// `delegate`. If `maybe_check_origin` is specified, the function ensures that the `check_origin` + /// account is the owner of the item, granting them permission to approve the transfer. The `delegate` + /// is the account that will be allowed to take control of the item. Optionally, a `deadline` can be + /// specified to set a time limit for the approval. The `deadline` is expressed in block numbers and + /// is added to the current block number to determine the absolute deadline for the approval. After + /// approving the transfer, the function emits the `TransferApproved` event. + /// + /// - `maybe_check_origin`: The optional account that is required to be the owner of the item, granting + /// permission to approve the transfer. If `None`, no permission check is performed. + /// - `collection`: The identifier of the collection containing the item to be transferred. + /// - `item`: The identifier of the item to be transferred. + /// - `delegate`: The account that will be allowed to take control of the item. + /// - `maybe_deadline`: The optional deadline (in block numbers) specifying the time limit for the approval. pub(crate) fn do_approve_transfer( maybe_check_origin: Option, collection: T::CollectionId, @@ -63,6 +81,19 @@ impl, I: 'static> Pallet { Ok(()) } + /// Cancels the approval for the transfer of an item to a delegate. + /// + /// This function is used to cancel the approval for the transfer of the specified `item` in the `collection` + /// to a `delegate`. If `maybe_check_origin` is specified, the function ensures that the `check_origin` + /// account is the owner of the item or that the approval is past its deadline, granting permission to + /// cancel the approval. After canceling the approval, the function emits the `ApprovalCancelled` event. + /// + /// - `maybe_check_origin`: The optional account that is required to be the owner of the item or that the + /// approval is past its deadline, granting permission to cancel the approval. If `None`, no permission + /// check is performed. + /// - `collection`: The identifier of the collection containing the item. + /// - `item`: The identifier of the item. + /// - `delegate`: The account that was previously allowed to take control of the item. pub(crate) fn do_cancel_approval( maybe_check_origin: Option, collection: T::CollectionId, @@ -100,6 +131,17 @@ impl, I: 'static> Pallet { Ok(()) } + /// Clears all transfer approvals for an item. + /// + /// This function is used to clear all transfer approvals for the specified `item` in the `collection`. + /// If `maybe_check_origin` is specified, the function ensures that the `check_origin` account is the + /// owner of the item, granting permission to clear all transfer approvals. After clearing all approvals, + /// the function emits the `AllApprovalsCancelled` event. + /// + /// - `maybe_check_origin`: The optional account that is required to be the owner of the item, granting + /// permission to clear all transfer approvals. If `None`, no permission check is performed. + /// - `collection`: The collection ID containing the item. + /// - `item`: The item ID for which transfer approvals will be cleared. pub(crate) fn do_clear_all_transfer_approvals( maybe_check_origin: Option, collection: T::CollectionId, From 9c153f4f380488c2bf4de01723d5181cf3a03ab8 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 25 Jul 2023 14:32:24 +0200 Subject: [PATCH 19/28] run cargo fmt --- frame/nfts/src/features/approvals.rs | 49 +++-- frame/nfts/src/features/atomic_swap.rs | 38 ++-- frame/nfts/src/features/attributes.rs | 198 ++++++++++-------- frame/nfts/src/features/buy_sell.rs | 36 ++-- .../src/features/create_delete_collection.rs | 3 +- frame/nfts/src/features/create_delete_item.rs | 81 +++---- frame/nfts/src/features/lock.rs | 22 +- frame/nfts/src/features/metadata.rs | 23 +- frame/nfts/src/features/roles.rs | 33 +-- frame/nfts/src/features/settings.rs | 118 +++++------ frame/nfts/src/features/transfer.rs | 29 ++- frame/nfts/src/lib.rs | 4 +- 12 files changed, 338 insertions(+), 296 deletions(-) diff --git a/frame/nfts/src/features/approvals.rs b/frame/nfts/src/features/approvals.rs index 678e6a8e866d4..e272cf52e4290 100644 --- a/frame/nfts/src/features/approvals.rs +++ b/frame/nfts/src/features/approvals.rs @@ -23,20 +23,23 @@ use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { /// Approves the transfer of an item to a delegate. /// - /// This function is used to approve the transfer of the specified `item` in the `collection` to a - /// `delegate`. If `maybe_check_origin` is specified, the function ensures that the `check_origin` - /// account is the owner of the item, granting them permission to approve the transfer. The `delegate` - /// is the account that will be allowed to take control of the item. Optionally, a `deadline` can be - /// specified to set a time limit for the approval. The `deadline` is expressed in block numbers and - /// is added to the current block number to determine the absolute deadline for the approval. After - /// approving the transfer, the function emits the `TransferApproved` event. + /// This function is used to approve the transfer of the specified `item` in the `collection` to + /// a `delegate`. If `maybe_check_origin` is specified, the function ensures that the + /// `check_origin` account is the owner of the item, granting them permission to approve the + /// transfer. The `delegate` is the account that will be allowed to take control of the item. + /// Optionally, a `deadline` can be specified to set a time limit for the approval. The + /// `deadline` is expressed in block numbers and is added to the current block number to + /// determine the absolute deadline for the approval. After approving the transfer, the function + /// emits the `TransferApproved` event. /// - /// - `maybe_check_origin`: The optional account that is required to be the owner of the item, granting + /// - `maybe_check_origin`: The optional account that is required to be the owner of the item, + /// granting /// permission to approve the transfer. If `None`, no permission check is performed. /// - `collection`: The identifier of the collection containing the item to be transferred. /// - `item`: The identifier of the item to be transferred. /// - `delegate`: The account that will be allowed to take control of the item. - /// - `maybe_deadline`: The optional deadline (in block numbers) specifying the time limit for the approval. + /// - `maybe_deadline`: The optional deadline (in block numbers) specifying the time limit for + /// the approval. pub(crate) fn do_approve_transfer( maybe_check_origin: Option, collection: T::CollectionId, @@ -83,14 +86,16 @@ impl, I: 'static> Pallet { /// Cancels the approval for the transfer of an item to a delegate. /// - /// This function is used to cancel the approval for the transfer of the specified `item` in the `collection` - /// to a `delegate`. If `maybe_check_origin` is specified, the function ensures that the `check_origin` - /// account is the owner of the item or that the approval is past its deadline, granting permission to - /// cancel the approval. After canceling the approval, the function emits the `ApprovalCancelled` event. + /// This function is used to cancel the approval for the transfer of the specified `item` in the + /// `collection` to a `delegate`. If `maybe_check_origin` is specified, the function ensures + /// that the `check_origin` account is the owner of the item or that the approval is past its + /// deadline, granting permission to cancel the approval. After canceling the approval, the + /// function emits the `ApprovalCancelled` event. /// - /// - `maybe_check_origin`: The optional account that is required to be the owner of the item or that the - /// approval is past its deadline, granting permission to cancel the approval. If `None`, no permission - /// check is performed. + /// - `maybe_check_origin`: The optional account that is required to be the owner of the item or + /// that the + /// approval is past its deadline, granting permission to cancel the approval. If `None`, no + /// permission check is performed. /// - `collection`: The identifier of the collection containing the item. /// - `item`: The identifier of the item. /// - `delegate`: The account that was previously allowed to take control of the item. @@ -133,12 +138,14 @@ impl, I: 'static> Pallet { /// Clears all transfer approvals for an item. /// - /// This function is used to clear all transfer approvals for the specified `item` in the `collection`. - /// If `maybe_check_origin` is specified, the function ensures that the `check_origin` account is the - /// owner of the item, granting permission to clear all transfer approvals. After clearing all approvals, - /// the function emits the `AllApprovalsCancelled` event. + /// This function is used to clear all transfer approvals for the specified `item` in the + /// `collection`. If `maybe_check_origin` is specified, the function ensures that the + /// `check_origin` account is the owner of the item, granting permission to clear all transfer + /// approvals. After clearing all approvals, the function emits the `AllApprovalsCancelled` + /// event. /// - /// - `maybe_check_origin`: The optional account that is required to be the owner of the item, granting + /// - `maybe_check_origin`: The optional account that is required to be the owner of the item, + /// granting /// permission to clear all transfer approvals. If `None`, no permission check is performed. /// - `collection`: The collection ID containing the item. /// - `item`: The item ID for which transfer approvals will be cleared. diff --git a/frame/nfts/src/features/atomic_swap.rs b/frame/nfts/src/features/atomic_swap.rs index 3b098d02d0829..dfd36d1538db8 100644 --- a/frame/nfts/src/features/atomic_swap.rs +++ b/frame/nfts/src/features/atomic_swap.rs @@ -15,7 +15,8 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module contains helper functions for performing atomic swaps implemented in the NFTs pallet. +//! This module contains helper functions for performing atomic swaps implemented in the NFTs +//! pallet. use crate::*; use frame_support::{ @@ -29,12 +30,12 @@ impl, I: 'static> Pallet { /// This function is used to create a new swap offer for the specified item. The `caller` /// account must be the owner of the item. The swap offer specifies the `offered_collection`, /// `offered_item`, `desired_collection`, `maybe_desired_item`, `maybe_price`, and `duration`. - /// The `duration` specifies the deadline by which the swap must be claimed. If `maybe_desired_item` - /// is `Some`, the specified item is expected in return for the swap. If `maybe_desired_item` is - /// `None`, it indicates that any item from the `desired_collection` can be offered in return. - /// The `maybe_price` specifies an optional price for the swap. If specified, the other party must - /// offer the specified `price` or higher for the swap. After creating the swap, the function emits - /// the `SwapCreated` event. + /// The `duration` specifies the deadline by which the swap must be claimed. If + /// `maybe_desired_item` is `Some`, the specified item is expected in return for the swap. If + /// `maybe_desired_item` is `None`, it indicates that any item from the `desired_collection` can + /// be offered in return. The `maybe_price` specifies an optional price for the swap. If + /// specified, the other party must offer the specified `price` or higher for the swap. After + /// creating the swap, the function emits the `SwapCreated` event. /// /// - `caller`: The account creating the swap offer, which must be the owner of the item. /// - `offered_collection_id`: The collection ID containing the offered item. @@ -100,9 +101,9 @@ impl, I: 'static> Pallet { } /// Cancels the specified swap offer. /// - /// This function is used to cancel the specified swap offer created by the `caller` account. If the - /// swap offer's deadline has not yet passed, the `caller` must be the owner of the offered item. After - /// canceling the swap offer, the function emits the `SwapCancelled` event. + /// This function is used to cancel the specified swap offer created by the `caller` account. If + /// the swap offer's deadline has not yet passed, the `caller` must be the owner of the offered + /// item. After canceling the swap offer, the function emits the `SwapCancelled` event. /// /// - `caller`: The account canceling the swap offer. /// - `offered_collection_id`: The collection ID containing the offered item. @@ -138,18 +139,21 @@ impl, I: 'static> Pallet { /// Claims the specified swap offer. /// - /// This function is used to claim a swap offer specified by the `send_collection_id`, `send_item_id`, - /// `receive_collection_id`, and `receive_item_id`. The `caller` account must be the owner of the item - /// specified by `send_collection_id` and `send_item_id`. If the claimed swap has an associated `price`, - /// it will be transferred between the owners of the two items based on the `price.direction`. After - /// the swap is completed, the function emits the `SwapClaimed` event. + /// This function is used to claim a swap offer specified by the `send_collection_id`, + /// `send_item_id`, `receive_collection_id`, and `receive_item_id`. The `caller` account must be + /// the owner of the item specified by `send_collection_id` and `send_item_id`. If the claimed + /// swap has an associated `price`, it will be transferred between the owners of the two items + /// based on the `price.direction`. After the swap is completed, the function emits the + /// `SwapClaimed` event. /// /// - `caller`: The account claiming the swap offer, which must be the owner of the sent item. /// - `send_collection_id`: The identifier of the collection containing the item being sent. /// - `send_item_id`: The identifier of the item being sent for the swap. - /// - `receive_collection_id`: The identifier of the collection containing the item being received. + /// - `receive_collection_id`: The identifier of the collection containing the item being + /// received. /// - `receive_item_id`: The identifier of the item being received in the swap. - /// - `witness_price`: The optional witness price for the swap (price that was offered in the swap). + /// - `witness_price`: The optional witness price for the swap (price that was offered in the + /// swap). pub(crate) fn do_claim_swap( caller: T::AccountId, send_collection_id: T::CollectionId, diff --git a/frame/nfts/src/features/attributes.rs b/frame/nfts/src/features/attributes.rs index 91060db669d04..24775ffb30b97 100644 --- a/frame/nfts/src/features/attributes.rs +++ b/frame/nfts/src/features/attributes.rs @@ -15,36 +15,40 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module contains helper methods to configure attributes for items and collections in the NFTs pallet. +//! This module contains helper methods to configure attributes for items and collections in the +//! NFTs pallet. use crate::*; use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { - /// Sets the attribute of an item or a collection. - /// - /// This function is used to set an attribute for an item or a collection. It checks the provided - /// `namespace` and verifies the permission of the caller to perform the action. The `collection` - /// and `maybe_item` parameters specify the target for the attribute. - /// - /// - `origin`: The account attempting to set the attribute. - /// - `collection`: The identifier of the collection to which the item belongs, or the collection - /// itself if setting a collection attribute. - /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if setting - /// a collection attribute. - /// - `namespace`: The namespace in which the attribute is being set. It can be either - /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). - /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined by - /// `T::KeyLimit`. - /// - `value`: The value of the attribute. It should be a vector of bytes within the limits defined by - /// `T::ValueLimit`. - /// - `depositor`: The account that is paying the deposit for the attribute. - /// - /// Note: For the `CollectionOwner` namespace, the collection must have the `UnlockedAttributes` - /// setting enabled. For the `ItemOwner` namespace, the item must not be locked for attributes. For - /// the `Account` namespace, the deposit is required based on the `T::DepositPerByte` and - /// `T::AttributeDepositBase` configuration. + /// + /// This function is used to set an attribute for an item or a collection. It checks the + /// provided `namespace` and verifies the permission of the caller to perform the action. The + /// `collection` and `maybe_item` parameters specify the target for the attribute. + /// + /// - `origin`: The account attempting to set the attribute. + /// - `collection`: The identifier of the collection to which the item belongs, or the + /// collection + /// itself if setting a collection attribute. + /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if + /// setting + /// a collection attribute. + /// - `namespace`: The namespace in which the attribute is being set. It can be either + /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined + /// by + /// `T::KeyLimit`. + /// - `value`: The value of the attribute. It should be a vector of bytes within the limits + /// defined by + /// `T::ValueLimit`. + /// - `depositor`: The account that is paying the deposit for the attribute. + /// + /// Note: For the `CollectionOwner` namespace, the collection must have the `UnlockedAttributes` + /// setting enabled. For the `ItemOwner` namespace, the item must not be locked for attributes. + /// For the `Account` namespace, the deposit is required based on the `T::DepositPerByte` and + /// `T::AttributeDepositBase` configuration. pub(crate) fn do_set_attribute( origin: T::AccountId, collection: T::CollectionId, @@ -154,23 +158,27 @@ impl, I: 'static> Pallet { Ok(()) } - /// Sets the attribute of an item or a collection without performing deposit checks. - /// - /// This function is used to force-set an attribute for an item or a collection without performing - /// the deposit checks. It bypasses the deposit requirement and should only be used in specific - /// situations where deposit checks are not necessary or handled separately. - /// - /// - `set_as`: The account that the attribute should be set as. - /// - `collection`: The identifier of the collection to which the item belongs, or the collection - /// itself if setting a collection attribute. - /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if setting - /// a collection attribute. - /// - `namespace`: The namespace in which the attribute is being set. It can be either - /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). - /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined by - /// `T::KeyLimit`. - /// - `value`: The value of the attribute. It should be a vector of bytes within the limits defined by - /// `T::ValueLimit`. + /// Sets the attribute of an item or a collection without performing deposit checks. + /// + /// This function is used to force-set an attribute for an item or a collection without + /// performing the deposit checks. It bypasses the deposit requirement and should only be used + /// in specific situations where deposit checks are not necessary or handled separately. + /// + /// - `set_as`: The account that the attribute should be set as. + /// - `collection`: The identifier of the collection to which the item belongs, or the + /// collection + /// itself if setting a collection attribute. + /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if + /// setting + /// a collection attribute. + /// - `namespace`: The namespace in which the attribute is being set. It can be either + /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined + /// by + /// `T::KeyLimit`. + /// - `value`: The value of the attribute. It should be a vector of bytes within the limits + /// defined by + /// `T::ValueLimit`. pub(crate) fn do_force_set_attribute( set_as: Option, collection: T::CollectionId, @@ -203,16 +211,17 @@ impl, I: 'static> Pallet { } /// Sets multiple attributes for an item or a collection in a single transaction. - /// - /// This function allows setting multiple attributes for an item or a collection at once. It is - /// intended to be used with pre-signed transactions for off-chain mints. The `signer` account must - /// have the `ItemOwner` or `Account` namespace permission, depending on the `namespace` provided - /// for each attribute. The transaction must be signed with the `signer` account's key. It is limited - /// by `T::MaxAttributesPerCall` to prevent excessive storage consumption in a single transaction. - /// - /// - `origin`: The account initiating the transaction. - /// - `data`: The data containing the details of the pre-signed attributes to be set. - /// - `signer`: The account of the pre-signed attributes signer. + /// + /// This function allows setting multiple attributes for an item or a collection at once. It is + /// intended to be used with pre-signed transactions for off-chain mints. The `signer` account + /// must have the `ItemOwner` or `Account` namespace permission, depending on the `namespace` + /// provided for each attribute. The transaction must be signed with the `signer` account's key. + /// It is limited by `T::MaxAttributesPerCall` to prevent excessive storage consumption in a + /// single transaction. + /// + /// - `origin`: The account initiating the transaction. + /// - `data`: The data containing the details of the pre-signed attributes to be set. + /// - `signer`: The account of the pre-signed attributes signer. pub(crate) fn do_set_attributes_pre_signed( origin: T::AccountId, data: PreSignedAttributesOf, @@ -266,23 +275,27 @@ impl, I: 'static> Pallet { Ok(()) } - /// Clears an attribute of an item or a collection. - /// - /// This function allows clearing an attribute from an item or a collection. It verifies the - /// permission of the caller to perform the action based on the provided `namespace` and `depositor` - /// account. The deposit associated with the attribute, if any, will be unreserved or moved to the - /// collection owner's deposit based on the deposit settings and the attribute namespace. - /// - /// - `maybe_check_origin`: An optional account that acts as an additional security check when - /// clearing the attribute. This can be `None` if no additional check is required. - /// - `collection`: The identifier of the collection to which the item belongs, or the collection - /// itself if clearing a collection attribute. - /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if clearing - /// a collection attribute. - /// - `namespace`: The namespace in which the attribute is being cleared. It can be either - /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). - /// - `key`: The key of the attribute to be cleared. It should be a vector of bytes within the limits - /// defined by `T::KeyLimit`. + /// Clears an attribute of an item or a collection. + /// + /// This function allows clearing an attribute from an item or a collection. It verifies the + /// permission of the caller to perform the action based on the provided `namespace` and + /// `depositor` account. The deposit associated with the attribute, if any, will be unreserved + /// or moved to the collection owner's deposit based on the deposit settings and the attribute + /// namespace. + /// + /// - `maybe_check_origin`: An optional account that acts as an additional security check when + /// clearing the attribute. This can be `None` if no additional check is required. + /// - `collection`: The identifier of the collection to which the item belongs, or the + /// collection + /// itself if clearing a collection attribute. + /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if + /// clearing + /// a collection attribute. + /// - `namespace`: The namespace in which the attribute is being cleared. It can be either + /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// - `key`: The key of the attribute to be cleared. It should be a vector of bytes within the + /// limits + /// defined by `T::KeyLimit`. pub(crate) fn do_clear_attribute( maybe_check_origin: Option, collection: T::CollectionId, @@ -359,17 +372,18 @@ impl, I: 'static> Pallet { Ok(()) } - /// Approves a delegate to set attributes on behalf of the item's owner. - /// - /// This function allows the owner of an item to approve a delegate to set attributes on their - /// behalf. The delegate must have the account namespace permission, and the item must belong to - /// the specified `collection`. The maximum number of approvals is determined by the configuration - /// `T::MaxAttributesApprovals`. - /// - /// - `check_origin`: The account of the item's owner attempting to approve the delegate. - /// - `collection`: The identifier of the collection to which the item belongs. - /// - `item`: The identifier of the item for which the delegate is being approved. - /// - `delegate`: The account that is being approved to set attributes on behalf of the item's owner. + /// Approves a delegate to set attributes on behalf of the item's owner. + /// + /// This function allows the owner of an item to approve a delegate to set attributes on their + /// behalf. The delegate must have the account namespace permission, and the item must belong to + /// the specified `collection`. The maximum number of approvals is determined by the + /// configuration `T::MaxAttributesApprovals`. + /// + /// - `check_origin`: The account of the item's owner attempting to approve the delegate. + /// - `collection`: The identifier of the collection to which the item belongs. + /// - `item`: The identifier of the item for which the delegate is being approved. + /// - `delegate`: The account that is being approved to set attributes on behalf of the item's + /// owner. pub(crate) fn do_approve_item_attributes( check_origin: T::AccountId, collection: T::CollectionId, @@ -395,18 +409,20 @@ impl, I: 'static> Pallet { } /// Cancels the approval of an item's attributes by a delegate. - /// - /// This function allows the owner of an item to cancel the approval of a delegate to set attributes - /// on their behalf. The delegate's approval is removed, and any unreserved deposit associated with - /// their approved attributes is returned to them. The number of attributes that the delegate has set - /// for the item must not exceed the `account_attributes` provided in the `witness`. This function is - /// used to prevent unintended or malicious cancellations. - /// - /// - `check_origin`: The account of the item's owner attempting to cancel the delegate's approval. - /// - `collection`: The identifier of the collection to which the item belongs. - /// - `item`: The identifier of the item for which the delegate's approval is being canceled. - /// - `delegate`: The account whose approval is being canceled. - /// - `witness`: The witness containing the number of attributes set by the delegate for the item. + /// + /// This function allows the owner of an item to cancel the approval of a delegate to set + /// attributes on their behalf. The delegate's approval is removed, and any unreserved deposit + /// associated with their approved attributes is returned to them. The number of attributes that + /// the delegate has set for the item must not exceed the `account_attributes` provided in the + /// `witness`. This function is used to prevent unintended or malicious cancellations. + /// + /// - `check_origin`: The account of the item's owner attempting to cancel the delegate's + /// approval. + /// - `collection`: The identifier of the collection to which the item belongs. + /// - `item`: The identifier of the item for which the delegate's approval is being canceled. + /// - `delegate`: The account whose approval is being canceled. + /// - `witness`: The witness containing the number of attributes set by the delegate for the + /// item. pub(crate) fn do_cancel_item_attributes_approval( check_origin: T::AccountId, collection: T::CollectionId, diff --git a/frame/nfts/src/features/buy_sell.rs b/frame/nfts/src/features/buy_sell.rs index d59cd6c27fcc1..81a453f71c8d5 100644 --- a/frame/nfts/src/features/buy_sell.rs +++ b/frame/nfts/src/features/buy_sell.rs @@ -15,7 +15,8 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module contains helper functions to perform the buy and sell functionalities of the NFTs pallet. +//! This module contains helper functions to perform the buy and sell functionalities of the NFTs +//! pallet. use crate::*; use frame_support::{ @@ -27,13 +28,13 @@ impl, I: 'static> Pallet { /// Pays the specified tips to the corresponding receivers. /// /// This function is used to pay tips from the `sender` account to multiple receivers. The tips - /// are specified as a `BoundedVec` of `ItemTipOf` with a maximum length of `T::MaxTips`. For each - /// tip, the function transfers the `amount` to the `receiver` account. The sender is responsible - /// for ensuring the validity of the provided tips. + /// are specified as a `BoundedVec` of `ItemTipOf` with a maximum length of `T::MaxTips`. For + /// each tip, the function transfers the `amount` to the `receiver` account. The sender is + /// responsible for ensuring the validity of the provided tips. /// /// - `sender`: The account that pays the tips. /// - `tips`: A `BoundedVec` containing the tips to be paid, where each tip contains the - /// `collection`, `item`, `receiver`, and `amount`. + /// `collection`, `item`, `receiver`, and `amount`. pub(crate) fn do_pay_tips( sender: T::AccountId, tips: BoundedVec, T::MaxTips>, @@ -54,16 +55,18 @@ impl, I: 'static> Pallet { /// Sets the price and whitelist information for an item in the specified collection. /// - /// This function is used to set the price and whitelist information for an item in the specified - /// `collection`. The `sender` account must be the owner of the item. The item's price and - /// whitelist information can be set to allow trading the item. If `price` is `None`, the item will - /// be marked as not for sale. + /// This function is used to set the price and whitelist information for an item in the + /// specified `collection`. The `sender` account must be the owner of the item. The item's price + /// and whitelist information can be set to allow trading the item. If `price` is `None`, the + /// item will be marked as not for sale. /// /// - `collection`: The identifier of the collection containing the item. - /// - `item`: The identifier of the item for which the price and whitelist information will be set. + /// - `item`: The identifier of the item for which the price and whitelist information will be + /// set. /// - `sender`: The account that sets the price and whitelist information for the item. /// - `price`: The optional price for the item. - /// - `whitelisted_buyer`: The optional account that is whitelisted to buy the item at the set price. + /// - `whitelisted_buyer`: The optional account that is whitelisted to buy the item at the set + /// price. pub(crate) fn do_set_price( collection: T::CollectionId, item: T::ItemId, @@ -109,11 +112,12 @@ impl, I: 'static> Pallet { /// Buys the specified item from the collection. /// - /// This function is used to buy an item from the specified `collection`. The `buyer` account will - /// attempt to buy the item with the provided `bid_price`. The item's current owner will receive - /// the bid price if it is equal to or higher than the item's set price. If `whitelisted_buyer` is - /// specified in the item's price information, only that account is allowed to buy the item. If the - /// item is not for sale, or the bid price is too low, the function will return an error. + /// This function is used to buy an item from the specified `collection`. The `buyer` account + /// will attempt to buy the item with the provided `bid_price`. The item's current owner will + /// receive the bid price if it is equal to or higher than the item's set price. If + /// `whitelisted_buyer` is specified in the item's price information, only that account is + /// allowed to buy the item. If the item is not for sale, or the bid price is too low, the + /// function will return an error. /// /// - `collection`: The identifier of the collection containing the item to be bought. /// - `item`: The identifier of the item to be bought. diff --git a/frame/nfts/src/features/create_delete_collection.rs b/frame/nfts/src/features/create_delete_collection.rs index fb0532128c74a..c5d6d2e1530a2 100644 --- a/frame/nfts/src/features/create_delete_collection.rs +++ b/frame/nfts/src/features/create_delete_collection.rs @@ -15,7 +15,8 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module contains helper methods to perform functionality associated with creating and destroying collections for the NFTs pallet. +//! This module contains helper methods to perform functionality associated with creating and +//! destroying collections for the NFTs pallet. use crate::*; use frame_support::pallet_prelude::*; diff --git a/frame/nfts/src/features/create_delete_item.rs b/frame/nfts/src/features/create_delete_item.rs index 023ae32743b23..b80c954b24022 100644 --- a/frame/nfts/src/features/create_delete_item.rs +++ b/frame/nfts/src/features/create_delete_item.rs @@ -15,29 +15,30 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module contains helper methods to perform functionality associated with minting and burning items for the NFTs pallet. +//! This module contains helper methods to perform functionality associated with minting and burning +//! items for the NFTs pallet. use crate::*; use frame_support::{pallet_prelude::*, traits::ExistenceRequirement}; impl, I: 'static> Pallet { /// Mints a new item in the specified collection and assigns it to the `mint_to` account. - /// - /// This function is used to mint a new item in the specified `collection` and assign it to the - /// `mint_to` account. The minting process involves creating the item, setting its attributes and - /// metadata, and reserving the required deposit amount from the `mint_to` account. The minting - /// process is configurable through the provided `item_config` parameter. The `with_details_and_config` - /// closure is called to validate the provided `collection_details` and `collection_config` before - /// minting the item. - /// - /// - `collection`: The collection ID in which the item is minted. - /// - `item`: The ID of the newly minted item. - /// - `maybe_depositor`: The optional account that deposits the required amount for the item. - /// - `mint_to`: The account that receives the newly minted item. - /// - `item_config`: The configuration settings for the newly minted item. - /// - `with_details_and_config`: A closure to perform custom validation for minting the item. It - /// is called with the `collection_details` and `collection_config`, allowing custom checks to - /// be performed. + /// + /// This function is used to mint a new item in the specified `collection` and assign it to the + /// `mint_to` account. The minting process involves creating the item, setting its attributes + /// and metadata, and reserving the required deposit amount from the `mint_to` account. The + /// minting process is configurable through the provided `item_config` parameter. The + /// `with_details_and_config` closure is called to validate the provided `collection_details` + /// and `collection_config` before minting the item. + /// + /// - `collection`: The collection ID in which the item is minted. + /// - `item`: The ID of the newly minted item. + /// - `maybe_depositor`: The optional account that deposits the required amount for the item. + /// - `mint_to`: The account that receives the newly minted item. + /// - `item_config`: The configuration settings for the newly minted item. + /// - `with_details_and_config`: A closure to perform custom validation for minting the item. It + /// is called with the `collection_details` and `collection_config`, allowing custom checks to + /// be performed. pub fn do_mint( collection: T::CollectionId, item: T::ItemId, @@ -105,19 +106,19 @@ impl, I: 'static> Pallet { Ok(()) } - /// Mints a new item using a pre-signed message. - /// - /// This function allows minting a new item using a pre-signed message. The minting process is - /// similar to the regular minting process, but it is performed by a pre-authorized account. The - /// `mint_to` account receives the newly minted item. The minting process is configurable through - /// the provided `mint_data`. The attributes, metadata, and price of the item are set according to - /// the provided `mint_data`. The `with_details_and_config` closure is called to validate the - /// provided `collection_details` and `collection_config` before minting the item. - /// - /// - `mint_to`: The account that receives the newly minted item. - /// - `mint_data`: The pre-signed minting data containing the `collection`, `item`, `attributes`, - /// `metadata`, `deadline`, `only_account`, and `mint_price`. - /// - `signer`: The account that is authorized to mint the item using the pre-signed message. + /// Mints a new item using a pre-signed message. + /// + /// This function allows minting a new item using a pre-signed message. The minting process is + /// similar to the regular minting process, but it is performed by a pre-authorized account. The + /// `mint_to` account receives the newly minted item. The minting process is configurable + /// through the provided `mint_data`. The attributes, metadata, and price of the item are set + /// according to the provided `mint_data`. The `with_details_and_config` closure is called to + /// validate the provided `collection_details` and `collection_config` before minting the item. + /// + /// - `mint_to`: The account that receives the newly minted item. + /// - `mint_data`: The pre-signed minting data containing the `collection`, `item`, + /// `attributes`, `metadata`, `deadline`, `only_account`, and `mint_price`. + /// - `signer`: The account that is authorized to mint the item using the pre-signed message. pub(crate) fn do_mint_pre_signed( mint_to: T::AccountId, mint_data: PreSignedMintOf, @@ -195,16 +196,16 @@ impl, I: 'static> Pallet { Ok(()) } - /// Burns the specified item from the collection. - /// - /// This function burns the specified `item` from the specified `collection`. The item's owner - /// can call this function to remove the item permanently from the collection. Any associated - /// deposit and metadata will be cleared from the item. Custom logic can be executed using the - /// `with_details` closure to perform additional checks or actions before burning the item. - /// - /// - `collection`: The ID of the collection from which the item will be burned. - /// - `item`: The ID of the item to be burned. - /// - `with_details`: A closure to perform custom validation or actions before burning the item. + /// Burns the specified item from the collection. + /// + /// This function burns the specified `item` from the specified `collection`. The item's owner + /// can call this function to remove the item permanently from the collection. Any associated + /// deposit and metadata will be cleared from the item. Custom logic can be executed using the + /// `with_details` closure to perform additional checks or actions before burning the item. + /// + /// - `collection`: The ID of the collection from which the item will be burned. + /// - `item`: The ID of the item to be burned. + /// - `with_details`: A closure to perform custom validation or actions before burning the item. pub fn do_burn( collection: T::CollectionId, item: T::ItemId, diff --git a/frame/nfts/src/features/lock.rs b/frame/nfts/src/features/lock.rs index 7e88141e4f1f4..b97819e68faf9 100644 --- a/frame/nfts/src/features/lock.rs +++ b/frame/nfts/src/features/lock.rs @@ -15,7 +15,8 @@ // See the License for the specific language governing permissions and // limitations under the License. -//! This module contains helper methods to configure locks on collections and items for the NFTs pallet. +//! This module contains helper methods to configure locks on collections and items for the NFTs +//! pallet. use crate::*; use frame_support::pallet_prelude::*; @@ -55,9 +56,9 @@ impl, I: 'static> Pallet { /// Locks the transfer of an item within a collection. /// - /// The origin must have the `Freezer` role within the collection to lock the transfer of the item. - /// This function disables the `Transferable` setting on the item, preventing it from being - /// transferred to other accounts. + /// The origin must have the `Freezer` role within the collection to lock the transfer of the + /// item. This function disables the `Transferable` setting on the item, preventing it from + /// being transferred to other accounts. /// /// - `origin`: The origin of the transaction, representing the account attempting to lock /// the item transfer. @@ -85,9 +86,9 @@ impl, I: 'static> Pallet { /// Unlocks the transfer of an item within a collection. /// - /// The origin must have the `Freezer` role within the collection to unlock the transfer of the item. - /// This function enables the `Transferable` setting on the item, allowing it to be transferred - /// to other accounts. + /// The origin must have the `Freezer` role within the collection to unlock the transfer of the + /// item. This function enables the `Transferable` setting on the item, allowing it to be + /// transferred to other accounts. /// /// - `origin`: The origin of the transaction, representing the account attempting to unlock /// the item transfer. @@ -115,9 +116,10 @@ impl, I: 'static> Pallet { /// Locks the metadata and attributes of an item within a collection. /// - /// The origin must have the `Admin` role within the collection to lock the metadata and attributes - /// of the item. This function disables the `UnlockedMetadata` and `UnlockedAttributes` settings on - /// the item, preventing modifications to its metadata and attributes. + /// The origin must have the `Admin` role within the collection to lock the metadata and + /// attributes of the item. This function disables the `UnlockedMetadata` and + /// `UnlockedAttributes` settings on the item, preventing modifications to its metadata and + /// attributes. /// /// - `maybe_check_origin`: An optional origin representing the account attempting to lock the /// item properties. If provided, this account must have the `Admin` role within the collection. diff --git a/frame/nfts/src/features/metadata.rs b/frame/nfts/src/features/metadata.rs index f3684ff91f4fd..4c7066258bba5 100644 --- a/frame/nfts/src/features/metadata.rs +++ b/frame/nfts/src/features/metadata.rs @@ -23,11 +23,13 @@ use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { /// Sets the metadata for a specific item within a collection. /// - /// - `maybe_check_origin`: An optional account ID that is allowed to set the metadata. If `None`, it's considered the root account. + /// - `maybe_check_origin`: An optional account ID that is allowed to set the metadata. If + /// `None`, it's considered the root account. /// - `collection`: The ID of the collection to which the item belongs. /// - `item`: The ID of the item to set the metadata for. /// - `data`: The metadata to set for the item. - /// - `maybe_depositor`: An optional account ID that will provide the deposit for the metadata. If `None`, the collection's owner provides the deposit. + /// - `maybe_depositor`: An optional account ID that will provide the deposit for the metadata. + /// If `None`, the collection's owner provides the deposit. /// /// Emits `ItemMetadataSet` event upon successful setting of the metadata. /// Returns `Ok(())` on success, or one of the following dispatch errors: @@ -109,7 +111,8 @@ impl, I: 'static> Pallet { /// Clears the metadata for a specific item within a collection. /// - /// - `maybe_check_origin`: An optional account ID that is allowed to clear the metadata. If `None`, it's considered the root account. + /// - `maybe_check_origin`: An optional account ID that is allowed to clear the metadata. If + /// `None`, it's considered the root account. /// - `collection`: The ID of the collection to which the item belongs. /// - `item`: The ID of the item for which to clear the metadata. /// @@ -161,14 +164,16 @@ impl, I: 'static> Pallet { /// Sets the metadata for a specific collection. /// - /// - `maybe_check_origin`: An optional account ID that is allowed to set the collection metadata. If `None`, it's considered the root account. + /// - `maybe_check_origin`: An optional account ID that is allowed to set the collection + /// metadata. If `None`, it's considered the root account. /// - `collection`: The ID of the collection for which to set the metadata. /// - `data`: The metadata to set for the collection. /// /// Emits `CollectionMetadataSet` event upon successful setting of the metadata. /// Returns `Ok(())` on success, or one of the following dispatch errors: /// - `UnknownCollection`: The specified collection does not exist. - /// - `LockedCollectionMetadata`: The metadata for the collection is locked and cannot be modified. + /// - `LockedCollectionMetadata`: The metadata for the collection is locked and cannot be + /// modified. /// - `NoPermission`: The caller does not have the required permission to set the metadata. pub(crate) fn do_set_collection_metadata( maybe_check_origin: Option, @@ -220,14 +225,16 @@ impl, I: 'static> Pallet { /// Clears the metadata for a specific collection. /// - /// - `maybe_check_origin`: An optional account ID that is allowed to clear the collection metadata. If `None`, it's considered the root account. + /// - `maybe_check_origin`: An optional account ID that is allowed to clear the collection + /// metadata. If `None`, it's considered the root account. /// - `collection`: The ID of the collection for which to clear the metadata. /// /// Emits `CollectionMetadataCleared` event upon successful clearing of the metadata. /// Returns `Ok(())` on success, or one of the following dispatch errors: /// - `UnknownCollection`: The specified collection does not exist. /// - `MetadataNotFound`: The metadata for the collection was not found. - /// - `LockedCollectionMetadata`: The metadata for the collection is locked and cannot be modified. + /// - `LockedCollectionMetadata`: The metadata for the collection is locked and cannot be + /// modified. /// - `NoPermission`: The caller does not have the required permission to clear the metadata. pub(crate) fn do_clear_collection_metadata( maybe_check_origin: Option, @@ -262,7 +269,7 @@ impl, I: 'static> Pallet { /// /// - `metadata`: A vector of bytes representing the metadata. /// - /// Returns `Ok(BoundedVec)` on successful construction, or `Error::IncorrectMetadata` + /// Returns `Ok(BoundedVec)` on successful construction, or `Error::IncorrectMetadata` /// if the metadata length exceeds the allowed limit. pub fn construct_metadata( metadata: Vec, diff --git a/frame/nfts/src/features/roles.rs b/frame/nfts/src/features/roles.rs index 37054890e43c4..23902571b8e98 100644 --- a/frame/nfts/src/features/roles.rs +++ b/frame/nfts/src/features/roles.rs @@ -22,17 +22,19 @@ use frame_support::pallet_prelude::*; use sp_std::collections::btree_map::BTreeMap; impl, I: 'static> Pallet { - /// Set the team roles for a specific collection. - /// - /// - `maybe_check_owner`: An optional account ID used to check ownership permission. If `None`, it is considered as the root. - /// - `collection`: The ID of the collection for which to set the team roles. - /// - `issuer`: An optional account ID representing the issuer role. - /// - `admin`: An optional account ID representing the admin role. - /// - `freezer`: An optional account ID representing the freezer role. - /// - /// This function allows the owner or the root (when `maybe_check_owner` is `None`) to set the team roles - /// for a specific collection. The root can change the role from `None` to `Some(account)`, but other roles - /// can only be updated by the root or an account with an existing role in the collection. + /// Set the team roles for a specific collection. + /// + /// - `maybe_check_owner`: An optional account ID used to check ownership permission. If `None`, + /// it is considered as the root. + /// - `collection`: The ID of the collection for which to set the team roles. + /// - `issuer`: An optional account ID representing the issuer role. + /// - `admin`: An optional account ID representing the admin role. + /// - `freezer`: An optional account ID representing the freezer role. + /// + /// This function allows the owner or the root (when `maybe_check_owner` is `None`) to set the + /// team roles for a specific collection. The root can change the role from `None` to + /// `Some(account)`, but other roles can only be updated by the root or an account with an + /// existing role in the collection. pub(crate) fn do_set_team( maybe_check_owner: Option, collection: T::CollectionId, @@ -89,8 +91,9 @@ impl, I: 'static> Pallet { /// /// - `collection_id`: A collection to clear the roles in. /// - /// This function clears all the roles associated with the given `collection_id`. It throws an error - /// if some of the roles were left in storage, indicating that the maximum number of roles may need to be adjusted. + /// This function clears all the roles associated with the given `collection_id`. It throws an + /// error if some of the roles were left in storage, indicating that the maximum number of roles + /// may need to be adjusted. pub(crate) fn clear_roles(collection_id: &T::CollectionId) -> Result<(), DispatchError> { let res = CollectionRoleOf::::clear_prefix( &collection_id, @@ -107,7 +110,7 @@ impl, I: 'static> Pallet { /// - `account_id`: An account to check the role for. /// - `role`: A role to validate. /// - /// Returns `true` if the account has the specified role, `false` otherwise. + /// Returns `true` if the account has the specified role, `false` otherwise. pub(crate) fn has_role( collection_id: &T::CollectionId, account_id: &T::AccountId, @@ -136,7 +139,7 @@ impl, I: 'static> Pallet { /// /// - `input`: A vector of (Account, Role) tuples. /// - /// Returns a grouped vector of (Account, Roles) tuples. + /// Returns a grouped vector of (Account, Roles) tuples. pub fn group_roles_by_account( input: Vec<(T::AccountId, CollectionRole)>, ) -> Vec<(T::AccountId, CollectionRoles)> { diff --git a/frame/nfts/src/features/settings.rs b/frame/nfts/src/features/settings.rs index 468b57c8b69d5..d4f7533ffa4eb 100644 --- a/frame/nfts/src/features/settings.rs +++ b/frame/nfts/src/features/settings.rs @@ -22,12 +22,12 @@ use frame_support::pallet_prelude::*; impl, I: 'static> Pallet { /// Forcefully change the configuration of a collection. - /// - /// - `collection`: The ID of the collection for which to update the configuration. - /// - `config`: The new collection configuration to set. - /// - /// This function allows for changing the configuration of a collection without any checks. - /// It updates the collection configuration and emits a `CollectionConfigChanged` event. + /// + /// - `collection`: The ID of the collection for which to update the configuration. + /// - `config`: The new collection configuration to set. + /// + /// This function allows for changing the configuration of a collection without any checks. + /// It updates the collection configuration and emits a `CollectionConfigChanged` event. pub(crate) fn do_force_collection_config( collection: T::CollectionId, config: CollectionConfigFor, @@ -38,22 +38,22 @@ impl, I: 'static> Pallet { Ok(()) } - /// Set the maximum supply for a collection. - /// - /// - `maybe_check_owner`: An optional account ID used to check permissions. - /// - `collection`: The ID of the collection for which to set the maximum supply. - /// - `max_supply`: The new maximum supply to set for the collection. - /// - /// This function checks if the setting `UnlockedMaxSupply` is enabled in the collection - /// configuration. If it is not enabled, it returns an `Error::MaxSupplyLocked`. If - /// `maybe_check_owner` is `Some(owner)`, it checks if the caller of the function is the - /// owner of the collection. If the caller is not the owner and the `maybe_check_owner` + /// Set the maximum supply for a collection. + /// + /// - `maybe_check_owner`: An optional account ID used to check permissions. + /// - `collection`: The ID of the collection for which to set the maximum supply. + /// - `max_supply`: The new maximum supply to set for the collection. + /// + /// This function checks if the setting `UnlockedMaxSupply` is enabled in the collection + /// configuration. If it is not enabled, it returns an `Error::MaxSupplyLocked`. If + /// `maybe_check_owner` is `Some(owner)`, it checks if the caller of the function is the + /// owner of the collection. If the caller is not the owner and the `maybe_check_owner` /// parameter is provided, it returns an `Error::NoPermission`. /// - /// It also checks if the new maximum supply is greater than the current number of items in - /// the collection, and if not, it returns an `Error::MaxSupplyTooSmall`. If all checks pass, - /// it updates the collection configuration with the new maximum supply and emits a - /// `CollectionMaxSupplySet` event. + /// It also checks if the new maximum supply is greater than the current number of items in + /// the collection, and if not, it returns an `Error::MaxSupplyTooSmall`. If all checks pass, + /// it updates the collection configuration with the new maximum supply and emits a + /// `CollectionMaxSupplySet` event. pub(crate) fn do_set_collection_max_supply( maybe_check_owner: Option, collection: T::CollectionId, @@ -81,18 +81,18 @@ impl, I: 'static> Pallet { }) } - /// Update the mint settings for a collection. - /// - /// - `maybe_check_origin`: An optional account ID used to check issuer permissions. - /// - `collection`: The ID of the collection for which to update the mint settings. - /// - `mint_settings`: The new mint settings to set for the collection. - /// - /// This function updates the mint settings for a collection. If `maybe_check_origin` is - /// `Some(origin)`, it checks if the caller of the function has the `CollectionRole::Issuer` - /// for the given collection. If the caller doesn't have the required permission and - /// `maybe_check_origin` is provided, it returns an `Error::NoPermission`. If all checks - /// pass, it updates the collection configuration with the new mint settings and emits a - /// `CollectionMintSettingsUpdated` event. + /// Update the mint settings for a collection. + /// + /// - `maybe_check_origin`: An optional account ID used to check issuer permissions. + /// - `collection`: The ID of the collection for which to update the mint settings. + /// - `mint_settings`: The new mint settings to set for the collection. + /// + /// This function updates the mint settings for a collection. If `maybe_check_origin` is + /// `Some(origin)`, it checks if the caller of the function has the `CollectionRole::Issuer` + /// for the given collection. If the caller doesn't have the required permission and + /// `maybe_check_origin` is provided, it returns an `Error::NoPermission`. If all checks + /// pass, it updates the collection configuration with the new mint settings and emits a + /// `CollectionMintSettingsUpdated` event. pub(crate) fn do_update_mint_settings( maybe_check_origin: Option, collection: T::CollectionId, @@ -118,12 +118,12 @@ impl, I: 'static> Pallet { } /// Get the configuration for a specific collection. - /// - /// - `collection_id`: The ID of the collection for which to retrieve the configuration. - /// - /// This function attempts to fetch the configuration (`CollectionConfigFor`) associated - /// with the given `collection_id`. If the configuration exists, it returns `Ok(config)`, - /// otherwise, it returns a `DispatchError` with `Error::NoConfig`. + /// + /// - `collection_id`: The ID of the collection for which to retrieve the configuration. + /// + /// This function attempts to fetch the configuration (`CollectionConfigFor`) associated + /// with the given `collection_id`. If the configuration exists, it returns `Ok(config)`, + /// otherwise, it returns a `DispatchError` with `Error::NoConfig`. pub(crate) fn get_collection_config( collection_id: &T::CollectionId, ) -> Result, DispatchError> { @@ -133,13 +133,13 @@ impl, I: 'static> Pallet { } /// Get the configuration for a specific item within a collection. - /// - /// - `collection_id`: The ID of the collection to which the item belongs. - /// - `item_id`: The ID of the item for which to retrieve the configuration. - /// - /// This function attempts to fetch the configuration (`ItemConfig`) associated with the given - /// `collection_id` and `item_id`. If the configuration exists, it returns `Ok(config)`, - /// otherwise, it returns a `DispatchError` with `Error::UnknownItem`. + /// + /// - `collection_id`: The ID of the collection to which the item belongs. + /// - `item_id`: The ID of the item for which to retrieve the configuration. + /// + /// This function attempts to fetch the configuration (`ItemConfig`) associated with the given + /// `collection_id` and `item_id`. If the configuration exists, it returns `Ok(config)`, + /// otherwise, it returns a `DispatchError` with `Error::UnknownItem`. pub(crate) fn get_item_config( collection_id: &T::CollectionId, item_id: &T::ItemId, @@ -149,13 +149,13 @@ impl, I: 'static> Pallet { Ok(config) } - /// Get the default item settings for a specific collection. - /// - /// - `collection_id`: The ID of the collection for which to retrieve the default item settings. - /// - /// This function fetches the `default_item_settings` from the collection configuration - /// associated with the given `collection_id`. If the collection configuration exists, it - /// returns `Ok(default_item_settings)`, otherwise, it returns a `DispatchError` with + /// Get the default item settings for a specific collection. + /// + /// - `collection_id`: The ID of the collection for which to retrieve the default item settings. + /// + /// This function fetches the `default_item_settings` from the collection configuration + /// associated with the given `collection_id`. If the collection configuration exists, it + /// returns `Ok(default_item_settings)`, otherwise, it returns a `DispatchError` with /// `Error::NoConfig`. pub(crate) fn get_default_item_settings( collection_id: &T::CollectionId, @@ -164,13 +164,13 @@ impl, I: 'static> Pallet { Ok(collection_config.mint_settings.default_item_settings) } - /// Check if a specified pallet feature is enabled. - /// - /// - `feature`: The feature to check. - /// - /// This function checks if the given `feature` is enabled in the runtime using the - /// pallet's `T::Features::get()` function. It returns `true` if the feature is enabled, - /// otherwise it returns `false`. + /// Check if a specified pallet feature is enabled. + /// + /// - `feature`: The feature to check. + /// + /// This function checks if the given `feature` is enabled in the runtime using the + /// pallet's `T::Features::get()` function. It returns `true` if the feature is enabled, + /// otherwise it returns `false`. pub(crate) fn is_pallet_feature_enabled(feature: PalletFeature) -> bool { let features = T::Features::get(); return features.is_enabled(feature) diff --git a/frame/nfts/src/features/transfer.rs b/frame/nfts/src/features/transfer.rs index 5f6d4a83ad351..22c7be2d9fb22 100644 --- a/frame/nfts/src/features/transfer.rs +++ b/frame/nfts/src/features/transfer.rs @@ -28,7 +28,7 @@ impl, I: 'static> Pallet { /// - `item`: The ID of the NFT to transfer. /// - `dest`: The destination account to which the NFT will be transferred. /// - `with_details`: A closure that provides access to the collection and item details, - /// allowing customization of the transfer process. + /// allowing customization of the transfer process. /// /// This function performs the actual transfer of an NFT to the destination account. /// It checks various conditions like item lock status and transferability settings @@ -42,14 +42,13 @@ impl, I: 'static> Pallet { &mut ItemDetailsFor, ) -> DispatchResult, ) -> DispatchResult { - // Retrieve collection details. let collection_details = Collection::::get(&collection).ok_or(Error::::UnknownCollection)?; - + // Ensure the item is not locked. ensure!(!T::Locker::is_locked(collection, item), Error::::ItemLocked); - + // Ensure the item is not transfer disabled on the system level attribute. ensure!( !Self::has_system_attribute(&collection, &item, PalletAttributes::TransferDisabled)?, @@ -62,21 +61,21 @@ impl, I: 'static> Pallet { collection_config.is_setting_enabled(CollectionSetting::TransferableItems), Error::::ItemsNonTransferable ); - + // Retrieve item config and check if the item is transferable. let item_config = Self::get_item_config(&collection, &item)?; ensure!( item_config.is_setting_enabled(ItemSetting::Transferable), Error::::ItemLocked ); - + // Retrieve the item details. let mut details = Item::::get(&collection, &item).ok_or(Error::::UnknownItem)?; - + // Perform the transfer with custom details using the provided closure. with_details(&collection_details, &mut details)?; - + // Update account ownership information. Account::::remove((&details.owner, &collection, &item)); Account::::insert((&dest, &collection, &item), ()); @@ -87,7 +86,7 @@ impl, I: 'static> Pallet { // would be possible, where the owner can approve their second account before making the // transaction and then claiming the item back. details.approvals.clear(); - + // Update item details. Item::::insert(&collection, &item, &details); ItemPriceOf::::remove(&collection, &item); @@ -117,7 +116,6 @@ impl, I: 'static> Pallet { collection: T::CollectionId, owner: T::AccountId, ) -> DispatchResult { - // Check if the new owner is acceptable based on the collection's acceptance settings. let acceptable_collection = OwnershipAcceptance::::get(&owner); ensure!(acceptable_collection.as_ref() == Some(&collection), Error::::Unaccepted); @@ -125,7 +123,7 @@ impl, I: 'static> Pallet { // Try to retrieve and mutate the collection details. Collection::::try_mutate(collection, |maybe_details| { let details = maybe_details.as_mut().ok_or(Error::::UnknownCollection)?; - // Check if the `origin` is the current owner of the collection. + // Check if the `origin` is the current owner of the collection. ensure!(origin == details.owner, Error::::NoPermission); if details.owner == owner { return Ok(()) @@ -138,14 +136,14 @@ impl, I: 'static> Pallet { details.owner_deposit, Reserved, )?; - + // Update account ownership information. CollectionAccount::::remove(&details.owner, &collection); CollectionAccount::::insert(&owner, &collection, ()); details.owner = owner.clone(); OwnershipAcceptance::::remove(&owner); - + // Emit `OwnerChanged` event. Self::deposit_event(Event::OwnerChanged { collection, new_owner: owner }); Ok(()) @@ -179,7 +177,7 @@ impl, I: 'static> Pallet { } else { OwnershipAcceptance::::remove(&who); } - + // Emit `OwnershipAcceptanceChanged` event. Self::deposit_event(Event::OwnershipAcceptanceChanged { who, maybe_collection }); Ok(()) @@ -197,7 +195,6 @@ impl, I: 'static> Pallet { collection: T::CollectionId, owner: T::AccountId, ) -> DispatchResult { - // Try to retrieve and mutate the collection details. Collection::::try_mutate(collection, |maybe_details| { let details = maybe_details.as_mut().ok_or(Error::::UnknownCollection)?; @@ -217,7 +214,7 @@ impl, I: 'static> Pallet { CollectionAccount::::remove(&details.owner, &collection); CollectionAccount::::insert(&owner, &collection, ()); details.owner = owner.clone(); - + // Emit `OwnerChanged` event. Self::deposit_event(Event::OwnerChanged { collection, new_owner: owner }); Ok(()) diff --git a/frame/nfts/src/lib.rs b/frame/nfts/src/lib.rs index fbcc5fbc85516..73f6676936052 100644 --- a/frame/nfts/src/lib.rs +++ b/frame/nfts/src/lib.rs @@ -37,8 +37,8 @@ pub mod mock; mod tests; mod common_functions; -/// A library providing the feature set of this pallet. It contains modules with helper methods that perform -/// storage updates and checks required by this pallet's dispatchables. +/// A library providing the feature set of this pallet. It contains modules with helper methods that +/// perform storage updates and checks required by this pallet's dispatchables. mod features; mod impl_nonfungibles; mod types; From afe7287c992623066c73805a2b74a41fed6985e8 Mon Sep 17 00:00:00 2001 From: Jegor Sidorenko Date: Tue, 8 Aug 2023 12:27:48 +0200 Subject: [PATCH 20/28] Fix issues with multi-line comments --- frame/nfts/src/features/approvals.rs | 12 ++++----- frame/nfts/src/features/attributes.rs | 39 ++++++++++----------------- frame/nfts/src/features/lock.rs | 17 ++++++------ 3 files changed, 28 insertions(+), 40 deletions(-) diff --git a/frame/nfts/src/features/approvals.rs b/frame/nfts/src/features/approvals.rs index e272cf52e4290..c647b13a68bdd 100644 --- a/frame/nfts/src/features/approvals.rs +++ b/frame/nfts/src/features/approvals.rs @@ -33,8 +33,7 @@ impl, I: 'static> Pallet { /// emits the `TransferApproved` event. /// /// - `maybe_check_origin`: The optional account that is required to be the owner of the item, - /// granting - /// permission to approve the transfer. If `None`, no permission check is performed. + /// granting permission to approve the transfer. If `None`, no permission check is performed. /// - `collection`: The identifier of the collection containing the item to be transferred. /// - `item`: The identifier of the item to be transferred. /// - `delegate`: The account that will be allowed to take control of the item. @@ -93,9 +92,8 @@ impl, I: 'static> Pallet { /// function emits the `ApprovalCancelled` event. /// /// - `maybe_check_origin`: The optional account that is required to be the owner of the item or - /// that the - /// approval is past its deadline, granting permission to cancel the approval. If `None`, no - /// permission check is performed. + /// that the approval is past its deadline, granting permission to cancel the approval. If + /// `None`, no permission check is performed. /// - `collection`: The identifier of the collection containing the item. /// - `item`: The identifier of the item. /// - `delegate`: The account that was previously allowed to take control of the item. @@ -145,8 +143,8 @@ impl, I: 'static> Pallet { /// event. /// /// - `maybe_check_origin`: The optional account that is required to be the owner of the item, - /// granting - /// permission to clear all transfer approvals. If `None`, no permission check is performed. + /// granting permission to clear all transfer approvals. If `None`, no permission check is + /// performed. /// - `collection`: The collection ID containing the item. /// - `item`: The item ID for which transfer approvals will be cleared. pub(crate) fn do_clear_all_transfer_approvals( diff --git a/frame/nfts/src/features/attributes.rs b/frame/nfts/src/features/attributes.rs index 24775ffb30b97..10e88b47f564d 100644 --- a/frame/nfts/src/features/attributes.rs +++ b/frame/nfts/src/features/attributes.rs @@ -30,19 +30,15 @@ impl, I: 'static> Pallet { /// /// - `origin`: The account attempting to set the attribute. /// - `collection`: The identifier of the collection to which the item belongs, or the - /// collection - /// itself if setting a collection attribute. + /// collection itself if setting a collection attribute. /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if - /// setting - /// a collection attribute. + /// setting a collection attribute. /// - `namespace`: The namespace in which the attribute is being set. It can be either - /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined - /// by - /// `T::KeyLimit`. + /// by `T::KeyLimit`. /// - `value`: The value of the attribute. It should be a vector of bytes within the limits - /// defined by - /// `T::ValueLimit`. + /// defined by `T::ValueLimit`. /// - `depositor`: The account that is paying the deposit for the attribute. /// /// Note: For the `CollectionOwner` namespace, the collection must have the `UnlockedAttributes` @@ -166,19 +162,15 @@ impl, I: 'static> Pallet { /// /// - `set_as`: The account that the attribute should be set as. /// - `collection`: The identifier of the collection to which the item belongs, or the - /// collection - /// itself if setting a collection attribute. + /// collection itself if setting a collection attribute. /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if - /// setting - /// a collection attribute. + /// setting a collection attribute. /// - `namespace`: The namespace in which the attribute is being set. It can be either - /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined - /// by - /// `T::KeyLimit`. + /// by `T::KeyLimit`. /// - `value`: The value of the attribute. It should be a vector of bytes within the limits - /// defined by - /// `T::ValueLimit`. + /// defined by `T::ValueLimit`. pub(crate) fn do_force_set_attribute( set_as: Option, collection: T::CollectionId, @@ -286,16 +278,13 @@ impl, I: 'static> Pallet { /// - `maybe_check_origin`: An optional account that acts as an additional security check when /// clearing the attribute. This can be `None` if no additional check is required. /// - `collection`: The identifier of the collection to which the item belongs, or the - /// collection - /// itself if clearing a collection attribute. + /// collection itself if clearing a collection attribute. /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if - /// clearing - /// a collection attribute. + /// clearing a collection attribute. /// - `namespace`: The namespace in which the attribute is being cleared. It can be either - /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). /// - `key`: The key of the attribute to be cleared. It should be a vector of bytes within the - /// limits - /// defined by `T::KeyLimit`. + /// limits defined by `T::KeyLimit`. pub(crate) fn do_clear_attribute( maybe_check_origin: Option, collection: T::CollectionId, diff --git a/frame/nfts/src/features/lock.rs b/frame/nfts/src/features/lock.rs index b97819e68faf9..fb22b039cf015 100644 --- a/frame/nfts/src/features/lock.rs +++ b/frame/nfts/src/features/lock.rs @@ -28,8 +28,8 @@ impl, I: 'static> Pallet { /// settings on the collection, including disabling the `DepositRequired` setting to allow for /// unlocking the collection in the future. /// - /// - `origin`: The origin of the transaction, representing the account attempting to lock - /// the collection. + /// - `origin`: The origin of the transaction, representing the account attempting to lock the + /// collection. /// - `collection`: The identifier of the collection to be locked. /// - `lock_settings`: The collection settings to be locked. pub(crate) fn do_lock_collection( @@ -60,8 +60,8 @@ impl, I: 'static> Pallet { /// item. This function disables the `Transferable` setting on the item, preventing it from /// being transferred to other accounts. /// - /// - `origin`: The origin of the transaction, representing the account attempting to lock - /// the item transfer. + /// - `origin`: The origin of the transaction, representing the account attempting to lock the + /// item transfer. /// - `collection`: The identifier of the collection to which the item belongs. /// - `item`: The identifier of the item to be locked for transfer. pub(crate) fn do_lock_item_transfer( @@ -90,8 +90,8 @@ impl, I: 'static> Pallet { /// item. This function enables the `Transferable` setting on the item, allowing it to be /// transferred to other accounts. /// - /// - `origin`: The origin of the transaction, representing the account attempting to unlock - /// the item transfer. + /// - `origin`: The origin of the transaction, representing the account attempting to unlock the + /// item transfer. /// - `collection`: The identifier of the collection to which the item belongs. /// - `item`: The identifier of the item to be unlocked for transfer. pub(crate) fn do_unlock_item_transfer( @@ -122,8 +122,9 @@ impl, I: 'static> Pallet { /// attributes. /// /// - `maybe_check_origin`: An optional origin representing the account attempting to lock the - /// item properties. If provided, this account must have the `Admin` role within the collection. - /// If `None`, no permission check is performed, and the function can be called from any origin. + /// item properties. If provided, this account must have the `Admin` role within the + /// collection. If `None`, no permission check is performed, and the function can be called + /// from any origin. /// - `collection`: The identifier of the collection to which the item belongs. /// - `item`: The identifier of the item to be locked for properties. /// - `lock_metadata`: A boolean indicating whether to lock the metadata of the item. From a642f359e0ae527ef38d265b026cd3b89fdd24a3 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Mon, 14 Aug 2023 09:10:53 +0200 Subject: [PATCH 21/28] Apply suggestions from code review Co-authored-by: Jegor Sidorenko <5252494+jsidorenko@users.noreply.github.com> --- frame/nfts/src/features/atomic_swap.rs | 3 +- frame/nfts/src/features/attributes.rs | 30 +++++++++---------- frame/nfts/src/features/buy_sell.rs | 6 ++-- frame/nfts/src/features/create_delete_item.rs | 2 +- frame/nfts/src/features/lock.rs | 6 ++-- 5 files changed, 24 insertions(+), 23 deletions(-) diff --git a/frame/nfts/src/features/atomic_swap.rs b/frame/nfts/src/features/atomic_swap.rs index dfd36d1538db8..75f375eb2ead1 100644 --- a/frame/nfts/src/features/atomic_swap.rs +++ b/frame/nfts/src/features/atomic_swap.rs @@ -103,7 +103,8 @@ impl, I: 'static> Pallet { /// /// This function is used to cancel the specified swap offer created by the `caller` account. If /// the swap offer's deadline has not yet passed, the `caller` must be the owner of the offered - /// item. After canceling the swap offer, the function emits the `SwapCancelled` event. + /// item; otherwise, anyone can cancel an expired offer. + /// After canceling the swap offer, the function emits the `SwapCancelled` event. /// /// - `caller`: The account canceling the swap offer. /// - `offered_collection_id`: The collection ID containing the offered item. diff --git a/frame/nfts/src/features/attributes.rs b/frame/nfts/src/features/attributes.rs index 10e88b47f564d..f907790c1a755 100644 --- a/frame/nfts/src/features/attributes.rs +++ b/frame/nfts/src/features/attributes.rs @@ -41,9 +41,9 @@ impl, I: 'static> Pallet { /// defined by `T::ValueLimit`. /// - `depositor`: The account that is paying the deposit for the attribute. /// - /// Note: For the `CollectionOwner` namespace, the collection must have the `UnlockedAttributes` - /// setting enabled. For the `ItemOwner` namespace, the item must not be locked for attributes. - /// For the `Account` namespace, the deposit is required based on the `T::DepositPerByte` and + /// Note: For the `CollectionOwner` namespace, the collection/item must have the `UnlockedAttributes` + /// setting enabled. + /// The deposit for setting an attribute is based on the `T::DepositPerByte` and /// `T::AttributeDepositBase` configuration. pub(crate) fn do_set_attribute( origin: T::AccountId, @@ -271,9 +271,7 @@ impl, I: 'static> Pallet { /// /// This function allows clearing an attribute from an item or a collection. It verifies the /// permission of the caller to perform the action based on the provided `namespace` and - /// `depositor` account. The deposit associated with the attribute, if any, will be unreserved - /// or moved to the collection owner's deposit based on the deposit settings and the attribute - /// namespace. + /// `depositor` account. The deposit associated with the attribute, if any, will be unreserved. /// /// - `maybe_check_origin`: An optional account that acts as an additional security check when /// clearing the attribute. This can be `None` if no additional check is required. @@ -282,7 +280,7 @@ impl, I: 'static> Pallet { /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if /// clearing a collection attribute. /// - `namespace`: The namespace in which the attribute is being cleared. It can be either - /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// `CollectionOwner`, `ItemOwner`, or `Account`. /// - `key`: The key of the attribute to be cleared. It should be a vector of bytes within the /// limits defined by `T::KeyLimit`. pub(crate) fn do_clear_attribute( @@ -363,10 +361,9 @@ impl, I: 'static> Pallet { /// Approves a delegate to set attributes on behalf of the item's owner. /// - /// This function allows the owner of an item to approve a delegate to set attributes on their - /// behalf. The delegate must have the account namespace permission, and the item must belong to - /// the specified `collection`. The maximum number of approvals is determined by the - /// configuration `T::MaxAttributesApprovals`. + /// This function allows the owner of an item to approve a delegate to set attributes in the + /// `Account(delegate)` namespace. The maximum number of approvals is determined by + /// the configuration `T::MaxAttributesApprovals`. /// /// - `check_origin`: The account of the item's owner attempting to approve the delegate. /// - `collection`: The identifier of the collection to which the item belongs. @@ -400,10 +397,11 @@ impl, I: 'static> Pallet { /// Cancels the approval of an item's attributes by a delegate. /// /// This function allows the owner of an item to cancel the approval of a delegate to set - /// attributes on their behalf. The delegate's approval is removed, and any unreserved deposit - /// associated with their approved attributes is returned to them. The number of attributes that - /// the delegate has set for the item must not exceed the `account_attributes` provided in the - /// `witness`. This function is used to prevent unintended or malicious cancellations. + /// attributes in the `Account(delegate)` namespace. The delegate's approval is removed, in + /// addition to attributes the `delegate` previously created, and any unreserved deposit + /// is returned. The number of attributes that the delegate has set for the item must + /// not exceed the `account_attributes` provided in the `witness`. + /// This function is used to prevent unintended or malicious cancellations. /// /// - `check_origin`: The account of the item's owner attempting to cancel the delegate's /// approval. @@ -455,7 +453,7 @@ impl, I: 'static> Pallet { }) } - /// A helper method to check whether a attribute namespace is valid. + /// A helper method to check whether an attribute namespace is valid. fn is_valid_namespace( origin: &T::AccountId, namespace: &AttributeNamespace, diff --git a/frame/nfts/src/features/buy_sell.rs b/frame/nfts/src/features/buy_sell.rs index 81a453f71c8d5..0df90cf6da72b 100644 --- a/frame/nfts/src/features/buy_sell.rs +++ b/frame/nfts/src/features/buy_sell.rs @@ -53,11 +53,11 @@ impl, I: 'static> Pallet { Ok(()) } - /// Sets the price and whitelist information for an item in the specified collection. + /// Sets the price and whitelists a buyer for an item in the specified collection. /// - /// This function is used to set the price and whitelist information for an item in the + /// This function is used to set the price and whitelist a buyer for an item in the /// specified `collection`. The `sender` account must be the owner of the item. The item's price - /// and whitelist information can be set to allow trading the item. If `price` is `None`, the + /// and the whitelisted buyer can be set to allow trading the item. If `price` is `None`, the /// item will be marked as not for sale. /// /// - `collection`: The identifier of the collection containing the item. diff --git a/frame/nfts/src/features/create_delete_item.rs b/frame/nfts/src/features/create_delete_item.rs index b80c954b24022..4f81e5933af49 100644 --- a/frame/nfts/src/features/create_delete_item.rs +++ b/frame/nfts/src/features/create_delete_item.rs @@ -26,7 +26,7 @@ impl, I: 'static> Pallet { /// /// This function is used to mint a new item in the specified `collection` and assign it to the /// `mint_to` account. The minting process involves creating the item, setting its attributes - /// and metadata, and reserving the required deposit amount from the `mint_to` account. The + /// and metadata, and reserving the required deposit amount from the `maybe_depositor` account. The /// minting process is configurable through the provided `item_config` parameter. The /// `with_details_and_config` closure is called to validate the provided `collection_details` /// and `collection_config` before minting the item. diff --git a/frame/nfts/src/features/lock.rs b/frame/nfts/src/features/lock.rs index fb22b039cf015..1c3c9c8672fbd 100644 --- a/frame/nfts/src/features/lock.rs +++ b/frame/nfts/src/features/lock.rs @@ -25,8 +25,10 @@ impl, I: 'static> Pallet { /// Locks a collection with specified settings. /// /// The origin must be the owner of the collection to lock it. This function disables certain - /// settings on the collection, including disabling the `DepositRequired` setting to allow for - /// unlocking the collection in the future. + /// settings on the collection. The only setting that can't be disabled is `DepositRequired`. + /// + /// Note: it's possible only to lock the setting, but not to unlock it after. + /// /// - `origin`: The origin of the transaction, representing the account attempting to lock the /// collection. From 00da3403859c8e13bede4a8f52837f808d6f803d Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Mon, 14 Aug 2023 17:22:16 +0200 Subject: [PATCH 22/28] update from review --- frame/nfts/src/features/attributes.rs | 15 ++++++--------- 1 file changed, 6 insertions(+), 9 deletions(-) diff --git a/frame/nfts/src/features/attributes.rs b/frame/nfts/src/features/attributes.rs index f907790c1a755..aae1d11b0e9c7 100644 --- a/frame/nfts/src/features/attributes.rs +++ b/frame/nfts/src/features/attributes.rs @@ -34,7 +34,7 @@ impl, I: 'static> Pallet { /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if /// setting a collection attribute. /// - `namespace`: The namespace in which the attribute is being set. It can be either - /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// `CollectionOwner`, `ItemOwner`, or `Account` (pre-approved external address). /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined /// by `T::KeyLimit`. /// - `value`: The value of the attribute. It should be a vector of bytes within the limits @@ -166,7 +166,7 @@ impl, I: 'static> Pallet { /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if /// setting a collection attribute. /// - `namespace`: The namespace in which the attribute is being set. It can be either - /// `CollectionOwner`, `ItemOwner`, or `Account` (for off-chain mints). + /// `CollectionOwner`, `ItemOwner`, or `Account` (pre-approved external address). /// - `key`: The key of the attribute. It should be a vector of bytes within the limits defined /// by `T::KeyLimit`. /// - `value`: The value of the attribute. It should be a vector of bytes within the limits @@ -202,14 +202,11 @@ impl, I: 'static> Pallet { Ok(()) } - /// Sets multiple attributes for an item or a collection in a single transaction. + /// Sets multiple attributes for an item or a collection. /// - /// This function allows setting multiple attributes for an item or a collection at once. It is - /// intended to be used with pre-signed transactions for off-chain mints. The `signer` account - /// must have the `ItemOwner` or `Account` namespace permission, depending on the `namespace` - /// provided for each attribute. The transaction must be signed with the `signer` account's key. - /// It is limited by `T::MaxAttributesPerCall` to prevent excessive storage consumption in a - /// single transaction. + /// This function checks the pre-signed data is valid and updates the attributes of an item or + /// collection. It is limited by [`T::MaxAttributesPerCall`] to prevent excessive storage + /// consumption in a single transaction. /// /// - `origin`: The account initiating the transaction. /// - `data`: The data containing the details of the pre-signed attributes to be set. From 02d0d6f9f0c3bf5da0dba5a8c4a163bb3fea2bdc Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Mon, 14 Aug 2023 17:22:26 +0200 Subject: [PATCH 23/28] fmt --- frame/nfts/src/features/attributes.rs | 4 ++-- frame/nfts/src/features/create_delete_item.rs | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/frame/nfts/src/features/attributes.rs b/frame/nfts/src/features/attributes.rs index aae1d11b0e9c7..a6434e609acaa 100644 --- a/frame/nfts/src/features/attributes.rs +++ b/frame/nfts/src/features/attributes.rs @@ -41,8 +41,8 @@ impl, I: 'static> Pallet { /// defined by `T::ValueLimit`. /// - `depositor`: The account that is paying the deposit for the attribute. /// - /// Note: For the `CollectionOwner` namespace, the collection/item must have the `UnlockedAttributes` - /// setting enabled. + /// Note: For the `CollectionOwner` namespace, the collection/item must have the + /// `UnlockedAttributes` setting enabled. /// The deposit for setting an attribute is based on the `T::DepositPerByte` and /// `T::AttributeDepositBase` configuration. pub(crate) fn do_set_attribute( diff --git a/frame/nfts/src/features/create_delete_item.rs b/frame/nfts/src/features/create_delete_item.rs index 4f81e5933af49..6ac50f592b376 100644 --- a/frame/nfts/src/features/create_delete_item.rs +++ b/frame/nfts/src/features/create_delete_item.rs @@ -26,8 +26,8 @@ impl, I: 'static> Pallet { /// /// This function is used to mint a new item in the specified `collection` and assign it to the /// `mint_to` account. The minting process involves creating the item, setting its attributes - /// and metadata, and reserving the required deposit amount from the `maybe_depositor` account. The - /// minting process is configurable through the provided `item_config` parameter. The + /// and metadata, and reserving the required deposit amount from the `maybe_depositor` account. + /// The minting process is configurable through the provided `item_config` parameter. The /// `with_details_and_config` closure is called to validate the provided `collection_details` /// and `collection_config` before minting the item. /// From df687c2e2ac22d5f4ad212d5855638baa90d0c64 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Mon, 14 Aug 2023 17:29:33 +0200 Subject: [PATCH 24/28] update from review --- frame/nfts/src/features/attributes.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frame/nfts/src/features/attributes.rs b/frame/nfts/src/features/attributes.rs index a6434e609acaa..8c2f83b2acc3c 100644 --- a/frame/nfts/src/features/attributes.rs +++ b/frame/nfts/src/features/attributes.rs @@ -160,7 +160,7 @@ impl, I: 'static> Pallet { /// performing the deposit checks. It bypasses the deposit requirement and should only be used /// in specific situations where deposit checks are not necessary or handled separately. /// - /// - `set_as`: The account that the attribute should be set as. + /// - `set_as`: The account that would normally pay for the deposit. /// - `collection`: The identifier of the collection to which the item belongs, or the /// collection itself if setting a collection attribute. /// - `maybe_item`: The identifier of the item to which the attribute belongs, or `None` if From 88ef7495208535ac072efb93bacb80755d5230c7 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Mon, 14 Aug 2023 17:36:14 +0200 Subject: [PATCH 25/28] remove bitflag example --- frame/nfts/src/macros.rs | 36 ------------------------------------ 1 file changed, 36 deletions(-) diff --git a/frame/nfts/src/macros.rs b/frame/nfts/src/macros.rs index b1c6cda00bf09..1a601ce0927fa 100644 --- a/frame/nfts/src/macros.rs +++ b/frame/nfts/src/macros.rs @@ -26,42 +26,6 @@ /// - `EncodeLike`: Trait indicating the type can be encoded as is. /// - `Decode`: Decodes the wrapper type from the input. /// - `TypeInfo`: Provides type information for the wrapper type. -/// -/// # Example -/// -/// ``` -/// # use codec::{Encode, Decode, MaxEncodedLen, TypeInfo}; -/// # use sp_std::prelude::BitFlags; -/// # use sp_core::Bytes; -/// -/// // Assume `MyBitflagEnum` is defined here. -/// # #[derive(Debug, Encode, Decode)] -/// # enum MyBitflagEnum { -/// # A = 0b0001, -/// # B = 0b0010, -/// # C = 0b0100, -/// # D = 0b1000, -/// # } -/// -/// // Define a newtype wrapper to hold the bitflags. -/// #[derive(Debug, Encode, Decode)] -/// struct MyBitflagsWrapper(BitFlags); -/// -/// // Implement the `impl_codec_bitflags` macro for the newtype wrapper. -/// impl_codec_bitflags!(MyBitflagsWrapper, u8, MyBitflagEnum); -/// -/// // Now you can use the `MyBitflagsWrapper` with the codec library for encoding/decoding. -/// let bitflags = MyBitflagsWrapper(BitFlags::from(MyBitflagEnum::A | MyBitflagEnum::C)); -/// let encoded_bytes = bitflags.using_encoded(|bytes| Bytes::from(bytes.to_vec())); -/// -/// // ... do something with `encoded_bytes` ... -/// -/// // Decode the bytes back to the wrapper type. -/// let decoded_bitflags = MyBitflagsWrapper::decode(&mut &encoded_bytes[..]) -/// .expect("Decoding failed"); -/// -/// assert_eq!(decoded_bitflags, bitflags); -/// ``` macro_rules! impl_codec_bitflags { ($wrapper:ty, $size:ty, $bitflag_enum:ty) => { impl MaxEncodedLen for $wrapper { From d0175279f62f00d197059ec1f0abd80df5812444 Mon Sep 17 00:00:00 2001 From: command-bot <> Date: Tue, 15 Aug 2023 10:26:38 +0000 Subject: [PATCH 26/28] ".git/.scripts/commands/fmt/fmt.sh" --- frame/nfts/src/features/transfer.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frame/nfts/src/features/transfer.rs b/frame/nfts/src/features/transfer.rs index ff58d34fa1496..0471bd67b2916 100644 --- a/frame/nfts/src/features/transfer.rs +++ b/frame/nfts/src/features/transfer.rs @@ -33,7 +33,7 @@ impl, I: 'static> Pallet { /// This function performs the actual transfer of an NFT to the destination account. /// It checks various conditions like item lock status and transferability settings /// for the collection and item before transferring the NFT. - /// + /// /// # Errors /// /// This function returns a dispatch error in the following cases: From b4dc0cbcce1ea4fa0818032c4757daaea5a2fbfc Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Tue, 15 Aug 2023 16:00:23 +0200 Subject: [PATCH 27/28] Apply suggestions from code review Co-authored-by: Squirrel --- frame/nfts/src/features/approvals.rs | 2 ++ frame/nfts/src/features/atomic_swap.rs | 2 ++ frame/nfts/src/features/attributes.rs | 4 +++- frame/nfts/src/features/buy_sell.rs | 2 ++ frame/nfts/src/features/roles.rs | 2 +- 5 files changed, 10 insertions(+), 2 deletions(-) diff --git a/frame/nfts/src/features/approvals.rs b/frame/nfts/src/features/approvals.rs index c647b13a68bdd..053fa67163b99 100644 --- a/frame/nfts/src/features/approvals.rs +++ b/frame/nfts/src/features/approvals.rs @@ -16,6 +16,8 @@ // limitations under the License. //! This module contains helper functions for the approval logic implemented in the NFTs pallet. +//! The bitflag [`PalletFeature::Approvals`] needs to be set in [`Config::Features`] for NFTs +//! to have the functionality defined in this module. use crate::*; use frame_support::pallet_prelude::*; diff --git a/frame/nfts/src/features/atomic_swap.rs b/frame/nfts/src/features/atomic_swap.rs index 75f375eb2ead1..830283b73c2aa 100644 --- a/frame/nfts/src/features/atomic_swap.rs +++ b/frame/nfts/src/features/atomic_swap.rs @@ -17,6 +17,8 @@ //! This module contains helper functions for performing atomic swaps implemented in the NFTs //! pallet. +//! The bitflag [`PalletFeature::Swaps`] needs to be set in [`Config::Features`] for NFTs +//! to have the functionality defined in this module. use crate::*; use frame_support::{ diff --git a/frame/nfts/src/features/attributes.rs b/frame/nfts/src/features/attributes.rs index 8a7248d64acae..28f7bd2c58ce7 100644 --- a/frame/nfts/src/features/attributes.rs +++ b/frame/nfts/src/features/attributes.rs @@ -17,6 +17,8 @@ //! This module contains helper methods to configure attributes for items and collections in the //! NFTs pallet. +//! The bitflag [`PalletFeature::Attributes`] needs to be set in [`Config::Features`] for NFTs +//! to have the functionality defined in this module. use crate::*; use frame_support::pallet_prelude::*; @@ -205,7 +207,7 @@ impl, I: 'static> Pallet { /// Sets multiple attributes for an item or a collection. /// /// This function checks the pre-signed data is valid and updates the attributes of an item or - /// collection. It is limited by [`T::MaxAttributesPerCall`] to prevent excessive storage + /// collection. It is limited by [`Config::MaxAttributesPerCall`] to prevent excessive storage /// consumption in a single transaction. /// /// - `origin`: The account initiating the transaction. diff --git a/frame/nfts/src/features/buy_sell.rs b/frame/nfts/src/features/buy_sell.rs index 0df90cf6da72b..d6ec6f50d2724 100644 --- a/frame/nfts/src/features/buy_sell.rs +++ b/frame/nfts/src/features/buy_sell.rs @@ -17,6 +17,8 @@ //! This module contains helper functions to perform the buy and sell functionalities of the NFTs //! pallet. +//! The bitflag [`PalletFeature::Trading`] needs to be set in the [`Config::Features`] for NFTs +//! to have the functionality defined in this module. use crate::*; use frame_support::{ diff --git a/frame/nfts/src/features/roles.rs b/frame/nfts/src/features/roles.rs index 23902571b8e98..f6d2785fd9cb4 100644 --- a/frame/nfts/src/features/roles.rs +++ b/frame/nfts/src/features/roles.rs @@ -139,7 +139,7 @@ impl, I: 'static> Pallet { /// /// - `input`: A vector of (Account, Role) tuples. /// - /// Returns a grouped vector of (Account, Roles) tuples. + /// Returns a grouped vector of `(Account, Roles)` tuples. pub fn group_roles_by_account( input: Vec<(T::AccountId, CollectionRole)>, ) -> Vec<(T::AccountId, CollectionRoles)> { From 876ad7ad5a312085ddc8a462ee6edf6c23f30809 Mon Sep 17 00:00:00 2001 From: Sacha Lansky Date: Wed, 16 Aug 2023 09:25:29 +0200 Subject: [PATCH 28/28] add note about pallet features --- frame/nfts/src/lib.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/frame/nfts/src/lib.rs b/frame/nfts/src/lib.rs index 293e6fc399971..333fe97dd4a1e 100644 --- a/frame/nfts/src/lib.rs +++ b/frame/nfts/src/lib.rs @@ -38,7 +38,9 @@ mod tests; mod common_functions; /// A library providing the feature set of this pallet. It contains modules with helper methods that -/// perform storage updates and checks required by this pallet's dispatchables. +/// perform storage updates and checks required by this pallet's dispatchables. To use pallet level +/// features, make sure to set appropriate bitflags for [`Config::Features`] in your runtime +/// configuration trait. mod features; mod impl_nonfungibles; mod types;