I found this puzzle in my last question, which is from one answer of my question.

There are at least two StorageMap structs in substrate framework.Their links are listed below:

https://paritytech.github.io/substrate/master/frame_support/storage/types/struct.StorageMap.html https://crates.parity.io/frame_support/pallet_prelude/struct.StorageMap.html

They are StroageMap structs with little difference. They have different function sets at first glance. I want to figure out which struct should I pick up when coding a pallet in substrate?

2 Answers 2


The one that you should use is the first one. If you take a look at the pallet_prelude crate, you can see that the StorageMap used across most of the tutorials is being 'imported' from the storage::types crate.

pub use crate::{
        dispatch::{DispatchError, DispatchResult, DispatchResultWithPostInfo, Parameter},
        inherent::{InherentData, InherentIdentifier, ProvideInherent},
                CountedStorageMap, Key as NMapKey, OptionQuery, StorageDoubleMap, StorageMap,
        HERE --> StorageNMap, StorageValue, ValueQuery,
            ConstU32, EnsureOrigin, Get, GetDefault, GetStorageVersion, Hooks, IsType,
            PalletInfoAccess, StorageInfoTrait,
        weights::{DispatchClass, Pays, Weight},
        Blake2_128, Blake2_128Concat, Blake2_256, CloneNoBound, DebugNoBound, EqNoBound, Identity,
        PartialEqNoBound, RuntimeDebug, RuntimeDebugNoBound, Twox128, Twox256, Twox64Concat,

So basically, when you call frame_support::pallet_prelude::StorageMap you are calling the one inside the storage::types crate.

As for the question 'why are there two StorageMaps?' I think the second one is used in old versions of FRAME, where you would use decl_storage to create your structures. It has to exist because although substrate is being updated constantly, it is backward compatible with old implementations of it. But I'm not 100% sure thats the reason.

Taking a look at the storage::StorageMap:

/// A strongly-typed map in storage.
/// Details on implementation can be found at [`generator::StorageMap`].
pub trait StorageMap<K: FullEncode, V: FullCodec> {

and then the generator::StorageMap:

/// Generator for `StorageMap` used by `decl_storage`.
/// ...

pub trait StorageMap<K: FullEncode, V: FullCodec> {

The docs of the implementation state that the generator is used by the decl_storage function.

  • 1
    Thank you for your answer!
    – kugool
    Aug 25, 2022 at 10:56

frame_support::pallet_prelude re-exports the most common used types and constants for ease of use.
The re-export happens here.
It is therefore exactly the same type, as you can discover by clicking on the src links.
The crates.io is outdated, that is why it looks a bit different.

  • I got it,thank you very much!
    – kugool
    Aug 26, 2022 at 5:08

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.