diff --git a/bin/node-template/pallets/template/src/mock.rs b/bin/node-template/pallets/template/src/mock.rs index 4eed0e1e75c3e..0da96c10dcc5a 100644 --- a/bin/node-template/pallets/template/src/mock.rs +++ b/bin/node-template/pallets/template/src/mock.rs @@ -45,7 +45,7 @@ impl system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } impl Trait for Test { diff --git a/bin/node-template/runtime/src/lib.rs b/bin/node-template/runtime/src/lib.rs index 68d4eeeb7ad3a..2fe50ee25e44f 100644 --- a/bin/node-template/runtime/src/lib.rs +++ b/bin/node-template/runtime/src/lib.rs @@ -182,7 +182,7 @@ impl system::Trait for Runtime { /// This type is being generated by `construct_runtime!`. type ModuleToIndex = ModuleToIndex; /// What to do if a new account is created. - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); /// What to do if an account is fully reaped from the system. type OnKilledAccount = (); /// The data to be stored in an account. diff --git a/bin/node/runtime/src/lib.rs b/bin/node/runtime/src/lib.rs index 229aa3a9bed4f..6f95d82a53559 100644 --- a/bin/node/runtime/src/lib.rs +++ b/bin/node/runtime/src/lib.rs @@ -164,6 +164,7 @@ impl frame_system::Trait for Runtime { type Version = Version; type ModuleToIndex = ModuleToIndex; type AccountData = pallet_balances::AccountData; + type MigrateAccount = (Balances, Identity, Democracy, Elections, ImOnline, Recovery, Session, Society, Staking, Vesting); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/assets/src/lib.rs b/frame/assets/src/lib.rs index 2c67a320c1eae..f6a042a320a20 100644 --- a/frame/assets/src/lib.rs +++ b/frame/assets/src/lib.rs @@ -325,7 +325,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } impl Trait for Test { diff --git a/frame/aura/src/mock.rs b/frame/aura/src/mock.rs index 84d895cd06099..09c8e596d1aee 100644 --- a/frame/aura/src/mock.rs +++ b/frame/aura/src/mock.rs @@ -67,7 +67,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/authority-discovery/src/lib.rs b/frame/authority-discovery/src/lib.rs index 1b7915ce3a4d4..80dbaeb8699ed 100644 --- a/frame/authority-discovery/src/lib.rs +++ b/frame/authority-discovery/src/lib.rs @@ -164,7 +164,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/authorship/src/lib.rs b/frame/authorship/src/lib.rs index b9b30bf41111a..2661d5e3cf2ab 100644 --- a/frame/authorship/src/lib.rs +++ b/frame/authorship/src/lib.rs @@ -439,7 +439,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/babe/src/lib.rs b/frame/babe/src/lib.rs index 91421739327ab..75c4a53ed4f37 100644 --- a/frame/babe/src/lib.rs +++ b/frame/babe/src/lib.rs @@ -208,6 +208,14 @@ decl_module! { // remove temporary "environment" entry from storage Lateness::::kill(); } + + fn on_runtime_upgrade() -> Weight { + for i in 0..=SegmentIndex::get() { + UnderConstruction::migrate_key_from_blake(i); + } + // TODO: determine weight + 0 + } } } diff --git a/frame/babe/src/mock.rs b/frame/babe/src/mock.rs index de00928171494..61f7565736641 100644 --- a/frame/babe/src/mock.rs +++ b/frame/babe/src/mock.rs @@ -78,7 +78,7 @@ impl frame_system::Trait for Test { type MaximumBlockLength = MaximumBlockLength; type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/balances/src/lib.rs b/frame/balances/src/lib.rs index 093362bdd2391..28edc7bfff951 100644 --- a/frame/balances/src/lib.rs +++ b/frame/balances/src/lib.rs @@ -165,7 +165,7 @@ use frame_support::{ Currency, OnKilledAccount, OnUnbalanced, TryDrop, StoredMap, WithdrawReason, WithdrawReasons, LockIdentifier, LockableCurrency, ExistenceRequirement, Imbalance, SignedImbalance, ReservableCurrency, Get, ExistenceRequirement::KeepAlive, - ExistenceRequirement::AllowDeath, IsDeadAccount, BalanceStatus as Status, + ExistenceRequirement::AllowDeath, IsDeadAccount, BalanceStatus as Status, MigrateAccount }, weights::Weight, }; @@ -569,6 +569,12 @@ impl OldBalanceLock { } } +impl, I: Instance> MigrateAccount for Module { + fn migrate_account(account: &T::AccountId) { + Locks::::migrate_key_from_blake(account); + } +} + impl, I: Instance> Module { // PRIVATE MUTABLES @@ -892,7 +898,7 @@ impl, I: Instance> frame_system::Trait for ElevatedTrait { type AvailableBlockRatio = T::AvailableBlockRatio; type Version = T::Version; type ModuleToIndex = T::ModuleToIndex; - type OnNewAccount = T::OnNewAccount; + type MigrateAccount = (); type OnNewAccount = T::OnNewAccount; type OnKilledAccount = T::OnKilledAccount; type AccountData = T::AccountData; } diff --git a/frame/balances/src/tests_composite.rs b/frame/balances/src/tests_composite.rs index 7b9ec1f91eade..e952cbb953731 100644 --- a/frame/balances/src/tests_composite.rs +++ b/frame/balances/src/tests_composite.rs @@ -77,7 +77,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = super::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } parameter_types! { diff --git a/frame/balances/src/tests_local.rs b/frame/balances/src/tests_local.rs index 9ff76839f4cb2..86745769e6634 100644 --- a/frame/balances/src/tests_local.rs +++ b/frame/balances/src/tests_local.rs @@ -77,7 +77,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = super::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = Module; } parameter_types! { diff --git a/frame/benchmarking/src/tests.rs b/frame/benchmarking/src/tests.rs index dc9d160b5ee92..f262b6ba0459e 100644 --- a/frame/benchmarking/src/tests.rs +++ b/frame/benchmarking/src/tests.rs @@ -88,7 +88,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/collective/src/lib.rs b/frame/collective/src/lib.rs index 3d6e41d98d561..6fdf3d52d928e 100644 --- a/frame/collective/src/lib.rs +++ b/frame/collective/src/lib.rs @@ -334,6 +334,16 @@ fn get_result_weight(result: DispatchResultWithPostInfo) -> Option { } } +mod migration { + use super::*; + + pub fn migrate, I: Instance>() { + for p in Proposals::::get().into_iter() { + ProposalOf::::migrate_key_from_blake(&p); + Voting::::migrate_key_from_blake(&p); + } + } +} // Note that councillor operations are assigned to the operational class. decl_module! { @@ -342,6 +352,12 @@ decl_module! { fn deposit_event() = default; + fn on_runtime_upgrade() -> Weight { + migration::migrate::(); + // TODO: determine actual weight + 0 + } + /// Set the collective's membership. /// /// - `new_members`: The new member list. Be nice to the chain and provide it sorted. @@ -990,7 +1006,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } impl Trait for Test { diff --git a/frame/contracts/src/tests.rs b/frame/contracts/src/tests.rs index 944bca622bfd2..e8268e7a1f277 100644 --- a/frame/contracts/src/tests.rs +++ b/frame/contracts/src/tests.rs @@ -103,6 +103,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/democracy/src/lib.rs b/frame/democracy/src/lib.rs index 9694d3105c069..060858be8c714 100644 --- a/frame/democracy/src/lib.rs +++ b/frame/democracy/src/lib.rs @@ -178,7 +178,7 @@ use frame_support::{ weights::{Weight, DispatchClass}, traits::{ Currency, ReservableCurrency, LockableCurrency, WithdrawReason, LockIdentifier, Get, - OnUnbalanced, BalanceStatus, schedule::Named as ScheduleNamed, EnsureOrigin + OnUnbalanced, BalanceStatus, schedule::Named as ScheduleNamed, EnsureOrigin, MigrateAccount, }, dispatch::DispatchResultWithPostInfo, }; @@ -623,6 +623,99 @@ mod weight_for { } } +impl MigrateAccount for Module { + fn migrate_account(a: &T::AccountId) { + mod deprecated { + use sp_std::prelude::*; + + use codec::{Encode, EncodeLike, Decode, Input, Output}; + use frame_support::{decl_module, decl_storage}; + use sp_runtime::RuntimeDebug; + use sp_std::convert::TryFrom; + + use crate::{Trait, ReferendumIndex, Conviction}; + + #[derive(Copy, Clone, Eq, PartialEq, Default, RuntimeDebug)] + pub struct Vote { + pub aye: bool, + pub conviction: Conviction, + } + + impl Encode for Vote { + fn encode_to(&self, output: &mut T) { + output.push_byte(u8::from(self.conviction) | if self.aye { 0b1000_0000 } else { 0 }); + } + } + + impl EncodeLike for Vote {} + + impl Decode for Vote { + fn decode(input: &mut I) -> core::result::Result { + let b = input.read_byte()?; + Ok(Vote { + aye: (b & 0b1000_0000) == 0b1000_0000, + conviction: Conviction::try_from(b & 0b0111_1111) + .map_err(|_| codec::Error::from("Invalid conviction"))?, + }) + } + } + + decl_module! { + pub struct Module for enum Call where origin: T::Origin { } + } + decl_storage! { + trait Store for Module as Democracy { + pub VoteOf get(fn vote_of): + map hasher(opaque_blake2_256) (ReferendumIndex, T::AccountId) => Vote; + pub Delegations get(fn delegations): + map hasher(opaque_blake2_256) T::AccountId => (T::AccountId, Conviction); + } + } + } + + Proxy::::migrate_key_from_blake(a); + Locks::::migrate_key_from_blake(a); + // TODO: will not actually do any useful migration + deprecated::Delegations::::migrate_key_from_blake(a); + for i in LowestUnbaked::get()..ReferendumCount::get() { + // TODO: will not actually do any useful migration + deprecated::VoteOf::::migrate_key_from_blake((i, a)); + } + } +} + +mod migration { + use super::*; + + pub fn migrate() { + mod deprecated { + use super::*; + + decl_module! { + pub struct Module for enum Call where origin: T::Origin { } + } + decl_storage! { + trait Store for Module as Democracy { + pub VotersFor get(fn voters_for): + map hasher(opaque_blake2_256) ReferendumIndex => Vec; + } + } + } + + Blacklist::::remove_all(); + Cancellations::::remove_all(); + for i in LowestUnbaked::get()..ReferendumCount::get() { + // TODO: will not actually do any useful migration + deprecated::VotersFor::::migrate_key_from_blake(i); + ReferendumInfoOf::::migrate_key_from_blake(i); + } + for (p, h, _) in PublicProps::::get().into_iter() { + DepositOf::::migrate_key_from_blake(p); + Preimages::::migrate_key_from_blake(h); + } + } +} + decl_module! { pub struct Module for enum Call where origin: T::Origin { type Error = Error; @@ -658,6 +751,9 @@ decl_module! { fn deposit_event() = default; fn on_runtime_upgrade() -> Weight { + // TODO: determine correct weight + migration::migrate::(); + if let None = StorageVersion::get() { StorageVersion::put(Releases::V1); diff --git a/frame/democracy/src/tests.rs b/frame/democracy/src/tests.rs index 103ac6a84b6b8..f34ef08a4cd4f 100644 --- a/frame/democracy/src/tests.rs +++ b/frame/democracy/src/tests.rs @@ -106,6 +106,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/elections-phragmen/src/lib.rs b/frame/elections-phragmen/src/lib.rs index 5d7d2bf503bc2..6bb8b6b7ff02b 100644 --- a/frame/elections-phragmen/src/lib.rs +++ b/frame/elections-phragmen/src/lib.rs @@ -102,6 +102,7 @@ use frame_support::{ }; use sp_phragmen::{build_support_map, ExtendedBalance, VoteWeight, PhragmenResult}; use frame_system::{self as system, ensure_signed, ensure_root}; +use frame_support::traits::MigrateAccount; mod benchmarking; @@ -694,6 +695,31 @@ decl_event!( } ); +impl MigrateAccount for Module { + fn migrate_account(a: &T::AccountId) { + mod deprecated { + use super::*; + + decl_module! { + pub struct Module for enum Call where origin: T::Origin { } + } + decl_storage! { + trait Store for Module as PhragmenElection { + pub VotesOf get(fn votes_of): + map hasher(opaque_blake2_256) T::AccountId => Vec; + pub StakeOf get(fn stake_of): + map hasher(opaque_blake2_256) T::AccountId => BalanceOf; + } + } + } + + // TODO: will not actually do any useful migration + if deprecated::StakeOf::::migrate_key_from_blake(a).is_some() { + deprecated::VotesOf::::migrate_key_from_blake(a); + } + } +} + impl Module { /// Attempts to remove a member `who`. If a runner-up exists, it is used as the replacement and /// Ok(true). is returned. @@ -1095,7 +1121,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/elections/src/mock.rs b/frame/elections/src/mock.rs index 9971dac572187..51395d4cb467d 100644 --- a/frame/elections/src/mock.rs +++ b/frame/elections/src/mock.rs @@ -60,7 +60,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/example-offchain-worker/src/tests.rs b/frame/example-offchain-worker/src/tests.rs index 30c9c22593035..6984c0b56d300 100644 --- a/frame/example-offchain-worker/src/tests.rs +++ b/frame/example-offchain-worker/src/tests.rs @@ -75,7 +75,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/example/src/lib.rs b/frame/example/src/lib.rs index 6b3d6b5e5fc9f..c0021fb1c50fe 100644 --- a/frame/example/src/lib.rs +++ b/frame/example/src/lib.rs @@ -760,7 +760,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } parameter_types! { diff --git a/frame/executive/src/lib.rs b/frame/executive/src/lib.rs index 04e095fec4364..4506f406a370c 100644 --- a/frame/executive/src/lib.rs +++ b/frame/executive/src/lib.rs @@ -566,6 +566,7 @@ mod tests { type Version = RuntimeVersion; type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/finality-tracker/src/lib.rs b/frame/finality-tracker/src/lib.rs index f4ecc899db07d..d288dc9da3020 100644 --- a/frame/finality-tracker/src/lib.rs +++ b/frame/finality-tracker/src/lib.rs @@ -28,11 +28,11 @@ use frame_support::weights::{DispatchClass, Weight}; use frame_system::{ensure_none, Trait as SystemTrait}; use sp_finality_tracker::{INHERENT_IDENTIFIER, FinalizedInherentData}; -mod migration; - pub const DEFAULT_WINDOW_SIZE: u32 = 101; pub const DEFAULT_REPORT_LATENCY: u32 = 1000; +mod migration; + pub trait Trait: SystemTrait { /// Something which can be notified when the timestamp is set. Set this to `()` /// if not needed. @@ -279,7 +279,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } parameter_types! { diff --git a/frame/generic-asset/src/lib.rs b/frame/generic-asset/src/lib.rs index f94c83b5ed59f..28f603fb7c845 100644 --- a/frame/generic-asset/src/lib.rs +++ b/frame/generic-asset/src/lib.rs @@ -1141,7 +1141,7 @@ impl frame_system::Trait for ElevatedTrait { type Version = T::Version; type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } impl Trait for ElevatedTrait { diff --git a/frame/generic-asset/src/mock.rs b/frame/generic-asset/src/mock.rs index 04fd565091b29..04d38ade524dc 100644 --- a/frame/generic-asset/src/mock.rs +++ b/frame/generic-asset/src/mock.rs @@ -67,7 +67,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/grandpa/src/lib.rs b/frame/grandpa/src/lib.rs index 3432c1102008b..51d5241e33c3c 100644 --- a/frame/grandpa/src/lib.rs +++ b/frame/grandpa/src/lib.rs @@ -41,7 +41,7 @@ use fg_primitives::{ }; use frame_support::{ decl_error, decl_event, decl_module, decl_storage, storage, traits::KeyOwnerProofSystem, - Parameter, + Parameter, weights::Weight, }; use frame_system::{self as system, ensure_signed, DigestOf}; use sp_runtime::{ @@ -224,12 +224,34 @@ decl_storage! { } } +mod migration { + use super::*; + pub fn migrate() { + for i in 0..=CurrentSetId::get() { + SetIdSession::migrate_key_from_blake(i); + } + } +} + decl_module! { pub struct Module for enum Call where origin: T::Origin { type Error = Error; fn deposit_event() = default; + fn on_runtime_upgrade() -> Weight { + migration::migrate::(); + // TODO: determine actual weight + 0 + } + + fn on_initialize() -> Weight { + #[cfg(feature = "migrate-authorities")] + Self::migrate_authorities(); + // TODO: determine actual weight + 0 + } + /// Report voter equivocation/misbehavior. This method will verify the /// equivocation proof and validate the given key ownership proof /// against the extracted offender. If both are valid, the offence diff --git a/frame/grandpa/src/mock.rs b/frame/grandpa/src/mock.rs index 08329fbb70b59..553d52b169f39 100644 --- a/frame/grandpa/src/mock.rs +++ b/frame/grandpa/src/mock.rs @@ -115,6 +115,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/identity/src/lib.rs b/frame/identity/src/lib.rs index a78ff5abbfcd8..22459d368bddc 100644 --- a/frame/identity/src/lib.rs +++ b/frame/identity/src/lib.rs @@ -79,9 +79,11 @@ use frame_support::{ weights::Weight, }; use frame_system::{self as system, ensure_signed, ensure_root}; +use frame_support::traits::MigrateAccount; #[cfg(feature = "runtime-benchmarks")] pub mod benchmarking; + mod migration; type BalanceOf = <::Currency as Currency<::AccountId>>::Balance; @@ -1151,6 +1153,18 @@ impl Module { } } +impl MigrateAccount for Module { + fn migrate_account(a: &T::AccountId) { + if IdentityOf::::migrate_key_from_blake(a).is_some() { + if let Some((_, subs)) = SubsOf::::migrate_key_from_blake(a) { + for sub in subs.into_iter() { + SuperOf::::migrate_key_from_blake(sub); + } + } + } + } +} + #[cfg(test)] mod tests { use super::*; @@ -1205,7 +1219,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } parameter_types! { diff --git a/frame/im-online/src/lib.rs b/frame/im-online/src/lib.rs index c1c93910ece22..4c279be54cabf 100644 --- a/frame/im-online/src/lib.rs +++ b/frame/im-online/src/lib.rs @@ -94,7 +94,7 @@ use sp_staking::{ }; use frame_support::{ decl_module, decl_event, decl_storage, Parameter, debug, decl_error, - traits::Get, + traits::{Get, MigrateAccount}, weights::Weight, }; use frame_system::{self as system, ensure_none}; @@ -311,12 +311,40 @@ decl_error! { } } +mod migration { + use super::*; + use frame_support::Blake2_256; + pub fn migrate() { + let current_index = >::current_index(); + let key_count = Keys::::get().len() as AuthIndex; + for i in 0..key_count { + ReceivedHeartbeats::migrate_keys::(current_index, i); + } + } +} + +impl MigrateAccount for Module { + fn migrate_account(a: &T::AccountId) { + use frame_support::Blake2_256; + let current_index = >::current_index(); + if let Ok(v) = a.using_encoded(|mut d| T::ValidatorId::decode(&mut d)) { + AuthoredBlocks::::migrate_keys::(current_index, v); + } + } +} + decl_module! { pub struct Module for enum Call where origin: T::Origin { type Error = Error; fn deposit_event() = default; + fn on_runtime_upgrade() -> Weight { + migration::migrate::(); + // TODO: determine actual weight + 0 + } + /// # /// - Complexity: `O(K + E)` where K is length of `Keys` and E is length of /// `Heartbeat.network_state.external_address` diff --git a/frame/im-online/src/mock.rs b/frame/im-online/src/mock.rs index 01e84102b1a5c..12a3a0f6aa7bc 100644 --- a/frame/im-online/src/mock.rs +++ b/frame/im-online/src/mock.rs @@ -125,7 +125,7 @@ impl frame_system::Trait for Runtime { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/indices/src/mock.rs b/frame/indices/src/mock.rs index 90ac1ae81b595..8a8fd98c2ab0f 100644 --- a/frame/indices/src/mock.rs +++ b/frame/indices/src/mock.rs @@ -71,7 +71,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/membership/src/lib.rs b/frame/membership/src/lib.rs index 669964c70c177..0cc3dc526cb9c 100644 --- a/frame/membership/src/lib.rs +++ b/frame/membership/src/lib.rs @@ -324,7 +324,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } ord_parameter_types! { diff --git a/frame/nicks/src/lib.rs b/frame/nicks/src/lib.rs index 11b23443d68b9..304063d6cef24 100644 --- a/frame/nicks/src/lib.rs +++ b/frame/nicks/src/lib.rs @@ -291,7 +291,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } parameter_types! { diff --git a/frame/offences/benchmarking/src/mock.rs b/frame/offences/benchmarking/src/mock.rs index 28263a5292cb5..b4c2a8f627b63 100644 --- a/frame/offences/benchmarking/src/mock.rs +++ b/frame/offences/benchmarking/src/mock.rs @@ -60,6 +60,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (Balances,); type BlockExecutionWeight = (); diff --git a/frame/offences/src/lib.rs b/frame/offences/src/lib.rs index a42f09697e3b4..40b8be2b12375 100644 --- a/frame/offences/src/lib.rs +++ b/frame/offences/src/lib.rs @@ -141,6 +141,14 @@ decl_module! { consumed } + + fn on_runtime_upgrade() -> Weight { + Reports::::remove_all(); + ConcurrentReportsIndex::::remove_all(); + ReportsByKindIndex::remove_all(); + // TODO: determine actual weight + 0 + } } } diff --git a/frame/offences/src/mock.rs b/frame/offences/src/mock.rs index 30d2409a00194..3aea787726b28 100644 --- a/frame/offences/src/mock.rs +++ b/frame/offences/src/mock.rs @@ -117,7 +117,7 @@ impl frame_system::Trait for Runtime { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/randomness-collective-flip/src/lib.rs b/frame/randomness-collective-flip/src/lib.rs index 4a851c926fb74..d3f960d436732 100644 --- a/frame/randomness-collective-flip/src/lib.rs +++ b/frame/randomness-collective-flip/src/lib.rs @@ -179,7 +179,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/recovery/src/lib.rs b/frame/recovery/src/lib.rs index cd3ba76b37012..808e8c8d323bb 100644 --- a/frame/recovery/src/lib.rs +++ b/frame/recovery/src/lib.rs @@ -165,6 +165,7 @@ use frame_support::{ dispatch::PostDispatchInfo, }; use frame_system::{self as system, ensure_signed, ensure_root}; +use frame_support::traits::MigrateAccount; #[cfg(test)] mod mock; @@ -259,6 +260,13 @@ decl_storage! { } } +impl MigrateAccount for Module { + fn migrate_account(a: &T::AccountId) { + Recoverable::::migrate_key_from_blake(a); + Proxy::::migrate_key_from_blake(a); + } +} + decl_event! { /// Events type. pub enum Event where diff --git a/frame/recovery/src/mock.rs b/frame/recovery/src/mock.rs index aae9b2b75cf8c..2632511a8c341 100644 --- a/frame/recovery/src/mock.rs +++ b/frame/recovery/src/mock.rs @@ -85,7 +85,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/scheduler/src/lib.rs b/frame/scheduler/src/lib.rs index 687fe46d16a67..2c7cc6a8aa3e6 100644 --- a/frame/scheduler/src/lib.rs +++ b/frame/scheduler/src/lib.rs @@ -508,6 +508,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/scored-pool/src/mock.rs b/frame/scored-pool/src/mock.rs index 1b61bb18846f4..23107b5ae6b0f 100644 --- a/frame/scored-pool/src/mock.rs +++ b/frame/scored-pool/src/mock.rs @@ -76,7 +76,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/session/benchmarking/src/mock.rs b/frame/session/benchmarking/src/mock.rs index 5c0e40096eaf8..0a19c581513d5 100644 --- a/frame/session/benchmarking/src/mock.rs +++ b/frame/session/benchmarking/src/mock.rs @@ -79,6 +79,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (Balances,); } diff --git a/frame/session/src/historical.rs b/frame/session/src/historical.rs index a1c286eb39245..84a86781c942c 100644 --- a/frame/session/src/historical.rs +++ b/frame/session/src/historical.rs @@ -32,7 +32,7 @@ use sp_runtime::KeyTypeId; use sp_runtime::traits::{Convert, OpaqueKeys}; use sp_session::{MembershipProof, ValidatorCount}; use frame_support::{decl_module, decl_storage}; -use frame_support::{Parameter, print}; +use frame_support::{Parameter, print, weights::Weight}; use sp_trie::{MemoryDB, Trie, TrieMut, Recorder, EMPTY_PREFIX}; use sp_trie::trie_types::{TrieDBMut, TrieDB}; use super::{SessionIndex, Module as SessionModule}; @@ -67,7 +67,30 @@ decl_storage! { } decl_module! { - pub struct Module for enum Call where origin: T::Origin {} + pub struct Module for enum Call where origin: T::Origin { + fn on_initialize(_n: T::BlockNumber) -> Weight { + CachedObsolete::::remove_all(); + // TODO: determine actual weight + 0 + } + + fn on_runtime_upgrade() -> Weight { + migration::migrate::(); + // TODO: determine actual weight + 0 + } + } +} + +mod migration { + use super::*; + pub fn migrate() { + if let Some((begin, end)) = StoredRange::get() { + for i in begin..end { + HistoricalSessions::::migrate_key_from_blake(i); + } + } + } } impl Module { diff --git a/frame/session/src/lib.rs b/frame/session/src/lib.rs index 47517702cc57a..f41821a3abf11 100644 --- a/frame/session/src/lib.rs +++ b/frame/session/src/lib.rs @@ -114,6 +114,7 @@ use frame_support::{ weights::Weight, }; use frame_system::{self as system, ensure_signed}; +use frame_support::traits::MigrateAccount; #[cfg(test)] mod mock; @@ -559,6 +560,18 @@ decl_module! { } } +impl MigrateAccount for Module { + fn migrate_account(a: &T::AccountId) { + if let Some(v) = T::ValidatorIdOf::convert(a.clone()) { + if let Some(keys) = NextKeys::::migrate_key_from_blake(v) { + for id in T::Keys::key_ids() { + KeyOwner::::migrate_key_from_blake((*id, keys.get_raw(*id))); + } + } + } + } +} + impl Module { /// Move on to next session. Register new validator set and session keys. Changes /// to the validator set have a session of delay to take effect. This allows for diff --git a/frame/session/src/mock.rs b/frame/session/src/mock.rs index e7a9896064844..a7e43d6a11948 100644 --- a/frame/session/src/mock.rs +++ b/frame/session/src/mock.rs @@ -194,7 +194,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/society/src/lib.rs b/frame/society/src/lib.rs index 122ed06b29119..b329b12ea68e7 100644 --- a/frame/society/src/lib.rs +++ b/frame/society/src/lib.rs @@ -264,7 +264,7 @@ use frame_support::{decl_error, decl_module, decl_storage, decl_event, ensure, d use frame_support::weights::Weight; use frame_support::traits::{ Currency, ReservableCurrency, Randomness, Get, ChangeMembers, BalanceStatus, - ExistenceRequirement::AllowDeath, EnsureOrigin + ExistenceRequirement::AllowDeath, EnsureOrigin, MigrateAccount, }; use frame_system::{self as system, ensure_signed, ensure_root}; @@ -1140,6 +1140,12 @@ decl_event! { } } +impl MigrateAccount for Module { + fn migrate_account(a: &T::AccountId) { + Payouts::::migrate_key_from_blake(a); + } +} + /// Simple ensure origin struct to filter for the founder account. pub struct EnsureFounder(sp_std::marker::PhantomData); impl EnsureOrigin for EnsureFounder { diff --git a/frame/society/src/mock.rs b/frame/society/src/mock.rs index 7ddd25ee6a09b..042c4d3794643 100644 --- a/frame/society/src/mock.rs +++ b/frame/society/src/mock.rs @@ -85,7 +85,7 @@ impl frame_system::Trait for Test { type AvailableBlockRatio = AvailableBlockRatio; type Version = (); type ModuleToIndex = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); type AccountData = pallet_balances::AccountData; } diff --git a/frame/staking/fuzzer/src/mock.rs b/frame/staking/fuzzer/src/mock.rs index 0e3b6cb13fbb7..5da529499c470 100644 --- a/frame/staking/fuzzer/src/mock.rs +++ b/frame/staking/fuzzer/src/mock.rs @@ -78,6 +78,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (Balances,); } diff --git a/frame/staking/src/lib.rs b/frame/staking/src/lib.rs index 4e9a8918c5ad7..1ebae2aca1cae 100644 --- a/frame/staking/src/lib.rs +++ b/frame/staking/src/lib.rs @@ -296,7 +296,7 @@ use frame_support::{ dispatch::{IsSubType, DispatchResult, DispatchResultWithPostInfo, WithPostDispatchInfo}, traits::{ Currency, LockIdentifier, LockableCurrency, WithdrawReasons, OnUnbalanced, Imbalance, Get, - UnixTime, EstimateNextNewSession, EnsureOrigin, + UnixTime, EstimateNextNewSession, EnsureOrigin, MigrateAccount, } }; use pallet_session::historical; @@ -1337,6 +1337,12 @@ decl_module! { } } } + + fn on_runtime_upgrade() -> Weight { + migrate::(); + // TODO: determine actual weight + 0 + } fn on_finalize() { // Set the start of the first era. @@ -2207,6 +2213,30 @@ decl_module! { } } +impl MigrateAccount for Module { + fn migrate_account(a: &T::AccountId) { + if let Some(controller) = Bonded::::migrate_key_from_blake(a) { + Ledger::::migrate_key_from_blake(controller); + Payee::::migrate_key_from_blake(a); + Validators::::migrate_key_from_blake(a); + Nominators::::migrate_key_from_blake(a); + SlashingSpans::::migrate_key_from_blake(a); + } + } +} + +fn migrate() { + if let Some(current_era) = CurrentEra::get() { + let history_depth = HistoryDepth::get(); + for era in current_era.saturating_sub(history_depth)..=current_era { + ErasStartSessionIndex::migrate_key_from_blake(era); + ErasValidatorReward::::migrate_key_from_blake(era); + ErasRewardPoints::::migrate_key_from_blake(era); + ErasTotalStake::::migrate_key_from_blake(era); + } + } +} + impl Module { /// The total balance that can be slashed from a stash account as of right now. pub fn slashable_balance_of(stash: &T::AccountId) -> BalanceOf { diff --git a/frame/staking/src/mock.rs b/frame/staking/src/mock.rs index 094ab6375ca0e..bf39173a62d2f 100644 --- a/frame/staking/src/mock.rs +++ b/frame/staking/src/mock.rs @@ -221,6 +221,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/sudo/src/mock.rs b/frame/sudo/src/mock.rs index a270787da66ec..b4df4b0bea490 100644 --- a/frame/sudo/src/mock.rs +++ b/frame/sudo/src/mock.rs @@ -142,6 +142,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/support/src/traits.rs b/frame/support/src/traits.rs index 0b48ac7f410e8..a352b953958c9 100644 --- a/frame/support/src/traits.rs +++ b/frame/support/src/traits.rs @@ -43,6 +43,13 @@ impl Filter for () { fn filter(_: &T) -> bool { true } } +/// Migrate a given account. +#[impl_trait_for_tuples::impl_for_tuples(30)] +pub trait MigrateAccount { + /// Migrate the `account`. + fn migrate_account(account: &A); +} + /// An abstraction of a value stored within storage, but possibly as part of a larger composite /// item. pub trait StoredMap { diff --git a/frame/system/benches/bench.rs b/frame/system/benches/bench.rs index 95b9b88c705fb..9a2364fcb535f 100644 --- a/frame/system/benches/bench.rs +++ b/frame/system/benches/bench.rs @@ -82,7 +82,7 @@ impl system::Trait for Runtime { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/system/benchmarking/src/mock.rs b/frame/system/benchmarking/src/mock.rs index 1e904302e3b9e..a4509f6d03933 100644 --- a/frame/system/benchmarking/src/mock.rs +++ b/frame/system/benchmarking/src/mock.rs @@ -72,6 +72,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/system/src/accounts.scale b/frame/system/src/accounts.scale new file mode 100644 index 0000000000000..bfd7e6277f20c Binary files /dev/null and b/frame/system/src/accounts.scale differ diff --git a/frame/system/src/lib.rs b/frame/system/src/lib.rs index 8360f6c4cb46e..e99e656ebc486 100644 --- a/frame/system/src/lib.rs +++ b/frame/system/src/lib.rs @@ -122,7 +122,7 @@ use frame_support::{ storage, traits::{ Contains, Get, ModuleToIndex, OnNewAccount, OnKilledAccount, IsDeadAccount, Happened, - StoredMap, EnsureOrigin, + StoredMap, EnsureOrigin, MigrateAccount, }, weights::{ Weight, RuntimeDbWeight, DispatchInfo, PostDispatchInfo, DispatchClass, @@ -136,6 +136,7 @@ use codec::{Encode, Decode, FullCodec, EncodeLike}; use sp_io::TestExternalities; pub mod offchain; +mod migration; /// Compute the trie root of a list of extrinsics. pub fn extrinsics_root(extrinsics: &[E]) -> H::Output { @@ -245,6 +246,9 @@ pub trait Trait: 'static + Eq + Clone { /// /// All resources should be cleaned up associated with the given account. type OnKilledAccount: OnKilledAccount; + + /// Migrate an account. + type MigrateAccount: MigrateAccount; } pub type DigestOf = generic::Digest<::Hash>; @@ -561,6 +565,17 @@ decl_module! { /// The maximum length of a block (in bytes). const MaximumBlockLength: u32 = T::MaximumBlockLength::get(); + + fn on_runtime_upgrade() -> Weight { + migration::migrate::(); + + // Remove the old `RuntimeUpgraded` storage entry. + let mut runtime_upgraded_key = sp_io::hashing::twox_128(b"System").to_vec(); + runtime_upgraded_key.extend(&sp_io::hashing::twox_128(b"RuntimeUpgraded")); + sp_io::storage::clear(&runtime_upgraded_key); + // TODO: determine actual weight + 0 + } /// A dispatch that will fill the block weight up to the given ratio. // TODO: This should only be available for testing, rather than in general usage, but @@ -748,6 +763,21 @@ decl_module! { ensure!(account.data == T::AccountData::default(), Error::::NonDefaultComposite); Account::::remove(who); } + + #[weight = FunctionOf( + |(accounts,): (&Vec,)| accounts.len() as Weight * 10_000, + DispatchClass::Normal, + Pays::Yes, + )] + fn migrate_accounts(origin, accounts: Vec) { + let _ = ensure_signed(origin)?; + for a in &accounts { + if Account::::migrate_key_from_blake(a).is_some() { + // Inform other modules about the account. + T::MigrateAccount::migrate_account(a); + } + } + } } } @@ -1939,7 +1969,7 @@ pub(crate) mod tests { type Version = Version; type ModuleToIndex = (); type AccountData = u32; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = RecordKilled; } diff --git a/frame/system/src/migration.rs b/frame/system/src/migration.rs new file mode 100644 index 0000000000000..ece389f4f8503 --- /dev/null +++ b/frame/system/src/migration.rs @@ -0,0 +1,37 @@ +use super::*; +use sp_runtime::traits::SaturatedConversion; + +pub fn migrate() { + // Number is current block - we obviously don't know that hash. + // Number - 1 is the parent block, who hash we record in this block, but then that's already + // with the new storage so we don't migrate it. + // Number - 2 is therefore the most recent block's hash that needs migrating. + if Number::::get() > One::one() { + sp_runtime::print("Migrating BlockHash..."); + BlockHash::::migrate_key_from_blake(T::BlockNumber::zero()); + let mut n = Number::::get() - One::one() - One::one(); + while !n.is_zero() { + sp_runtime::print(n.saturated_into::()); + if BlockHash::::migrate_key_from_blake(n).is_none() { + break; + } + n -= One::one(); + } + } + + sp_runtime::print("Migrating Accounts..."); + let mut count = 0u32; + if let Ok(accounts) = Vec::::decode(&mut &include_bytes!("accounts.scale")[..]) { + for a in &accounts { + if Account::::migrate_key_from_blake(a).is_some() { + // Inform other modules about the account. + T::MigrateAccount::migrate_account(a); + count += 1; + if count % 1000 == 0 { + sp_runtime::print(count); + } + } + } + } + sp_runtime::print(count); +} diff --git a/frame/timestamp/src/lib.rs b/frame/timestamp/src/lib.rs index 6d38919f31b1b..94048cb148e6e 100644 --- a/frame/timestamp/src/lib.rs +++ b/frame/timestamp/src/lib.rs @@ -335,7 +335,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } parameter_types! { diff --git a/frame/transaction-payment/src/lib.rs b/frame/transaction-payment/src/lib.rs index 584f2e2580e33..c38d9545471e7 100644 --- a/frame/transaction-payment/src/lib.rs +++ b/frame/transaction-payment/src/lib.rs @@ -410,7 +410,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/treasury/src/lib.rs b/frame/treasury/src/lib.rs index d1fed8fa2860a..62555adffe357 100644 --- a/frame/treasury/src/lib.rs +++ b/frame/treasury/src/lib.rs @@ -290,6 +290,16 @@ decl_error! { } } +mod migration { + use super::*; + pub fn migrate() { + for i in 0..ProposalCount::get() { + Proposals::::migrate_key_from_blake(i); + } + Reasons::::remove_all(); + } +} + decl_module! { pub struct Module for enum Call where origin: T::Origin { /// Fraction of a proposal's value that should be bonded in order to place the proposal. @@ -324,6 +334,12 @@ decl_module! { fn deposit_event() = default; + fn on_runtime_upgrade() -> Weight { + migration::migrate::(); + // TODO: determine actual weight + 0 + } + /// Put forward a suggestion for spending. A deposit proportional to the value /// is reserved and slashed if the proposal is rejected. It is returned once the /// proposal is awarded. diff --git a/frame/treasury/src/tests.rs b/frame/treasury/src/tests.rs index 0b68c51a1080c..95303b9241cf0 100644 --- a/frame/treasury/src/tests.rs +++ b/frame/treasury/src/tests.rs @@ -81,6 +81,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/utility/src/tests.rs b/frame/utility/src/tests.rs index daf3d6c53ade3..892f738bc9d4b 100644 --- a/frame/utility/src/tests.rs +++ b/frame/utility/src/tests.rs @@ -81,6 +81,7 @@ impl frame_system::Trait for Test { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } diff --git a/frame/vesting/src/lib.rs b/frame/vesting/src/lib.rs index c5a2c90eba279..4bb1e49c5b867 100644 --- a/frame/vesting/src/lib.rs +++ b/frame/vesting/src/lib.rs @@ -56,7 +56,7 @@ use sp_runtime::{DispatchResult, RuntimeDebug, traits::{ use frame_support::{decl_module, decl_event, decl_storage, decl_error, ensure}; use frame_support::traits::{ Currency, LockableCurrency, VestingSchedule, WithdrawReason, LockIdentifier, - ExistenceRequirement, Get + ExistenceRequirement, Get, MigrateAccount, }; use frame_system::{self as system, ensure_signed}; @@ -270,6 +270,12 @@ decl_module! { } } +impl MigrateAccount for Module { + fn migrate_account(a: &T::AccountId) { + Vesting::::migrate_key_from_blake(a); + } +} + impl Module { /// (Re)set or remove the module's currency lock on `who`'s account in accordance with their /// current unvested amount. @@ -402,7 +408,7 @@ mod tests { type Version = (); type ModuleToIndex = (); type AccountData = pallet_balances::AccountData; - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); } impl pallet_balances::Trait for Test { diff --git a/test-utils/runtime/src/lib.rs b/test-utils/runtime/src/lib.rs index eaceef2defb49..7e6c7774aab51 100644 --- a/test-utils/runtime/src/lib.rs +++ b/test-utils/runtime/src/lib.rs @@ -420,7 +420,7 @@ impl frame_system::Trait for Runtime { type Version = (); type ModuleToIndex = (); type AccountData = (); - type OnNewAccount = (); + type MigrateAccount = (); type OnNewAccount = (); type OnKilledAccount = (); }