diff --git a/contracts/feature-tests/basic-features/scenarios/storage_mapper_get_at_address.scen.json b/contracts/feature-tests/basic-features/scenarios/storage_mapper_get_at_address.scen.json index 3076c1e82b..77ffdda1ee 100644 --- a/contracts/feature-tests/basic-features/scenarios/storage_mapper_get_at_address.scen.json +++ b/contracts/feature-tests/basic-features/scenarios/storage_mapper_get_at_address.scen.json @@ -332,7 +332,9 @@ "from": "address:an_account", "to": "sc:caller", "function": "contains_unordered_at_address", - "arguments": ["5"], + "arguments": [ + "5" + ], "gasLimit": "50,000,000", "gasPrice": "0" }, diff --git a/contracts/feature-tests/basic-features/scenarios/storage_mapper_get_at_address_extra_key.scen.json b/contracts/feature-tests/basic-features/scenarios/storage_mapper_get_at_address_extra_key.scen.json new file mode 100644 index 0000000000..e124fd7e1a --- /dev/null +++ b/contracts/feature-tests/basic-features/scenarios/storage_mapper_get_at_address_extra_key.scen.json @@ -0,0 +1,90 @@ +{ + "name": "storage mapper get at address", + "gasSchedule": "v3", + "steps": [ + { + "step": "setState", + "accounts": { + "sc:basic-features": { + "nonce": "0", + "balance": "0", + "code": "mxsc:../output/basic-features.mxsc.json" + }, + "sc:with-storage": { + "nonce": "0", + "balance": "0", + "code": "mxsc:../output/basic-features.mxsc.json" + }, + "address:an_account": { + "nonce": "0", + "balance": "0" + } + } + }, + { + "step": "scCall", + "id": "set single_value_with_keys", + "tx": { + "from": "address:an_account", + "to": "sc:with-storage", + "function": "set_single_value_mapper_with_key", + "arguments": [ + "5", + "str:to-read" + ], + "gasLimit": "50,000,000", + "gasPrice": "0" + }, + "expect": { + "out": [], + "status": "", + "logs": "*", + "gas": "*", + "refund": "*" + } + }, + { + "step": "scQuery", + "id": "check single_value_with_keys", + "tx": { + "to": "sc:basic-features", + "function": "get_value_from_address_with_keys", + "arguments": [ + "sc:with-storage", + "5" + ] + }, + "expect": { + "out": [ + "str:to-read" + ], + "status": "", + "logs": "*", + "gas": "*", + "refund": "*" + } + }, + { + "step": "checkState", + "accounts": { + "sc:basic-features": { + "nonce": "0", + "balance": "0", + "code": "mxsc:../output/basic-features.mxsc.json" + }, + "sc:with-storage": { + "nonce": "0", + "balance": "0", + "storage": { + "str:single_value_mapper_with_key|0x00000005": "str:to-read" + }, + "code": "mxsc:../output/basic-features.mxsc.json" + }, + "address:an_account": { + "nonce": "*", + "balance": "0" + } + } + } + ] +} \ No newline at end of file diff --git a/contracts/feature-tests/basic-features/src/basic_features_main.rs b/contracts/feature-tests/basic-features/src/basic_features_main.rs index 2f0cb9a830..d88ab8bad6 100644 --- a/contracts/feature-tests/basic-features/src/basic_features_main.rs +++ b/contracts/feature-tests/basic-features/src/basic_features_main.rs @@ -32,6 +32,7 @@ pub mod storage_mapper_set; pub mod storage_mapper_single; pub mod storage_mapper_token_attributes; pub mod storage_mapper_unique_id_mapper; +pub mod storage_mapper_unordered_set; pub mod storage_mapper_vec; pub mod storage_mapper_whitelist; pub mod storage_raw_api_features; @@ -71,6 +72,7 @@ pub trait BasicFeatures: + storage_mapper_fungible_token::FungibleTokenMapperFeatures + storage_mapper_non_fungible_token::NonFungibleTokenMapperFeatures + storage_mapper_unique_id_mapper::UniqueIdMapperFeatures + + storage_mapper_unordered_set::UnorderedSetMapperFeatures + struct_eq::StructEquals + small_num_overflow_test_ops::SmallIntOverflow + token_identifier_features::TokenIdentifierFeatures diff --git a/contracts/feature-tests/basic-features/src/storage_mapper_get_at_address.rs b/contracts/feature-tests/basic-features/src/storage_mapper_get_at_address.rs index a3eff89cdb..324df37021 100644 --- a/contracts/feature-tests/basic-features/src/storage_mapper_get_at_address.rs +++ b/contracts/feature-tests/basic-features/src/storage_mapper_get_at_address.rs @@ -129,4 +129,21 @@ pub trait StorageMapperGetAtAddress { self.unordered_set_mapper().insert(item); } } + + #[storage_mapper_from_address("single_value_mapper_with_key")] + fn single_value_from_address_with_keys( + &self, + address: ManagedAddress, + extra_key: usize, + ) -> SingleValueMapper; + + #[view] + fn get_value_from_address_with_keys( + &self, + address: ManagedAddress, + extra_key: usize, + ) -> ManagedBuffer { + self.single_value_from_address_with_keys(address, extra_key) + .get() + } } diff --git a/contracts/feature-tests/basic-features/src/storage_mapper_single.rs b/contracts/feature-tests/basic-features/src/storage_mapper_single.rs index 69ea1280c5..f8e8228038 100644 --- a/contracts/feature-tests/basic-features/src/storage_mapper_single.rs +++ b/contracts/feature-tests/basic-features/src/storage_mapper_single.rs @@ -13,6 +13,9 @@ pub trait SingleValueMapperFeatures { address: ManagedAddress, ) -> SingleValueMapper; + #[storage_mapper("single_value_mapper_with_key")] + fn single_value_mapper_with_key(&self, extra_key: usize) -> SingleValueMapper; + #[endpoint] fn my_single_value_mapper_increment_1(&self, amount: BigInt) { let my_single_value_mapper = self.map_my_single_value_mapper(); @@ -67,4 +70,9 @@ pub trait SingleValueMapperFeatures { fn raw_byte_length_single_value_mapper(&self) -> usize { self.map_my_single_value_mapper().raw_byte_length() } + + #[endpoint] + fn set_single_value_mapper_with_key(&self, key: usize, value: ManagedBuffer) { + self.single_value_mapper_with_key(key).set(value); + } } diff --git a/contracts/feature-tests/basic-features/src/storage_mapper_unordered_set.rs b/contracts/feature-tests/basic-features/src/storage_mapper_unordered_set.rs index de4e189a9b..9bca7f9378 100644 --- a/contracts/feature-tests/basic-features/src/storage_mapper_unordered_set.rs +++ b/contracts/feature-tests/basic-features/src/storage_mapper_unordered_set.rs @@ -4,24 +4,24 @@ multiversx_sc::imports!(); #[multiversx_sc::module] pub trait UnorderedSetMapperFeatures { #[view] - #[storage_mapper("set_mapper")] - fn set_mapper(&self) -> UnorderedSetMapper; + #[storage_mapper("unordered_set_mapper")] + fn unordered_set_mapper(&self) -> UnorderedSetMapper; #[endpoint] - fn set_mapper_insert(&self, item: u32) -> bool { - let mut set_mapper = self.set_mapper(); + fn unordered_set_mapper_insert(&self, item: u32) -> bool { + let mut set_mapper = self.unordered_set_mapper(); set_mapper.insert(item) } #[endpoint] - fn set_mapper_contains(&self, item: u32) -> bool { - let set_mapper = self.set_mapper(); + fn unordered_set_mapper_contains(&self, item: u32) -> bool { + let set_mapper = self.unordered_set_mapper(); set_mapper.contains(&item) } #[endpoint] - fn set_mapper_remove(&self, item: u32) -> bool { - let mut set_mapper = self.set_mapper(); - set_mapper.remove(&item) + fn unordered_set_mapper_remove(&self, item: u32) -> bool { + let mut set_mapper = self.unordered_set_mapper(); + set_mapper.swap_remove(&item) } } diff --git a/contracts/feature-tests/basic-features/tests/basic_features_scenario_go_test.rs b/contracts/feature-tests/basic-features/tests/basic_features_scenario_go_test.rs index 6ef518cf9f..a6fd3babc4 100644 --- a/contracts/feature-tests/basic-features/tests/basic_features_scenario_go_test.rs +++ b/contracts/feature-tests/basic-features/tests/basic_features_scenario_go_test.rs @@ -371,6 +371,11 @@ fn storage_mapper_get_at_address_go() { world().run("scenarios/storage_mapper_get_at_address.scen.json"); } +#[test] +fn storage_mapper_get_at_address_extra_key_go() { + world().run("scenarios/storage_mapper_get_at_address_extra_key.scen.json"); +} + #[test] fn storage_mapper_linked_list_go() { world().run("scenarios/storage_mapper_linked_list.scen.json"); diff --git a/contracts/feature-tests/basic-features/tests/basic_features_scenario_rs_test.rs b/contracts/feature-tests/basic-features/tests/basic_features_scenario_rs_test.rs index 48762ce617..836795516b 100644 --- a/contracts/feature-tests/basic-features/tests/basic_features_scenario_rs_test.rs +++ b/contracts/feature-tests/basic-features/tests/basic_features_scenario_rs_test.rs @@ -388,6 +388,11 @@ fn storage_mapper_get_at_address_rs() { world().run("scenarios/storage_mapper_get_at_address.scen.json"); } +#[test] +fn storage_mapper_get_at_address_extra_key_rs() { + world().run("scenarios/storage_mapper_get_at_address_extra_key.scen.json"); +} + #[test] fn storage_mapper_linked_list_rs() { world().run("scenarios/storage_mapper_linked_list.scen.json"); diff --git a/contracts/feature-tests/basic-features/wasm/src/lib.rs b/contracts/feature-tests/basic-features/wasm/src/lib.rs index 6dcb5c59be..2f1071712c 100644 --- a/contracts/feature-tests/basic-features/wasm/src/lib.rs +++ b/contracts/feature-tests/basic-features/wasm/src/lib.rs @@ -5,9 +5,9 @@ //////////////////////////////////////////////////// // Init: 1 -// Endpoints: 389 +// Endpoints: 395 // Async Callback: 1 -// Total number of exported functions: 391 +// Total number of exported functions: 397 #![no_std] @@ -322,6 +322,7 @@ multiversx_sc_wasm_adapter::endpoints! { is_empty_single_value_mapper => is_empty_single_value_mapper is_empty_at_address_single_value_mapper => is_empty_at_address_single_value_mapper raw_byte_length_single_value_mapper => raw_byte_length_single_value_mapper + set_single_value_mapper_with_key => set_single_value_mapper_with_key vec_mapper => vec_mapper vec_mapper_push => vec_mapper_push vec_mapper_get => vec_mapper_get @@ -366,6 +367,10 @@ multiversx_sc_wasm_adapter::endpoints! { unique_id_mapper_swap_remove => unique_id_mapper_swap_remove unique_id_mapper_set => unique_id_mapper_set unique_id_mapper => unique_id_mapper + unordered_set_mapper => unordered_set_mapper + unordered_set_mapper_insert => unordered_set_mapper_insert + unordered_set_mapper_contains => unordered_set_mapper_contains + unordered_set_mapper_remove => unordered_set_mapper_remove managed_struct_eq => managed_struct_eq no_overflow_usize => no_overflow_usize no_overflow_u8 => no_overflow_u8 @@ -407,6 +412,7 @@ multiversx_sc_wasm_adapter::endpoints! { fill_set_mapper => fill_set_mapper fill_map_mapper => fill_map_mapper fill_unordered_set_mapper => fill_unordered_set_mapper + get_value_from_address_with_keys => get_value_from_address_with_keys ) } diff --git a/framework/base/src/storage/mappers/vec_mapper.rs b/framework/base/src/storage/mappers/vec_mapper.rs index 65b4818a98..80f8c6018a 100644 --- a/framework/base/src/storage/mappers/vec_mapper.rs +++ b/framework/base/src/storage/mappers/vec_mapper.rs @@ -12,7 +12,7 @@ use crate::{ storage::{storage_clear, storage_set, StorageKey}, types::{ManagedAddress, ManagedType, MultiValueEncoded}, }; -use core::{marker::PhantomData, usize}; +use core::marker::PhantomData; const ITEM_SUFFIX: &[u8] = b".item"; const LEN_SUFFIX: &[u8] = b".len";