Skip to content
This repository was archived by the owner on Nov 15, 2023. It is now read-only.

Commit 947a6bc

Browse files
chemewheresaddietomusdrw
authored
Allow transaction for offchain indexing (#7290)
* Moving offchain change set to state machine overlay change set, preparing use of change set internally. * Make change set generic over key and value, and use it for offchain indexing. * test ui change * remaining delta * generating with standard method * Remove 'drain_committed' function, and documentation. * Default constructor for enabling offchain indexing. * Remove offchain change specific iterators. * remove pub accessor * keep previous hierarchy, just expose iterator instead. * Update primitives/state-machine/src/overlayed_changes/mod.rs Co-authored-by: Tomasz Drwięga <tomusdrw@users.noreply.github.com> * fix line break * missing renamings * fix import * fix new state-machine tests. * Don't expose InnerValue type. * Add test similar to set_storage. * Remove conditional offchain storage (hard to instantiate correctly). * fix * offchain as children cannot fail if top doesn't Co-authored-by: Addie Wagenknecht <addie@nortd.com> Co-authored-by: Tomasz Drwięga <tomusdrw@users.noreply.github.com>
1 parent bd5c9a6 commit 947a6bc

13 files changed

Lines changed: 382 additions & 249 deletions

File tree

client/api/src/backend.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -21,12 +21,12 @@
2121
use std::sync::Arc;
2222
use std::collections::{HashMap, HashSet};
2323
use sp_core::ChangesTrieConfigurationRange;
24-
use sp_core::offchain::{OffchainStorage,storage::OffchainOverlayedChanges};
24+
use sp_core::offchain::OffchainStorage;
2525
use sp_runtime::{generic::BlockId, Justification, Storage};
2626
use sp_runtime::traits::{Block as BlockT, NumberFor, HashFor};
2727
use sp_state_machine::{
2828
ChangesTrieState, ChangesTrieStorage as StateChangesTrieStorage, ChangesTrieTransaction,
29-
StorageCollection, ChildStorageCollection,
29+
StorageCollection, ChildStorageCollection, OffchainChangesCollection,
3030
};
3131
use sp_storage::{StorageData, StorageKey, PrefixedStorageKey, ChildInfo};
3232
use crate::{
@@ -174,7 +174,7 @@ pub trait BlockImportOperation<Block: BlockT> {
174174
/// Write offchain storage changes to the database.
175175
fn update_offchain_storage(
176176
&mut self,
177-
_offchain_update: OffchainOverlayedChanges,
177+
_offchain_update: OffchainChangesCollection,
178178
) -> sp_blockchain::Result<()> {
179179
Ok(())
180180
}

client/db/src/lib.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ use hash_db::Prefix;
6767
use sp_trie::{MemoryDB, PrefixedMemoryDB, prefixed_key};
6868
use sp_database::Transaction;
6969
use sp_core::{Hasher, ChangesTrieConfiguration};
70-
use sp_core::offchain::storage::{OffchainOverlayedChange, OffchainOverlayedChanges};
70+
use sp_core::offchain::OffchainOverlayedChange;
7171
use sp_core::storage::{well_known_keys, ChildInfo};
7272
use sp_arithmetic::traits::Saturating;
7373
use sp_runtime::{generic::{DigestItem, BlockId}, Justification, Storage};
@@ -76,7 +76,7 @@ use sp_runtime::traits::{
7676
};
7777
use sp_state_machine::{
7878
DBValue, ChangesTrieTransaction, ChangesTrieCacheAction, UsageInfo as StateUsageInfo,
79-
StorageCollection, ChildStorageCollection,
79+
StorageCollection, ChildStorageCollection, OffchainChangesCollection,
8080
backend::Backend as StateBackend, StateMachineStats,
8181
};
8282
use crate::utils::{DatabaseType, Meta, meta_keys, read_db, read_meta};
@@ -667,7 +667,7 @@ pub struct BlockImportOperation<Block: BlockT> {
667667
db_updates: PrefixedMemoryDB<HashFor<Block>>,
668668
storage_updates: StorageCollection,
669669
child_storage_updates: ChildStorageCollection,
670-
offchain_storage_updates: OffchainOverlayedChanges,
670+
offchain_storage_updates: OffchainChangesCollection,
671671
changes_trie_updates: MemoryDB<HashFor<Block>>,
672672
changes_trie_build_cache_update: Option<ChangesTrieCacheAction<Block::Hash, NumberFor<Block>>>,
673673
changes_trie_config_update: Option<Option<ChangesTrieConfiguration>>,
@@ -680,7 +680,7 @@ pub struct BlockImportOperation<Block: BlockT> {
680680

681681
impl<Block: BlockT> BlockImportOperation<Block> {
682682
fn apply_offchain(&mut self, transaction: &mut Transaction<DbHash>) {
683-
for ((prefix, key), value_operation) in self.offchain_storage_updates.drain() {
683+
for ((prefix, key), value_operation) in self.offchain_storage_updates.drain(..) {
684684
let key = crate::offchain::concatenate_prefix_and_key(&prefix, &key);
685685
match value_operation {
686686
OffchainOverlayedChange::SetValue(val) =>
@@ -798,7 +798,7 @@ impl<Block: BlockT> sc_client_api::backend::BlockImportOperation<Block> for Bloc
798798

799799
fn update_offchain_storage(
800800
&mut self,
801-
offchain_update: OffchainOverlayedChanges,
801+
offchain_update: OffchainChangesCollection,
802802
) -> ClientResult<()> {
803803
self.offchain_storage_updates = offchain_update;
804804
Ok(())

client/executor/src/integration_tests/mod.rs

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -475,13 +475,11 @@ fn offchain_index(wasm_method: WasmExecutionMethod) {
475475
&mut ext.ext(),
476476
).unwrap();
477477

478-
use sp_core::offchain::storage::OffchainOverlayedChange;
479-
assert_eq!(
480-
ext.overlayed_changes()
481-
.offchain_overlay()
482-
.get(sp_core::offchain::STORAGE_PREFIX, b"k"),
483-
Some(OffchainOverlayedChange::SetValue(b"v".to_vec()))
484-
);
478+
use sp_core::offchain::OffchainOverlayedChange;
479+
let data = ext.overlayed_changes().clone().offchain_drain_committed().find(|(k, _v)| {
480+
k == &(sp_core::offchain::STORAGE_PREFIX.to_vec(), b"k".to_vec())
481+
});
482+
assert_eq!(data.map(|data| data.1), Some(OffchainOverlayedChange::SetValue(b"v".to_vec())));
485483
}
486484

487485
test_wasm_execution!(offchain_local_storage_should_work);

primitives/core/src/offchain/mod.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -746,6 +746,14 @@ impl TransactionPoolExt {
746746
}
747747
}
748748

749+
/// Change to be applied to the offchain worker db in regards to a key.
750+
#[derive(Debug, Clone, Hash, Eq, PartialEq)]
751+
pub enum OffchainOverlayedChange {
752+
/// Remove the data associated with the key
753+
Remove,
754+
/// Overwrite the value of an associated key
755+
SetValue(Vec<u8>),
756+
}
749757

750758
#[cfg(test)]
751759
mod tests {

primitives/core/src/offchain/storage.rs

Lines changed: 0 additions & 95 deletions
Original file line numberDiff line numberDiff line change
@@ -83,98 +83,3 @@ impl OffchainStorage for InMemOffchainStorage {
8383
}
8484
}
8585
}
86-
87-
/// Change to be applied to the offchain worker db in regards to a key.
88-
#[derive(Debug,Clone,Hash,Eq,PartialEq)]
89-
pub enum OffchainOverlayedChange {
90-
/// Remove the data associated with the key
91-
Remove,
92-
/// Overwrite the value of an associated key
93-
SetValue(Vec<u8>),
94-
}
95-
96-
/// In-memory storage for offchain workers recoding changes for the actual offchain storage implementation.
97-
#[derive(Debug, Clone, Default)]
98-
pub struct OffchainOverlayedChanges {
99-
changes: HashMap<(Vec<u8>, Vec<u8>), OffchainOverlayedChange>,
100-
}
101-
102-
impl OffchainOverlayedChanges {
103-
/// Consume the offchain storage and iterate over all key value pairs.
104-
pub fn into_iter(self) -> impl Iterator<Item = ((Vec<u8>, Vec<u8>), OffchainOverlayedChange)> {
105-
self.changes.into_iter()
106-
}
107-
108-
/// Iterate over all key value pairs by reference.
109-
pub fn iter(&self) -> impl Iterator<Item = (&(Vec<u8>, Vec<u8>), &OffchainOverlayedChange)> {
110-
self.changes.iter()
111-
}
112-
113-
/// Drain all elements of changeset.
114-
pub fn drain(&mut self) -> impl Iterator<Item = ((Vec<u8>, Vec<u8>), OffchainOverlayedChange)> + '_ {
115-
self.changes.drain()
116-
}
117-
118-
/// Remove a key and its associated value from the offchain database.
119-
pub fn remove(&mut self, prefix: &[u8], key: &[u8]) {
120-
self.changes.insert((prefix.to_vec(), key.to_vec()), OffchainOverlayedChange::Remove);
121-
}
122-
123-
/// Set the value associated with a key under a prefix to the value provided.
124-
pub fn set(&mut self, prefix: &[u8], key: &[u8], value: &[u8]) {
125-
self.changes.insert(
126-
(prefix.to_vec(), key.to_vec()),
127-
OffchainOverlayedChange::SetValue(value.to_vec()),
128-
);
129-
}
130-
131-
/// Obtain a associated value to the given key in storage with prefix.
132-
pub fn get(&self, prefix: &[u8], key: &[u8]) -> Option<OffchainOverlayedChange> {
133-
let key = (prefix.to_vec(), key.to_vec());
134-
self.changes.get(&key).cloned()
135-
}
136-
}
137-
138-
#[cfg(test)]
139-
mod test {
140-
use super::*;
141-
use super::super::STORAGE_PREFIX;
142-
143-
#[test]
144-
fn test_drain() {
145-
let mut ooc = OffchainOverlayedChanges::default();
146-
ooc.set(STORAGE_PREFIX,b"kkk", b"vvv");
147-
let drained = ooc.drain().count();
148-
assert_eq!(drained, 1);
149-
let leftover = ooc.iter().count();
150-
assert_eq!(leftover, 0);
151-
152-
ooc.set(STORAGE_PREFIX, b"a", b"v");
153-
ooc.set(STORAGE_PREFIX, b"b", b"v");
154-
ooc.set(STORAGE_PREFIX, b"c", b"v");
155-
ooc.set(STORAGE_PREFIX, b"d", b"v");
156-
ooc.set(STORAGE_PREFIX, b"e", b"v");
157-
assert_eq!(ooc.iter().count(), 5);
158-
}
159-
160-
#[test]
161-
fn test_accumulated_set_remove_set() {
162-
let mut ooc = OffchainOverlayedChanges::default();
163-
ooc.set(STORAGE_PREFIX, b"ppp", b"qqq");
164-
ooc.remove(STORAGE_PREFIX, b"ppp");
165-
// keys are equiv, so it will overwrite the value and the overlay will contain
166-
// one item
167-
assert_eq!(ooc.iter().count(), 1);
168-
169-
ooc.set(STORAGE_PREFIX, b"ppp", b"rrr");
170-
let mut iter = ooc.into_iter();
171-
assert_eq!(
172-
iter.next(),
173-
Some(
174-
((STORAGE_PREFIX.to_vec(), b"ppp".to_vec()),
175-
OffchainOverlayedChange::SetValue(b"rrr".to_vec()))
176-
)
177-
);
178-
assert_eq!(iter.next(), None);
179-
}
180-
}

primitives/core/src/offchain/testing.rs

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,8 @@ use std::{
2727
use crate::OpaquePeerId;
2828
use crate::offchain::{
2929
self,
30-
storage::{InMemOffchainStorage, OffchainOverlayedChange, OffchainOverlayedChanges},
30+
OffchainOverlayedChange,
31+
storage::InMemOffchainStorage,
3132
HttpError,
3233
HttpRequestId as RequestId,
3334
HttpRequestStatus as RequestStatus,
@@ -80,9 +81,12 @@ impl TestPersistentOffchainDB {
8081
}
8182

8283
/// Apply a set of off-chain changes directly to the test backend
83-
pub fn apply_offchain_changes(&mut self, changes: &mut OffchainOverlayedChanges) {
84+
pub fn apply_offchain_changes(
85+
&mut self,
86+
changes: impl Iterator<Item = ((Vec<u8>, Vec<u8>), OffchainOverlayedChange)>,
87+
) {
8488
let mut me = self.persistent.write();
85-
for ((_prefix, key), value_operation) in changes.drain() {
89+
for ((_prefix, key), value_operation) in changes {
8690
match value_operation {
8791
OffchainOverlayedChange::SetValue(val) => me.set(Self::PREFIX, key.as_slice(), val.as_slice()),
8892
OffchainOverlayedChange::Remove => me.remove(Self::PREFIX, key.as_slice()),

primitives/offchain/src/lib.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@
2121
#![warn(missing_docs)]
2222

2323
/// Re-export of parent module scope storage prefix.
24-
pub use sp_core::offchain::STORAGE_PREFIX as STORAGE_PREFIX;
24+
pub use sp_core::offchain::STORAGE_PREFIX;
2525

2626
sp_api::decl_runtime_apis! {
2727
/// The offchain worker api.

primitives/state-machine/src/ext.rs

Lines changed: 3 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -193,18 +193,10 @@ where
193193
B: Backend<H>,
194194
N: crate::changes_trie::BlockNumber,
195195
{
196-
#[cfg(feature = "std")]
197196
fn set_offchain_storage(&mut self, key: &[u8], value: Option<&[u8]>) {
198-
use sp_core::offchain::STORAGE_PREFIX;
199-
match value {
200-
Some(value) => self.overlay.offchain_set_storage(STORAGE_PREFIX, key, value),
201-
None => self.overlay.offchain_remove_storage(STORAGE_PREFIX, key),
202-
}
197+
self.overlay.set_offchain_storage(key, value)
203198
}
204199

205-
#[cfg(not(feature = "std"))]
206-
fn set_offchain_storage(&mut self, _key: &[u8], _value: Option<&[u8]>) {}
207-
208200
fn storage(&self, key: &[u8]) -> Option<StorageValue> {
209201
let _guard = guard();
210202
let result = self.overlay.storage(key).map(|x| x.map(|x| x.to_vec())).unwrap_or_else(||
@@ -790,7 +782,6 @@ mod tests {
790782
H256,
791783
Blake2Hasher,
792784
map,
793-
offchain,
794785
storage::{
795786
Storage,
796787
StorageChild,
@@ -813,14 +804,11 @@ mod tests {
813804
changes.set_extrinsic_index(1);
814805
changes.set_storage(vec![1], Some(vec![100]));
815806
changes.set_storage(EXTRINSIC_INDEX.to_vec(), Some(3u32.encode()));
807+
changes.set_offchain_storage(b"k1", Some(b"v1"));
808+
changes.set_offchain_storage(b"k2", Some(b"v2"));
816809
changes
817810
}
818811

819-
fn prepare_offchain_overlay_with_changes(overlay: &mut OverlayedChanges) {
820-
overlay.offchain_set_storage(offchain::STORAGE_PREFIX, b"k1", b"v1");
821-
overlay.offchain_set_storage(offchain::STORAGE_PREFIX, b"k2", b"v2");
822-
}
823-
824812
fn changes_trie_config() -> ChangesTrieConfiguration {
825813
ChangesTrieConfiguration {
826814
digest_interval: 0,
@@ -849,7 +837,6 @@ mod tests {
849837
#[test]
850838
fn storage_changes_root_is_some_when_extrinsic_changes_are_non_empty() {
851839
let mut overlay = prepare_overlay_with_changes();
852-
prepare_offchain_overlay_with_changes(&mut overlay);
853840
let mut cache = StorageTransactionCache::default();
854841
let storage = TestChangesTrieStorage::with_blocks(vec![(99, Default::default())]);
855842
let state = Some(ChangesTrieState::new(changes_trie_config(), Zero::zero(), &storage));
@@ -864,7 +851,6 @@ mod tests {
864851
#[test]
865852
fn storage_changes_root_is_some_when_extrinsic_changes_are_empty() {
866853
let mut overlay = prepare_overlay_with_changes();
867-
prepare_offchain_overlay_with_changes(&mut overlay);
868854
let mut cache = StorageTransactionCache::default();
869855
overlay.set_collect_extrinsics(false);
870856
overlay.set_storage(vec![1], None);
@@ -884,7 +870,6 @@ mod tests {
884870
let mut overlay = OverlayedChanges::default();
885871
overlay.set_storage(vec![20], None);
886872
overlay.set_storage(vec![30], Some(vec![31]));
887-
prepare_offchain_overlay_with_changes(&mut overlay);
888873
let backend = Storage {
889874
top: map![
890875
vec![10] => vec![10],
@@ -939,8 +924,6 @@ mod tests {
939924
],
940925
}.into();
941926

942-
prepare_offchain_overlay_with_changes(&mut overlay);
943-
944927
let ext = TestExt::new(&mut overlay, &mut cache, &backend, None, None);
945928

946929
// next_backend < next_overlay
@@ -971,7 +954,6 @@ mod tests {
971954
let mut overlay = OverlayedChanges::default();
972955
overlay.set_child_storage(child_info, vec![20], None);
973956
overlay.set_child_storage(child_info, vec![30], Some(vec![31]));
974-
prepare_offchain_overlay_with_changes(&mut overlay);
975957
let backend = Storage {
976958
top: map![],
977959
children_default: map![
@@ -1013,7 +995,6 @@ mod tests {
1013995
let child_info = &child_info;
1014996
let mut cache = StorageTransactionCache::default();
1015997
let mut overlay = OverlayedChanges::default();
1016-
prepare_offchain_overlay_with_changes(&mut overlay);
1017998
let backend = Storage {
1018999
top: map![],
10191000
children_default: map![

primitives/state-machine/src/lib.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,8 @@ pub use crate::overlayed_changes::{
119119
OverlayedChanges, StorageKey, StorageValue,
120120
StorageCollection, ChildStorageCollection,
121121
StorageChanges, StorageTransactionCache,
122+
OffchainChangesCollection,
123+
OffchainOverlayedChanges,
122124
};
123125
pub use crate::backend::Backend;
124126
pub use crate::trie_backend_essence::{TrieBackendStorage, Storage};

0 commit comments

Comments
 (0)