Repository: paritytech/substrate
File: frame/elections-phragmen/src/migrations/unlock_and_unreserve_all_funds.rs (Rust)

Code before:
use sp_core::Get;
use sp_runtime::traits::Zero;
use sp_std::{collections::btree_map::BTreeMap, vec::Vec};

#[cfg(feature = "try-runtime")]
use codec::{Decode, Encode};

#[cfg(feature = "try-runtime")]
use frame_support::ensure;

#[cfg(feature = "try-runtime")]
#[derive(Debug, Encode, Decode)]
struct PreMigrationData<T: frame_system::Config + pallet_balances::Config> {
	account_locked_before: BTreeMap<T::AccountId, T::Balance>,
	account_reserved_before: BTreeMap<T::AccountId, T::Balance>,
}

/// A migration that unreserves all deposit and unlocks all stake held in the context of this
/// pallet.
///
/// Useful to prevent funds from being locked up when the pallet is being deprecated.
///
/// The pallet should be made inoperable before or immediately after this migration is run.
///
/// (See also the `RemovePallet` migration in `frame/support/src/migrations.rs`)
pub struct UnlockAndUnreserveAllFunds<T: crate::Config + pallet_balances::Config>(
	sp_std::marker::PhantomData<T>,
);

impl<T: crate::Config + pallet_balances::Config> UnlockAndUnreserveAllFunds<T>
where
	<T as pallet_balances::Config>::Balance: From<
		<<T as crate::Config>::Currency as frame_support::traits::Currency<
			<T as frame_system::Config>::AccountId,
		>>::Balance,
	>,
	<T as pallet_balances::Config>::Balance: Sum<<T as pallet_balances::Config>::Balance>,
{
	/// Calculates and returns the total amounts deposited and staked by each account in the context
	/// of this pallet.
	///
	/// The deposited and staked amounts are returned in two separate `BTreeMap` collections.
	///
	/// The first `BTreeMap`, `account_deposited_sums`, contains each account's total amount
	/// deposited. This includes deposits made by Members, RunnerUps, Candidates, and Voters.
	///
	/// The second `BTreeMap`, `account_staked_sums`, contains each account's total amount staked.
	/// This includes stakes made by Voters.
	///
	/// # Returns
	///

Review comment (suggestion):
So if a runtime does not have this, it would need to temporarily implement `Config` again, and pass it to this crate. I can see it work.

Alternative would be to create `trait MigrationConfig` and only ask for the user to implement that. 

It is reasonable to say that usually you want to call this migration either in the same PR as when you remove the pallet, or after. This is a good data-point to help you decide.

Trying against Kusama which does not have this pallet anymore might help you answer that. 

Code after:
use sp_std::collections::btree_map::BTreeMap;

#[cfg(feature = "try-runtime")]
use sp_std::vec::Vec;

const LOG_TARGET: &str = "elections_phragmen::migrations::unlock_and_unreserve_all_funds";

/// A migration that unreserves all deposit and unlocks all stake held in the context of this
/// pallet.
///
/// Useful to prevent funds from being locked up when the pallet is being deprecated.
///
/// The pallet should be made inoperable before this migration is run.
///
/// (See also [`RemovePallet`][frame_support::migrations::RemovePallet])
pub struct UnlockAndUnreserveAllFunds<T: crate::Config>(sp_std::marker::PhantomData<T>);

impl<T: crate::Config> UnlockAndUnreserveAllFunds<T> {
	/// Calculates and returns the total amounts deposited and staked by each account in the context
	/// of this pallet.
	///
	/// The deposited and staked amounts are returned in two separate `BTreeMap` collections.
	///
	/// The first `BTreeMap`, `account_deposited_sums`, contains each account's total amount
	/// deposited. This includes deposits made by Members, RunnerUps, Candidates, and Voters.
	///
	/// The second `BTreeMap`, `account_staked_sums`, contains each account's total amount staked.
	/// This includes stakes made by Voters.
	///
	/// # Returns
	///
	/// This function returns a tuple of two `BTreeMap` collections and the weight of the reads:
	///
	/// * `BTreeMap<T::AccountId, BalanceOf<T>>`: Map of account IDs to their respective total
	///   deposit sums.
	/// * `BTreeMap<T::AccountId, BalanceOf<T>>`: Map of account IDs to their respective total
	///   staked sums.
	/// * `frame_support::weights::Weight`: The weight of reading the storage.
	fn get_account_deposited_and_staked_sums() -> (
		BTreeMap<T::AccountId, BalanceOf<T>>,
		BTreeMap<T::AccountId, BalanceOf<T>>,
		frame_support::weights::Weight,
	) {
		use crate::Voting;
		use sp_runtime::Saturating;

		let members = crate::Members::<T>::get();
		let runner_ups = crate::RunnersUp::<T>::get();
		let candidates = crate::Candidates::<T>::get();

		// Get the total amount deposited (Members, RunnerUps, Candidates and Voters all can have