mirror of
https://github.com/pezkuwichain/pezkuwi-subxt.git
synced 2026-06-13 07:01:05 +00:00
Run cargo fmt on the whole code base (#9394)
* Run cargo fmt on the whole code base * Second run * Add CI check * Fix compilation * More unnecessary braces * Handle weights * Use --all * Use correct attributes... * Fix UI tests * AHHHHHHHHH * 🤦 * Docs * Fix compilation * 🤷 * Please stop * 🤦 x 2 * More * make rustfmt.toml consistent with polkadot Co-authored-by: André Silva <andrerfosilva@gmail.com>
This commit is contained in:
@@ -19,13 +19,15 @@
|
||||
|
||||
use super::*;
|
||||
|
||||
use frame_benchmarking::{benchmarks, account, whitelist_account, impl_benchmark_test_suite};
|
||||
use frame_benchmarking::{account, benchmarks, impl_benchmark_test_suite, whitelist_account};
|
||||
use frame_support::{
|
||||
assert_noop, assert_ok,
|
||||
traits::{Currency, Get, EnsureOrigin, OnInitialize, UnfilteredDispatchable, schedule::DispatchTime},
|
||||
traits::{
|
||||
schedule::DispatchTime, Currency, EnsureOrigin, Get, OnInitialize, UnfilteredDispatchable,
|
||||
},
|
||||
};
|
||||
use frame_system::{RawOrigin, Pallet as System, self};
|
||||
use sp_runtime::traits::{Bounded, One, BadOrigin};
|
||||
use frame_system::{Pallet as System, RawOrigin};
|
||||
use sp_runtime::traits::{BadOrigin, Bounded, One};
|
||||
|
||||
use crate::Pallet as Democracy;
|
||||
|
||||
@@ -49,11 +51,7 @@ fn add_proposal<T: Config>(n: u32) -> Result<T::Hash, &'static str> {
|
||||
let value = T::MinimumDeposit::get();
|
||||
let proposal_hash: T::Hash = T::Hashing::hash_of(&n);
|
||||
|
||||
Democracy::<T>::propose(
|
||||
RawOrigin::Signed(other).into(),
|
||||
proposal_hash,
|
||||
value.into(),
|
||||
)?;
|
||||
Democracy::<T>::propose(RawOrigin::Signed(other).into(), proposal_hash, value.into())?;
|
||||
|
||||
Ok(proposal_hash)
|
||||
}
|
||||
@@ -76,20 +74,15 @@ fn add_referendum<T: Config>(n: u32) -> Result<ReferendumIndex, &'static str> {
|
||||
63,
|
||||
frame_system::RawOrigin::Root.into(),
|
||||
Call::enact_proposal(proposal_hash, referendum_index).into(),
|
||||
).map_err(|_| "failed to schedule named")?;
|
||||
)
|
||||
.map_err(|_| "failed to schedule named")?;
|
||||
Ok(referendum_index)
|
||||
}
|
||||
|
||||
fn account_vote<T: Config>(b: BalanceOf<T>) -> AccountVote<BalanceOf<T>> {
|
||||
let v = Vote {
|
||||
aye: true,
|
||||
conviction: Conviction::Locked1x,
|
||||
};
|
||||
let v = Vote { aye: true, conviction: Conviction::Locked1x };
|
||||
|
||||
AccountVote::Standard {
|
||||
vote: v,
|
||||
balance: b,
|
||||
}
|
||||
AccountVote::Standard { vote: v, balance: b }
|
||||
}
|
||||
|
||||
benchmarks! {
|
||||
@@ -224,8 +217,8 @@ benchmarks! {
|
||||
// Place our proposal in the external queue, too.
|
||||
let hash = T::Hashing::hash_of(&0);
|
||||
assert_ok!(
|
||||
Democracy::<T>::external_propose(T::ExternalOrigin::successful_origin(), hash.clone())
|
||||
);
|
||||
Democracy::<T>::external_propose(T::ExternalOrigin::successful_origin(), hash.clone())
|
||||
);
|
||||
|
||||
// Add a referendum of our proposal.
|
||||
let referendum_index = add_referendum::<T>(0)?;
|
||||
@@ -237,9 +230,9 @@ benchmarks! {
|
||||
verify {
|
||||
// Referendum has been canceled
|
||||
assert_noop!(
|
||||
Democracy::<T>::referendum_status(referendum_index),
|
||||
Error::<T>::ReferendumInvalid
|
||||
);
|
||||
Democracy::<T>::referendum_status(referendum_index),
|
||||
Error::<T>::ReferendumInvalid
|
||||
);
|
||||
}
|
||||
|
||||
// Worst case scenario, we external propose a previously blacklisted proposal
|
||||
@@ -785,9 +778,4 @@ benchmarks! {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
impl_benchmark_test_suite!(
|
||||
Democracy,
|
||||
crate::tests::new_test_ext(),
|
||||
crate::tests::Test,
|
||||
);
|
||||
impl_benchmark_test_suite!(Democracy, crate::tests::new_test_ext(), crate::tests::Test,);
|
||||
|
||||
@@ -17,10 +17,13 @@
|
||||
|
||||
//! The conviction datatype.
|
||||
|
||||
use sp_std::{result::Result, convert::TryFrom};
|
||||
use sp_runtime::{RuntimeDebug, traits::{Zero, Bounded, CheckedMul, CheckedDiv}};
|
||||
use codec::{Encode, Decode};
|
||||
use crate::types::Delegations;
|
||||
use codec::{Decode, Encode};
|
||||
use sp_runtime::{
|
||||
traits::{Bounded, CheckedDiv, CheckedMul, Zero},
|
||||
RuntimeDebug,
|
||||
};
|
||||
use sp_std::{convert::TryFrom, result::Result};
|
||||
|
||||
/// A value denoting the strength of conviction of a vote.
|
||||
#[derive(Encode, Decode, Copy, Clone, Eq, PartialEq, Ord, PartialOrd, RuntimeDebug)]
|
||||
@@ -93,9 +96,10 @@ impl Conviction {
|
||||
}
|
||||
|
||||
/// The votes of a voter of the given `balance` with our conviction.
|
||||
pub fn votes<
|
||||
B: From<u8> + Zero + Copy + CheckedMul + CheckedDiv + Bounded
|
||||
>(self, capital: B) -> Delegations<B> {
|
||||
pub fn votes<B: From<u8> + Zero + Copy + CheckedMul + CheckedDiv + Bounded>(
|
||||
self,
|
||||
capital: B,
|
||||
) -> Delegations<B> {
|
||||
let votes = match self {
|
||||
Conviction::None => capital.checked_div(&10u8.into()).unwrap_or_else(Zero::zero),
|
||||
x => capital.checked_mul(&u8::from(x).into()).unwrap_or_else(B::max_value),
|
||||
|
||||
@@ -121,7 +121,7 @@
|
||||
//! This call can only be made by the `ExternalMajorityOrigin`.
|
||||
//!
|
||||
//! - `external_propose_majority` - Schedules a proposal to become a majority-carries
|
||||
//! referendum once it is legal for an externally proposed referendum.
|
||||
//! referendum once it is legal for an externally proposed referendum.
|
||||
//!
|
||||
//! #### External Default Origin
|
||||
//!
|
||||
@@ -149,34 +149,36 @@
|
||||
//! - `cancel_queued` - Cancels a proposal that is queued for enactment.
|
||||
//! - `clear_public_proposal` - Removes all public proposals.
|
||||
|
||||
#![recursion_limit="128"]
|
||||
#![recursion_limit = "128"]
|
||||
#![cfg_attr(not(feature = "std"), no_std)]
|
||||
|
||||
use sp_std::prelude::*;
|
||||
use sp_runtime::{
|
||||
DispatchResult, DispatchError, ArithmeticError, RuntimeDebug,
|
||||
traits::{Zero, Hash, Dispatchable, Saturating, Bounded},
|
||||
};
|
||||
use codec::{Encode, Decode, Input};
|
||||
use codec::{Decode, Encode, Input};
|
||||
use frame_support::{
|
||||
ensure, weights::Weight,
|
||||
ensure,
|
||||
traits::{
|
||||
Currency, ReservableCurrency, LockableCurrency, WithdrawReasons, LockIdentifier, Get,
|
||||
OnUnbalanced, BalanceStatus, schedule::{Named as ScheduleNamed, DispatchTime},
|
||||
schedule::{DispatchTime, Named as ScheduleNamed},
|
||||
BalanceStatus, Currency, Get, LockIdentifier, LockableCurrency, OnUnbalanced,
|
||||
ReservableCurrency, WithdrawReasons,
|
||||
},
|
||||
weights::Weight,
|
||||
};
|
||||
use sp_runtime::{
|
||||
traits::{Bounded, Dispatchable, Hash, Saturating, Zero},
|
||||
ArithmeticError, DispatchError, DispatchResult, RuntimeDebug,
|
||||
};
|
||||
use sp_std::prelude::*;
|
||||
|
||||
mod vote_threshold;
|
||||
mod vote;
|
||||
mod conviction;
|
||||
mod types;
|
||||
mod vote;
|
||||
mod vote_threshold;
|
||||
pub mod weights;
|
||||
pub use weights::WeightInfo;
|
||||
pub use vote_threshold::{Approved, VoteThreshold};
|
||||
pub use vote::{Vote, AccountVote, Voting};
|
||||
pub use conviction::Conviction;
|
||||
pub use types::{ReferendumInfo, ReferendumStatus, Tally, UnvoteScope, Delegations};
|
||||
pub use pallet::*;
|
||||
pub use types::{Delegations, ReferendumInfo, ReferendumStatus, Tally, UnvoteScope};
|
||||
pub use vote::{AccountVote, Vote, Voting};
|
||||
pub use vote_threshold::{Approved, VoteThreshold};
|
||||
pub use weights::WeightInfo;
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests;
|
||||
@@ -197,9 +199,11 @@ pub type PropIndex = u32;
|
||||
/// A referendum index.
|
||||
pub type ReferendumIndex = u32;
|
||||
|
||||
type BalanceOf<T> = <<T as Config>::Currency as Currency<<T as frame_system::Config>::AccountId>>::Balance;
|
||||
type NegativeImbalanceOf<T> =
|
||||
<<T as Config>::Currency as Currency<<T as frame_system::Config>::AccountId>>::NegativeImbalance;
|
||||
type BalanceOf<T> =
|
||||
<<T as Config>::Currency as Currency<<T as frame_system::Config>::AccountId>>::Balance;
|
||||
type NegativeImbalanceOf<T> = <<T as Config>::Currency as Currency<
|
||||
<T as frame_system::Config>::AccountId,
|
||||
>>::NegativeImbalance;
|
||||
|
||||
#[derive(Clone, Encode, Decode, RuntimeDebug)]
|
||||
pub enum PreimageStatus<AccountId, Balance, BlockNumber> {
|
||||
@@ -235,13 +239,16 @@ enum Releases {
|
||||
|
||||
#[frame_support::pallet]
|
||||
pub mod pallet {
|
||||
use sp_runtime::DispatchResult;
|
||||
use frame_support::{
|
||||
pallet_prelude::*, Parameter,
|
||||
weights::{DispatchClass, Pays}, traits::EnsureOrigin, dispatch::DispatchResultWithPostInfo,
|
||||
};
|
||||
use frame_system::{pallet_prelude::*, ensure_signed, ensure_root};
|
||||
use super::*;
|
||||
use frame_support::{
|
||||
dispatch::DispatchResultWithPostInfo,
|
||||
pallet_prelude::*,
|
||||
traits::EnsureOrigin,
|
||||
weights::{DispatchClass, Pays},
|
||||
Parameter,
|
||||
};
|
||||
use frame_system::{ensure_root, ensure_signed, pallet_prelude::*};
|
||||
use sp_runtime::DispatchResult;
|
||||
|
||||
#[pallet::pallet]
|
||||
#[pallet::generate_store(pub(super) trait Store)]
|
||||
@@ -249,12 +256,12 @@ pub mod pallet {
|
||||
|
||||
#[pallet::config]
|
||||
pub trait Config: frame_system::Config + Sized {
|
||||
type Proposal: Parameter + Dispatchable<Origin=Self::Origin> + From<Call<Self>>;
|
||||
type Proposal: Parameter + Dispatchable<Origin = Self::Origin> + From<Call<Self>>;
|
||||
type Event: From<Event<Self>> + IsType<<Self as frame_system::Config>::Event>;
|
||||
|
||||
/// Currency type for this pallet.
|
||||
type Currency: ReservableCurrency<Self::AccountId>
|
||||
+ LockableCurrency<Self::AccountId, Moment=Self::BlockNumber>;
|
||||
+ LockableCurrency<Self::AccountId, Moment = Self::BlockNumber>;
|
||||
|
||||
/// The minimum period of locking and the period between a proposal being approved and enacted.
|
||||
///
|
||||
@@ -323,7 +330,7 @@ pub mod pallet {
|
||||
///
|
||||
/// The number of Vetoers for a proposal must be small, extrinsics are weighted according to
|
||||
/// [MAX_VETOERS](./const.MAX_VETOERS.html)
|
||||
type VetoOrigin: EnsureOrigin<Self::Origin, Success=Self::AccountId>;
|
||||
type VetoOrigin: EnsureOrigin<Self::Origin, Success = Self::AccountId>;
|
||||
|
||||
/// Period in blocks where an external proposal may not be re-submitted after being vetoed.
|
||||
#[pallet::constant]
|
||||
@@ -334,7 +341,7 @@ pub mod pallet {
|
||||
type PreimageByteDeposit: Get<BalanceOf<Self>>;
|
||||
|
||||
/// An origin that can provide a preimage using operational extrinsics.
|
||||
type OperationalPreimageOrigin: EnsureOrigin<Self::Origin, Success=Self::AccountId>;
|
||||
type OperationalPreimageOrigin: EnsureOrigin<Self::Origin, Success = Self::AccountId>;
|
||||
|
||||
/// Handler for the unbalanced reduction when slashing a preimage deposit.
|
||||
type Slash: OnUnbalanced<NegativeImbalanceOf<Self>>;
|
||||
@@ -370,18 +377,16 @@ pub mod pallet {
|
||||
/// The public proposals. Unsorted. The second item is the proposal's hash.
|
||||
#[pallet::storage]
|
||||
#[pallet::getter(fn public_props)]
|
||||
pub type PublicProps<T: Config> = StorageValue<_, Vec<(PropIndex, T::Hash, T::AccountId)>, ValueQuery>;
|
||||
pub type PublicProps<T: Config> =
|
||||
StorageValue<_, Vec<(PropIndex, T::Hash, T::AccountId)>, ValueQuery>;
|
||||
|
||||
/// Those who have locked a deposit.
|
||||
///
|
||||
/// TWOX-NOTE: Safe, as increasing integer keys are safe.
|
||||
#[pallet::storage]
|
||||
#[pallet::getter(fn deposit_of)]
|
||||
pub type DepositOf<T: Config> = StorageMap<
|
||||
_,
|
||||
Twox64Concat, PropIndex,
|
||||
(Vec<T::AccountId>, BalanceOf<T>),
|
||||
>;
|
||||
pub type DepositOf<T: Config> =
|
||||
StorageMap<_, Twox64Concat, PropIndex, (Vec<T::AccountId>, BalanceOf<T>)>;
|
||||
|
||||
/// Map of hashes to the proposal preimage, along with who registered it and their deposit.
|
||||
/// The block number is the block at which it was deposited.
|
||||
@@ -390,7 +395,8 @@ pub mod pallet {
|
||||
#[pallet::storage]
|
||||
pub type Preimages<T: Config> = StorageMap<
|
||||
_,
|
||||
Identity, T::Hash,
|
||||
Identity,
|
||||
T::Hash,
|
||||
PreimageStatus<T::AccountId, BalanceOf<T>, T::BlockNumber>,
|
||||
>;
|
||||
|
||||
@@ -412,7 +418,8 @@ pub mod pallet {
|
||||
#[pallet::getter(fn referendum_info)]
|
||||
pub type ReferendumInfoOf<T: Config> = StorageMap<
|
||||
_,
|
||||
Twox64Concat, ReferendumIndex,
|
||||
Twox64Concat,
|
||||
ReferendumIndex,
|
||||
ReferendumInfo<T::BlockNumber, T::Hash, BalanceOf<T>>,
|
||||
>;
|
||||
|
||||
@@ -422,7 +429,9 @@ pub mod pallet {
|
||||
/// TWOX-NOTE: SAFE as `AccountId`s are crypto hashes anyway.
|
||||
#[pallet::storage]
|
||||
pub type VotingOf<T: Config> = StorageMap<
|
||||
_, Twox64Concat, T::AccountId,
|
||||
_,
|
||||
Twox64Concat,
|
||||
T::AccountId,
|
||||
Voting<BalanceOf<T>, T::AccountId, T::BlockNumber>,
|
||||
ValueQuery,
|
||||
>;
|
||||
@@ -452,7 +461,8 @@ pub mod pallet {
|
||||
/// A record of who vetoed what. Maps proposal hash to a possible existent block number
|
||||
/// (until when it may not be resubmitted) and who vetoed it.
|
||||
#[pallet::storage]
|
||||
pub type Blacklist<T: Config> = StorageMap<_, Identity, T::Hash, (T::BlockNumber, Vec<T::AccountId>)>;
|
||||
pub type Blacklist<T: Config> =
|
||||
StorageMap<_, Identity, T::Hash, (T::BlockNumber, Vec<T::AccountId>)>;
|
||||
|
||||
/// Record of all proposals that have been subject to emergency cancellation.
|
||||
#[pallet::storage]
|
||||
@@ -472,9 +482,7 @@ pub mod pallet {
|
||||
#[cfg(feature = "std")]
|
||||
impl<T: Config> Default for GenesisConfig<T> {
|
||||
fn default() -> Self {
|
||||
GenesisConfig {
|
||||
_phantom: Default::default(),
|
||||
}
|
||||
GenesisConfig { _phantom: Default::default() }
|
||||
}
|
||||
}
|
||||
|
||||
@@ -684,11 +692,10 @@ pub mod pallet {
|
||||
) -> DispatchResult {
|
||||
let who = ensure_signed(origin)?;
|
||||
|
||||
let seconds = Self::len_of_deposit_of(proposal)
|
||||
.ok_or_else(|| Error::<T>::ProposalMissing)?;
|
||||
let seconds =
|
||||
Self::len_of_deposit_of(proposal).ok_or_else(|| Error::<T>::ProposalMissing)?;
|
||||
ensure!(seconds <= seconds_upper_bound, Error::<T>::WrongUpperBound);
|
||||
let mut deposit = Self::deposit_of(proposal)
|
||||
.ok_or(Error::<T>::ProposalMissing)?;
|
||||
let mut deposit = Self::deposit_of(proposal).ok_or(Error::<T>::ProposalMissing)?;
|
||||
T::Currency::reserve(&who, deposit.1)?;
|
||||
deposit.0.push(who);
|
||||
<DepositOf<T>>::insert(proposal, deposit);
|
||||
@@ -726,7 +733,10 @@ pub mod pallet {
|
||||
///
|
||||
/// Weight: `O(1)`.
|
||||
#[pallet::weight((T::WeightInfo::emergency_cancel(), DispatchClass::Operational))]
|
||||
pub fn emergency_cancel(origin: OriginFor<T>, ref_index: ReferendumIndex) -> DispatchResult {
|
||||
pub fn emergency_cancel(
|
||||
origin: OriginFor<T>,
|
||||
ref_index: ReferendumIndex,
|
||||
) -> DispatchResult {
|
||||
T::CancellationOrigin::ensure_origin(origin)?;
|
||||
|
||||
let status = Self::referendum_status(ref_index)?;
|
||||
@@ -842,8 +852,8 @@ pub mod pallet {
|
||||
ensure!(T::InstantAllowed::get(), Error::<T>::InstantNotAllowed);
|
||||
}
|
||||
|
||||
let (e_proposal_hash, threshold) = <NextExternal<T>>::get()
|
||||
.ok_or(Error::<T>::ProposalMissing)?;
|
||||
let (e_proposal_hash, threshold) =
|
||||
<NextExternal<T>>::get().ok_or(Error::<T>::ProposalMissing)?;
|
||||
ensure!(
|
||||
threshold != VoteThreshold::SuperMajorityApprove,
|
||||
Error::<T>::NotSimpleMajority,
|
||||
@@ -875,11 +885,10 @@ pub mod pallet {
|
||||
Err(Error::<T>::NoProposal)?;
|
||||
}
|
||||
|
||||
let mut existing_vetoers = <Blacklist<T>>::get(&proposal_hash)
|
||||
.map(|pair| pair.1)
|
||||
.unwrap_or_else(Vec::new);
|
||||
let insert_position = existing_vetoers.binary_search(&who)
|
||||
.err().ok_or(Error::<T>::AlreadyVetoed)?;
|
||||
let mut existing_vetoers =
|
||||
<Blacklist<T>>::get(&proposal_hash).map(|pair| pair.1).unwrap_or_else(Vec::new);
|
||||
let insert_position =
|
||||
existing_vetoers.binary_search(&who).err().ok_or(Error::<T>::AlreadyVetoed)?;
|
||||
|
||||
existing_vetoers.insert(insert_position, who.clone());
|
||||
let until = <frame_system::Pallet<T>>::block_number() + T::CooloffPeriod::get();
|
||||
@@ -949,7 +958,7 @@ pub mod pallet {
|
||||
origin: OriginFor<T>,
|
||||
to: T::AccountId,
|
||||
conviction: Conviction,
|
||||
balance: BalanceOf<T>
|
||||
balance: BalanceOf<T>,
|
||||
) -> DispatchResultWithPostInfo {
|
||||
let who = ensure_signed(origin)?;
|
||||
let votes = Self::try_delegate(who, to, conviction, balance)?;
|
||||
@@ -1089,10 +1098,11 @@ pub mod pallet {
|
||||
|
||||
let (provider, deposit, since, expiry) = <Preimages<T>>::get(&proposal_hash)
|
||||
.and_then(|m| match m {
|
||||
PreimageStatus::Available { provider, deposit, since, expiry, .. }
|
||||
=> Some((provider, deposit, since, expiry)),
|
||||
PreimageStatus::Available { provider, deposit, since, expiry, .. } =>
|
||||
Some((provider, deposit, since, expiry)),
|
||||
_ => None,
|
||||
}).ok_or(Error::<T>::PreimageMissing)?;
|
||||
})
|
||||
.ok_or(Error::<T>::PreimageMissing)?;
|
||||
|
||||
let now = <frame_system::Pallet<T>>::block_number();
|
||||
let (voting, enactment) = (T::VotingPeriod::get(), T::EnactmentPeriod::get());
|
||||
@@ -1100,7 +1110,8 @@ pub mod pallet {
|
||||
ensure!(now >= since + voting + additional, Error::<T>::TooEarly);
|
||||
ensure!(expiry.map_or(true, |e| now > e), Error::<T>::Imminent);
|
||||
|
||||
let res = T::Currency::repatriate_reserved(&provider, &who, deposit, BalanceStatus::Free);
|
||||
let res =
|
||||
T::Currency::repatriate_reserved(&provider, &who, deposit, BalanceStatus::Free);
|
||||
debug_assert!(res.is_ok());
|
||||
<Preimages<T>>::remove(&proposal_hash);
|
||||
Self::deposit_event(Event::<T>::PreimageReaped(proposal_hash, provider, deposit, who));
|
||||
@@ -1211,7 +1222,8 @@ pub mod pallet {
|
||||
/// Weight: `O(p)` (though as this is an high-privilege dispatch, we assume it has a
|
||||
/// reasonable value).
|
||||
#[pallet::weight((T::WeightInfo::blacklist(T::MaxProposals::get()), DispatchClass::Operational))]
|
||||
pub fn blacklist(origin: OriginFor<T>,
|
||||
pub fn blacklist(
|
||||
origin: OriginFor<T>,
|
||||
proposal_hash: T::Hash,
|
||||
maybe_ref_index: Option<ReferendumIndex>,
|
||||
) -> DispatchResult {
|
||||
@@ -1288,7 +1300,7 @@ impl<T: Config> Pallet<T> {
|
||||
|
||||
/// Get all referenda ready for tally at block `n`.
|
||||
pub fn maturing_referenda_at(
|
||||
n: T::BlockNumber
|
||||
n: T::BlockNumber,
|
||||
) -> Vec<(ReferendumIndex, ReferendumStatus<T::BlockNumber, T::Hash, BalanceOf<T>>)> {
|
||||
let next = Self::lowest_unbaked();
|
||||
let last = Self::referendum_count();
|
||||
@@ -1299,7 +1311,8 @@ impl<T: Config> Pallet<T> {
|
||||
n: T::BlockNumber,
|
||||
range: core::ops::Range<PropIndex>,
|
||||
) -> Vec<(ReferendumIndex, ReferendumStatus<T::BlockNumber, T::Hash, BalanceOf<T>>)> {
|
||||
range.into_iter()
|
||||
range
|
||||
.into_iter()
|
||||
.map(|i| (i, Self::referendum_info(i)))
|
||||
.filter_map(|(i, maybe_info)| match maybe_info {
|
||||
Some(ReferendumInfo::Ongoing(status)) => Some((i, status)),
|
||||
@@ -1315,13 +1328,13 @@ impl<T: Config> Pallet<T> {
|
||||
pub fn internal_start_referendum(
|
||||
proposal_hash: T::Hash,
|
||||
threshold: VoteThreshold,
|
||||
delay: T::BlockNumber
|
||||
delay: T::BlockNumber,
|
||||
) -> ReferendumIndex {
|
||||
<Pallet<T>>::inject_referendum(
|
||||
<frame_system::Pallet<T>>::block_number() + T::VotingPeriod::get(),
|
||||
proposal_hash,
|
||||
threshold,
|
||||
delay
|
||||
delay,
|
||||
)
|
||||
}
|
||||
|
||||
@@ -1334,25 +1347,28 @@ impl<T: Config> Pallet<T> {
|
||||
// private.
|
||||
|
||||
/// Ok if the given referendum is active, Err otherwise
|
||||
fn ensure_ongoing(r: ReferendumInfo<T::BlockNumber, T::Hash, BalanceOf<T>>)
|
||||
-> Result<ReferendumStatus<T::BlockNumber, T::Hash, BalanceOf<T>>, DispatchError>
|
||||
{
|
||||
fn ensure_ongoing(
|
||||
r: ReferendumInfo<T::BlockNumber, T::Hash, BalanceOf<T>>,
|
||||
) -> Result<ReferendumStatus<T::BlockNumber, T::Hash, BalanceOf<T>>, DispatchError> {
|
||||
match r {
|
||||
ReferendumInfo::Ongoing(s) => Ok(s),
|
||||
_ => Err(Error::<T>::ReferendumInvalid.into()),
|
||||
}
|
||||
}
|
||||
|
||||
fn referendum_status(ref_index: ReferendumIndex)
|
||||
-> Result<ReferendumStatus<T::BlockNumber, T::Hash, BalanceOf<T>>, DispatchError>
|
||||
{
|
||||
let info = ReferendumInfoOf::<T>::get(ref_index)
|
||||
.ok_or(Error::<T>::ReferendumInvalid)?;
|
||||
fn referendum_status(
|
||||
ref_index: ReferendumIndex,
|
||||
) -> Result<ReferendumStatus<T::BlockNumber, T::Hash, BalanceOf<T>>, DispatchError> {
|
||||
let info = ReferendumInfoOf::<T>::get(ref_index).ok_or(Error::<T>::ReferendumInvalid)?;
|
||||
Self::ensure_ongoing(info)
|
||||
}
|
||||
|
||||
/// Actually enact a vote, if legit.
|
||||
fn try_vote(who: &T::AccountId, ref_index: ReferendumIndex, vote: AccountVote<BalanceOf<T>>) -> DispatchResult {
|
||||
fn try_vote(
|
||||
who: &T::AccountId,
|
||||
ref_index: ReferendumIndex,
|
||||
vote: AccountVote<BalanceOf<T>>,
|
||||
) -> DispatchResult {
|
||||
let mut status = Self::referendum_status(ref_index)?;
|
||||
ensure!(vote.balance() <= T::Currency::free_balance(who), Error::<T>::InsufficientFunds);
|
||||
VotingOf::<T>::try_mutate(who, |voting| -> DispatchResult {
|
||||
@@ -1365,11 +1381,14 @@ impl<T: Config> Pallet<T> {
|
||||
status.tally.reduce(approve, *delegations);
|
||||
}
|
||||
votes[i].1 = vote;
|
||||
}
|
||||
},
|
||||
Err(i) => {
|
||||
ensure!(votes.len() as u32 <= T::MaxVotes::get(), Error::<T>::MaxVotesReached);
|
||||
ensure!(
|
||||
votes.len() as u32 <= T::MaxVotes::get(),
|
||||
Error::<T>::MaxVotesReached
|
||||
);
|
||||
votes.insert(i, (ref_index, vote));
|
||||
}
|
||||
},
|
||||
}
|
||||
// Shouldn't be possible to fail, but we handle it gracefully.
|
||||
status.tally.add(vote).ok_or(ArithmeticError::Overflow)?;
|
||||
@@ -1383,12 +1402,7 @@ impl<T: Config> Pallet<T> {
|
||||
})?;
|
||||
// Extend the lock to `balance` (rather than setting it) since we don't know what other
|
||||
// votes are in place.
|
||||
T::Currency::extend_lock(
|
||||
DEMOCRACY_ID,
|
||||
who,
|
||||
vote.balance(),
|
||||
WithdrawReasons::TRANSFER
|
||||
);
|
||||
T::Currency::extend_lock(DEMOCRACY_ID, who, vote.balance(), WithdrawReasons::TRANSFER);
|
||||
ReferendumInfoOf::<T>::insert(ref_index, ReferendumInfo::Ongoing(status));
|
||||
Ok(())
|
||||
}
|
||||
@@ -1399,11 +1413,17 @@ impl<T: Config> Pallet<T> {
|
||||
/// - The referendum has finished and the voter's lock period is up.
|
||||
///
|
||||
/// This will generally be combined with a call to `unlock`.
|
||||
fn try_remove_vote(who: &T::AccountId, ref_index: ReferendumIndex, scope: UnvoteScope) -> DispatchResult {
|
||||
fn try_remove_vote(
|
||||
who: &T::AccountId,
|
||||
ref_index: ReferendumIndex,
|
||||
scope: UnvoteScope,
|
||||
) -> DispatchResult {
|
||||
let info = ReferendumInfoOf::<T>::get(ref_index);
|
||||
VotingOf::<T>::try_mutate(who, |voting| -> DispatchResult {
|
||||
if let Voting::Direct { ref mut votes, delegations, ref mut prior } = voting {
|
||||
let i = votes.binary_search_by_key(&ref_index, |i| i.0).map_err(|_| Error::<T>::NotVoter)?;
|
||||
let i = votes
|
||||
.binary_search_by_key(&ref_index, |i| i.0)
|
||||
.map_err(|_| Error::<T>::NotVoter)?;
|
||||
match info {
|
||||
Some(ReferendumInfo::Ongoing(mut status)) => {
|
||||
ensure!(matches!(scope, UnvoteScope::Any), Error::<T>::NoPermission);
|
||||
@@ -1413,17 +1433,20 @@ impl<T: Config> Pallet<T> {
|
||||
status.tally.reduce(approve, *delegations);
|
||||
}
|
||||
ReferendumInfoOf::<T>::insert(ref_index, ReferendumInfo::Ongoing(status));
|
||||
}
|
||||
Some(ReferendumInfo::Finished{end, approved}) =>
|
||||
},
|
||||
Some(ReferendumInfo::Finished { end, approved }) =>
|
||||
if let Some((lock_periods, balance)) = votes[i].1.locked_if(approved) {
|
||||
let unlock_at = end + T::EnactmentPeriod::get() * lock_periods.into();
|
||||
let now = frame_system::Pallet::<T>::block_number();
|
||||
if now < unlock_at {
|
||||
ensure!(matches!(scope, UnvoteScope::Any), Error::<T>::NoPermission);
|
||||
ensure!(
|
||||
matches!(scope, UnvoteScope::Any),
|
||||
Error::<T>::NoPermission
|
||||
);
|
||||
prior.accumulate(unlock_at, balance)
|
||||
}
|
||||
},
|
||||
None => {} // Referendum was cancelled.
|
||||
None => {}, // Referendum was cancelled.
|
||||
}
|
||||
votes.remove(i);
|
||||
}
|
||||
@@ -1444,15 +1467,15 @@ impl<T: Config> Pallet<T> {
|
||||
*delegations = delegations.saturating_add(amount);
|
||||
for &(ref_index, account_vote) in votes.iter() {
|
||||
if let AccountVote::Standard { vote, .. } = account_vote {
|
||||
ReferendumInfoOf::<T>::mutate(ref_index, |maybe_info|
|
||||
ReferendumInfoOf::<T>::mutate(ref_index, |maybe_info| {
|
||||
if let Some(ReferendumInfo::Ongoing(ref mut status)) = maybe_info {
|
||||
status.tally.increase(vote.aye, amount);
|
||||
}
|
||||
);
|
||||
});
|
||||
}
|
||||
}
|
||||
votes.len() as u32
|
||||
}
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
@@ -1463,20 +1486,20 @@ impl<T: Config> Pallet<T> {
|
||||
// We don't support second level delegating, so we don't need to do anything more.
|
||||
*delegations = delegations.saturating_sub(amount);
|
||||
1
|
||||
}
|
||||
},
|
||||
Voting::Direct { votes, delegations, .. } => {
|
||||
*delegations = delegations.saturating_sub(amount);
|
||||
for &(ref_index, account_vote) in votes.iter() {
|
||||
if let AccountVote::Standard { vote, .. } = account_vote {
|
||||
ReferendumInfoOf::<T>::mutate(ref_index, |maybe_info|
|
||||
ReferendumInfoOf::<T>::mutate(ref_index, |maybe_info| {
|
||||
if let Some(ReferendumInfo::Ongoing(ref mut status)) = maybe_info {
|
||||
status.tally.reduce(vote.aye, amount);
|
||||
}
|
||||
);
|
||||
});
|
||||
}
|
||||
}
|
||||
votes.len() as u32
|
||||
}
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
@@ -1505,22 +1528,17 @@ impl<T: Config> Pallet<T> {
|
||||
// remove any delegation votes to our current target.
|
||||
Self::reduce_upstream_delegation(&target, conviction.votes(balance));
|
||||
voting.set_common(delegations, prior);
|
||||
}
|
||||
},
|
||||
Voting::Direct { votes, delegations, prior } => {
|
||||
// here we just ensure that we're currently idling with no votes recorded.
|
||||
ensure!(votes.is_empty(), Error::<T>::VotesExist);
|
||||
voting.set_common(delegations, prior);
|
||||
}
|
||||
},
|
||||
}
|
||||
let votes = Self::increase_upstream_delegation(&target, conviction.votes(balance));
|
||||
// Extend the lock to `balance` (rather than setting it) since we don't know what other
|
||||
// votes are in place.
|
||||
T::Currency::extend_lock(
|
||||
DEMOCRACY_ID,
|
||||
&who,
|
||||
balance,
|
||||
WithdrawReasons::TRANSFER
|
||||
);
|
||||
T::Currency::extend_lock(DEMOCRACY_ID, &who, balance, WithdrawReasons::TRANSFER);
|
||||
Ok(votes)
|
||||
})?;
|
||||
Self::deposit_event(Event::<T>::Delegated(who, target));
|
||||
@@ -1535,25 +1553,18 @@ impl<T: Config> Pallet<T> {
|
||||
let mut old = Voting::default();
|
||||
sp_std::mem::swap(&mut old, voting);
|
||||
match old {
|
||||
Voting::Delegating {
|
||||
balance,
|
||||
target,
|
||||
conviction,
|
||||
delegations,
|
||||
mut prior,
|
||||
} => {
|
||||
Voting::Delegating { balance, target, conviction, delegations, mut prior } => {
|
||||
// remove any delegation votes to our current target.
|
||||
let votes = Self::reduce_upstream_delegation(&target, conviction.votes(balance));
|
||||
let votes =
|
||||
Self::reduce_upstream_delegation(&target, conviction.votes(balance));
|
||||
let now = frame_system::Pallet::<T>::block_number();
|
||||
let lock_periods = conviction.lock_periods().into();
|
||||
prior.accumulate(now + T::EnactmentPeriod::get() * lock_periods, balance);
|
||||
voting.set_common(delegations, prior);
|
||||
|
||||
Ok(votes)
|
||||
}
|
||||
Voting::Direct { .. } => {
|
||||
Err(Error::<T>::NotDelegating.into())
|
||||
}
|
||||
},
|
||||
Voting::Direct { .. } => Err(Error::<T>::NotDelegating.into()),
|
||||
}
|
||||
})?;
|
||||
Self::deposit_event(Event::<T>::Undelegated(who));
|
||||
@@ -1583,7 +1594,8 @@ impl<T: Config> Pallet<T> {
|
||||
) -> ReferendumIndex {
|
||||
let ref_index = Self::referendum_count();
|
||||
ReferendumCount::<T>::put(ref_index + 1);
|
||||
let status = ReferendumStatus { end, proposal_hash, threshold, delay, tally: Default::default() };
|
||||
let status =
|
||||
ReferendumStatus { end, proposal_hash, threshold, delay, tally: Default::default() };
|
||||
let item = ReferendumInfo::Ongoing(status);
|
||||
<ReferendumInfoOf<T>>::insert(ref_index, item);
|
||||
Self::deposit_event(Event::<T>::Started(ref_index, threshold));
|
||||
@@ -1596,7 +1608,8 @@ impl<T: Config> Pallet<T> {
|
||||
Self::launch_public(now).or_else(|_| Self::launch_external(now))
|
||||
} else {
|
||||
Self::launch_external(now).or_else(|_| Self::launch_public(now))
|
||||
}.map_err(|_| Error::<T>::NoneWaiting.into())
|
||||
}
|
||||
.map_err(|_| Error::<T>::NoneWaiting.into())
|
||||
}
|
||||
|
||||
/// Table the waiting external proposal for a vote, if there is one.
|
||||
@@ -1654,8 +1667,10 @@ impl<T: Config> Pallet<T> {
|
||||
debug_assert!(err_amount.is_zero());
|
||||
Self::deposit_event(Event::<T>::PreimageUsed(proposal_hash, provider, deposit));
|
||||
|
||||
let res = proposal.dispatch(frame_system::RawOrigin::Root.into())
|
||||
.map(|_| ()).map_err(|e| e.error);
|
||||
let res = proposal
|
||||
.dispatch(frame_system::RawOrigin::Root.into())
|
||||
.map(|_| ())
|
||||
.map_err(|e| e.error);
|
||||
Self::deposit_event(Event::<T>::Executed(index, res));
|
||||
|
||||
Ok(())
|
||||
@@ -1685,10 +1700,14 @@ impl<T: Config> Pallet<T> {
|
||||
} else {
|
||||
let when = now + status.delay;
|
||||
// Note that we need the preimage now.
|
||||
Preimages::<T>::mutate_exists(&status.proposal_hash, |maybe_pre| match *maybe_pre {
|
||||
Some(PreimageStatus::Available { ref mut expiry, .. }) => *expiry = Some(when),
|
||||
ref mut a => *a = Some(PreimageStatus::Missing(when)),
|
||||
});
|
||||
Preimages::<T>::mutate_exists(
|
||||
&status.proposal_hash,
|
||||
|maybe_pre| match *maybe_pre {
|
||||
Some(PreimageStatus::Available { ref mut expiry, .. }) =>
|
||||
*expiry = Some(when),
|
||||
ref mut a => *a = Some(PreimageStatus::Missing(when)),
|
||||
},
|
||||
);
|
||||
|
||||
if T::Scheduler::schedule_named(
|
||||
(DEMOCRACY_ID, index).encode(),
|
||||
@@ -1697,7 +1716,9 @@ impl<T: Config> Pallet<T> {
|
||||
63,
|
||||
frame_system::RawOrigin::Root.into(),
|
||||
Call::enact_proposal(status.proposal_hash, index).into(),
|
||||
).is_err() {
|
||||
)
|
||||
.is_err()
|
||||
{
|
||||
frame_support::print("LOGIC ERROR: bake_referendum/schedule_named failed");
|
||||
}
|
||||
}
|
||||
@@ -1762,7 +1783,8 @@ impl<T: Config> Pallet<T> {
|
||||
// To decode the enum variant we only need the first byte.
|
||||
let mut buf = [0u8; 1];
|
||||
let key = <Preimages<T>>::hashed_key_for(proposal_hash);
|
||||
let bytes = sp_io::storage::read(&key, &mut buf, 0).ok_or_else(|| Error::<T>::NotImminent)?;
|
||||
let bytes =
|
||||
sp_io::storage::read(&key, &mut buf, 0).ok_or_else(|| Error::<T>::NotImminent)?;
|
||||
// The value may be smaller that 1 byte.
|
||||
let mut input = &buf[0..buf.len().min(bytes as usize)];
|
||||
|
||||
@@ -1772,7 +1794,7 @@ impl<T: Config> Pallet<T> {
|
||||
_ => {
|
||||
sp_runtime::print("Failed to decode `PreimageStatus` variant");
|
||||
Err(Error::<T>::NotImminent.into())
|
||||
}
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1790,7 +1812,8 @@ impl<T: Config> Pallet<T> {
|
||||
// * at most 5 bytes to decode a `Compact<u32>`
|
||||
let mut buf = [0u8; 6];
|
||||
let key = <Preimages<T>>::hashed_key_for(proposal_hash);
|
||||
let bytes = sp_io::storage::read(&key, &mut buf, 0).ok_or_else(|| Error::<T>::PreimageMissing)?;
|
||||
let bytes =
|
||||
sp_io::storage::read(&key, &mut buf, 0).ok_or_else(|| Error::<T>::PreimageMissing)?;
|
||||
// The value may be smaller that 6 bytes.
|
||||
let mut input = &buf[0..buf.len().min(bytes as usize)];
|
||||
|
||||
@@ -1799,15 +1822,17 @@ impl<T: Config> Pallet<T> {
|
||||
Ok(0) => return Err(Error::<T>::PreimageMissing.into()),
|
||||
_ => {
|
||||
sp_runtime::print("Failed to decode `PreimageStatus` variant");
|
||||
return Err(Error::<T>::PreimageMissing.into());
|
||||
}
|
||||
return Err(Error::<T>::PreimageMissing.into())
|
||||
},
|
||||
}
|
||||
|
||||
// Decode the length of the vector.
|
||||
let len = codec::Compact::<u32>::decode(&mut input).map_err(|_| {
|
||||
sp_runtime::print("Failed to decode `PreimageStatus` variant");
|
||||
DispatchError::from(Error::<T>::PreimageMissing)
|
||||
})?.0;
|
||||
let len = codec::Compact::<u32>::decode(&mut input)
|
||||
.map_err(|_| {
|
||||
sp_runtime::print("Failed to decode `PreimageStatus` variant");
|
||||
DispatchError::from(Error::<T>::PreimageMissing)
|
||||
})?
|
||||
.0;
|
||||
|
||||
Ok(len)
|
||||
}
|
||||
@@ -1837,7 +1862,10 @@ impl<T: Config> Pallet<T> {
|
||||
}
|
||||
|
||||
// See `note_imminent_preimage`
|
||||
fn note_imminent_preimage_inner(who: T::AccountId, encoded_proposal: Vec<u8>) -> DispatchResult {
|
||||
fn note_imminent_preimage_inner(
|
||||
who: T::AccountId,
|
||||
encoded_proposal: Vec<u8>,
|
||||
) -> DispatchResult {
|
||||
let proposal_hash = T::Hashing::hash(&encoded_proposal[..]);
|
||||
Self::check_pre_image_is_missing(proposal_hash)?;
|
||||
let status = Preimages::<T>::get(&proposal_hash).ok_or(Error::<T>::NotImminent)?;
|
||||
@@ -1873,6 +1901,6 @@ fn decode_compact_u32_at(key: &[u8]) -> Option<u32> {
|
||||
sp_runtime::print("Failed to decode compact u32 at:");
|
||||
sp_runtime::print(key);
|
||||
None
|
||||
}
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,23 +17,25 @@
|
||||
|
||||
//! The crate's tests.
|
||||
|
||||
use crate as pallet_democracy;
|
||||
use super::*;
|
||||
use crate as pallet_democracy;
|
||||
use codec::Encode;
|
||||
use frame_support::{
|
||||
assert_noop, assert_ok, parameter_types, ord_parameter_types,
|
||||
traits::{SortedMembers, OnInitialize, Filter, GenesisBuild},
|
||||
assert_noop, assert_ok, ord_parameter_types, parameter_types,
|
||||
traits::{Filter, GenesisBuild, OnInitialize, SortedMembers},
|
||||
weights::Weight,
|
||||
};
|
||||
use frame_system::{EnsureRoot, EnsureSignedBy};
|
||||
use pallet_balances::{BalanceLock, Error as BalancesError};
|
||||
use sp_core::H256;
|
||||
use sp_runtime::{
|
||||
traits::{BlakeTwo256, IdentityLookup, BadOrigin},
|
||||
testing::Header, Perbill,
|
||||
testing::Header,
|
||||
traits::{BadOrigin, BlakeTwo256, IdentityLookup},
|
||||
Perbill,
|
||||
};
|
||||
use pallet_balances::{BalanceLock, Error as BalancesError};
|
||||
use frame_system::{EnsureSignedBy, EnsureRoot};
|
||||
|
||||
mod cancellation;
|
||||
mod decoders;
|
||||
mod delegation;
|
||||
mod external_proposing;
|
||||
mod fast_tracking;
|
||||
@@ -42,7 +44,6 @@ mod preimage;
|
||||
mod public_proposals;
|
||||
mod scheduling;
|
||||
mod voting;
|
||||
mod decoders;
|
||||
|
||||
const AYE: Vote = Vote { aye: true, conviction: Conviction::None };
|
||||
const NAY: Vote = Vote { aye: false, conviction: Conviction::None };
|
||||
@@ -194,10 +195,14 @@ impl Config for Test {
|
||||
|
||||
pub fn new_test_ext() -> sp_io::TestExternalities {
|
||||
let mut t = frame_system::GenesisConfig::default().build_storage::<Test>().unwrap();
|
||||
pallet_balances::GenesisConfig::<Test>{
|
||||
pallet_balances::GenesisConfig::<Test> {
|
||||
balances: vec![(1, 10), (2, 20), (3, 30), (4, 40), (5, 50), (6, 60)],
|
||||
}.assimilate_storage(&mut t).unwrap();
|
||||
pallet_democracy::GenesisConfig::<Test>::default().assimilate_storage(&mut t).unwrap();
|
||||
}
|
||||
.assimilate_storage(&mut t)
|
||||
.unwrap();
|
||||
pallet_democracy::GenesisConfig::<Test>::default()
|
||||
.assimilate_storage(&mut t)
|
||||
.unwrap();
|
||||
let mut ext = sp_io::TestExternalities::new(t);
|
||||
ext.execute_with(|| System::set_block_number(1));
|
||||
ext
|
||||
@@ -246,19 +251,11 @@ fn set_balance_proposal_hash_and_note(value: u64) -> H256 {
|
||||
}
|
||||
|
||||
fn propose_set_balance(who: u64, value: u64, delay: u64) -> DispatchResult {
|
||||
Democracy::propose(
|
||||
Origin::signed(who),
|
||||
set_balance_proposal_hash(value),
|
||||
delay,
|
||||
)
|
||||
Democracy::propose(Origin::signed(who), set_balance_proposal_hash(value), delay)
|
||||
}
|
||||
|
||||
fn propose_set_balance_and_note(who: u64, value: u64, delay: u64) -> DispatchResult {
|
||||
Democracy::propose(
|
||||
Origin::signed(who),
|
||||
set_balance_proposal_hash_and_note(value),
|
||||
delay,
|
||||
)
|
||||
Democracy::propose(Origin::signed(who), set_balance_proposal_hash_and_note(value), delay)
|
||||
}
|
||||
|
||||
fn next_block() {
|
||||
|
||||
@@ -26,7 +26,7 @@ fn cancel_referendum_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, aye(1)));
|
||||
assert_ok!(Democracy::cancel_referendum(Origin::root(), r.into()));
|
||||
@@ -67,7 +67,7 @@ fn emergency_cancel_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
2
|
||||
2,
|
||||
);
|
||||
assert!(Democracy::referendum_status(r).is_ok());
|
||||
|
||||
@@ -81,7 +81,7 @@ fn emergency_cancel_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
2
|
||||
2,
|
||||
);
|
||||
assert!(Democracy::referendum_status(r).is_ok());
|
||||
assert_noop!(
|
||||
|
||||
@@ -66,7 +66,7 @@ fn pre_image() {
|
||||
assert_noop!(Democracy::check_pre_image_is_missing(key), Error::<Test>::NotImminent);
|
||||
|
||||
for l in vec![0, 10, 100, 1000u32] {
|
||||
let available = PreimageStatus::Available{
|
||||
let available = PreimageStatus::Available {
|
||||
data: (0..l).map(|i| i as u8).collect(),
|
||||
provider: 0,
|
||||
deposit: 0,
|
||||
@@ -76,8 +76,10 @@ fn pre_image() {
|
||||
|
||||
Preimages::<Test>::insert(key, available);
|
||||
assert_eq!(Democracy::pre_image_data_len(key), Ok(l));
|
||||
assert_noop!(Democracy::check_pre_image_is_missing(key),
|
||||
Error::<Test>::DuplicatePreimage);
|
||||
assert_noop!(
|
||||
Democracy::check_pre_image_is_missing(key),
|
||||
Error::<Test>::DuplicatePreimage
|
||||
);
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
@@ -34,17 +34,17 @@ fn veto_external_works() {
|
||||
// cancelled.
|
||||
assert!(!<NextExternal<Test>>::exists());
|
||||
// fails - same proposal can't be resubmitted.
|
||||
assert_noop!(Democracy::external_propose(
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash(2),
|
||||
), Error::<Test>::ProposalBlacklisted);
|
||||
assert_noop!(
|
||||
Democracy::external_propose(Origin::signed(2), set_balance_proposal_hash(2),),
|
||||
Error::<Test>::ProposalBlacklisted
|
||||
);
|
||||
|
||||
fast_forward_to(1);
|
||||
// fails as we're still in cooloff period.
|
||||
assert_noop!(Democracy::external_propose(
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash(2),
|
||||
), Error::<Test>::ProposalBlacklisted);
|
||||
assert_noop!(
|
||||
Democracy::external_propose(Origin::signed(2), set_balance_proposal_hash(2),),
|
||||
Error::<Test>::ProposalBlacklisted
|
||||
);
|
||||
|
||||
fast_forward_to(2);
|
||||
// works; as we're out of the cooloff period.
|
||||
@@ -67,10 +67,10 @@ fn veto_external_works() {
|
||||
|
||||
fast_forward_to(3);
|
||||
// same proposal fails as we're still in cooloff
|
||||
assert_noop!(Democracy::external_propose(
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash(2),
|
||||
), Error::<Test>::ProposalBlacklisted);
|
||||
assert_noop!(
|
||||
Democracy::external_propose(Origin::signed(2), set_balance_proposal_hash(2),),
|
||||
Error::<Test>::ProposalBlacklisted
|
||||
);
|
||||
// different proposal works fine.
|
||||
assert_ok!(Democracy::external_propose(
|
||||
Origin::signed(2),
|
||||
@@ -96,10 +96,7 @@ fn external_blacklisting_should_work() {
|
||||
assert_noop!(Democracy::referendum_status(0), Error::<Test>::ReferendumInvalid);
|
||||
|
||||
assert_noop!(
|
||||
Democracy::external_propose(
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
),
|
||||
Democracy::external_propose(Origin::signed(2), set_balance_proposal_hash_and_note(2),),
|
||||
Error::<Test>::ProposalBlacklisted,
|
||||
);
|
||||
});
|
||||
@@ -110,20 +107,17 @@ fn external_referendum_works() {
|
||||
new_test_ext().execute_with(|| {
|
||||
System::set_block_number(0);
|
||||
assert_noop!(
|
||||
Democracy::external_propose(
|
||||
Origin::signed(1),
|
||||
set_balance_proposal_hash(2),
|
||||
),
|
||||
Democracy::external_propose(Origin::signed(1), set_balance_proposal_hash(2),),
|
||||
BadOrigin,
|
||||
);
|
||||
assert_ok!(Democracy::external_propose(
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
));
|
||||
assert_noop!(Democracy::external_propose(
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash(1),
|
||||
), Error::<Test>::DuplicateProposal);
|
||||
assert_noop!(
|
||||
Democracy::external_propose(Origin::signed(2), set_balance_proposal_hash(1),),
|
||||
Error::<Test>::DuplicateProposal
|
||||
);
|
||||
fast_forward_to(2);
|
||||
assert_eq!(
|
||||
Democracy::referendum_status(0),
|
||||
@@ -143,10 +137,7 @@ fn external_majority_referendum_works() {
|
||||
new_test_ext().execute_with(|| {
|
||||
System::set_block_number(0);
|
||||
assert_noop!(
|
||||
Democracy::external_propose_majority(
|
||||
Origin::signed(1),
|
||||
set_balance_proposal_hash(2)
|
||||
),
|
||||
Democracy::external_propose_majority(Origin::signed(1), set_balance_proposal_hash(2)),
|
||||
BadOrigin,
|
||||
);
|
||||
assert_ok!(Democracy::external_propose_majority(
|
||||
@@ -172,10 +163,7 @@ fn external_default_referendum_works() {
|
||||
new_test_ext().execute_with(|| {
|
||||
System::set_block_number(0);
|
||||
assert_noop!(
|
||||
Democracy::external_propose_default(
|
||||
Origin::signed(3),
|
||||
set_balance_proposal_hash(2)
|
||||
),
|
||||
Democracy::external_propose_default(Origin::signed(3), set_balance_proposal_hash(2)),
|
||||
BadOrigin,
|
||||
);
|
||||
assert_ok!(Democracy::external_propose_default(
|
||||
@@ -196,7 +184,6 @@ fn external_default_referendum_works() {
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
#[test]
|
||||
fn external_and_public_interleaving_works() {
|
||||
new_test_ext().execute_with(|| {
|
||||
@@ -222,9 +209,9 @@ fn external_and_public_interleaving_works() {
|
||||
);
|
||||
// replenish external
|
||||
assert_ok!(Democracy::external_propose(
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash_and_note(3),
|
||||
));
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash_and_note(3),
|
||||
));
|
||||
|
||||
fast_forward_to(4);
|
||||
|
||||
@@ -256,9 +243,9 @@ fn external_and_public_interleaving_works() {
|
||||
);
|
||||
// replenish external
|
||||
assert_ok!(Democracy::external_propose(
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash_and_note(5),
|
||||
));
|
||||
Origin::signed(2),
|
||||
set_balance_proposal_hash_and_note(5),
|
||||
));
|
||||
|
||||
fast_forward_to(8);
|
||||
|
||||
|
||||
@@ -24,7 +24,10 @@ fn fast_track_referendum_works() {
|
||||
new_test_ext().execute_with(|| {
|
||||
System::set_block_number(0);
|
||||
let h = set_balance_proposal_hash_and_note(2);
|
||||
assert_noop!(Democracy::fast_track(Origin::signed(5), h, 3, 2), Error::<Test>::ProposalMissing);
|
||||
assert_noop!(
|
||||
Democracy::fast_track(Origin::signed(5), h, 3, 2),
|
||||
Error::<Test>::ProposalMissing
|
||||
);
|
||||
assert_ok!(Democracy::external_propose_majority(
|
||||
Origin::signed(3),
|
||||
set_balance_proposal_hash_and_note(2)
|
||||
@@ -49,14 +52,20 @@ fn instant_referendum_works() {
|
||||
new_test_ext().execute_with(|| {
|
||||
System::set_block_number(0);
|
||||
let h = set_balance_proposal_hash_and_note(2);
|
||||
assert_noop!(Democracy::fast_track(Origin::signed(5), h, 3, 2), Error::<Test>::ProposalMissing);
|
||||
assert_noop!(
|
||||
Democracy::fast_track(Origin::signed(5), h, 3, 2),
|
||||
Error::<Test>::ProposalMissing
|
||||
);
|
||||
assert_ok!(Democracy::external_propose_majority(
|
||||
Origin::signed(3),
|
||||
set_balance_proposal_hash_and_note(2)
|
||||
));
|
||||
assert_noop!(Democracy::fast_track(Origin::signed(1), h, 3, 2), BadOrigin);
|
||||
assert_noop!(Democracy::fast_track(Origin::signed(5), h, 1, 0), BadOrigin);
|
||||
assert_noop!(Democracy::fast_track(Origin::signed(6), h, 1, 0), Error::<Test>::InstantNotAllowed);
|
||||
assert_noop!(
|
||||
Democracy::fast_track(Origin::signed(6), h, 1, 0),
|
||||
Error::<Test>::InstantNotAllowed
|
||||
);
|
||||
INSTANT_ALLOWED.with(|v| *v.borrow_mut() = true);
|
||||
assert_ok!(Democracy::fast_track(Origin::signed(6), h, 1, 0));
|
||||
assert_eq!(
|
||||
|
||||
@@ -23,23 +23,19 @@ use std::convert::TryFrom;
|
||||
fn aye(x: u8, balance: u64) -> AccountVote<u64> {
|
||||
AccountVote::Standard {
|
||||
vote: Vote { aye: true, conviction: Conviction::try_from(x).unwrap() },
|
||||
balance
|
||||
balance,
|
||||
}
|
||||
}
|
||||
|
||||
fn nay(x: u8, balance: u64) -> AccountVote<u64> {
|
||||
AccountVote::Standard {
|
||||
vote: Vote { aye: false, conviction: Conviction::try_from(x).unwrap() },
|
||||
balance
|
||||
balance,
|
||||
}
|
||||
}
|
||||
|
||||
fn the_lock(amount: u64) -> BalanceLock<u64> {
|
||||
BalanceLock {
|
||||
id: DEMOCRACY_ID,
|
||||
amount,
|
||||
reasons: pallet_balances::Reasons::Misc,
|
||||
}
|
||||
BalanceLock { id: DEMOCRACY_ID, amount, reasons: pallet_balances::Reasons::Misc }
|
||||
}
|
||||
|
||||
#[test]
|
||||
@@ -50,7 +46,7 @@ fn lock_voting_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, nay(5, 10)));
|
||||
assert_ok!(Democracy::vote(Origin::signed(2), r, aye(4, 20)));
|
||||
@@ -74,7 +70,10 @@ fn lock_voting_should_work() {
|
||||
assert_ok!(Democracy::unlock(Origin::signed(2), 5));
|
||||
|
||||
// 2, 3, 4 got their way with the vote, so they cannot be reaped by others.
|
||||
assert_noop!(Democracy::remove_other_vote(Origin::signed(1), 2, r), Error::<Test>::NoPermission);
|
||||
assert_noop!(
|
||||
Democracy::remove_other_vote(Origin::signed(1), 2, r),
|
||||
Error::<Test>::NoPermission
|
||||
);
|
||||
// However, they can be unvoted by the owner, though it will make no difference to the lock.
|
||||
assert_ok!(Democracy::remove_vote(Origin::signed(2), r));
|
||||
assert_ok!(Democracy::unlock(Origin::signed(2), 2));
|
||||
@@ -86,10 +85,12 @@ fn lock_voting_should_work() {
|
||||
assert_eq!(Balances::locks(5), vec![]);
|
||||
assert_eq!(Balances::free_balance(42), 2);
|
||||
|
||||
|
||||
fast_forward_to(5);
|
||||
// No change yet...
|
||||
assert_noop!(Democracy::remove_other_vote(Origin::signed(1), 4, r), Error::<Test>::NoPermission);
|
||||
assert_noop!(
|
||||
Democracy::remove_other_vote(Origin::signed(1), 4, r),
|
||||
Error::<Test>::NoPermission
|
||||
);
|
||||
assert_ok!(Democracy::unlock(Origin::signed(1), 4));
|
||||
assert_eq!(Balances::locks(4), vec![the_lock(40)]);
|
||||
fast_forward_to(6);
|
||||
@@ -99,7 +100,10 @@ fn lock_voting_should_work() {
|
||||
assert_eq!(Balances::locks(4), vec![]);
|
||||
|
||||
fast_forward_to(9);
|
||||
assert_noop!(Democracy::remove_other_vote(Origin::signed(1), 3, r), Error::<Test>::NoPermission);
|
||||
assert_noop!(
|
||||
Democracy::remove_other_vote(Origin::signed(1), 3, r),
|
||||
Error::<Test>::NoPermission
|
||||
);
|
||||
assert_ok!(Democracy::unlock(Origin::signed(1), 3));
|
||||
assert_eq!(Balances::locks(3), vec![the_lock(30)]);
|
||||
fast_forward_to(10);
|
||||
@@ -145,7 +149,7 @@ fn lock_voting_should_work_with_delegation() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, nay(5, 10)));
|
||||
assert_ok!(Democracy::vote(Origin::signed(2), r, aye(4, 20)));
|
||||
@@ -168,7 +172,7 @@ fn setup_three_referenda() -> (u32, u32, u32) {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SimpleMajority,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(5), r1, aye(4, 10)));
|
||||
|
||||
@@ -176,7 +180,7 @@ fn setup_three_referenda() -> (u32, u32, u32) {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SimpleMajority,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(5), r2, aye(3, 20)));
|
||||
|
||||
@@ -184,7 +188,7 @@ fn setup_three_referenda() -> (u32, u32, u32) {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SimpleMajority,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(5), r3, aye(2, 50)));
|
||||
|
||||
@@ -202,7 +206,10 @@ fn prior_lockvotes_should_be_enforced() {
|
||||
// r.2 locked 50 until #6.
|
||||
|
||||
fast_forward_to(5);
|
||||
assert_noop!(Democracy::remove_other_vote(Origin::signed(1), 5, r.2), Error::<Test>::NoPermission);
|
||||
assert_noop!(
|
||||
Democracy::remove_other_vote(Origin::signed(1), 5, r.2),
|
||||
Error::<Test>::NoPermission
|
||||
);
|
||||
assert_ok!(Democracy::unlock(Origin::signed(5), 5));
|
||||
assert_eq!(Balances::locks(5), vec![the_lock(50)]);
|
||||
fast_forward_to(6);
|
||||
@@ -210,7 +217,10 @@ fn prior_lockvotes_should_be_enforced() {
|
||||
assert_ok!(Democracy::unlock(Origin::signed(5), 5));
|
||||
assert_eq!(Balances::locks(5), vec![the_lock(20)]);
|
||||
fast_forward_to(9);
|
||||
assert_noop!(Democracy::remove_other_vote(Origin::signed(1), 5, r.1), Error::<Test>::NoPermission);
|
||||
assert_noop!(
|
||||
Democracy::remove_other_vote(Origin::signed(1), 5, r.1),
|
||||
Error::<Test>::NoPermission
|
||||
);
|
||||
assert_ok!(Democracy::unlock(Origin::signed(5), 5));
|
||||
assert_eq!(Balances::locks(5), vec![the_lock(20)]);
|
||||
fast_forward_to(10);
|
||||
@@ -218,7 +228,10 @@ fn prior_lockvotes_should_be_enforced() {
|
||||
assert_ok!(Democracy::unlock(Origin::signed(5), 5));
|
||||
assert_eq!(Balances::locks(5), vec![the_lock(10)]);
|
||||
fast_forward_to(17);
|
||||
assert_noop!(Democracy::remove_other_vote(Origin::signed(1), 5, r.0), Error::<Test>::NoPermission);
|
||||
assert_noop!(
|
||||
Democracy::remove_other_vote(Origin::signed(1), 5, r.0),
|
||||
Error::<Test>::NoPermission
|
||||
);
|
||||
assert_ok!(Democracy::unlock(Origin::signed(5), 5));
|
||||
assert_eq!(Balances::locks(5), vec![the_lock(10)]);
|
||||
fast_forward_to(18);
|
||||
@@ -296,7 +309,7 @@ fn locks_should_persist_from_voting_to_delegation() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SimpleMajority,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(5), r, aye(4, 10)));
|
||||
fast_forward_to(2);
|
||||
|
||||
@@ -26,7 +26,7 @@ fn missing_preimage_should_fail() {
|
||||
2,
|
||||
set_balance_proposal_hash(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, aye(1)));
|
||||
|
||||
@@ -43,8 +43,11 @@ fn preimage_deposit_should_be_required_and_returned() {
|
||||
// fee of 100 is too much.
|
||||
PREIMAGE_BYTE_DEPOSIT.with(|v| *v.borrow_mut() = 100);
|
||||
assert_noop!(
|
||||
if operational { Democracy::note_preimage_operational(Origin::signed(6), vec![0; 500]) }
|
||||
else { Democracy::note_preimage(Origin::signed(6), vec![0; 500]) },
|
||||
if operational {
|
||||
Democracy::note_preimage_operational(Origin::signed(6), vec![0; 500])
|
||||
} else {
|
||||
Democracy::note_preimage(Origin::signed(6), vec![0; 500])
|
||||
},
|
||||
BalancesError::<Test, _>::InsufficientBalance,
|
||||
);
|
||||
// fee of 1 is reasonable.
|
||||
@@ -53,7 +56,7 @@ fn preimage_deposit_should_be_required_and_returned() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, aye(1)));
|
||||
|
||||
@@ -72,10 +75,11 @@ fn preimage_deposit_should_be_required_and_returned() {
|
||||
fn preimage_deposit_should_be_reapable_earlier_by_owner() {
|
||||
new_test_ext_execute_with_cond(|operational| {
|
||||
PREIMAGE_BYTE_DEPOSIT.with(|v| *v.borrow_mut() = 1);
|
||||
assert_ok!(
|
||||
if operational { Democracy::note_preimage_operational(Origin::signed(6), set_balance_proposal(2)) }
|
||||
else { Democracy::note_preimage(Origin::signed(6), set_balance_proposal(2)) }
|
||||
);
|
||||
assert_ok!(if operational {
|
||||
Democracy::note_preimage_operational(Origin::signed(6), set_balance_proposal(2))
|
||||
} else {
|
||||
Democracy::note_preimage(Origin::signed(6), set_balance_proposal(2))
|
||||
});
|
||||
|
||||
assert_eq!(Balances::reserved_balance(6), 12);
|
||||
|
||||
@@ -85,7 +89,11 @@ fn preimage_deposit_should_be_reapable_earlier_by_owner() {
|
||||
Error::<Test>::TooEarly
|
||||
);
|
||||
next_block();
|
||||
assert_ok!(Democracy::reap_preimage(Origin::signed(6), set_balance_proposal_hash(2), u32::MAX));
|
||||
assert_ok!(Democracy::reap_preimage(
|
||||
Origin::signed(6),
|
||||
set_balance_proposal_hash(2),
|
||||
u32::MAX
|
||||
));
|
||||
|
||||
assert_eq!(Balances::free_balance(6), 60);
|
||||
assert_eq!(Balances::reserved_balance(6), 0);
|
||||
@@ -96,27 +104,32 @@ fn preimage_deposit_should_be_reapable_earlier_by_owner() {
|
||||
fn preimage_deposit_should_be_reapable() {
|
||||
new_test_ext_execute_with_cond(|operational| {
|
||||
assert_noop!(
|
||||
Democracy::reap_preimage(Origin::signed(5), set_balance_proposal_hash(2), u32::MAX),
|
||||
Error::<Test>::PreimageMissing
|
||||
);
|
||||
Democracy::reap_preimage(Origin::signed(5), set_balance_proposal_hash(2), u32::MAX),
|
||||
Error::<Test>::PreimageMissing
|
||||
);
|
||||
|
||||
PREIMAGE_BYTE_DEPOSIT.with(|v| *v.borrow_mut() = 1);
|
||||
assert_ok!(
|
||||
if operational { Democracy::note_preimage_operational(Origin::signed(6), set_balance_proposal(2)) }
|
||||
else { Democracy::note_preimage(Origin::signed(6), set_balance_proposal(2)) }
|
||||
);
|
||||
assert_ok!(if operational {
|
||||
Democracy::note_preimage_operational(Origin::signed(6), set_balance_proposal(2))
|
||||
} else {
|
||||
Democracy::note_preimage(Origin::signed(6), set_balance_proposal(2))
|
||||
});
|
||||
assert_eq!(Balances::reserved_balance(6), 12);
|
||||
|
||||
next_block();
|
||||
next_block();
|
||||
next_block();
|
||||
assert_noop!(
|
||||
Democracy::reap_preimage(Origin::signed(5), set_balance_proposal_hash(2), u32::MAX),
|
||||
Error::<Test>::TooEarly
|
||||
);
|
||||
Democracy::reap_preimage(Origin::signed(5), set_balance_proposal_hash(2), u32::MAX),
|
||||
Error::<Test>::TooEarly
|
||||
);
|
||||
|
||||
next_block();
|
||||
assert_ok!(Democracy::reap_preimage(Origin::signed(5), set_balance_proposal_hash(2), u32::MAX));
|
||||
assert_ok!(Democracy::reap_preimage(
|
||||
Origin::signed(5),
|
||||
set_balance_proposal_hash(2),
|
||||
u32::MAX
|
||||
));
|
||||
assert_eq!(Balances::reserved_balance(6), 0);
|
||||
assert_eq!(Balances::free_balance(6), 48);
|
||||
assert_eq!(Balances::free_balance(5), 62);
|
||||
@@ -132,13 +145,19 @@ fn noting_imminent_preimage_for_free_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
1
|
||||
1,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, aye(1)));
|
||||
|
||||
assert_noop!(
|
||||
if operational { Democracy::note_imminent_preimage_operational(Origin::signed(6), set_balance_proposal(2)) }
|
||||
else { Democracy::note_imminent_preimage(Origin::signed(6), set_balance_proposal(2)) },
|
||||
if operational {
|
||||
Democracy::note_imminent_preimage_operational(
|
||||
Origin::signed(6),
|
||||
set_balance_proposal(2),
|
||||
)
|
||||
} else {
|
||||
Democracy::note_imminent_preimage(Origin::signed(6), set_balance_proposal(2))
|
||||
},
|
||||
Error::<Test>::NotImminent
|
||||
);
|
||||
|
||||
@@ -161,7 +180,10 @@ fn reaping_imminent_preimage_should_fail() {
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, aye(1)));
|
||||
next_block();
|
||||
next_block();
|
||||
assert_noop!(Democracy::reap_preimage(Origin::signed(6), h, u32::MAX), Error::<Test>::Imminent);
|
||||
assert_noop!(
|
||||
Democracy::reap_preimage(Origin::signed(6), h, u32::MAX),
|
||||
Error::<Test>::Imminent
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
@@ -174,7 +196,7 @@ fn note_imminent_preimage_can_only_be_successful_once() {
|
||||
2,
|
||||
set_balance_proposal_hash(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
1
|
||||
1,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, aye(1)));
|
||||
next_block();
|
||||
|
||||
@@ -89,10 +89,7 @@ fn poor_seconder_should_not_work() {
|
||||
fn invalid_seconds_upper_bound_should_not_work() {
|
||||
new_test_ext().execute_with(|| {
|
||||
assert_ok!(propose_set_balance_and_note(1, 2, 5));
|
||||
assert_noop!(
|
||||
Democracy::second(Origin::signed(2), 0, 0),
|
||||
Error::<Test>::WrongUpperBound
|
||||
);
|
||||
assert_noop!(Democracy::second(Origin::signed(2), 0, 0), Error::<Test>::WrongUpperBound);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@@ -26,7 +26,7 @@ fn simple_passing_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, aye(1)));
|
||||
assert_eq!(tally(r), Tally { ayes: 1, nays: 0, turnout: 10 });
|
||||
@@ -43,7 +43,7 @@ fn simple_failing_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, nay(1)));
|
||||
assert_eq!(tally(r), Tally { ayes: 0, nays: 1, turnout: 10 });
|
||||
@@ -62,13 +62,13 @@ fn ooo_inject_referendums_should_work() {
|
||||
3,
|
||||
set_balance_proposal_hash_and_note(3),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
let r2 = Democracy::inject_referendum(
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r2, aye(1)));
|
||||
@@ -92,7 +92,7 @@ fn delayed_enactment_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
1
|
||||
1,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, aye(1)));
|
||||
assert_ok!(Democracy::vote(Origin::signed(2), r, aye(2)));
|
||||
|
||||
@@ -23,7 +23,10 @@ use super::*;
|
||||
fn overvoting_should_fail() {
|
||||
new_test_ext().execute_with(|| {
|
||||
let r = begin_referendum();
|
||||
assert_noop!(Democracy::vote(Origin::signed(1), r, aye(2)), Error::<Test>::InsufficientFunds);
|
||||
assert_noop!(
|
||||
Democracy::vote(Origin::signed(1), r, aye(2)),
|
||||
Error::<Test>::InsufficientFunds
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
@@ -102,7 +105,7 @@ fn controversial_voting_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
|
||||
assert_ok!(Democracy::vote(Origin::signed(1), r, big_aye(1)));
|
||||
@@ -128,7 +131,7 @@ fn controversial_low_turnout_voting_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(5), r, big_nay(5)));
|
||||
assert_ok!(Democracy::vote(Origin::signed(6), r, big_aye(6)));
|
||||
@@ -152,7 +155,7 @@ fn passing_low_turnout_voting_should_work() {
|
||||
2,
|
||||
set_balance_proposal_hash_and_note(2),
|
||||
VoteThreshold::SuperMajorityApprove,
|
||||
0
|
||||
0,
|
||||
);
|
||||
assert_ok!(Democracy::vote(Origin::signed(4), r, big_aye(4)));
|
||||
assert_ok!(Democracy::vote(Origin::signed(5), r, big_nay(5)));
|
||||
|
||||
@@ -17,29 +17,31 @@
|
||||
|
||||
//! Miscellaneous additional datatypes.
|
||||
|
||||
use codec::{Encode, Decode};
|
||||
use sp_runtime::RuntimeDebug;
|
||||
use sp_runtime::traits::{Zero, Bounded, CheckedAdd, CheckedSub, CheckedMul, CheckedDiv, Saturating};
|
||||
use crate::{Vote, VoteThreshold, AccountVote, Conviction};
|
||||
use crate::{AccountVote, Conviction, Vote, VoteThreshold};
|
||||
use codec::{Decode, Encode};
|
||||
use sp_runtime::{
|
||||
traits::{Bounded, CheckedAdd, CheckedDiv, CheckedMul, CheckedSub, Saturating, Zero},
|
||||
RuntimeDebug,
|
||||
};
|
||||
|
||||
/// Info regarding an ongoing referendum.
|
||||
#[derive(Encode, Decode, Default, Clone, PartialEq, Eq, RuntimeDebug)]
|
||||
pub struct Tally<Balance> {
|
||||
/// The number of aye votes, expressed in terms of post-conviction lock-vote.
|
||||
pub (crate) ayes: Balance,
|
||||
pub(crate) ayes: Balance,
|
||||
/// The number of nay votes, expressed in terms of post-conviction lock-vote.
|
||||
pub (crate) nays: Balance,
|
||||
pub(crate) nays: Balance,
|
||||
/// The amount of funds currently expressing its opinion. Pre-conviction.
|
||||
pub (crate) turnout: Balance,
|
||||
pub(crate) turnout: Balance,
|
||||
}
|
||||
|
||||
/// Amount of votes and capital placed in delegation for an account.
|
||||
#[derive(Encode, Decode, Default, Copy, Clone, PartialEq, Eq, RuntimeDebug)]
|
||||
pub struct Delegations<Balance> {
|
||||
/// The number of votes (this is post-conviction).
|
||||
pub (crate) votes: Balance,
|
||||
pub(crate) votes: Balance,
|
||||
/// The amount of raw capital, used for the turnout.
|
||||
pub (crate) capital: Balance,
|
||||
pub(crate) capital: Balance,
|
||||
}
|
||||
|
||||
impl<Balance: Saturating> Saturating for Delegations<Balance> {
|
||||
@@ -65,22 +67,24 @@ impl<Balance: Saturating> Saturating for Delegations<Balance> {
|
||||
}
|
||||
|
||||
fn saturating_pow(self, exp: usize) -> Self {
|
||||
Self {
|
||||
votes: self.votes.saturating_pow(exp),
|
||||
capital: self.capital.saturating_pow(exp),
|
||||
}
|
||||
Self { votes: self.votes.saturating_pow(exp), capital: self.capital.saturating_pow(exp) }
|
||||
}
|
||||
}
|
||||
|
||||
impl<
|
||||
Balance: From<u8> + Zero + Copy + CheckedAdd + CheckedSub + CheckedMul + CheckedDiv + Bounded +
|
||||
Saturating
|
||||
> Tally<Balance> {
|
||||
Balance: From<u8>
|
||||
+ Zero
|
||||
+ Copy
|
||||
+ CheckedAdd
|
||||
+ CheckedSub
|
||||
+ CheckedMul
|
||||
+ CheckedDiv
|
||||
+ Bounded
|
||||
+ Saturating,
|
||||
> Tally<Balance>
|
||||
{
|
||||
/// Create a new tally.
|
||||
pub fn new(
|
||||
vote: Vote,
|
||||
balance: Balance,
|
||||
) -> Self {
|
||||
pub fn new(vote: Vote, balance: Balance) -> Self {
|
||||
let Delegations { votes, capital } = vote.conviction.votes(balance);
|
||||
Self {
|
||||
ayes: if vote.aye { votes } else { Zero::zero() },
|
||||
@@ -90,10 +94,7 @@ impl<
|
||||
}
|
||||
|
||||
/// Add an account's vote into the tally.
|
||||
pub fn add(
|
||||
&mut self,
|
||||
vote: AccountVote<Balance>,
|
||||
) -> Option<()> {
|
||||
pub fn add(&mut self, vote: AccountVote<Balance>) -> Option<()> {
|
||||
match vote {
|
||||
AccountVote::Standard { vote, balance } => {
|
||||
let Delegations { votes, capital } = vote.conviction.votes(balance);
|
||||
@@ -102,23 +103,20 @@ impl<
|
||||
true => self.ayes = self.ayes.checked_add(&votes)?,
|
||||
false => self.nays = self.nays.checked_add(&votes)?,
|
||||
}
|
||||
}
|
||||
},
|
||||
AccountVote::Split { aye, nay } => {
|
||||
let aye = Conviction::None.votes(aye);
|
||||
let nay = Conviction::None.votes(nay);
|
||||
self.turnout = self.turnout.checked_add(&aye.capital)?.checked_add(&nay.capital)?;
|
||||
self.ayes = self.ayes.checked_add(&aye.votes)?;
|
||||
self.nays = self.nays.checked_add(&nay.votes)?;
|
||||
}
|
||||
},
|
||||
}
|
||||
Some(())
|
||||
}
|
||||
|
||||
/// Remove an account's vote from the tally.
|
||||
pub fn remove(
|
||||
&mut self,
|
||||
vote: AccountVote<Balance>,
|
||||
) -> Option<()> {
|
||||
pub fn remove(&mut self, vote: AccountVote<Balance>) -> Option<()> {
|
||||
match vote {
|
||||
AccountVote::Standard { vote, balance } => {
|
||||
let Delegations { votes, capital } = vote.conviction.votes(balance);
|
||||
@@ -127,14 +125,14 @@ impl<
|
||||
true => self.ayes = self.ayes.checked_sub(&votes)?,
|
||||
false => self.nays = self.nays.checked_sub(&votes)?,
|
||||
}
|
||||
}
|
||||
},
|
||||
AccountVote::Split { aye, nay } => {
|
||||
let aye = Conviction::None.votes(aye);
|
||||
let nay = Conviction::None.votes(nay);
|
||||
self.turnout = self.turnout.checked_sub(&aye.capital)?.checked_sub(&nay.capital)?;
|
||||
self.ayes = self.ayes.checked_sub(&aye.votes)?;
|
||||
self.nays = self.nays.checked_sub(&nay.votes)?;
|
||||
}
|
||||
},
|
||||
}
|
||||
Some(())
|
||||
}
|
||||
@@ -164,15 +162,15 @@ impl<
|
||||
#[derive(Encode, Decode, Clone, PartialEq, Eq, RuntimeDebug)]
|
||||
pub struct ReferendumStatus<BlockNumber, Hash, Balance> {
|
||||
/// When voting on this referendum will end.
|
||||
pub (crate) end: BlockNumber,
|
||||
pub(crate) end: BlockNumber,
|
||||
/// The hash of the proposal being voted on.
|
||||
pub (crate) proposal_hash: Hash,
|
||||
pub(crate) proposal_hash: Hash,
|
||||
/// The thresholding mechanism to determine whether it passed.
|
||||
pub (crate) threshold: VoteThreshold,
|
||||
pub(crate) threshold: VoteThreshold,
|
||||
/// The delay (in blocks) to wait after a successful referendum before deploying.
|
||||
pub (crate) delay: BlockNumber,
|
||||
pub(crate) delay: BlockNumber,
|
||||
/// The current tally of votes in this referendum.
|
||||
pub (crate) tally: Tally<Balance>,
|
||||
pub(crate) tally: Tally<Balance>,
|
||||
}
|
||||
|
||||
/// Info regarding a referendum, present or past.
|
||||
@@ -181,7 +179,7 @@ pub enum ReferendumInfo<BlockNumber, Hash, Balance> {
|
||||
/// Referendum is happening, the arg is the block number at which it will end.
|
||||
Ongoing(ReferendumStatus<BlockNumber, Hash, Balance>),
|
||||
/// Referendum finished at `end`, and has been `approved` or rejected.
|
||||
Finished{approved: bool, end: BlockNumber},
|
||||
Finished { approved: bool, end: BlockNumber },
|
||||
}
|
||||
|
||||
impl<BlockNumber, Hash, Balance: Default> ReferendumInfo<BlockNumber, Hash, Balance> {
|
||||
@@ -192,7 +190,7 @@ impl<BlockNumber, Hash, Balance: Default> ReferendumInfo<BlockNumber, Hash, Bala
|
||||
threshold: VoteThreshold,
|
||||
delay: BlockNumber,
|
||||
) -> Self {
|
||||
let s = ReferendumStatus{ end, proposal_hash, threshold, delay, tally: Tally::default() };
|
||||
let s = ReferendumStatus { end, proposal_hash, threshold, delay, tally: Tally::default() };
|
||||
ReferendumInfo::Ongoing(s)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,10 +17,13 @@
|
||||
|
||||
//! The vote datatype.
|
||||
|
||||
use sp_std::{prelude::*, result::Result, convert::TryFrom};
|
||||
use codec::{Encode, EncodeLike, Decode, Output, Input};
|
||||
use sp_runtime::{RuntimeDebug, traits::{Saturating, Zero}};
|
||||
use crate::{Conviction, ReferendumIndex, Delegations};
|
||||
use crate::{Conviction, Delegations, ReferendumIndex};
|
||||
use codec::{Decode, Encode, EncodeLike, Input, Output};
|
||||
use sp_runtime::{
|
||||
traits::{Saturating, Zero},
|
||||
RuntimeDebug,
|
||||
};
|
||||
use sp_std::{convert::TryFrom, prelude::*, result::Result};
|
||||
|
||||
/// A number of lock periods, plus a vote, one way or the other.
|
||||
#[derive(Copy, Clone, Eq, PartialEq, Default, RuntimeDebug)]
|
||||
@@ -136,7 +139,9 @@ pub enum Voting<Balance, AccountId, BlockNumber> {
|
||||
},
|
||||
}
|
||||
|
||||
impl<Balance: Default, AccountId, BlockNumber: Zero> Default for Voting<Balance, AccountId, BlockNumber> {
|
||||
impl<Balance: Default, AccountId, BlockNumber: Zero> Default
|
||||
for Voting<Balance, AccountId, BlockNumber>
|
||||
{
|
||||
fn default() -> Self {
|
||||
Voting::Direct {
|
||||
votes: Vec::new(),
|
||||
@@ -146,31 +151,30 @@ impl<Balance: Default, AccountId, BlockNumber: Zero> Default for Voting<Balance,
|
||||
}
|
||||
}
|
||||
|
||||
impl<
|
||||
Balance: Saturating + Ord + Zero + Copy,
|
||||
BlockNumber: Ord + Copy + Zero,
|
||||
AccountId,
|
||||
> Voting<Balance, AccountId, BlockNumber> {
|
||||
impl<Balance: Saturating + Ord + Zero + Copy, BlockNumber: Ord + Copy + Zero, AccountId>
|
||||
Voting<Balance, AccountId, BlockNumber>
|
||||
{
|
||||
pub fn rejig(&mut self, now: BlockNumber) {
|
||||
match self {
|
||||
Voting::Direct { prior, .. } => prior,
|
||||
Voting::Delegating { prior, .. } => prior,
|
||||
}.rejig(now);
|
||||
}
|
||||
.rejig(now);
|
||||
}
|
||||
|
||||
/// The amount of this account's balance that much currently be locked due to voting.
|
||||
pub fn locked_balance(&self) -> Balance {
|
||||
match self {
|
||||
Voting::Direct { votes, prior, .. } => votes.iter()
|
||||
.map(|i| i.1.balance())
|
||||
.fold(prior.locked(), |a, i| a.max(i)),
|
||||
Voting::Direct { votes, prior, .. } =>
|
||||
votes.iter().map(|i| i.1.balance()).fold(prior.locked(), |a, i| a.max(i)),
|
||||
Voting::Delegating { balance, .. } => *balance,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn set_common(&mut self,
|
||||
pub fn set_common(
|
||||
&mut self,
|
||||
delegations: Delegations<Balance>,
|
||||
prior: PriorLock<BlockNumber, Balance>
|
||||
prior: PriorLock<BlockNumber, Balance>,
|
||||
) {
|
||||
let (d, p) = match self {
|
||||
Voting::Direct { ref mut delegations, ref mut prior, .. } => (delegations, prior),
|
||||
|
||||
@@ -17,12 +17,12 @@
|
||||
|
||||
//! Voting thresholds.
|
||||
|
||||
#[cfg(feature = "std")]
|
||||
use serde::{Serialize, Deserialize};
|
||||
use codec::{Encode, Decode};
|
||||
use sp_runtime::traits::{Zero, IntegerSquareRoot};
|
||||
use sp_std::ops::{Add, Mul, Div, Rem};
|
||||
use crate::Tally;
|
||||
use codec::{Decode, Encode};
|
||||
#[cfg(feature = "std")]
|
||||
use serde::{Deserialize, Serialize};
|
||||
use sp_runtime::traits::{IntegerSquareRoot, Zero};
|
||||
use sp_std::ops::{Add, Div, Mul, Rem};
|
||||
|
||||
/// A means of determining if a vote is past pass threshold.
|
||||
#[derive(Clone, Copy, PartialEq, Eq, Encode, Decode, sp_runtime::RuntimeDebug)]
|
||||
@@ -43,25 +43,32 @@ pub trait Approved<Balance> {
|
||||
}
|
||||
|
||||
/// Return `true` iff `n1 / d1 < n2 / d2`. `d1` and `d2` may not be zero.
|
||||
fn compare_rationals<T: Zero + Mul<T, Output = T> + Div<T, Output = T> + Rem<T, Output = T> + Ord + Copy>(mut n1: T, mut d1: T, mut n2: T, mut d2: T) -> bool {
|
||||
fn compare_rationals<
|
||||
T: Zero + Mul<T, Output = T> + Div<T, Output = T> + Rem<T, Output = T> + Ord + Copy,
|
||||
>(
|
||||
mut n1: T,
|
||||
mut d1: T,
|
||||
mut n2: T,
|
||||
mut d2: T,
|
||||
) -> bool {
|
||||
// Uses a continued fractional representation for a non-overflowing compare.
|
||||
// Detailed at https://janmr.com/blog/2014/05/comparing-rational-numbers-without-overflow/.
|
||||
loop {
|
||||
let q1 = n1 / d1;
|
||||
let q2 = n2 / d2;
|
||||
if q1 < q2 {
|
||||
return true;
|
||||
return true
|
||||
}
|
||||
if q2 < q1 {
|
||||
return false;
|
||||
return false
|
||||
}
|
||||
let r1 = n1 % d1;
|
||||
let r2 = n2 % d2;
|
||||
if r2.is_zero() {
|
||||
return false;
|
||||
return false
|
||||
}
|
||||
if r1.is_zero() {
|
||||
return true;
|
||||
return true
|
||||
}
|
||||
n1 = d2;
|
||||
n2 = d1;
|
||||
@@ -71,14 +78,22 @@ fn compare_rationals<T: Zero + Mul<T, Output = T> + Div<T, Output = T> + Rem<T,
|
||||
}
|
||||
|
||||
impl<
|
||||
Balance: IntegerSquareRoot + Zero + Ord + Add<Balance, Output = Balance>
|
||||
+ Mul<Balance, Output = Balance> + Div<Balance, Output = Balance>
|
||||
+ Rem<Balance, Output = Balance> + Copy,
|
||||
> Approved<Balance> for VoteThreshold {
|
||||
Balance: IntegerSquareRoot
|
||||
+ Zero
|
||||
+ Ord
|
||||
+ Add<Balance, Output = Balance>
|
||||
+ Mul<Balance, Output = Balance>
|
||||
+ Div<Balance, Output = Balance>
|
||||
+ Rem<Balance, Output = Balance>
|
||||
+ Copy,
|
||||
> Approved<Balance> for VoteThreshold
|
||||
{
|
||||
fn approved(&self, tally: Tally<Balance>, electorate: Balance) -> bool {
|
||||
let sqrt_voters = tally.turnout.integer_sqrt();
|
||||
let sqrt_electorate = electorate.integer_sqrt();
|
||||
if sqrt_voters.is_zero() { return false; }
|
||||
if sqrt_voters.is_zero() {
|
||||
return false
|
||||
}
|
||||
match *self {
|
||||
VoteThreshold::SuperMajorityApprove =>
|
||||
compare_rationals(tally.nays, sqrt_voters, tally.ayes, sqrt_electorate),
|
||||
@@ -95,7 +110,9 @@ mod tests {
|
||||
|
||||
#[test]
|
||||
fn should_work() {
|
||||
assert!(!VoteThreshold::SuperMajorityApprove.approved(Tally{ayes: 60, nays: 50, turnout: 110}, 210));
|
||||
assert!(VoteThreshold::SuperMajorityApprove.approved(Tally{ayes: 100, nays: 50, turnout: 150}, 210));
|
||||
assert!(!VoteThreshold::SuperMajorityApprove
|
||||
.approved(Tally { ayes: 60, nays: 50, turnout: 110 }, 210));
|
||||
assert!(VoteThreshold::SuperMajorityApprove
|
||||
.approved(Tally { ayes: 100, nays: 50, turnout: 150 }, 210));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -36,6 +36,7 @@
|
||||
// --template=./.maintain/frame-weight-template.hbs
|
||||
|
||||
|
||||
#![cfg_attr(rustfmt, rustfmt_skip)]
|
||||
#![allow(unused_parens)]
|
||||
#![allow(unused_imports)]
|
||||
|
||||
|
||||
Reference in New Issue
Block a user