difftreelog
feat make collection ERC721 compatible
in: master
4 files changed
pallets/unique/src/eth/mod.rsdiffbeforeafterboth--- a/pallets/unique/src/eth/mod.rs
+++ b/pallets/unique/src/eth/mod.rs
@@ -27,6 +27,7 @@
CollectionHelpersEvents,
static_property::{key, value as property_value},
},
+ Pallet as PalletCommon,
};
use pallet_evm_coder_substrate::{dispatch_to_evm, SubstrateRecorder, WithRecorder};
use pallet_evm::{account::CrossAccountId, OnMethodCall, PrecompileHandle, PrecompileResult};
@@ -340,6 +341,83 @@
)
}
+ #[solidity(rename_selector = "makeCollectionERC721MetadataCompatible")]
+ fn make_collection_metadata_compatible(
+ &mut self,
+ caller: caller,
+ collection: address,
+ base_uri: string,
+ ) -> Result<()> {
+ let caller = T::CrossAccountId::from_eth(caller);
+ let collection =
+ pallet_common::eth::map_eth_to_id(&collection).ok_or("not a collection address")?;
+ let mut collection =
+ <crate::CollectionHandle<T>>::new(collection).ok_or("collection not found")?;
+
+ if !matches!(
+ collection.mode,
+ CollectionMode::NFT | CollectionMode::ReFungible
+ ) {
+ return Err("target collection should be either NFT or Refungible".into());
+ }
+
+ self.recorder().consume_sstore()?;
+ collection
+ .check_is_owner_or_admin(&caller)
+ .map_err(dispatch_to_evm::<T>)?;
+
+ if collection.flags.erc721metadata {
+ return Err("target collection is already Erc721Metadata compatible".into());
+ }
+ collection.flags.erc721metadata = true;
+
+ let all_permissions = <pallet_common::CollectionPropertyPermissions<T>>::get(collection.id);
+ if all_permissions.get(&key::url()).is_none() {
+ self.recorder().consume_sstore()?;
+ <PalletCommon<T>>::set_property_permission(&collection, &caller, default_url_pkp())
+ .map_err(dispatch_to_evm::<T>)?;
+ }
+ if all_permissions.get(&key::suffix()).is_none() {
+ self.recorder().consume_sstore()?;
+ <PalletCommon<T>>::set_property_permission(&collection, &caller, default_suffix_pkp())
+ .map_err(dispatch_to_evm::<T>)?;
+ }
+
+ let all_properties = <pallet_common::CollectionProperties<T>>::get(collection.id);
+ let mut new_properties = vec![];
+ if all_properties.get(&key::schema_name()).is_none() {
+ self.recorder().consume_sstore()?;
+ new_properties.push(up_data_structs::Property {
+ key: key::schema_name(),
+ value: property_value::erc721(),
+ });
+ new_properties.push(up_data_structs::Property {
+ key: key::schema_version(),
+ value: property_value::schema_version(),
+ });
+ }
+ if all_properties.get(&key::base_uri()).is_none() && !base_uri.is_empty() {
+ new_properties.push(up_data_structs::Property {
+ key: key::base_uri(),
+ value: base_uri
+ .into_bytes()
+ .try_into()
+ .map_err(|_| "base uri is too large")?,
+ });
+ }
+
+ if !new_properties.is_empty() {
+ self.recorder().consume_sstore()?;
+ <PalletCommon<T>>::set_collection_properties(&collection, &caller, new_properties)
+ .map_err(dispatch_to_evm::<T>)?;
+ }
+
+ self.recorder().consume_sstore()?;
+ collection.save().map_err(dispatch_to_evm::<T>)?;
+
+ Ok(())
+ }
+
/// Check if a collection exists
/// @param collectionAddress Address of the collection in question
/// @return bool Does the collection exist?
pallets/unique/src/eth/stubs/CollectionHelpers.soldiffbeforeafterboth1// SPDX-License-Identifier: OTHER2// This code is automatically generated34pragma solidity >=0.8.0 <0.9.0;56/// @dev common stubs holder7contract Dummy {8 uint8 dummy;9 string stub_error = "this contract is implemented in native";10}1112contract ERC165 is Dummy {13 function supportsInterface(bytes4 interfaceID) external view returns (bool) {14 require(false, stub_error);15 interfaceID;16 return true;17 }18}1920/// @dev inlined interface21contract CollectionHelpersEvents {22 event CollectionCreated(address indexed owner, address indexed collectionId);23}2425/// @title Contract, which allows users to operate with collections26/// @dev the ERC-165 identifier for this interface is 0xd14d122127contract CollectionHelpers is Dummy, ERC165, CollectionHelpersEvents {28 /// Create an NFT collection29 /// @param name Name of the collection30 /// @param description Informative description of the collection31 /// @param tokenPrefix Token prefix to represent the collection tokens in UI and user applications32 /// @return address Address of the newly created collection33 /// @dev EVM selector for this function is: 0x844af658,34 /// or in textual repr: createNFTCollection(string,string,string)35 function createNFTCollection(36 string memory name,37 string memory description,38 string memory tokenPrefix39 ) public payable returns (address) {40 require(false, stub_error);41 name;42 description;43 tokenPrefix;44 dummy = 0;45 return 0x0000000000000000000000000000000000000000;46 }4748 /// Create an NFT collection49 /// @param name Name of the collection50 /// @param description Informative description of the collection51 /// @param tokenPrefix Token prefix to represent the collection tokens in UI and user applications52 /// @return address Address of the newly created collection53 /// @dev EVM selector for this function is: 0xe34a6844,54 /// or in textual repr: createNonfungibleCollection(string,string,string)55 function createNonfungibleCollection(56 string memory name,57 string memory description,58 string memory tokenPrefix59 ) public payable returns (address) {60 require(false, stub_error);61 name;62 description;63 tokenPrefix;64 dummy = 0;65 return 0x0000000000000000000000000000000000000000;66 }6768 /// @dev EVM selector for this function is: 0xa9e7b5c0,69 /// or in textual repr: createERC721MetadataCompatibleNFTCollection(string,string,string,string)70 function createERC721MetadataCompatibleNFTCollection(71 string memory name,72 string memory description,73 string memory tokenPrefix,74 string memory baseUri75 ) public payable returns (address) {76 require(false, stub_error);77 name;78 description;79 tokenPrefix;80 baseUri;81 dummy = 0;82 return 0x0000000000000000000000000000000000000000;83 }8485 /// @dev EVM selector for this function is: 0xab173450,86 /// or in textual repr: createRFTCollection(string,string,string)87 function createRFTCollection(88 string memory name,89 string memory description,90 string memory tokenPrefix91 ) public payable returns (address) {92 require(false, stub_error);93 name;94 description;95 tokenPrefix;96 dummy = 0;97 return 0x0000000000000000000000000000000000000000;98 }99100 /// @dev EVM selector for this function is: 0xa5596388,101 /// or in textual repr: createERC721MetadataCompatibleRFTCollection(string,string,string,string)102 function createERC721MetadataCompatibleRFTCollection(103 string memory name,104 string memory description,105 string memory tokenPrefix,106 string memory baseUri107 ) public payable returns (address) {108 require(false, stub_error);109 name;110 description;111 tokenPrefix;112 baseUri;113 dummy = 0;114 return 0x0000000000000000000000000000000000000000;115 }116117 /// Check if a collection exists118 /// @param collectionAddress Address of the collection in question119 /// @return bool Does the collection exist?120 /// @dev EVM selector for this function is: 0xc3de1494,121 /// or in textual repr: isCollectionExist(address)122 function isCollectionExist(address collectionAddress) public view returns (bool) {123 require(false, stub_error);124 collectionAddress;125 dummy;126 return false;127 }128129 /// @dev EVM selector for this function is: 0xd23a7ab1,130 /// or in textual repr: collectionCreationFee()131 function collectionCreationFee() public view returns (uint256) {132 require(false, stub_error);133 dummy;134 return 0;135 }136}1// SPDX-License-Identifier: OTHER2// This code is automatically generated34pragma solidity >=0.8.0 <0.9.0;56/// @dev common stubs holder7contract Dummy {8 uint8 dummy;9 string stub_error = "this contract is implemented in native";10}1112contract ERC165 is Dummy {13 function supportsInterface(bytes4 interfaceID) external view returns (bool) {14 require(false, stub_error);15 interfaceID;16 return true;17 }18}1920/// @dev inlined interface21contract CollectionHelpersEvents {22 event CollectionCreated(address indexed owner, address indexed collectionId);23}2425/// @title Contract, which allows users to operate with collections26/// @dev the ERC-165 identifier for this interface is 0x542f507927contract CollectionHelpers is Dummy, ERC165, CollectionHelpersEvents {28 /// Create an NFT collection29 /// @param name Name of the collection30 /// @param description Informative description of the collection31 /// @param tokenPrefix Token prefix to represent the collection tokens in UI and user applications32 /// @return address Address of the newly created collection33 /// @dev EVM selector for this function is: 0x844af658,34 /// or in textual repr: createNFTCollection(string,string,string)35 function createNFTCollection(36 string memory name,37 string memory description,38 string memory tokenPrefix39 ) public payable returns (address) {40 require(false, stub_error);41 name;42 description;43 tokenPrefix;44 dummy = 0;45 return 0x0000000000000000000000000000000000000000;46 }4748 /// Create an NFT collection49 /// @param name Name of the collection50 /// @param description Informative description of the collection51 /// @param tokenPrefix Token prefix to represent the collection tokens in UI and user applications52 /// @return address Address of the newly created collection53 /// @dev EVM selector for this function is: 0xe34a6844,54 /// or in textual repr: createNonfungibleCollection(string,string,string)55 function createNonfungibleCollection(56 string memory name,57 string memory description,58 string memory tokenPrefix59 ) public payable returns (address) {60 require(false, stub_error);61 name;62 description;63 tokenPrefix;64 dummy = 0;65 return 0x0000000000000000000000000000000000000000;66 }6768 /// @dev EVM selector for this function is: 0xa9e7b5c0,69 /// or in textual repr: createERC721MetadataCompatibleNFTCollection(string,string,string,string)70 function createERC721MetadataCompatibleNFTCollection(71 string memory name,72 string memory description,73 string memory tokenPrefix,74 string memory baseUri75 ) public payable returns (address) {76 require(false, stub_error);77 name;78 description;79 tokenPrefix;80 baseUri;81 dummy = 0;82 return 0x0000000000000000000000000000000000000000;83 }8485 /// @dev EVM selector for this function is: 0xab173450,86 /// or in textual repr: createRFTCollection(string,string,string)87 function createRFTCollection(88 string memory name,89 string memory description,90 string memory tokenPrefix91 ) public payable returns (address) {92 require(false, stub_error);93 name;94 description;95 tokenPrefix;96 dummy = 0;97 return 0x0000000000000000000000000000000000000000;98 }99100 /// @dev EVM selector for this function is: 0xa5596388,101 /// or in textual repr: createERC721MetadataCompatibleRFTCollection(string,string,string,string)102 function createERC721MetadataCompatibleRFTCollection(103 string memory name,104 string memory description,105 string memory tokenPrefix,106 string memory baseUri107 ) public payable returns (address) {108 require(false, stub_error);109 name;110 description;111 tokenPrefix;112 baseUri;113 dummy = 0;114 return 0x0000000000000000000000000000000000000000;115 }116117 /// @dev EVM selector for this function is: 0x85624258,118 /// or in textual repr: makeCollectionERC721MetadataCompatible(address,string)119 function makeCollectionERC721MetadataCompatible(address collection, string memory baseUri) public {120 require(false, stub_error);121 collection;122 baseUri;123 dummy = 0;124 }125126 /// Check if a collection exists127 /// @param collectionAddress Address of the collection in question128 /// @return bool Does the collection exist?129 /// @dev EVM selector for this function is: 0xc3de1494,130 /// or in textual repr: isCollectionExist(address)131 function isCollectionExist(address collectionAddress) public view returns (bool) {132 require(false, stub_error);133 collectionAddress;134 dummy;135 return false;136 }137138 /// @dev EVM selector for this function is: 0xd23a7ab1,139 /// or in textual repr: collectionCreationFee()140 function collectionCreationFee() public view returns (uint256) {141 require(false, stub_error);142 dummy;143 return 0;144 }145}tests/src/eth/api/CollectionHelpers.soldiffbeforeafterboth--- a/tests/src/eth/api/CollectionHelpers.sol
+++ b/tests/src/eth/api/CollectionHelpers.sol
@@ -18,7 +18,7 @@
}
/// @title Contract, which allows users to operate with collections
-/// @dev the ERC-165 identifier for this interface is 0xd14d1221
+/// @dev the ERC-165 identifier for this interface is 0x542f5079
interface CollectionHelpers is Dummy, ERC165, CollectionHelpersEvents {
/// Create an NFT collection
/// @param name Name of the collection
@@ -72,6 +72,10 @@
string memory baseUri
) external payable returns (address);
+ /// @dev EVM selector for this function is: 0x85624258,
+ /// or in textual repr: makeCollectionERC721MetadataCompatible(address,string)
+ function makeCollectionERC721MetadataCompatible(address collection, string memory baseUri) external;
+
/// Check if a collection exists
/// @param collectionAddress Address of the collection in question
/// @return bool Does the collection exist?
tests/src/eth/collectionHelpersAbi.jsondiffbeforeafterboth--- a/tests/src/eth/collectionHelpersAbi.json
+++ b/tests/src/eth/collectionHelpersAbi.json
@@ -97,6 +97,16 @@
},
{
"inputs": [
+ { "internalType": "address", "name": "collection", "type": "address" },
+ { "internalType": "string", "name": "baseUri", "type": "string" }
+ ],
+ "name": "makeCollectionERC721MetadataCompatible",
+ "outputs": [],
+ "stateMutability": "nonpayable",
+ "type": "function"
+ },
+ {
+ "inputs": [
{ "internalType": "bytes4", "name": "interfaceID", "type": "bytes4" }
],
"name": "supportsInterface",