Skip to content
This repository was archived by the owner on Aug 27, 2024. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from 5 commits
Commits
Show all changes
31 commits
Select commit Hold shift + click to select a range
368c7bc
Update storage.md
shawntabrizi Sep 24, 2019
ac6d78b
skeleton of storage doc
shawntabrizi Sep 24, 2019
09fb5dd
typo
shawntabrizi Sep 24, 2019
7b8b959
Update storage.md
shawntabrizi Sep 24, 2019
97e85f5
Integrate feedback
shawntabrizi Sep 26, 2019
402bba0
fixes
shawntabrizi Sep 27, 2019
89c720c
clarify kind of node
shawntabrizi Sep 27, 2019
d77a40b
Clarify
shawntabrizi Sep 27, 2019
999d39f
typo, fix line width
shawntabrizi Sep 27, 2019
68a8592
fixes
shawntabrizi Sep 27, 2019
5bbead7
replace misleading data
shawntabrizi Sep 27, 2019
ec323ac
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
5813b88
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
d6d7292
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
1c5993e
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
ab8caad
update from feedback
shawntabrizi Sep 28, 2019
e3ceff2
Merge branch 'shawntabrizi-storage-doc' of https://github.com/shawnta…
shawntabrizi Sep 28, 2019
f4570ee
Add a section on why to use child tries
shawntabrizi Sep 28, 2019
9db4f54
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
23f725b
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
59f529a
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
07026a3
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
9240c48
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
2cc0216
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
9cb7da5
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
df67541
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
96fee72
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
330d8a1
Update docs/conceptual/core/storage.md
shawntabrizi Sep 28, 2019
72550f5
Final fixes
shawntabrizi Sep 28, 2019
2018486
add todo
shawntabrizi Sep 28, 2019
0e33445
Merge branch 'source' into shawntabrizi-storage-doc
shawntabrizi Sep 29, 2019
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
52 changes: 49 additions & 3 deletions docs/conceptual/core/storage.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,54 @@
title: Storage
---

* Key Value Database, RocksDB
The Substrate uses a simple a key-value data store implemented as a database-backed modified Merkle tree.

* Trie abstraction
## Key-Value Database

* Runtime Storage abstraction
Substrate implements it's storage database with [RocksDB](https://rocksdb.org/), a persistent key-value store for fast storage environments.

This is used for all the components of Substrate which require persistent storage such as:

* Substrate clients
* Substrate light-clients
* Off-chain workers

## Trie Abstraction

One advantage of using a simple key-value store is that you are able to easily abstract other storage structures on top.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we put a bit more content on how a Trie is abstracting on top of a K-V store? I have worked with storage from highest level (SRML), to the lowest (raw RPC to to encoded key) and from the looks of it, honestly, I never really felt like I am working with a Trie here. It always looked more like a bare bone KV store to me.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would need to know what that information would look like...

Implementation details like this could be above the level of "conceptual" docs, but I agree we would want this information in the reference docs.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would say it is interesting to keep in mind as a runtime developper that the trie is way more costy than a standard k-v store.
General idea being that you should rather store a serialized struct with two field at a storage location rather than both field at different location, except if you want to reduce the size of the proof.
That is something that can get quite clear when you apply storage cost (if you have a base cost and variable cost for size to store).


Substrate uses a Base-16 Modified Merkle Patricia tree ("trie") from [`paritytech/trie`](https://github.com/paritytech/trie) to provide a trie structure whose contents can be modified and whose root hash is recalculated efficiently.

Tries are important tool for blockchains because the allows for efficient storing and sharing of historical of block state. You don't have a state trie per block, but a trie hash that will point to the nodes from previous block states. However, accessing data to trie data is costly. Each read operation takes O(log N) time, where N is the number of elements stored in the trie. To mitigate this, we use a key value cache.
Comment thread
shawntabrizi marked this conversation as resolved.
Outdated

All trie node are stored in RocksDB and part of the trie state can get pruned, i.e. a key-value pair can be deleted from the storage when it is out of pruning range for non archive nodes. Trie nodes are also encoded to allow for any key type, while still be able to avoid key collision. We do not use [reference counting](http://en.wikipedia.org/wiki/Reference_counting) for performance reasons.
Comment thread
shawntabrizi marked this conversation as resolved.
Outdated

### State Trie

Substrate has a single main trie, called the state trie, whose changing root hash is placed in each block header. This is used to easily verify the state of the blockchain and provide a basis for light clients to verify proofs.

This trie only stores content for the canonical chain, not forks. There is a separate `state_db` layer that maintain the trie state with references counted in memory for all that is non canonical. See JournalDB.

### Child Trie

Substrate also provides an API to generate new child tries with their own root hash that can be used in the runtime.

Child tries are identical to main state trie, except their root is stored and updated in the main trie instead of the block header. Since their headers are a part of the main state trie, it is still easy to verify of the complete node state when it includes child tries.

## Runtime Storage API

The Substrate runtime support library provides utilities which generates unique, deterministic keys for your runtime module storage items. These storage items are placed in the main trie and are accessible by querying the trie by key.

## Next Steps

### Learn More

* Learn how to add [storage items](development/module/storage.md) into your Substrate runtime modules.

### Examples

* View an example of creating [child tries]() in your Substrate runtime module.

### References

* Visit the reference docs for [`paritytech/trie`](https://substrate.dev/rustdocs/master/trie_db/trait.Trie.html).
2 changes: 1 addition & 1 deletion docs/development/module/storage.md
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ TODO

### Examples

TODO
* View this example to see how you can use a `double_map` to act as a `killable` single-map.

### References

Expand Down