I am adding a feature to the Sputnik DAO v2 near contract to map tokens to a number of votes.
Here is my constructor:
#[ext_contract(ext_self)]
pub trait Contract {
fn exchange_callback_post_withdraw(&mut self, sender_id: AccountId, token_id: String, amount: U128);
}
#[near_bindgen]
impl Contract {
#[init]
pub fn new(
owner_id: AccountId,
token_ids: UnorderedSet<String>,
unstake_period: U64,
token_vote_weights: LookupMap<String, U128>,
) -> Self {
Self {
owner_id: owner_id.into(),
vote_token_ids: token_ids,
users: LookupMap::new(StorageKeys::Users),
total_amount: UnorderedMap::new(StorageKeys::ValidNFTs),
unstake_period: unstake_period.0,
token_vote_weights,
}
}
I get this error:
error[E0277]: the trait bound `LookupMap<std::string::String, near_sdk::json_types::U128>: Serialize` is not satisfied
--> sputnik-nft-staking/src/lib.rs:67:1
|
67 | #[near_bindgen]
| ^^^^^^^^^^^^^^^ the trait `Serialize` is not implemented for `LookupMap<std::string::String, near_sdk::json_types::U128>`
|
::: /home/rashi/.cargo/registry/src/github.com-1ecc6299db9ec823/serde_json-1.0.64/src/value/mod.rs:965:8
|
965 | T: Serialize,
| --------- required by this bound in `to_value`
|
= note: required because of the requirements on the impl of `Serialize` for `&LookupMap<std::string::String, near_sdk::json_types::U128>`
How might I serialize the string, or is there a code change that might better help achieve my goal of associating a voting weight with a token?
So there are two main points about why this can't be serialized (assuming you're expecting it to be serialized as a map):
LookupMap does not store all keys in storage, so it is not iterable and is not aware of what it contains. If you want an iterable map, you can use
UnorderedMaporTreeMapfrom the SDK.Even if it was iterable, like in the case of the data structures mentioned above, it is very expensive to load all elements if the data structure grows large. This serialization implementation isn't done by default because it should generally be avoided.
If you want to return the whole contract state as JSON, you would have to manually implement serialize or put values into a structure that can be serialized. If you do want to load the storage values from storage to return from the function, consider either limiting the max amount of values or having some sort of pagination.
Can limit doing something like this. Not limited to this but just an option: