git.delta.rocks / unique-network / refs/commits / cf884d838f57

difftreelog

feat(rmrk-rpc) decoding properties

Fahrrader2022-05-24parent: #bdae39b.patch.diff
in: master

3 files changed

modifiedpallets/proxy-rmrk-core/src/lib.rsdiffbeforeafterboth
--- a/pallets/proxy-rmrk-core/src/lib.rs
+++ b/pallets/proxy-rmrk-core/src/lib.rs
@@ -420,7 +420,7 @@
         Ok(())
     }
 
-    fn get_typed_nft_collection(
+    pub fn get_typed_nft_collection(
         collection_id: CollectionId,
         collection_type: CollectionType
     ) -> Result<NonfungibleHandle<T>, DispatchError> {
modifiedpallets/proxy-rmrk-core/src/misc.rsdiffbeforeafterboth
--- a/pallets/proxy-rmrk-core/src/misc.rs
+++ b/pallets/proxy-rmrk-core/src/misc.rs
@@ -82,6 +82,18 @@
     }
 }
 
+pub trait RmrkDecode<T: Decode> {
+    fn decode_property(&self) -> Option<T>;
+}
+
+impl<T: Decode> RmrkDecode<T> for RmrkString {
+    fn decode_property(&self) -> Option<T> { // todo access runtime errors? // but then rmrk_nft_type must have it too
+        let mut value = self.as_slice();
+
+        T::decode(&mut value).ok()
+    }
+}
+
 #[derive(Encode, Decode, PartialEq, Eq)]
 pub enum CollectionType {
     Regular,
modifiedruntime/common/src/runtime_apis.rsdiffbeforeafterboth
148 // TODO decide on displacement to palettes -- does RMRK belong there, spread across common and nonfungible?148 // TODO decide on displacement to palettes -- does RMRK belong there, spread across common and nonfungible?
149 use frame_support::BoundedVec;149 use frame_support::BoundedVec;
150 use scale_info::prelude::string::String;150 use scale_info::prelude::string::String;
151 use pallet_proxy_rmrk_core::RmrkProperty;151 use pallet_proxy_rmrk_core::{RmrkProperty, misc::CollectionType};
152152
153 // todo check if this is a rmrk collection? or simply trust and provide anyway?153 // todo check if this is a rmrk standard collection? or simply trust and provide anyway?
154 // client-is-always-right / enforce authority and order ?154 // client-is-always-right / enforce authority and order ?
155155
156 let collection_id = CollectionId(collection_id);156 let collection_id = CollectionId(collection_id);
157 let collection = <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_nft_collection(collection_id)?;157 let collection = <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_typed_nft_collection(collection_id, CollectionType::Regular)?;
158 // todo Vec::from(["rmrk:metadata", "rmrk:collection-type"])158
159 let metadata = BoundedVec::try_from(159 let metadata = BoundedVec::try_from(
160 <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_collection_property(collection_id, RmrkProperty::Metadata)?.into_inner()160 <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_collection_property(collection_id, RmrkProperty::Metadata)?.into_inner()
161 ).map_err(|_| <pallet_common::Error<Runtime>>::PropertyKeyIsTooLong)?;//unwrap_or_default();161 ).map_err(|_| <pallet_common::Error<Runtime>>::PropertyKeyIsTooLong)?;
162
162 let nfts_count = (dispatch_unique_runtime!(collection_id.total_supply()) as Result<u32, DispatchError>)?; // todo? <Runtime>::total_supply(collection_id)163 let nfts_count = (dispatch_unique_runtime!(collection_id.total_supply()) as Result<u32, DispatchError>)?; // todo? <Runtime>::total_supply(collection_id)
163164
174 fn nft_by_id(collection_id: RmrkCollectionId, nft_by_id: RmrkNftId) -> Result<Option<RmrkInstanceInfo<AccountId>>, DispatchError> {175 fn nft_by_id(collection_id: RmrkCollectionId, nft_by_id: RmrkNftId) -> Result<Option<RmrkInstanceInfo<AccountId>>, DispatchError> {
175 use frame_support::BoundedVec;176 use frame_support::BoundedVec;
176 use up_data_structs::mapping::TokenAddressMapping;177 use up_data_structs::mapping::TokenAddressMapping;
177 use pallet_proxy_rmrk_core::RmrkProperty;178 use pallet_proxy_rmrk_core::{RmrkProperty, misc::RmrkDecode};
178179
179 let collection_id = CollectionId(collection_id);180 let collection_id = CollectionId(collection_id);
180 let nft_id = TokenId(nft_by_id);181 let nft_id = TokenId(nft_by_id);
187 None => return Ok(None)188 None => return Ok(None)
188 };189 };
189190
191 // todo displace querying property key array to rmrk proxy pallet
190 let keys = [192 let keys = [
191 RmrkProperty::RoyaltyInfo,193 RmrkProperty::RoyaltyInfo,
192 RmrkProperty::Metadata,194 RmrkProperty::Metadata,
196198
197 let properties = keys.into_iter().map(199 let properties = keys.into_iter().map(
198 |key| BoundedVec::try_from(200 |key| BoundedVec::try_from(
199 // todo nft property, not collection
200 <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_nft_property(collection_id, nft_id, key).unwrap().into_inner()201 <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_nft_property(collection_id, nft_id, key).unwrap().into_inner()
201 ).unwrap()202 ).unwrap()
202 )203 )
203 .collect::<Vec<RmrkString>>();204 .collect::<Vec<RmrkString>>();
205
206 let allowance = pallet_nonfungible::Allowance::<Runtime>::get((collection_id, nft_id));
204207
205 Ok(Some(RmrkInstanceInfo {208 Ok(Some(RmrkInstanceInfo {
206 owner: owner,209 owner: owner,
207 //recipient: , // prop?210 //recipient: , // prop?
208 royalty: None,//Permill::from_percent(0), // prop, decode211 royalty: properties[0].clone().decode_property().unwrap(),
209 metadata: properties[1].clone(),212 metadata: properties[1].clone(),
210 equipped: false, // prop, decode213 equipped: properties[2].clone().decode_property().unwrap(),
211 pending: false, // prop, decode214 pending: allowance.is_some(),
212 }))215 }))
213 }216 }
214 fn account_tokens(account_id: AccountId, collection_id: RmrkCollectionId) -> Result<Vec<RmrkNftId>, DispatchError> {217 fn account_tokens(account_id: AccountId, collection_id: RmrkCollectionId) -> Result<Vec<RmrkNftId>, DispatchError> {
234 Ok(237 Ok(
235 pallet_nonfungible::Owned::<Runtime>::iter_prefix((collection_id, cross_account_id))238 pallet_nonfungible::Owned::<Runtime>::iter_prefix((collection_id, cross_account_id))
236 .map(|(child_id, _)| RmrkNftChild {239 .map(|(child_id, _)| RmrkNftChild {
237 collection_id: collection_id.0, // todo make sure they're always from this collection240 collection_id: collection_id.0, // todo make sure they're always from this collection // spoiler: they're not
238 nft_id: child_id.0,241 nft_id: child_id.0,
239 })242 })
240 .collect()243 .collect()
315 let nft_id = TokenId(nft_id);318 let nft_id = TokenId(nft_id);
316319
317 // let keys = [320 // let keys = [
318 // RmrkProperty::Royalty,321 // RmrkProperty::RoyaltyInfo,
319 // RmrkProperty::Metadata,322 // RmrkProperty::Metadata,
320 // RmrkProperty::Equipped,323 // RmrkProperty::Equipped,
321 // RmrkProperty::Pending,324 // RmrkProperty::Pending,
339 fn base(base_id: RmrkBaseId) -> Result<Option<RmrkBaseInfo<AccountId>>, DispatchError> {342 fn base(base_id: RmrkBaseId) -> Result<Option<RmrkBaseInfo<AccountId>>, DispatchError> {
340 use frame_support::BoundedVec;343 use frame_support::BoundedVec;
341 use scale_info::prelude::string::String;344 use scale_info::prelude::string::String;
342 use pallet_proxy_rmrk_core::RmrkProperty;345 use pallet_proxy_rmrk_core::{RmrkProperty, misc::CollectionType};
343346
344 let collection_id = CollectionId(base_id);347 let collection_id = CollectionId(base_id);
345 let collection = <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_nft_collection(collection_id)?;348 let collection = <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_typed_nft_collection(collection_id, CollectionType::Base)?;
349 // todo check prop for being a base
346350
347 // todo export to macro? redundancy351 // todo export to macro? redundancy
348 let keys = [352 let keys = [
368 }372 }
369 fn base_parts(base_id: RmrkBaseId) -> Result<Vec<RmrkPartType>, DispatchError> {373 fn base_parts(base_id: RmrkBaseId) -> Result<Vec<RmrkPartType>, DispatchError> {
370 use frame_support::BoundedVec;374 use frame_support::BoundedVec;
371 use pallet_proxy_rmrk_core::RmrkProperty;375 use pallet_proxy_rmrk_core::{RmrkProperty, misc::{RmrkNft, RmrkDecode}};
372376
373 let collection_id = CollectionId(base_id);377 let collection_id = CollectionId(base_id);
374378 // todo check prop for being a base
375 let keys = [
376 //RmrkProperty::NftType)?,
377 //RmrkProperty::PartId)?,
378 RmrkProperty::Src,
379 RmrkProperty::ZIndex,
380 RmrkProperty::EquippableList,
381 ];
382379
383 let parts = (dispatch_unique_runtime!(collection_id.collection_tokens()) as Result<Vec<TokenId>, DispatchError>)?380 let parts = (dispatch_unique_runtime!(collection_id.collection_tokens()) as Result<Vec<TokenId>, DispatchError>)?
384 .iter()381 .iter()
385 .filter_map(|token_id| {382 .filter_map(|token_id| {
386 /*let properties = keys.into_iter().map(
387 |key| BoundedVec::try_from(
388 <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_nft_property(collection_id, *token_id, key).unwrap().into_inner()
389 ).unwrap()
390 ).collect::<Vec<RmrkString>>();*/
391
392 // todo ping properties for "rmrk:nft-type"
393 // if none, skip, None
394 let nft_type = "fixed-part";383 let nft_type = <pallet_nonfungible::TokenData<Runtime>>::get((collection_id, token_id))
384 //.map_err(|_| ) // no need, tis a filter_map
385 .unwrap()
386 .rmrk_nft_type()?;
387
388 // dislocate to rmrkproxycore and simply send an array of keys
389 let keys = [
390 //RmrkProperty::PartId)?,
391 RmrkProperty::Src,
392 RmrkProperty::ZIndex,
393 RmrkProperty::EquippableList,
394 ];
395
396 let properties = keys.into_iter().map(
397 |key| BoundedVec::try_from(
398 <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_nft_property(collection_id, *token_id, key).unwrap().into_inner()
399 ).unwrap()
400 ).collect::<Vec<RmrkString>>();
395401
396 match nft_type {402 match nft_type {
397 "fixed-part" => Some(RmrkPartType::FixedPart(RmrkFixedPart {403 FixedPart => Some(RmrkPartType::FixedPart(RmrkFixedPart {
398 id: token_id.0,404 id: token_id.0,
399 src: BoundedVec::default(), // "rmrk:src"405 src: properties[0].clone().decode_property().unwrap(),
400 z: 0, // "rmrk:z-index"406 z: properties[1].clone().decode_property().unwrap(),
401 })),407 })),
402 "slot-part" => Some(RmrkPartType::SlotPart(RmrkSlotPart {408 SlotPart => Some(RmrkPartType::SlotPart(RmrkSlotPart {
403 id: token_id.0,409 id: token_id.0,
404 equippable: RmrkEquippableList::Empty, // "rmrk:equippable-list" ?
405 src: BoundedVec::default(), // "rmrk:src"410 src: properties[0].clone().decode_property().unwrap(),
406 z: 0, // "rmrk:z-index"411 z: properties[1].clone().decode_property().unwrap(),
412 equippable: properties[2].clone().decode_property().unwrap(),
407 })),413 })),
408 _ => None414 _ => None
409 }415 }
415 }420 }
416 fn theme_names(base_id: RmrkBaseId) -> Result<Vec<RmrkThemeName>, DispatchError> {421 fn theme_names(base_id: RmrkBaseId) -> Result<Vec<RmrkThemeName>, DispatchError> {
417 use frame_support::BoundedVec;422 use frame_support::BoundedVec;
423 use pallet_proxy_rmrk_core::{RmrkProperty, misc::{RmrkNft, RmrkDecode}};
418424
419 let collection_id = CollectionId(base_id);425 let collection_id = CollectionId(base_id);
426 // todo make sure this is theme
420427
421 let theme_names = (dispatch_unique_runtime!(collection_id.collection_tokens()) as Result<Vec<TokenId>, DispatchError>)?428 let theme_names = (dispatch_unique_runtime!(collection_id.collection_tokens()) as Result<Vec<TokenId>, DispatchError>)?
422 .iter()429 .iter()
423 .filter_map(|token_id| {430 .filter_map(|token_id| {
424 let properties = pallet_nonfungible::Pallet::<Runtime>::token_properties((collection_id, token_id));431 let nft_type = <pallet_nonfungible::TokenData<Runtime>>::get((collection_id, token_id))
425432 .unwrap()
426 // todo ping property for "rmrk:nft-type"433 .rmrk_nft_type()?;
427 // if none or not "theme", skip, None434
428 let nft_type = "theme";435 match nft_type {
429 // can't call dispatch_unique_runtime! from here??436 Theme => Some(
430 <pallet_nonfungible::TokenData<Runtime>>::get((collection_id, token_id))437 <pallet_proxy_rmrk_core::Pallet<Runtime>>::get_nft_property(
438 collection_id, *token_id, RmrkProperty::ThemeName
431 .map(|t| t.const_data.into_inner())439 ).unwrap()
432 //.unwrap_or_default()440 .into_inner()
433 // todo rework to reduce independence441 ),
442 _ => None
443 }
434 })444 })
435 .collect();445 .collect::<Vec<RmrkThemeName>>();
436446
437 Ok(theme_names)447 Ok(theme_names)
438 }448 }