diff --git a/prdoc/pr_3953.prdoc b/prdoc/pr_3953.prdoc new file mode 100644 index 000000000000..f52227924604 --- /dev/null +++ b/prdoc/pr_3953.prdoc @@ -0,0 +1,19 @@ +# Schema: Polkadot SDK PRDoc Schema (prdoc) v1.0.0 +# See doc at https://raw.githubusercontent.com/paritytech/polkadot-sdk/master/prdoc/schema_user.json + +title: Adapt RemoteExternalities and its related types to be used with generic hash parameters + +doc: + - audience: Node Dev + description: | + Modify `RemoteExternalities`, `Mode`, `OnlineConfig` and`Snapshot` to rely now on generic parameter, instead of `BlockT`. + Adjust in consequence their implementation to be compatible with types `Hash`, or if possible any generic. + Adapt Builder struct and implementation for these bounds. + +crates: +- name: frame-remote-externalities + bump: major +- name: pallet-state-trie-migration + bump: patch +- name: try-runtime-cli + bump: patch \ No newline at end of file diff --git a/substrate/frame/state-trie-migration/src/lib.rs b/substrate/frame/state-trie-migration/src/lib.rs index 6e1de865ab4f..5c54c27966cd 100644 --- a/substrate/frame/state-trie-migration/src/lib.rs +++ b/substrate/frame/state-trie-migration/src/lib.rs @@ -1698,8 +1698,10 @@ pub(crate) mod remote_tests { /// /// This will print some very useful statistics, make sure [`crate::LOG_TARGET`] is enabled. #[allow(dead_code)] - pub(crate) async fn run_with_limits(limits: MigrationLimits, mode: Mode) - where + pub(crate) async fn run_with_limits( + limits: MigrationLimits, + mode: Mode, + ) where Runtime: crate::Config, Block: BlockT + DeserializeOwned, Block::Header: serde::de::DeserializeOwned, diff --git a/substrate/utils/frame/remote-externalities/src/lib.rs b/substrate/utils/frame/remote-externalities/src/lib.rs index 254d33deec80..e429d39669f1 100644 --- a/substrate/utils/frame/remote-externalities/src/lib.rs +++ b/substrate/utils/frame/remote-externalities/src/lib.rs @@ -36,7 +36,7 @@ use sp_core::{ }, }; use sp_runtime::{ - traits::{Block as BlockT, HashingFor}, + traits::{Block as BlockT, Hash, HashingFor}, StateVersion, }; use sp_state_machine::TestExternalities; @@ -63,21 +63,21 @@ const SNAPSHOT_VERSION: SnapshotVersion = Compact(3); /// The snapshot that we store on disk. #[derive(Decode, Encode)] -struct Snapshot { +struct Snapshot { snapshot_version: SnapshotVersion, state_version: StateVersion, - block_hash: B::Hash, + block_hash: H, // > raw_storage: Vec<(Vec, (Vec, i32))>, - storage_root: B::Hash, + storage_root: H, } -impl Snapshot { +impl Snapshot { pub fn new( state_version: StateVersion, - block_hash: B::Hash, + block_hash: H, raw_storage: Vec<(Vec, (Vec, i32))>, - storage_root: B::Hash, + storage_root: H, ) -> Self { Self { snapshot_version: SNAPSHOT_VERSION, @@ -88,7 +88,7 @@ impl Snapshot { } } - fn load(path: &PathBuf) -> Result, &'static str> { + fn load(path: &PathBuf) -> Result, &'static str> { let bytes = fs::read(path).map_err(|_| "fs::read failed.")?; // The first item in the SCALE encoded struct bytes is the snapshot version. We decode and // check that first, before proceeding to decode the rest of the snapshot. @@ -105,21 +105,21 @@ impl Snapshot { /// An externalities that acts exactly the same as [`sp_io::TestExternalities`] but has a few extra /// bits and pieces to it, and can be loaded remotely. -pub struct RemoteExternalities { +pub struct RemoteExternalities { /// The inner externalities. - pub inner_ext: TestExternalities>, - /// The block hash it which we created this externality env. - pub block_hash: B::Hash, + pub inner_ext: TestExternalities, + /// The block hash with which we created this externality env. + pub block_hash: H::Out, } -impl Deref for RemoteExternalities { - type Target = TestExternalities>; +impl Deref for RemoteExternalities { + type Target = TestExternalities; fn deref(&self) -> &Self::Target { &self.inner_ext } } -impl DerefMut for RemoteExternalities { +impl DerefMut for RemoteExternalities { fn deref_mut(&mut self) -> &mut Self::Target { &mut self.inner_ext } @@ -127,16 +127,16 @@ impl DerefMut for RemoteExternalities { /// The execution mode. #[derive(Clone)] -pub enum Mode { +pub enum Mode { /// Online. Potentially writes to a snapshot file. - Online(OnlineConfig), + Online(OnlineConfig), /// Offline. Uses a state snapshot file and needs not any client config. Offline(OfflineConfig), /// Prefer using a snapshot file if it exists, else use a remote server. - OfflineOrElseOnline(OfflineConfig, OnlineConfig), + OfflineOrElseOnline(OfflineConfig, OnlineConfig), } -impl Default for Mode { +impl Default for Mode { fn default() -> Self { Mode::Online(OnlineConfig::default()) } @@ -221,10 +221,10 @@ impl From for Transport { /// /// A state snapshot config may be present and will be written to in that case. #[derive(Clone)] -pub struct OnlineConfig { +pub struct OnlineConfig { /// The block hash at which to get the runtime state. Will be latest finalized head if not /// provided. - pub at: Option, + pub at: Option, /// An optional state snapshot file to WRITE to, not for reading. Not written if set to `None`. pub state_snapshot: Option, /// The pallets to scrape. These values are hashed and added to `hashed_prefix`. @@ -240,7 +240,7 @@ pub struct OnlineConfig { pub hashed_keys: Vec>, } -impl OnlineConfig { +impl OnlineConfig { /// Return rpc (http) client reference. fn rpc_client(&self) -> &HttpClient { self.transport @@ -248,12 +248,12 @@ impl OnlineConfig { .expect("http client must have been initialized by now; qed.") } - fn at_expected(&self) -> B::Hash { - self.at.expect("block at must be initialized; qed") + fn at_expected(&self) -> H { + self.at.clone().expect("block at must be initialized; qed") } } -impl Default for OnlineConfig { +impl Default for OnlineConfig { fn default() -> Self { Self { transport: Transport::from(DEFAULT_HTTP_ENDPOINT.to_owned()), @@ -267,7 +267,7 @@ impl Default for OnlineConfig { } } -impl From for OnlineConfig { +impl From for OnlineConfig { fn from(t: String) -> Self { Self { transport: t.into(), ..Default::default() } } @@ -307,7 +307,7 @@ pub struct Builder { /// The keys that will be excluded from the final externality. The *hashed* key must be given. hashed_blacklist: Vec>, /// Connectivity mode, online or offline. - mode: Mode, + mode: Mode, /// If provided, overwrite the state version with this. Otherwise, the state_version of the /// remote node is used. All cache files also store their state version. /// @@ -328,7 +328,7 @@ impl Default for Builder { // Mode methods impl Builder { - fn as_online(&self) -> &OnlineConfig { + fn as_online(&self) -> &OnlineConfig { match &self.mode { Mode::Online(config) => config, Mode::OfflineOrElseOnline(_, config) => config, @@ -336,7 +336,7 @@ impl Builder { } } - fn as_online_mut(&mut self) -> &mut OnlineConfig { + fn as_online_mut(&mut self) -> &mut OnlineConfig { match &mut self.mode { Mode::Online(config) => config, Mode::OfflineOrElseOnline(_, config) => config, @@ -1055,7 +1055,7 @@ where // If we need to save a snapshot, save the raw storage and root hash to the snapshot. if let Some(path) = self.as_online().state_snapshot.clone().map(|c| c.path) { let (raw_storage, storage_root) = pending_ext.into_raw_snapshot(); - let snapshot = Snapshot::::new( + let snapshot = Snapshot::::new( state_version, self.as_online() .at @@ -1083,7 +1083,7 @@ where Ok(pending_ext) } - async fn do_load_remote(&mut self) -> Result, &'static str> { + async fn do_load_remote(&mut self) -> Result>, &'static str> { self.init_remote_client().await?; let block_hash = self.as_online().at_expected(); let inner_ext = self.load_remote_and_maybe_save().await?; @@ -1093,12 +1093,12 @@ where fn do_load_offline( &mut self, config: OfflineConfig, - ) -> Result, &'static str> { + ) -> Result>, &'static str> { let mut sp = Spinner::with_timer(Spinners::Dots, "Loading snapshot...".into()); let start = Instant::now(); info!(target: LOG_TARGET, "Loading snapshot from {:?}", &config.state_snapshot.path); let Snapshot { snapshot_version: _, block_hash, state_version, raw_storage, storage_root } = - Snapshot::::load(&config.state_snapshot.path)?; + Snapshot::::load(&config.state_snapshot.path)?; let inner_ext = TestExternalities::from_raw_snapshot( raw_storage, @@ -1110,7 +1110,9 @@ where Ok(RemoteExternalities { inner_ext, block_hash }) } - pub(crate) async fn pre_build(mut self) -> Result, &'static str> { + pub(crate) async fn pre_build( + mut self, + ) -> Result>, &'static str> { let mut ext = match self.mode.clone() { Mode::Offline(config) => self.do_load_offline(config)?, Mode::Online(_) => self.do_load_remote().await?, @@ -1175,7 +1177,7 @@ where } /// Configure a state snapshot to be used. - pub fn mode(mut self, mode: Mode) -> Self { + pub fn mode(mut self, mode: Mode) -> Self { self.mode = mode; self } @@ -1186,7 +1188,7 @@ where self } - pub async fn build(self) -> Result, &'static str> { + pub async fn build(self) -> Result>, &'static str> { let mut ext = self.pre_build().await?; ext.commit_all().unwrap(); diff --git a/substrate/utils/frame/try-runtime/cli/src/lib.rs b/substrate/utils/frame/try-runtime/cli/src/lib.rs index 73952ce816af..606cf8a1e144 100644 --- a/substrate/utils/frame/try-runtime/cli/src/lib.rs +++ b/substrate/utils/frame/try-runtime/cli/src/lib.rs @@ -288,7 +288,7 @@ impl State { executor: &WasmExecutor, state_snapshot: Option, try_runtime_check: bool, - ) -> sc_cli::Result> + ) -> sc_cli::Result>> where Block::Header: DeserializeOwned, ::Err: Debug,