difftreelog
refactor(pallet-unique) switch to #[pallet] macro
in: master
3 files changed
pallets/unique/src/eth/mod.rsdiffbeforeafterboth1// Copyright 2019-2022 Unique Network (Gibraltar) Ltd.2// This file is part of Unique Network.34// Unique Network is free software: you can redistribute it and/or modify5// it under the terms of the GNU General Public License as published by6// the Free Software Foundation, either version 3 of the License, or7// (at your option) any later version.89// Unique Network is distributed in the hope that it will be useful,10// but WITHOUT ANY WARRANTY; without even the implied warranty of11// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the12// GNU General Public License for more details.1314// You should have received a copy of the GNU General Public License15// along with Unique Network. If not, see <http://www.gnu.org/licenses/>.1617//! Implementation of CollectionHelpers contract.1819use core::marker::PhantomData;20use ethereum as _;21use evm_coder::{abi::AbiType, generate_stubgen, solidity_interface, types::*};22use frame_support::traits::Get;23use crate::Pallet;2425use pallet_common::{26 CollectionById,27 dispatch::CollectionDispatch,28 erc::{CollectionHelpersEvents, static_property::key},29 eth::{map_eth_to_id, collection_id_to_address},30 Pallet as PalletCommon,31};32use pallet_evm::{account::CrossAccountId, OnMethodCall, PrecompileHandle, PrecompileResult};33use pallet_evm_coder_substrate::{34 dispatch_to_evm, SubstrateRecorder, WithRecorder,35 execution::{PreDispatch, Result, Error},36 frontier_contract,37};38use up_data_structs::{39 CollectionDescription, CollectionMode, CollectionName, CollectionTokenPrefix,40 CreateCollectionData,41};4243use crate::{weights::WeightInfo, Config, SelfWeightOf};4445use alloc::format;46use sp_std::vec::Vec;4748frontier_contract! {49 macro_rules! EvmCollectionHelpers_result {...}50 impl<T: Config> Contract for EvmCollectionHelpers<T> {...}51}52/// See [`CollectionHelpersCall`]53pub struct EvmCollectionHelpers<T: Config>(SubstrateRecorder<T>);54impl<T: Config> WithRecorder<T> for EvmCollectionHelpers<T> {55 fn recorder(&self) -> &SubstrateRecorder<T> {56 &self.057 }5859 fn into_recorder(self) -> SubstrateRecorder<T> {60 self.061 }62}6364fn convert_data<T: Config>(65 caller: Caller,66 name: String,67 description: String,68 token_prefix: String,69) -> Result<(70 T::CrossAccountId,71 CollectionName,72 CollectionDescription,73 CollectionTokenPrefix,74)> {75 let caller = T::CrossAccountId::from_eth(caller);76 let name = name77 .encode_utf16()78 .collect::<Vec<u16>>()79 .try_into()80 .map_err(|_| error_field_too_long(stringify!(name), CollectionName::bound()))?;81 let description = description82 .encode_utf16()83 .collect::<Vec<u16>>()84 .try_into()85 .map_err(|_| {86 error_field_too_long(stringify!(description), CollectionDescription::bound())87 })?;88 let token_prefix = token_prefix.into_bytes().try_into().map_err(|_| {89 error_field_too_long(stringify!(token_prefix), CollectionTokenPrefix::bound())90 })?;91 Ok((caller, name, description, token_prefix))92}9394#[inline(always)]95fn create_collection_internal<T: Config>(96 caller: Caller,97 value: Value,98 name: String,99 collection_mode: CollectionMode,100 description: String,101 token_prefix: String,102) -> Result<Address> {103 let (caller, name, description, token_prefix) =104 convert_data::<T>(caller, name, description, token_prefix)?;105 let data = CreateCollectionData {106 name,107 mode: collection_mode,108 description,109 token_prefix,110 ..Default::default()111 };112 check_sent_amount_equals_collection_creation_price::<T>(value)?;113 let collection_helpers_address =114 T::CrossAccountId::from_eth(<T as pallet_common::Config>::ContractAddress::get());115116 let collection_id = T::CollectionDispatch::create(117 caller.clone(),118 collection_helpers_address,119 data,120 Default::default(),121 )122 .map_err(pallet_evm_coder_substrate::dispatch_to_evm::<T>)?;123 let address = pallet_common::eth::collection_id_to_address(collection_id);124 Ok(address)125}126127fn check_sent_amount_equals_collection_creation_price<T: Config>(value: Value) -> Result<()> {128 let value = value.as_u128();129 let creation_price: u128 = T::CollectionCreationPrice::get()130 .try_into()131 .map_err(|_| ()) // workaround for `expect` requiring `Debug` trait132 .expect("Collection creation price should be convertible to u128");133 if value != creation_price {134 return Err(format!(135 "Sent amount not equals to collection creation price ({0})",136 creation_price137 )138 .into());139 }140 Ok(())141}142143/// @title Contract, which allows users to operate with collections144#[solidity_interface(name = CollectionHelpers, events(CollectionHelpersEvents), enum(derive(PreDispatch)), enum_attr(weight))]145impl<T> EvmCollectionHelpers<T>146where147 T: Config + pallet_common::Config + pallet_nonfungible::Config + pallet_refungible::Config,148{149 /// Create an NFT collection150 /// @param name Name of the collection151 /// @param description Informative description of the collection152 /// @param tokenPrefix Token prefix to represent the collection tokens in UI and user applications153 /// @return address Address of the newly created collection154 #[weight(<SelfWeightOf<T>>::create_collection())]155 #[solidity(rename_selector = "createNFTCollection")]156 fn create_nft_collection(157 &mut self,158 caller: Caller,159 value: Value,160 name: String,161 description: String,162 token_prefix: String,163 ) -> Result<Address> {164 let (caller, name, description, token_prefix) =165 convert_data::<T>(caller, name, description, token_prefix)?;166 let data = CreateCollectionData {167 name,168 mode: CollectionMode::NFT,169 description,170 token_prefix,171 ..Default::default()172 };173 check_sent_amount_equals_collection_creation_price::<T>(value)?;174 let collection_helpers_address =175 T::CrossAccountId::from_eth(<T as pallet_common::Config>::ContractAddress::get());176 let collection_id = T::CollectionDispatch::create(177 caller,178 collection_helpers_address,179 data,180 Default::default(),181 )182 .map_err(dispatch_to_evm::<T>)?;183184 let address = pallet_common::eth::collection_id_to_address(collection_id);185 Ok(address)186 }187 /// Create an NFT collection188 /// @param name Name of the collection189 /// @param description Informative description of the collection190 /// @param tokenPrefix Token prefix to represent the collection tokens in UI and user applications191 /// @return address Address of the newly created collection192 #[deprecated(note = "mathod was renamed to `create_nft_collection`, prefer it instead")]193 #[solidity(hide)]194 #[weight(<SelfWeightOf<T>>::create_collection())]195 fn create_nonfungible_collection(196 &mut self,197 caller: Caller,198 value: Value,199 name: String,200 description: String,201 token_prefix: String,202 ) -> Result<Address> {203 create_collection_internal::<T>(204 caller,205 value,206 name,207 CollectionMode::NFT,208 description,209 token_prefix,210 )211 }212213 #[weight(<SelfWeightOf<T>>::create_collection())]214 #[solidity(rename_selector = "createRFTCollection")]215 fn create_rft_collection(216 &mut self,217 caller: Caller,218 value: Value,219 name: String,220 description: String,221 token_prefix: String,222 ) -> Result<Address> {223 create_collection_internal::<T>(224 caller,225 value,226 name,227 CollectionMode::ReFungible,228 description,229 token_prefix,230 )231 }232233 #[weight(<SelfWeightOf<T>>::create_collection())]234 #[solidity(rename_selector = "createFTCollection")]235 fn create_fungible_collection(236 &mut self,237 caller: Caller,238 value: Value,239 name: String,240 decimals: u8,241 description: String,242 token_prefix: String,243 ) -> Result<Address> {244 create_collection_internal::<T>(245 caller,246 value,247 name,248 CollectionMode::Fungible(decimals),249 description,250 token_prefix,251 )252 }253254 #[solidity(rename_selector = "makeCollectionERC721MetadataCompatible")]255 fn make_collection_metadata_compatible(256 &mut self,257 caller: Caller,258 collection: Address,259 base_uri: String,260 ) -> Result<()> {261 let caller = T::CrossAccountId::from_eth(caller);262 let collection =263 pallet_common::eth::map_eth_to_id(&collection).ok_or("not a collection address")?;264 let mut collection =265 <crate::CollectionHandle<T>>::new(collection).ok_or("collection not found")?;266267 if !matches!(268 collection.mode,269 CollectionMode::NFT | CollectionMode::ReFungible270 ) {271 return Err("target collection should be either NFT or Refungible".into());272 }273274 self.recorder().consume_sstore()?;275 collection276 .check_is_owner_or_admin(&caller)277 .map_err(dispatch_to_evm::<T>)?;278279 if collection.flags.erc721metadata {280 return Err("target collection is already Erc721Metadata compatible".into());281 }282 collection.flags.erc721metadata = true;283284 let all_permissions = <pallet_common::CollectionPropertyPermissions<T>>::get(collection.id);285 if all_permissions.get(&key::url()).is_none() {286 self.recorder().consume_sstore()?;287 <PalletCommon<T>>::set_property_permission(288 &collection,289 &caller,290 up_data_structs::PropertyKeyPermission {291 key: key::url(),292 permission: up_data_structs::PropertyPermission {293 mutable: true,294 collection_admin: true,295 token_owner: false,296 },297 },298 )299 .map_err(dispatch_to_evm::<T>)?;300 }301 if all_permissions.get(&key::suffix()).is_none() {302 self.recorder().consume_sstore()?;303 <PalletCommon<T>>::set_property_permission(304 &collection,305 &caller,306 up_data_structs::PropertyKeyPermission {307 key: key::suffix(),308 permission: up_data_structs::PropertyPermission {309 mutable: true,310 collection_admin: true,311 token_owner: false,312 },313 },314 )315 .map_err(dispatch_to_evm::<T>)?;316 }317318 let all_properties = <pallet_common::CollectionProperties<T>>::get(collection.id);319 if all_properties.get(&key::base_uri()).is_none() && !base_uri.is_empty() {320 self.recorder().consume_sstore()?;321 <PalletCommon<T>>::set_collection_properties(322 &collection,323 &caller,324 [up_data_structs::Property {325 key: key::base_uri(),326 value: base_uri327 .into_bytes()328 .try_into()329 .map_err(|_| "base uri is too large")?,330 }]331 .into_iter(),332 )333 .map_err(dispatch_to_evm::<T>)?;334 }335336 self.recorder().consume_sstore()?;337 collection.save().map_err(dispatch_to_evm::<T>)?;338339 Ok(())340 }341342 #[weight(<SelfWeightOf<T>>::destroy_collection())]343 fn destroy_collection(&mut self, caller: Caller, collection_address: Address) -> Result<()> {344 let caller = T::CrossAccountId::from_eth(caller);345346 let collection_id = pallet_common::eth::map_eth_to_id(&collection_address)347 .ok_or("Invalid collection address format")?;348 <Pallet<T>>::destroy_collection_internal(caller, collection_id)349 .map_err(pallet_evm_coder_substrate::dispatch_to_evm::<T>)350 }351352 /// Check if a collection exists353 /// @param collectionAddress Address of the collection in question354 /// @return bool Does the collection exist?355 fn is_collection_exist(&self, _caller: Caller, collection_address: Address) -> Result<bool> {356 if let Some(id) = pallet_common::eth::map_eth_to_id(&collection_address) {357 let collection_id = id;358 return Ok(<CollectionById<T>>::contains_key(collection_id));359 }360361 Ok(false)362 }363364 fn collection_creation_fee(&self) -> Result<Value> {365 let price: u128 = T::CollectionCreationPrice::get()366 .try_into()367 .map_err(|_| ()) // workaround for `expect` requiring `Debug` trait368 .expect("Collection creation price should be convertible to u128");369 Ok(price.into())370 }371372 /// Returns address of a collection.373 /// @param collectionId - CollectionId of the collection374 /// @return eth mirror address of the collection375 fn collection_address(&self, collection_id: u32) -> Result<Address> {376 Ok(collection_id_to_address(collection_id.into()))377 }378379 /// Returns collectionId of a collection.380 /// @param collectionAddress - Eth address of the collection381 /// @return collectionId of the collection382 fn collection_id(&self, collection_address: Address) -> Result<u32> {383 map_eth_to_id(&collection_address)384 .map(|id| id.0)385 .ok_or(Error::Revert(format!(386 "failed to convert address {} into collectionId.",387 collection_address388 )))389 }390}391392/// Implements [`OnMethodCall`], which delegates call to [`EvmCollectionHelpers`]393pub struct CollectionHelpersOnMethodCall<T: Config>(PhantomData<*const T>);394impl<T: Config + pallet_nonfungible::Config + pallet_refungible::Config> OnMethodCall<T>395 for CollectionHelpersOnMethodCall<T>396{397 fn is_reserved(contract: &sp_core::H160) -> bool {398 contract == &T::ContractAddress::get()399 }400401 fn is_used(contract: &sp_core::H160) -> bool {402 contract == &T::ContractAddress::get()403 }404405 fn call(handle: &mut impl PrecompileHandle) -> Option<PrecompileResult> {406 if handle.code_address() != T::ContractAddress::get() {407 return None;408 }409410 let helpers =411 EvmCollectionHelpers::<T>(SubstrateRecorder::<T>::new(handle.remaining_gas()));412 pallet_evm_coder_substrate::call(handle, helpers)413 }414415 fn get_code(contract: &sp_core::H160) -> Option<Vec<u8>> {416 (contract == &T::ContractAddress::get())417 .then(|| include_bytes!("./stubs/CollectionHelpers.raw").to_vec())418 }419}420421generate_stubgen!(collection_helper_impl, CollectionHelpersCall<()>, true);422generate_stubgen!(collection_helper_iface, CollectionHelpersCall<()>, false);423424fn error_field_too_long(feild: &str, bound: usize) -> Error {425 Error::Revert(format!("{} is too long. Max length is {}.", feild, bound))426}1// Copyright 2019-2022 Unique Network (Gibraltar) Ltd.2// This file is part of Unique Network.34// Unique Network is free software: you can redistribute it and/or modify5// it under the terms of the GNU General Public License as published by6// the Free Software Foundation, either version 3 of the License, or7// (at your option) any later version.89// Unique Network is distributed in the hope that it will be useful,10// but WITHOUT ANY WARRANTY; without even the implied warranty of11// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the12// GNU General Public License for more details.1314// You should have received a copy of the GNU General Public License15// along with Unique Network. If not, see <http://www.gnu.org/licenses/>.1617//! Implementation of CollectionHelpers contract.1819use core::marker::PhantomData;20use ethereum as _;21use evm_coder::{abi::AbiType, generate_stubgen, solidity_interface, types::*};22use frame_support::traits::Get;23use crate::Pallet;2425use pallet_common::{26 CollectionById,27 dispatch::CollectionDispatch,28 erc::{CollectionHelpersEvents, static_property::key},29 eth::{map_eth_to_id, collection_id_to_address},30 Pallet as PalletCommon, CollectionHandle,31};32use pallet_evm::{account::CrossAccountId, OnMethodCall, PrecompileHandle, PrecompileResult};33use pallet_evm_coder_substrate::{34 dispatch_to_evm, SubstrateRecorder, WithRecorder,35 execution::{PreDispatch, Result, Error},36 frontier_contract,37};38use up_data_structs::{39 CollectionDescription, CollectionMode, CollectionName, CollectionTokenPrefix,40 CreateCollectionData,41};4243use crate::{weights::WeightInfo, Config, SelfWeightOf};4445use alloc::format;46use sp_std::vec::Vec;4748frontier_contract! {49 macro_rules! EvmCollectionHelpers_result {...}50 impl<T: Config> Contract for EvmCollectionHelpers<T> {...}51}52/// See [`CollectionHelpersCall`]53pub struct EvmCollectionHelpers<T: Config>(SubstrateRecorder<T>);54impl<T: Config> WithRecorder<T> for EvmCollectionHelpers<T> {55 fn recorder(&self) -> &SubstrateRecorder<T> {56 &self.057 }5859 fn into_recorder(self) -> SubstrateRecorder<T> {60 self.061 }62}6364fn convert_data<T: Config>(65 caller: Caller,66 name: String,67 description: String,68 token_prefix: String,69) -> Result<(70 T::CrossAccountId,71 CollectionName,72 CollectionDescription,73 CollectionTokenPrefix,74)> {75 let caller = T::CrossAccountId::from_eth(caller);76 let name = name77 .encode_utf16()78 .collect::<Vec<u16>>()79 .try_into()80 .map_err(|_| error_field_too_long(stringify!(name), CollectionName::bound()))?;81 let description = description82 .encode_utf16()83 .collect::<Vec<u16>>()84 .try_into()85 .map_err(|_| {86 error_field_too_long(stringify!(description), CollectionDescription::bound())87 })?;88 let token_prefix = token_prefix.into_bytes().try_into().map_err(|_| {89 error_field_too_long(stringify!(token_prefix), CollectionTokenPrefix::bound())90 })?;91 Ok((caller, name, description, token_prefix))92}9394#[inline(always)]95fn create_collection_internal<T: Config>(96 caller: Caller,97 value: Value,98 name: String,99 collection_mode: CollectionMode,100 description: String,101 token_prefix: String,102) -> Result<Address> {103 let (caller, name, description, token_prefix) =104 convert_data::<T>(caller, name, description, token_prefix)?;105 let data = CreateCollectionData {106 name,107 mode: collection_mode,108 description,109 token_prefix,110 ..Default::default()111 };112 check_sent_amount_equals_collection_creation_price::<T>(value)?;113 let collection_helpers_address =114 T::CrossAccountId::from_eth(<T as pallet_common::Config>::ContractAddress::get());115116 let collection_id = T::CollectionDispatch::create(117 caller.clone(),118 collection_helpers_address,119 data,120 Default::default(),121 )122 .map_err(pallet_evm_coder_substrate::dispatch_to_evm::<T>)?;123 let address = pallet_common::eth::collection_id_to_address(collection_id);124 Ok(address)125}126127fn check_sent_amount_equals_collection_creation_price<T: Config>(value: Value) -> Result<()> {128 let value = value.as_u128();129 let creation_price: u128 = T::CollectionCreationPrice::get()130 .try_into()131 .map_err(|_| ()) // workaround for `expect` requiring `Debug` trait132 .expect("Collection creation price should be convertible to u128");133 if value != creation_price {134 return Err(format!(135 "Sent amount not equals to collection creation price ({0})",136 creation_price137 )138 .into());139 }140 Ok(())141}142143/// @title Contract, which allows users to operate with collections144#[solidity_interface(name = CollectionHelpers, events(CollectionHelpersEvents), enum(derive(PreDispatch)), enum_attr(weight))]145impl<T> EvmCollectionHelpers<T>146where147 T: Config + pallet_common::Config + pallet_nonfungible::Config + pallet_refungible::Config,148{149 /// Create an NFT collection150 /// @param name Name of the collection151 /// @param description Informative description of the collection152 /// @param tokenPrefix Token prefix to represent the collection tokens in UI and user applications153 /// @return address Address of the newly created collection154 #[weight(<SelfWeightOf<T>>::create_collection())]155 #[solidity(rename_selector = "createNFTCollection")]156 fn create_nft_collection(157 &mut self,158 caller: Caller,159 value: Value,160 name: String,161 description: String,162 token_prefix: String,163 ) -> Result<Address> {164 let (caller, name, description, token_prefix) =165 convert_data::<T>(caller, name, description, token_prefix)?;166 let data = CreateCollectionData {167 name,168 mode: CollectionMode::NFT,169 description,170 token_prefix,171 ..Default::default()172 };173 check_sent_amount_equals_collection_creation_price::<T>(value)?;174 let collection_helpers_address =175 T::CrossAccountId::from_eth(<T as pallet_common::Config>::ContractAddress::get());176 let collection_id = T::CollectionDispatch::create(177 caller,178 collection_helpers_address,179 data,180 Default::default(),181 )182 .map_err(dispatch_to_evm::<T>)?;183184 let address = pallet_common::eth::collection_id_to_address(collection_id);185 Ok(address)186 }187 /// Create an NFT collection188 /// @param name Name of the collection189 /// @param description Informative description of the collection190 /// @param tokenPrefix Token prefix to represent the collection tokens in UI and user applications191 /// @return address Address of the newly created collection192 #[deprecated(note = "mathod was renamed to `create_nft_collection`, prefer it instead")]193 #[solidity(hide)]194 #[weight(<SelfWeightOf<T>>::create_collection())]195 fn create_nonfungible_collection(196 &mut self,197 caller: Caller,198 value: Value,199 name: String,200 description: String,201 token_prefix: String,202 ) -> Result<Address> {203 create_collection_internal::<T>(204 caller,205 value,206 name,207 CollectionMode::NFT,208 description,209 token_prefix,210 )211 }212213 #[weight(<SelfWeightOf<T>>::create_collection())]214 #[solidity(rename_selector = "createRFTCollection")]215 fn create_rft_collection(216 &mut self,217 caller: Caller,218 value: Value,219 name: String,220 description: String,221 token_prefix: String,222 ) -> Result<Address> {223 create_collection_internal::<T>(224 caller,225 value,226 name,227 CollectionMode::ReFungible,228 description,229 token_prefix,230 )231 }232233 #[weight(<SelfWeightOf<T>>::create_collection())]234 #[solidity(rename_selector = "createFTCollection")]235 fn create_fungible_collection(236 &mut self,237 caller: Caller,238 value: Value,239 name: String,240 decimals: u8,241 description: String,242 token_prefix: String,243 ) -> Result<Address> {244 create_collection_internal::<T>(245 caller,246 value,247 name,248 CollectionMode::Fungible(decimals),249 description,250 token_prefix,251 )252 }253254 #[solidity(rename_selector = "makeCollectionERC721MetadataCompatible")]255 fn make_collection_metadata_compatible(256 &mut self,257 caller: Caller,258 collection: Address,259 base_uri: String,260 ) -> Result<()> {261 let caller = T::CrossAccountId::from_eth(caller);262 let collection =263 pallet_common::eth::map_eth_to_id(&collection).ok_or("not a collection address")?;264 let mut collection =265 <CollectionHandle<T>>::new(collection).ok_or("collection not found")?;266267 if !matches!(268 collection.mode,269 CollectionMode::NFT | CollectionMode::ReFungible270 ) {271 return Err("target collection should be either NFT or Refungible".into());272 }273274 self.recorder().consume_sstore()?;275 collection276 .check_is_owner_or_admin(&caller)277 .map_err(dispatch_to_evm::<T>)?;278279 if collection.flags.erc721metadata {280 return Err("target collection is already Erc721Metadata compatible".into());281 }282 collection.flags.erc721metadata = true;283284 let all_permissions = <pallet_common::CollectionPropertyPermissions<T>>::get(collection.id);285 if all_permissions.get(&key::url()).is_none() {286 self.recorder().consume_sstore()?;287 <PalletCommon<T>>::set_property_permission(288 &collection,289 &caller,290 up_data_structs::PropertyKeyPermission {291 key: key::url(),292 permission: up_data_structs::PropertyPermission {293 mutable: true,294 collection_admin: true,295 token_owner: false,296 },297 },298 )299 .map_err(dispatch_to_evm::<T>)?;300 }301 if all_permissions.get(&key::suffix()).is_none() {302 self.recorder().consume_sstore()?;303 <PalletCommon<T>>::set_property_permission(304 &collection,305 &caller,306 up_data_structs::PropertyKeyPermission {307 key: key::suffix(),308 permission: up_data_structs::PropertyPermission {309 mutable: true,310 collection_admin: true,311 token_owner: false,312 },313 },314 )315 .map_err(dispatch_to_evm::<T>)?;316 }317318 let all_properties = <pallet_common::CollectionProperties<T>>::get(collection.id);319 if all_properties.get(&key::base_uri()).is_none() && !base_uri.is_empty() {320 self.recorder().consume_sstore()?;321 <PalletCommon<T>>::set_collection_properties(322 &collection,323 &caller,324 [up_data_structs::Property {325 key: key::base_uri(),326 value: base_uri327 .into_bytes()328 .try_into()329 .map_err(|_| "base uri is too large")?,330 }]331 .into_iter(),332 )333 .map_err(dispatch_to_evm::<T>)?;334 }335336 self.recorder().consume_sstore()?;337 collection.save().map_err(dispatch_to_evm::<T>)?;338339 Ok(())340 }341342 #[weight(<SelfWeightOf<T>>::destroy_collection())]343 fn destroy_collection(&mut self, caller: Caller, collection_address: Address) -> Result<()> {344 let caller = T::CrossAccountId::from_eth(caller);345346 let collection_id = pallet_common::eth::map_eth_to_id(&collection_address)347 .ok_or("Invalid collection address format")?;348 <Pallet<T>>::destroy_collection_internal(caller, collection_id)349 .map_err(pallet_evm_coder_substrate::dispatch_to_evm::<T>)350 }351352 /// Check if a collection exists353 /// @param collectionAddress Address of the collection in question354 /// @return bool Does the collection exist?355 fn is_collection_exist(&self, _caller: Caller, collection_address: Address) -> Result<bool> {356 if let Some(id) = pallet_common::eth::map_eth_to_id(&collection_address) {357 let collection_id = id;358 return Ok(<CollectionById<T>>::contains_key(collection_id));359 }360361 Ok(false)362 }363364 fn collection_creation_fee(&self) -> Result<Value> {365 let price: u128 = T::CollectionCreationPrice::get()366 .try_into()367 .map_err(|_| ()) // workaround for `expect` requiring `Debug` trait368 .expect("Collection creation price should be convertible to u128");369 Ok(price.into())370 }371372 /// Returns address of a collection.373 /// @param collectionId - CollectionId of the collection374 /// @return eth mirror address of the collection375 fn collection_address(&self, collection_id: u32) -> Result<Address> {376 Ok(collection_id_to_address(collection_id.into()))377 }378379 /// Returns collectionId of a collection.380 /// @param collectionAddress - Eth address of the collection381 /// @return collectionId of the collection382 fn collection_id(&self, collection_address: Address) -> Result<u32> {383 map_eth_to_id(&collection_address)384 .map(|id| id.0)385 .ok_or(Error::Revert(format!(386 "failed to convert address {} into collectionId.",387 collection_address388 )))389 }390}391392/// Implements [`OnMethodCall`], which delegates call to [`EvmCollectionHelpers`]393pub struct CollectionHelpersOnMethodCall<T: Config>(PhantomData<*const T>);394impl<T: Config + pallet_nonfungible::Config + pallet_refungible::Config> OnMethodCall<T>395 for CollectionHelpersOnMethodCall<T>396{397 fn is_reserved(contract: &sp_core::H160) -> bool {398 contract == &T::ContractAddress::get()399 }400401 fn is_used(contract: &sp_core::H160) -> bool {402 contract == &T::ContractAddress::get()403 }404405 fn call(handle: &mut impl PrecompileHandle) -> Option<PrecompileResult> {406 if handle.code_address() != T::ContractAddress::get() {407 return None;408 }409410 let helpers =411 EvmCollectionHelpers::<T>(SubstrateRecorder::<T>::new(handle.remaining_gas()));412 pallet_evm_coder_substrate::call(handle, helpers)413 }414415 fn get_code(contract: &sp_core::H160) -> Option<Vec<u8>> {416 (contract == &T::ContractAddress::get())417 .then(|| include_bytes!("./stubs/CollectionHelpers.raw").to_vec())418 }419}420421generate_stubgen!(collection_helper_impl, CollectionHelpersCall<()>, true);422generate_stubgen!(collection_helper_iface, CollectionHelpersCall<()>, false);423424fn error_field_too_long(feild: &str, bound: usize) -> Error {425 Error::Revert(format!("{} is too long. Max length is {}.", feild, bound))426}pallets/unique/src/lib.rsdiffbeforeafterboth--- a/pallets/unique/src/lib.rs
+++ b/pallets/unique/src/lib.rs
@@ -73,42 +73,52 @@
extern crate alloc;
-use frame_support::{
- decl_module, decl_storage, decl_error,
- dispatch::DispatchResult,
- ensure, fail,
- weights::{Weight},
- pallet_prelude::{DispatchResultWithPostInfo, ConstU32},
- BoundedVec,
-};
-use scale_info::TypeInfo;
-use frame_system::{self as system, ensure_signed, ensure_root};
-use sp_std::{vec, vec::Vec};
-use up_data_structs::{
- MAX_COLLECTION_NAME_LENGTH, MAX_COLLECTION_DESCRIPTION_LENGTH, MAX_TOKEN_PREFIX_LENGTH,
- MAX_PROPERTIES_PER_ITEM, MAX_PROPERTY_KEY_LENGTH, MAX_PROPERTY_VALUE_LENGTH,
- MAX_COLLECTION_PROPERTIES_SIZE, COLLECTION_ADMINS_LIMIT, MAX_TOKEN_PROPERTIES_SIZE,
- CreateItemData, CollectionLimits, CollectionPermissions, CollectionId, CollectionMode, TokenId,
- CreateCollectionData, CreateItemExData, budget, Property, PropertyKey, PropertyKeyPermission,
-};
-use pallet_evm::account::CrossAccountId;
-use pallet_common::{
- CollectionHandle, Pallet as PalletCommon, CommonWeightInfo, dispatch::dispatch_tx,
- dispatch::CollectionDispatch, RefungibleExtensionsWeightInfo,
-};
+pub use pallet::*;
+use frame_support::pallet_prelude::*;
+use frame_system::pallet_prelude::*;
pub mod eth;
#[cfg(feature = "runtime-benchmarks")]
pub mod benchmarking;
pub mod weights;
-use weights::WeightInfo;
-/// A maximum number of levels of depth in the token nesting tree.
-pub const NESTING_BUDGET: u32 = 5;
+#[frame_support::pallet]
+pub mod pallet {
+ use super::*;
-decl_error! {
+ use frame_support::{
+ dispatch::DispatchResult,
+ ensure, fail,
+ weights::{Weight},
+ pallet_prelude::{*},
+ BoundedVec,
+ storage::Key,
+ };
+ use frame_system::pallet_prelude::*;
+ use scale_info::TypeInfo;
+ use frame_system::{self as system, ensure_signed, ensure_root};
+ use sp_std::{vec, vec::Vec};
+ use up_data_structs::{
+ MAX_COLLECTION_NAME_LENGTH, MAX_COLLECTION_DESCRIPTION_LENGTH, MAX_TOKEN_PREFIX_LENGTH,
+ MAX_PROPERTIES_PER_ITEM, MAX_PROPERTY_KEY_LENGTH, MAX_PROPERTY_VALUE_LENGTH,
+ MAX_COLLECTION_PROPERTIES_SIZE, COLLECTION_ADMINS_LIMIT, MAX_TOKEN_PROPERTIES_SIZE,
+ CreateItemData, CollectionLimits, CollectionPermissions, CollectionId, CollectionMode,
+ TokenId, CreateCollectionData, CreateItemExData, budget, Property, PropertyKey,
+ PropertyKeyPermission,
+ };
+ use pallet_evm::account::CrossAccountId;
+ use pallet_common::{
+ CollectionHandle, Pallet as PalletCommon, CommonWeightInfo, dispatch::dispatch_tx,
+ dispatch::CollectionDispatch, RefungibleExtensionsWeightInfo,
+ };
+ use weights::WeightInfo;
+
+ /// A maximum number of levels of depth in the token nesting tree.
+ pub const NESTING_BUDGET: u32 = 5;
+
/// Errors for the common Unique transactions.
- pub enum Error for Module<T: Config> {
+ #[pallet::error]
+ pub enum Error<T> {
/// Decimal_points parameter must be lower than [`up_data_structs::MAX_DECIMAL_POINTS`].
CollectionDecimalPointLimitExceeded,
/// Length of items properties must be greater than 0.
@@ -116,135 +126,219 @@
/// Repertition is only supported by refungible collection.
RepartitionCalledOnNonRefungibleCollection,
}
-}
-/// Configuration trait of this pallet.
-pub trait Config: system::Config + pallet_common::Config + Sized + TypeInfo {
- /// Weight information for extrinsics in this pallet.
- type WeightInfo: WeightInfo;
+ /// Configuration trait of this pallet.
+ #[pallet::config]
+ pub trait Config: frame_system::Config + pallet_common::Config + Sized + TypeInfo {
+ /// Weight information for extrinsics in this pallet.
+ type WeightInfo: WeightInfo;
- /// Weight information for common pallet operations.
- type CommonWeightInfo: CommonWeightInfo<Self::CrossAccountId>;
+ /// Weight information for common pallet operations.
+ type CommonWeightInfo: CommonWeightInfo<Self::CrossAccountId>;
- /// Weight info information for extra refungible pallet operations.
- type RefungibleExtensionsWeightInfo: RefungibleExtensionsWeightInfo;
-}
+ /// Weight info information for extra refungible pallet operations.
+ type RefungibleExtensionsWeightInfo: RefungibleExtensionsWeightInfo;
+ }
-type SelfWeightOf<T> = <T as Config>::WeightInfo;
+ #[pallet::pallet]
+ pub struct Pallet<T>(_);
-// # Used definitions
-//
-// ## User control levels
-//
-// chain-controlled - key is uncontrolled by user
-// i.e autoincrementing index
-// can use non-cryptographic hash
-// real - key is controlled by user
-// but it is hard to generate enough colliding values, i.e owner of signed txs
-// can use non-cryptographic hash
-// controlled - key is completly controlled by users
-// i.e maps with mutable keys
-// should use cryptographic hash
-//
-// ## User control level downgrade reasons
-//
-// ?1 - chain-controlled -> controlled
-// collections/tokens can be destroyed, resulting in massive holes
-// ?2 - chain-controlled -> controlled
-// same as ?1, but can be only added, resulting in easier exploitation
-// ?3 - real -> controlled
-// no confirmation required, so addresses can be easily generated
-decl_storage! {
- trait Store for Module<T: Config> as Unique {
+ pub type SelfWeightOf<T> = <T as Config>::WeightInfo;
- //#region Private members
- /// Used for migrations
- ChainVersion: u64;
- //#endregion
+ // # Used definitions
+ //
+ // ## User control levels
+ //
+ // chain-controlled - key is uncontrolled by user
+ // i.e autoincrementing index
+ // can use non-cryptographic hash
+ // real - key is controlled by user
+ // but it is hard to generate enough colliding values, i.e owner of signed txs
+ // can use non-cryptographic hash
+ // controlled - key is completly controlled by users
+ // i.e maps with mutable keys
+ // should use cryptographic hash
+ //
+ // ## User control level downgrade reasons
+ //
+ // ?1 - chain-controlled -> controlled
+ // collections/tokens can be destroyed, resulting in massive holes
+ // ?2 - chain-controlled -> controlled
+ // same as ?1, but can be only added, resulting in easier exploitation
+ // ?3 - real -> controlled
+ // no confirmation required, so addresses can be easily generated
- //#region Tokens transfer sponosoring rate limit baskets
- /// (Collection id (controlled?2), who created (real))
- /// TODO: Off chain worker should remove from this map when collection gets removed
- pub CreateItemBasket get(fn create_item_basket): map hasher(blake2_128_concat) (CollectionId, T::AccountId) => Option<T::BlockNumber>;
- /// Collection id (controlled?2), token id (controlled?2)
- pub NftTransferBasket get(fn nft_transfer_basket): double_map hasher(blake2_128_concat) CollectionId, hasher(blake2_128_concat) TokenId => Option<T::BlockNumber>;
- /// Collection id (controlled?2), owning user (real)
- pub FungibleTransferBasket get(fn fungible_transfer_basket): double_map hasher(blake2_128_concat) CollectionId, hasher(twox_64_concat) T::AccountId => Option<T::BlockNumber>;
- /// Collection id (controlled?2), token id (controlled?2)
- pub ReFungibleTransferBasket get(fn refungible_transfer_basket): nmap hasher(blake2_128_concat) CollectionId, hasher(blake2_128_concat) TokenId, hasher(twox_64_concat) T::AccountId => Option<T::BlockNumber>;
- //#endregion
+ //#region Private members
+ /// Used for migrations
+ #[pallet::storage]
+ pub type ChainVersion<T> = StorageValue<_, u64, ValueQuery>;
+ //#endregion
- /// Variable metadata sponsoring
- /// Collection id (controlled?2), token id (controlled?2)
- #[deprecated]
- pub VariableMetaDataBasket get(fn variable_meta_data_basket): double_map hasher(blake2_128_concat) CollectionId, hasher(blake2_128_concat) TokenId => Option<T::BlockNumber>;
- /// Last sponsoring of token property setting // todo:doc rephrase this and the following
- pub TokenPropertyBasket get(fn token_property_basket): double_map hasher(blake2_128_concat) CollectionId, hasher(blake2_128_concat) TokenId => Option<T::BlockNumber>;
+ //#region Tokens transfer sponosoring rate limit baskets
+ /// (Collection id (controlled?2), who created (real))
+ /// TODO: Off chain worker should remove from this map when collection gets removed
+ #[pallet::storage]
+ #[pallet::getter(fn create_item_busket)]
+ pub type CreateItemBasket<T: Config> = StorageMap<
+ Hasher = Blake2_128Concat,
+ Key = (CollectionId, T::AccountId),
+ Value = T::BlockNumber,
+ QueryKind = OptionQuery,
+ >;
+ /// Collection id (controlled?2), token id (controlled?2)
+ #[pallet::storage]
+ #[pallet::getter(fn nft_transfer_basket)]
+ pub type NftTransferBasket<T: Config> = StorageDoubleMap<
+ Hasher1 = Blake2_128Concat,
+ Key1 = CollectionId,
+ Hasher2 = Blake2_128Concat,
+ Key2 = TokenId,
+ Value = T::BlockNumber,
+ QueryKind = OptionQuery,
+ >;
+ /// Collection id (controlled?2), owning user (real)
+ #[pallet::storage]
+ #[pallet::getter(fn fungible_transfer_basket)]
+ pub type FungibleTransferBasket<T: Config> = StorageDoubleMap<
+ Hasher1 = Blake2_128Concat,
+ Key1 = CollectionId,
+ Hasher2 = Twox64Concat,
+ Key2 = T::AccountId,
+ Value = T::BlockNumber,
+ QueryKind = OptionQuery,
+ >;
+ /// Collection id (controlled?2), token id (controlled?2)
+ #[pallet::storage]
+ #[pallet::getter(fn refungible_transfer_basket)]
+ pub type ReFungibleTransferBasket<T: Config> = StorageNMap<
+ Key = (
+ Key<Blake2_128Concat, CollectionId>,
+ Key<Blake2_128Concat, TokenId>,
+ Key<Twox64Concat, T::AccountId>,
+ ),
+ Value = T::BlockNumber,
+ QueryKind = OptionQuery,
+ >;
+ //#endregion
- /// Last sponsoring of NFT approval in a collection
- pub NftApproveBasket get(fn nft_approve_basket): double_map hasher(blake2_128_concat) CollectionId, hasher(blake2_128_concat) TokenId => Option<T::BlockNumber>;
- /// Last sponsoring of fungible tokens approval in a collection
- pub FungibleApproveBasket get(fn fungible_approve_basket): double_map hasher(blake2_128_concat) CollectionId, hasher(twox_64_concat) T::AccountId => Option<T::BlockNumber>;
- /// Last sponsoring of RFT approval in a collection
- pub RefungibleApproveBasket get(fn refungible_approve_basket): nmap hasher(blake2_128_concat) CollectionId, hasher(blake2_128_concat) TokenId, hasher(twox_64_concat) T::AccountId => Option<T::BlockNumber>;
- }
-}
+ /// Last sponsoring of token property setting // todo:doc rephrase this and the following
+ #[pallet::storage]
+ #[pallet::getter(fn token_property_basket)]
+ pub type TokenPropertyBasket<T: Config> = StorageDoubleMap<
+ Hasher1 = Blake2_128Concat,
+ Key1 = CollectionId,
+ Hasher2 = Blake2_128Concat,
+ Key2 = TokenId,
+ Value = T::BlockNumber,
+ QueryKind = OptionQuery,
+ >;
-decl_module! {
- /// Type alias to Pallet, to be used by construct_runtime.
- pub struct Module<T: Config> for enum Call
- where
- origin: T::RuntimeOrigin
- {
- type Error = Error<T>;
+ /// Last sponsoring of NFT approval in a collection
+ #[pallet::storage]
+ #[pallet::getter(fn nft_approve_basket)]
+ pub type NftApproveBasket<T: Config> = StorageDoubleMap<
+ Hasher1 = Blake2_128Concat,
+ Key1 = CollectionId,
+ Hasher2 = Blake2_128Concat,
+ Key2 = TokenId,
+ Value = T::BlockNumber,
+ QueryKind = OptionQuery,
+ >;
+ /// Last sponsoring of fungible tokens approval in a collection
+ #[pallet::storage]
+ #[pallet::getter(fn fungible_approve_basket)]
+ pub type FungibleApproveBasket<T: Config> = StorageDoubleMap<
+ Hasher1 = Blake2_128Concat,
+ Key1 = CollectionId,
+ Hasher2 = Twox64Concat,
+ Key2 = T::AccountId,
+ Value = T::BlockNumber,
+ QueryKind = OptionQuery,
+ >;
+ /// Last sponsoring of RFT approval in a collection
+ #[pallet::storage]
+ #[pallet::getter(fn refungible_approve_basket)]
+ pub type RefungibleApproveBasket<T: Config> = StorageNMap<
+ Key = (
+ Key<Blake2_128Concat, CollectionId>,
+ Key<Blake2_128Concat, TokenId>,
+ Key<Twox64Concat, T::AccountId>,
+ ),
+ Value = T::BlockNumber,
+ QueryKind = OptionQuery,
+ >;
- #[doc = "A maximum number of levels of depth in the token nesting tree."]
- const NESTING_BUDGET: u32 = NESTING_BUDGET;
+ #[pallet::extra_constants]
+ impl<T: Config> Pallet<T> {
+ /// A maximum number of levels of depth in the token nesting tree.
+ fn nesting_budget() -> u32 {
+ NESTING_BUDGET
+ }
- #[doc = "Maximal length of a collection name."]
- const MAX_COLLECTION_NAME_LENGTH: u32 = MAX_COLLECTION_NAME_LENGTH;
+ /// Maximal length of a collection name.
+ fn max_collection_name_length() -> u32 {
+ MAX_COLLECTION_NAME_LENGTH
+ }
- #[doc = "Maximal length of a collection description."]
- const MAX_COLLECTION_DESCRIPTION_LENGTH: u32 = MAX_COLLECTION_DESCRIPTION_LENGTH;
+ /// Maximal length of a collection description.
+ fn max_collection_description_length() -> u32 {
+ MAX_COLLECTION_DESCRIPTION_LENGTH
+ }
- #[doc = "Maximal length of a token prefix."]
- const MAX_TOKEN_PREFIX_LENGTH: u32 = MAX_TOKEN_PREFIX_LENGTH;
+ /// Maximal length of a token prefix.
+ fn max_token_prefix_length() -> u32 {
+ MAX_TOKEN_PREFIX_LENGTH
+ }
- #[doc = "Maximum admins per collection."]
- const COLLECTION_ADMINS_LIMIT: u32 = COLLECTION_ADMINS_LIMIT;
+ /// Maximum admins per collection.
+ fn collection_admins_limit() -> u32 {
+ COLLECTION_ADMINS_LIMIT
+ }
- #[doc = "Maximal length of a property key."]
- const MAX_PROPERTY_KEY_LENGTH: u32 = MAX_PROPERTY_KEY_LENGTH;
+ /// Maximal length of a property key.
+ fn max_property_key_length() -> u32 {
+ MAX_PROPERTY_KEY_LENGTH
+ }
- #[doc = "Maximal length of a property value."]
- const MAX_PROPERTY_VALUE_LENGTH: u32 = MAX_PROPERTY_VALUE_LENGTH;
+ /// Maximal length of a property value.
+ fn max_property_value_length() -> u32 {
+ MAX_PROPERTY_VALUE_LENGTH
+ }
- #[doc = "A maximum number of token properties."]
- const MAX_PROPERTIES_PER_ITEM: u32 = MAX_PROPERTIES_PER_ITEM;
+ /// A maximum number of token properties.
+ fn max_properties_per_item() -> u32 {
+ MAX_PROPERTIES_PER_ITEM
+ }
- #[doc = "Maximum size for all collection properties."]
- const MAX_COLLECTION_PROPERTIES_SIZE: u32 = MAX_COLLECTION_PROPERTIES_SIZE;
+ /// Maximum size for all collection properties.
+ fn max_collection_properties_size() -> u32 {
+ MAX_COLLECTION_PROPERTIES_SIZE
+ }
- #[doc = "Maximum size of all token properties."]
- const MAX_TOKEN_PROPERTIES_SIZE: u32 = MAX_TOKEN_PROPERTIES_SIZE;
-
- #[doc = "Default NFT collection limit."]
- const NFT_DEFAULT_COLLECTION_LIMITS: CollectionLimits = CollectionLimits::with_default_limits(CollectionMode::NFT);
-
- #[doc = "Default RFT collection limit."]
- const RFT_DEFAULT_COLLECTION_LIMITS: CollectionLimits = CollectionLimits::with_default_limits(CollectionMode::ReFungible);
+ /// Maximum size of all token properties.
+ fn max_token_properties_size() -> u32 {
+ MAX_TOKEN_PROPERTIES_SIZE
+ }
- #[doc = "Default FT collection limit."]
- const FT_DEFAULT_COLLECTION_LIMITS: CollectionLimits = CollectionLimits::with_default_limits(CollectionMode::Fungible(0));
+ /// Default NFT collection limit.
+ fn nft_default_collection_limits() -> CollectionLimits {
+ CollectionLimits::with_default_limits(CollectionMode::NFT)
+ }
- fn on_initialize(_now: T::BlockNumber) -> Weight {
- Weight::zero()
+ /// Default RFT collection limit.
+ fn rft_default_collection_limits() -> CollectionLimits {
+ CollectionLimits::with_default_limits(CollectionMode::ReFungible)
}
- fn on_runtime_upgrade() -> Weight {
- Weight::zero()
+ /// Default FT collection limit.
+ fn ft_default_collection_limits() -> CollectionLimits {
+ CollectionLimits::with_default_limits(CollectionMode::Fungible(0))
}
+ }
+ /// Type alias to Pallet, to be used by construct_runtime.
+ #[pallet::call]
+ impl<T: Config> Pallet<T> {
/// Create a collection of tokens.
///
/// Each Token may have multiple properties encoded as an array of bytes
@@ -270,13 +364,14 @@
/// returns collection ID
///
/// Deprecated: `create_collection_ex` is more up-to-date and advanced, prefer it instead.
- #[weight = <SelfWeightOf<T>>::create_collection()]
- fn create_collection(
- origin,
+ #[pallet::call_index(0)]
+ #[pallet::weight(<SelfWeightOf<T>>::create_collection())]
+ pub fn create_collection(
+ origin: OriginFor<T>,
collection_name: BoundedVec<u16, ConstU32<MAX_COLLECTION_NAME_LENGTH>>,
collection_description: BoundedVec<u16, ConstU32<MAX_COLLECTION_DESCRIPTION_LENGTH>>,
token_prefix: BoundedVec<u8, ConstU32<MAX_TOKEN_PREFIX_LENGTH>>,
- mode: CollectionMode
+ mode: CollectionMode,
) -> DispatchResult {
let data: CreateCollectionData<T::AccountId> = CreateCollectionData {
name: collection_name,
@@ -299,13 +394,18 @@
/// # Arguments
///
/// * `data`: Explicit data of a collection used for its creation.
- #[weight = <SelfWeightOf<T>>::create_collection()]
- pub fn create_collection_ex(origin, data: CreateCollectionData<T::AccountId>) -> DispatchResult {
+ #[pallet::call_index(1)]
+ #[pallet::weight(<SelfWeightOf<T>>::create_collection())]
+ pub fn create_collection_ex(
+ origin: OriginFor<T>,
+ data: CreateCollectionData<T::AccountId>,
+ ) -> DispatchResult {
let sender = ensure_signed(origin)?;
// =========
let sender = T::CrossAccountId::from_sub(sender);
- let _id = T::CollectionDispatch::create(sender.clone(), sender, data, Default::default())?;
+ let _id =
+ T::CollectionDispatch::create(sender.clone(), sender, data, Default::default())?;
Ok(())
}
@@ -319,8 +419,12 @@
/// # Arguments
///
/// * `collection_id`: Collection to destroy.
- #[weight = <SelfWeightOf<T>>::destroy_collection()]
- pub fn destroy_collection(origin, collection_id: CollectionId) -> DispatchResult {
+ #[pallet::call_index(2)]
+ #[pallet::weight(<SelfWeightOf<T>>::destroy_collection())]
+ pub fn destroy_collection(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ ) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
Self::destroy_collection_internal(sender, collection_id)
@@ -337,19 +441,18 @@
///
/// * `collection_id`: ID of the modified collection.
/// * `address`: ID of the address to be added to the allowlist.
- #[weight = <SelfWeightOf<T>>::add_to_allow_list()]
- pub fn add_to_allow_list(origin, collection_id: CollectionId, address: T::CrossAccountId) -> DispatchResult{
-
+ #[pallet::call_index(3)]
+ #[pallet::weight(<SelfWeightOf<T>>::add_to_allow_list())]
+ pub fn add_to_allow_list(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ address: T::CrossAccountId,
+ ) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let collection = <CollectionHandle<T>>::try_get(collection_id)?;
collection.check_is_internal()?;
- <PalletCommon<T>>::toggle_allowlist(
- &collection,
- &sender,
- &address,
- true,
- )?;
+ <PalletCommon<T>>::toggle_allowlist(&collection, &sender, &address, true)?;
Ok(())
}
@@ -365,19 +468,18 @@
///
/// * `collection_id`: ID of the modified collection.
/// * `address`: ID of the address to be removed from the allowlist.
- #[weight = <SelfWeightOf<T>>::remove_from_allow_list()]
- pub fn remove_from_allow_list(origin, collection_id: CollectionId, address: T::CrossAccountId) -> DispatchResult{
-
+ #[pallet::call_index(4)]
+ #[pallet::weight(<SelfWeightOf<T>>::remove_from_allow_list())]
+ pub fn remove_from_allow_list(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ address: T::CrossAccountId,
+ ) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let collection = <CollectionHandle<T>>::try_get(collection_id)?;
collection.check_is_internal()?;
- <PalletCommon<T>>::toggle_allowlist(
- &collection,
- &sender,
- &address,
- false,
- )?;
+ <PalletCommon<T>>::toggle_allowlist(&collection, &sender, &address, false)?;
Ok(())
}
@@ -392,8 +494,13 @@
///
/// * `collection_id`: ID of the modified collection.
/// * `new_owner`: ID of the account that will become the owner.
- #[weight = <SelfWeightOf<T>>::change_collection_owner()]
- pub fn change_collection_owner(origin, collection_id: CollectionId, new_owner: T::AccountId) -> DispatchResult {
+ #[pallet::call_index(5)]
+ #[pallet::weight(<SelfWeightOf<T>>::change_collection_owner())]
+ pub fn change_collection_owner(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ new_owner: T::AccountId,
+ ) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let new_owner = T::CrossAccountId::from_sub(new_owner);
let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
@@ -416,8 +523,13 @@
///
/// * `collection_id`: ID of the Collection to add an admin for.
/// * `new_admin`: Address of new admin to add.
- #[weight = <SelfWeightOf<T>>::add_collection_admin()]
- pub fn add_collection_admin(origin, collection_id: CollectionId, new_admin_id: T::CrossAccountId) -> DispatchResult {
+ #[pallet::call_index(6)]
+ #[pallet::weight(<SelfWeightOf<T>>::add_collection_admin())]
+ pub fn add_collection_admin(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ new_admin_id: T::CrossAccountId,
+ ) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let collection = <CollectionHandle<T>>::try_get(collection_id)?;
<PalletCommon<T>>::toggle_admin(&collection, &sender, &new_admin_id, true)
@@ -437,8 +549,13 @@
///
/// * `collection_id`: ID of the collection to remove the admin for.
/// * `account_id`: Address of the admin to remove.
- #[weight = <SelfWeightOf<T>>::remove_collection_admin()]
- pub fn remove_collection_admin(origin, collection_id: CollectionId, account_id: T::CrossAccountId) -> DispatchResult {
+ #[pallet::call_index(7)]
+ #[pallet::weight(<SelfWeightOf<T>>::remove_collection_admin())]
+ pub fn remove_collection_admin(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ account_id: T::CrossAccountId,
+ ) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let collection = <CollectionHandle<T>>::try_get(collection_id)?;
<PalletCommon<T>>::toggle_admin(&collection, &sender, &account_id, false)
@@ -457,8 +574,13 @@
///
/// * `collection_id`: ID of the modified collection.
/// * `new_sponsor`: ID of the account of the sponsor-to-be.
- #[weight = <SelfWeightOf<T>>::set_collection_sponsor()]
- pub fn set_collection_sponsor(origin, collection_id: CollectionId, new_sponsor: T::AccountId) -> DispatchResult {
+ #[pallet::call_index(8)]
+ #[pallet::weight(<SelfWeightOf<T>>::set_collection_sponsor())]
+ pub fn set_collection_sponsor(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ new_sponsor: T::AccountId,
+ ) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
target_collection.set_sponsor(&sender, new_sponsor.clone())
@@ -477,8 +599,12 @@
/// # Arguments
///
/// * `collection_id`: ID of the collection with the pending sponsor.
- #[weight = <SelfWeightOf<T>>::confirm_sponsorship()]
- pub fn confirm_sponsorship(origin, collection_id: CollectionId) -> DispatchResult {
+ #[pallet::call_index(9)]
+ #[pallet::weight(<SelfWeightOf<T>>::confirm_sponsorship())]
+ pub fn confirm_sponsorship(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ ) -> DispatchResult {
let sender = ensure_signed(origin)?;
let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
target_collection.confirm_sponsorship(&sender)
@@ -493,8 +619,12 @@
/// # Arguments
///
/// * `collection_id`: ID of the collection with the sponsor to remove.
- #[weight = <SelfWeightOf<T>>::remove_collection_sponsor()]
- pub fn remove_collection_sponsor(origin, collection_id: CollectionId) -> DispatchResult {
+ #[pallet::call_index(10)]
+ #[pallet::weight(<SelfWeightOf<T>>::remove_collection_sponsor())]
+ pub fn remove_collection_sponsor(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ ) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
target_collection.remove_sponsor(&sender)
@@ -518,12 +648,20 @@
/// * `collection_id`: ID of the collection to which an item would belong.
/// * `owner`: Address of the initial owner of the item.
/// * `data`: Token data describing the item to store on chain.
- #[weight = T::CommonWeightInfo::create_item(&data)]
- pub fn create_item(origin, collection_id: CollectionId, owner: T::CrossAccountId, data: CreateItemData) -> DispatchResultWithPostInfo {
+ #[pallet::call_index(11)]
+ #[pallet::weight(T::CommonWeightInfo::create_item(&data))]
+ pub fn create_item(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ owner: T::CrossAccountId,
+ data: CreateItemData,
+ ) -> DispatchResultWithPostInfo {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let budget = budget::Value::new(NESTING_BUDGET);
- dispatch_tx::<T, _>(collection_id, |d| d.create_item(sender, owner, data, &budget))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.create_item(sender, owner, data, &budget)
+ })
}
/// Create multiple items within a collection.
@@ -544,13 +682,21 @@
/// * `collection_id`: ID of the collection to which the tokens would belong.
/// * `owner`: Address of the initial owner of the tokens.
/// * `items_data`: Vector of data describing each item to be created.
- #[weight = T::CommonWeightInfo::create_multiple_items(&items_data)]
- pub fn create_multiple_items(origin, collection_id: CollectionId, owner: T::CrossAccountId, items_data: Vec<CreateItemData>) -> DispatchResultWithPostInfo {
+ #[pallet::call_index(12)]
+ #[pallet::weight(T::CommonWeightInfo::create_multiple_items(&items_data))]
+ pub fn create_multiple_items(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ owner: T::CrossAccountId,
+ items_data: Vec<CreateItemData>,
+ ) -> DispatchResultWithPostInfo {
ensure!(!items_data.is_empty(), Error::<T>::EmptyArgument);
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let budget = budget::Value::new(NESTING_BUDGET);
- dispatch_tx::<T, _>(collection_id, |d| d.create_multiple_items(sender, owner, items_data, &budget))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.create_multiple_items(sender, owner, items_data, &budget)
+ })
}
/// Add or change collection properties.
@@ -565,17 +711,20 @@
/// * `collection_id`: ID of the modified collection.
/// * `properties`: Vector of key-value pairs stored as the collection's metadata.
/// Keys support Latin letters, `-`, `_`, and `.` as symbols.
- #[weight = T::CommonWeightInfo::set_collection_properties(properties.len() as u32)]
+ #[pallet::call_index(13)]
+ #[pallet::weight(T::CommonWeightInfo::set_collection_properties(properties.len() as u32))]
pub fn set_collection_properties(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
- properties: Vec<Property>
+ properties: Vec<Property>,
) -> DispatchResultWithPostInfo {
ensure!(!properties.is_empty(), Error::<T>::EmptyArgument);
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
- dispatch_tx::<T, _>(collection_id, |d| d.set_collection_properties(sender, properties))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.set_collection_properties(sender, properties)
+ })
}
/// Delete specified collection properties.
@@ -590,9 +739,10 @@
/// * `collection_id`: ID of the modified collection.
/// * `property_keys`: Vector of keys of the properties to be deleted.
/// Keys support Latin letters, `-`, `_`, and `.` as symbols.
- #[weight = T::CommonWeightInfo::delete_collection_properties(property_keys.len() as u32)]
+ #[pallet::call_index(14)]
+ #[pallet::weight(T::CommonWeightInfo::delete_collection_properties(property_keys.len() as u32))]
pub fn delete_collection_properties(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
property_keys: Vec<PropertyKey>,
) -> DispatchResultWithPostInfo {
@@ -600,7 +750,9 @@
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
- dispatch_tx::<T, _>(collection_id, |d| d.delete_collection_properties(&sender, property_keys))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.delete_collection_properties(&sender, property_keys)
+ })
}
/// Add or change token properties according to collection's permissions.
@@ -621,19 +773,22 @@
/// * `token_id`: ID of the modified token.
/// * `properties`: Vector of key-value pairs stored as the token's metadata.
/// Keys support Latin letters, `-`, `_`, and `.` as symbols.
- #[weight = T::CommonWeightInfo::set_token_properties(properties.len() as u32)]
+ #[pallet::call_index(15)]
+ #[pallet::weight(T::CommonWeightInfo::set_token_properties(properties.len() as u32))]
pub fn set_token_properties(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
token_id: TokenId,
- properties: Vec<Property>
+ properties: Vec<Property>,
) -> DispatchResultWithPostInfo {
ensure!(!properties.is_empty(), Error::<T>::EmptyArgument);
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let budget = budget::Value::new(NESTING_BUDGET);
- dispatch_tx::<T, _>(collection_id, |d| d.set_token_properties(sender, token_id, properties, &budget))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.set_token_properties(sender, token_id, properties, &budget)
+ })
}
/// Delete specified token properties. Currently properties only work with NFTs.
@@ -651,19 +806,22 @@
/// * `token_id`: ID of the modified token.
/// * `property_keys`: Vector of keys of the properties to be deleted.
/// Keys support Latin letters, `-`, `_`, and `.` as symbols.
- #[weight = T::CommonWeightInfo::delete_token_properties(property_keys.len() as u32)]
+ #[pallet::call_index(16)]
+ #[pallet::weight(T::CommonWeightInfo::delete_token_properties(property_keys.len() as u32))]
pub fn delete_token_properties(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
token_id: TokenId,
- property_keys: Vec<PropertyKey>
+ property_keys: Vec<PropertyKey>,
) -> DispatchResultWithPostInfo {
ensure!(!property_keys.is_empty(), Error::<T>::EmptyArgument);
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let budget = budget::Value::new(NESTING_BUDGET);
- dispatch_tx::<T, _>(collection_id, |d| d.delete_token_properties(sender, token_id, property_keys, &budget))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.delete_token_properties(sender, token_id, property_keys, &budget)
+ })
}
/// Add or change token property permissions of a collection.
@@ -681,9 +839,10 @@
/// * `collection_id`: ID of the modified collection.
/// * `property_permissions`: Vector of permissions for property keys.
/// Keys support Latin letters, `-`, `_`, and `.` as symbols.
- #[weight = T::CommonWeightInfo::set_token_property_permissions(property_permissions.len() as u32)]
+ #[pallet::call_index(17)]
+ #[pallet::weight(T::CommonWeightInfo::set_token_property_permissions(property_permissions.len() as u32))]
pub fn set_token_property_permissions(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
property_permissions: Vec<PropertyKeyPermission>,
) -> DispatchResultWithPostInfo {
@@ -691,7 +850,9 @@
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
- dispatch_tx::<T, _>(collection_id, |d| d.set_token_property_permissions(&sender, property_permissions))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.set_token_property_permissions(&sender, property_permissions)
+ })
}
/// Create multiple items within a collection with explicitly specified initial parameters.
@@ -709,12 +870,19 @@
///
/// * `collection_id`: ID of the collection to which the tokens would belong.
/// * `data`: Explicit item creation data.
- #[weight = T::CommonWeightInfo::create_multiple_items_ex(&data)]
- pub fn create_multiple_items_ex(origin, collection_id: CollectionId, data: CreateItemExData<T::CrossAccountId>) -> DispatchResultWithPostInfo {
+ #[pallet::call_index(18)]
+ #[pallet::weight(T::CommonWeightInfo::create_multiple_items_ex(&data))]
+ pub fn create_multiple_items_ex(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ data: CreateItemExData<T::CrossAccountId>,
+ ) -> DispatchResultWithPostInfo {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let budget = budget::Value::new(NESTING_BUDGET);
- dispatch_tx::<T, _>(collection_id, |d| d.create_multiple_items_ex(sender, data, &budget))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.create_multiple_items_ex(sender, data, &budget)
+ })
}
/// Completely allow or disallow transfers for a particular collection.
@@ -727,8 +895,13 @@
///
/// * `collection_id`: ID of the collection.
/// * `value`: New value of the flag, are transfers allowed?
- #[weight = <SelfWeightOf<T>>::set_transfers_enabled_flag()]
- pub fn set_transfers_enabled_flag(origin, collection_id: CollectionId, value: bool) -> DispatchResult {
+ #[pallet::call_index(19)]
+ #[pallet::weight(<SelfWeightOf<T>>::set_transfers_enabled_flag())]
+ pub fn set_transfers_enabled_flag(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ value: bool,
+ ) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
target_collection.check_is_internal()?;
@@ -756,11 +929,18 @@
/// * Non-Fungible Mode: An NFT is indivisible, there is always 1 corresponding to an ID.
/// * Fungible Mode: The desired number of pieces to burn.
/// * Re-Fungible Mode: The desired number of pieces to burn.
- #[weight = T::CommonWeightInfo::burn_item()]
- pub fn burn_item(origin, collection_id: CollectionId, item_id: TokenId, value: u128) -> DispatchResultWithPostInfo {
+ #[pallet::call_index(20)]
+ #[pallet::weight(T::CommonWeightInfo::burn_item())]
+ pub fn burn_item(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ item_id: TokenId,
+ value: u128,
+ ) -> DispatchResultWithPostInfo {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
- let post_info = dispatch_tx::<T, _>(collection_id, |d| d.burn_item(sender, item_id, value))?;
+ let post_info =
+ dispatch_tx::<T, _>(collection_id, |d| d.burn_item(sender, item_id, value))?;
if value == 1 {
<NftTransferBasket<T>>::remove(collection_id, item_id);
<NftApproveBasket<T>>::remove(collection_id, item_id);
@@ -794,12 +974,21 @@
/// * Non-Fungible Mode: An NFT is indivisible, there is always 1 corresponding to an ID.
/// * Fungible Mode: The desired number of pieces to burn.
/// * Re-Fungible Mode: The desired number of pieces to burn.
- #[weight = T::CommonWeightInfo::burn_from()]
- pub fn burn_from(origin, collection_id: CollectionId, from: T::CrossAccountId, item_id: TokenId, value: u128) -> DispatchResultWithPostInfo {
+ #[pallet::call_index(21)]
+ #[pallet::weight(T::CommonWeightInfo::burn_from())]
+ pub fn burn_from(
+ origin: OriginFor<T>,
+ collection_id: CollectionId,
+ from: T::CrossAccountId,
+ item_id: TokenId,
+ value: u128,
+ ) -> DispatchResultWithPostInfo {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let budget = budget::Value::new(NESTING_BUDGET);
- dispatch_tx::<T, _>(collection_id, |d| d.burn_from(sender, from, item_id, value, &budget))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.burn_from(sender, from, item_id, value, &budget)
+ })
}
/// Change ownership of the token.
@@ -823,12 +1012,21 @@
/// * Non-Fungible Mode: An NFT is indivisible, there is always 1 corresponding to an ID.
/// * Fungible Mode: The desired number of pieces to transfer.
/// * Re-Fungible Mode: The desired number of pieces to transfer.
- #[weight = T::CommonWeightInfo::transfer()]
- pub fn transfer(origin, recipient: T::CrossAccountId, collection_id: CollectionId, item_id: TokenId, value: u128) -> DispatchResultWithPostInfo {
+ #[pallet::call_index(22)]
+ #[pallet::weight(T::CommonWeightInfo::transfer())]
+ pub fn transfer(
+ origin: OriginFor<T>,
+ recipient: T::CrossAccountId,
+ collection_id: CollectionId,
+ item_id: TokenId,
+ value: u128,
+ ) -> DispatchResultWithPostInfo {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let budget = budget::Value::new(NESTING_BUDGET);
- dispatch_tx::<T, _>(collection_id, |d| d.transfer(sender, recipient, item_id, value, &budget))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.transfer(sender, recipient, item_id, value, &budget)
+ })
}
/// Allow a non-permissioned address to transfer or burn an item.
@@ -846,11 +1044,20 @@
/// * `item_id`: ID of the item transactions on which are now approved.
/// * `amount`: Number of pieces of the item approved for a transaction (maximum of 1 for NFTs).
/// Set to 0 to revoke the approval.
- #[weight = T::CommonWeightInfo::approve()]
- pub fn approve(origin, spender: T::CrossAccountId, collection_id: CollectionId, item_id: TokenId, amount: u128) -> DispatchResultWithPostInfo {
+ #[pallet::call_index(23)]
+ #[pallet::weight(T::CommonWeightInfo::approve())]
+ pub fn approve(
+ origin: OriginFor<T>,
+ spender: T::CrossAccountId,
+ collection_id: CollectionId,
+ item_id: TokenId,
+ amount: u128,
+ ) -> DispatchResultWithPostInfo {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
- dispatch_tx::<T, _>(collection_id, |d| d.approve(sender, spender, item_id, amount))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.approve(sender, spender, item_id, amount)
+ })
}
/// Allow a non-permissioned address to transfer or burn an item from owner's eth mirror.
@@ -869,11 +1076,21 @@
/// * `item_id`: ID of the item transactions on which are now approved.
/// * `amount`: Number of pieces of the item approved for a transaction (maximum of 1 for NFTs).
/// Set to 0 to revoke the approval.
- #[weight = T::CommonWeightInfo::approve_from()]
- pub fn approve_from(origin, from:T::CrossAccountId, to: T::CrossAccountId, collection_id: CollectionId, item_id: TokenId, amount: u128) -> DispatchResultWithPostInfo {
+ #[pallet::call_index(24)]
+ #[pallet::weight(T::CommonWeightInfo::approve_from())]
+ pub fn approve_from(
+ origin: OriginFor<T>,
+ from: T::CrossAccountId,
+ to: T::CrossAccountId,
+ collection_id: CollectionId,
+ item_id: TokenId,
+ amount: u128,
+ ) -> DispatchResultWithPostInfo {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
- dispatch_tx::<T, _>(collection_id, |d| d.approve_from(sender, from, to, item_id, amount))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.approve_from(sender, from, to, item_id, amount)
+ })
}
/// Change ownership of an item on behalf of the owner as a non-owner account.
@@ -900,12 +1117,22 @@
/// * Non-Fungible Mode: An NFT is indivisible, there is always 1 corresponding to an ID.
/// * Fungible Mode: The desired number of pieces to transfer.
/// * Re-Fungible Mode: The desired number of pieces to transfer.
- #[weight = T::CommonWeightInfo::transfer_from()]
- pub fn transfer_from(origin, from: T::CrossAccountId, recipient: T::CrossAccountId, collection_id: CollectionId, item_id: TokenId, value: u128 ) -> DispatchResultWithPostInfo {
+ #[pallet::call_index(25)]
+ #[pallet::weight(T::CommonWeightInfo::transfer_from())]
+ pub fn transfer_from(
+ origin: OriginFor<T>,
+ from: T::CrossAccountId,
+ recipient: T::CrossAccountId,
+ collection_id: CollectionId,
+ item_id: TokenId,
+ value: u128,
+ ) -> DispatchResultWithPostInfo {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let budget = budget::Value::new(NESTING_BUDGET);
- dispatch_tx::<T, _>(collection_id, |d| d.transfer_from(sender, from, recipient, item_id, value, &budget))
+ dispatch_tx::<T, _>(collection_id, |d| {
+ d.transfer_from(sender, from, recipient, item_id, value, &budget)
+ })
}
/// Set specific limits of a collection. Empty, or None fields mean chain default.
@@ -920,9 +1147,10 @@
/// * `collection_id`: ID of the modified collection.
/// * `new_limit`: New limits of the collection. Fields that are not set (None)
/// will not overwrite the old ones.
- #[weight = <SelfWeightOf<T>>::set_collection_limits()]
+ #[pallet::call_index(26)]
+ #[pallet::weight(<SelfWeightOf<T>>::set_collection_limits())]
pub fn set_collection_limits(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
new_limit: CollectionLimits,
) -> DispatchResult {
@@ -943,19 +1171,16 @@
/// * `collection_id`: ID of the modified collection.
/// * `new_permission`: New permissions of the collection. Fields that are not set (None)
/// will not overwrite the old ones.
- #[weight = <SelfWeightOf<T>>::set_collection_limits()]
+ #[pallet::call_index(27)]
+ #[pallet::weight(<SelfWeightOf<T>>::set_collection_limits())]
pub fn set_collection_permissions(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
new_permission: CollectionPermissions,
) -> DispatchResult {
let sender = T::CrossAccountId::from_sub(ensure_signed(origin)?);
let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
- <PalletCommon<T>>::update_permissions(
- &sender,
- &mut target_collection,
- new_permission
- )
+ <PalletCommon<T>>::update_permissions(&sender, &mut target_collection, new_permission)
}
/// Re-partition a refungible token, while owning all of its parts/pieces.
@@ -969,9 +1194,10 @@
/// * `collection_id`: ID of the collection the RFT belongs to.
/// * `token_id`: ID of the RFT.
/// * `amount`: New number of parts/pieces into which the token shall be partitioned.
- #[weight = T::RefungibleExtensionsWeightInfo::repartition()]
+ #[pallet::call_index(28)]
+ #[pallet::weight(T::RefungibleExtensionsWeightInfo::repartition())]
pub fn repartition(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
token_id: TokenId,
amount: u128,
@@ -995,9 +1221,10 @@
/// * `owner`: Token owner
/// * `operator`: Operator
/// * `approve`: Should operator status be granted or revoked?
- #[weight = T::CommonWeightInfo::set_allowance_for_all()]
+ #[pallet::call_index(29)]
+ #[pallet::weight(T::CommonWeightInfo::set_allowance_for_all())]
pub fn set_allowance_for_all(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
operator: T::CrossAccountId,
approve: bool,
@@ -1013,9 +1240,10 @@
/// # Arguments
///
/// * `collection_id`: ID of the collection to repair.
- #[weight = <SelfWeightOf<T>>::force_repair_collection()]
+ #[pallet::call_index(30)]
+ #[pallet::weight(<SelfWeightOf<T>>::force_repair_collection())]
pub fn force_repair_collection(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
) -> DispatchResult {
ensure_root(origin)?;
@@ -1028,69 +1256,71 @@
///
/// * `collection_id`: ID of the collection the item belongs to.
/// * `item_id`: ID of the item.
- #[weight = T::CommonWeightInfo::force_repair_item()]
+ #[pallet::call_index(31)]
+ #[pallet::weight(T::CommonWeightInfo::force_repair_item())]
pub fn force_repair_item(
- origin,
+ origin: OriginFor<T>,
collection_id: CollectionId,
item_id: TokenId,
) -> DispatchResultWithPostInfo {
ensure_root(origin)?;
- dispatch_tx::<T, _>(collection_id, |d| {
- d.repair_item(item_id)
- })
+ dispatch_tx::<T, _>(collection_id, |d| d.repair_item(item_id))
}
}
-}
-impl<T: Config> Pallet<T> {
- /// Force set `sponsor` for `collection`.
- ///
- /// Differs from [`set_collection_sponsor`][`Pallet::set_collection_sponsor`] in that confirmation
- /// from the `sponsor` is not required.
- ///
- /// # Arguments
- ///
- /// * `sponsor`: ID of the account of the sponsor-to-be.
- /// * `collection_id`: ID of the modified collection.
- pub fn force_set_sponsor(sponsor: T::AccountId, collection_id: CollectionId) -> DispatchResult {
- let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
- target_collection.force_set_sponsor(sponsor.clone())
- }
+ impl<T: Config> Pallet<T> {
+ /// Force set `sponsor` for `collection`.
+ ///
+ /// Differs from [`set_collection_sponsor`][`Pallet::set_collection_sponsor`] in that confirmation
+ /// from the `sponsor` is not required.
+ ///
+ /// # Arguments
+ ///
+ /// * `sponsor`: ID of the account of the sponsor-to-be.
+ /// * `collection_id`: ID of the modified collection.
+ pub fn force_set_sponsor(
+ sponsor: T::AccountId,
+ collection_id: CollectionId,
+ ) -> DispatchResult {
+ let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
+ target_collection.force_set_sponsor(sponsor.clone())
+ }
- /// Force remove `sponsor` for `collection`.
- ///
- /// Differs from `remove_sponsor` in that
- /// it doesn't require consent from the `owner` of the collection.
- ///
- /// # Arguments
- ///
- /// * `collection_id`: ID of the modified collection.
- pub fn force_remove_collection_sponsor(collection_id: CollectionId) -> DispatchResult {
- let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
- target_collection.force_remove_sponsor()
- }
+ /// Force remove `sponsor` for `collection`.
+ ///
+ /// Differs from `remove_sponsor` in that
+ /// it doesn't require consent from the `owner` of the collection.
+ ///
+ /// # Arguments
+ ///
+ /// * `collection_id`: ID of the modified collection.
+ pub fn force_remove_collection_sponsor(collection_id: CollectionId) -> DispatchResult {
+ let mut target_collection = <CollectionHandle<T>>::try_get(collection_id)?;
+ target_collection.force_remove_sponsor()
+ }
- #[inline(always)]
- pub(crate) fn destroy_collection_internal(
- sender: T::CrossAccountId,
- collection_id: CollectionId,
- ) -> DispatchResult {
- let collection = <CollectionHandle<T>>::try_get(collection_id)?;
- collection.check_is_internal()?;
+ #[inline(always)]
+ pub(crate) fn destroy_collection_internal(
+ sender: T::CrossAccountId,
+ collection_id: CollectionId,
+ ) -> DispatchResult {
+ let collection = <CollectionHandle<T>>::try_get(collection_id)?;
+ collection.check_is_internal()?;
- T::CollectionDispatch::destroy(sender, collection)?;
+ T::CollectionDispatch::destroy(sender, collection)?;
- // TODO: basket cleanup should be moved elsewhere
- // Maybe runtime dispatch.rs should perform it?
+ // TODO: basket cleanup should be moved elsewhere
+ // Maybe runtime dispatch.rs should perform it?
- let _ = <NftTransferBasket<T>>::clear_prefix(collection_id, u32::MAX, None);
- let _ = <FungibleTransferBasket<T>>::clear_prefix(collection_id, u32::MAX, None);
- let _ = <ReFungibleTransferBasket<T>>::clear_prefix((collection_id,), u32::MAX, None);
+ let _ = <NftTransferBasket<T>>::clear_prefix(collection_id, u32::MAX, None);
+ let _ = <FungibleTransferBasket<T>>::clear_prefix(collection_id, u32::MAX, None);
+ let _ = <ReFungibleTransferBasket<T>>::clear_prefix((collection_id,), u32::MAX, None);
- let _ = <NftApproveBasket<T>>::clear_prefix(collection_id, u32::MAX, None);
- let _ = <FungibleApproveBasket<T>>::clear_prefix(collection_id, u32::MAX, None);
- let _ = <RefungibleApproveBasket<T>>::clear_prefix((collection_id,), u32::MAX, None);
+ let _ = <NftApproveBasket<T>>::clear_prefix(collection_id, u32::MAX, None);
+ let _ = <FungibleApproveBasket<T>>::clear_prefix(collection_id, u32::MAX, None);
+ let _ = <RefungibleApproveBasket<T>>::clear_prefix((collection_id,), u32::MAX, None);
- Ok(())
+ Ok(())
+ }
}
}
runtime/common/sponsoring.rsdiffbeforeafterboth--- a/runtime/common/sponsoring.rs
+++ b/runtime/common/sponsoring.rs
@@ -18,7 +18,6 @@
use up_sponsorship::SponsorshipHandler;
use frame_support::{
traits::{IsSubType},
- storage::{StorageMap, StorageDoubleMap, StorageNMap},
};
use up_data_structs::{
CollectionId, FUNGIBLE_SPONSOR_TRANSFER_TIMEOUT, NFT_SPONSOR_TRANSFER_TIMEOUT,