diff --git a/.github/workflows/check.yml b/.github/workflows/check.yml index 6ad097d..bfbae2a 100644 --- a/.github/workflows/check.yml +++ b/.github/workflows/check.yml @@ -37,3 +37,7 @@ jobs: - name: Check Build run: | SKIP_WASM_BUILD=1 cargo check --release + + - name: Test the pallet + run: | + cargo test -p pallet-slashing-voting diff --git a/Cargo.lock b/Cargo.lock index 857139d..1f3c1f3 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -4110,6 +4110,8 @@ dependencies = [ "frame-benchmarking", "frame-support", "frame-system", + "pallet-balances", + "pallet-identity", "parity-scale-codec", "scale-info", "sp-core", diff --git a/README.md b/README.md index 7ce955c..e8cf76e 100644 --- a/README.md +++ b/README.md @@ -9,7 +9,7 @@ The additional feature is the slashing mechanism which provides an incentive for Navigate to [`pallet/slashing-voting`](pallets/slashing-voting/README.md) -**NOTE**: *This is an experimental pallet, no research has not conducted to actually prove economic costs of this governance system.* +**NOTE**: *This is an experimental pallet, no research has been conducted to actually prove economic costs of this governance system.* ## Idea diff --git a/pallets/slashing-voting/Cargo.toml b/pallets/slashing-voting/Cargo.toml index 17a902f..4c70cac 100644 --- a/pallets/slashing-voting/Cargo.toml +++ b/pallets/slashing-voting/Cargo.toml @@ -27,6 +27,8 @@ branch = 'polkadot-v0.9.26' # Must *match* the rest of your Substrate deps! [dev-dependencies] sp-io = { default-features = false, version = "6.0.0", git = "https://github.com/paritytech/substrate.git", branch = "polkadot-v0.9.26" } sp-core = { default-features = false, version = "6.0.0", git = "https://github.com/paritytech/substrate.git", branch = "polkadot-v0.9.26" } +pallet-identity = { version = "4.0.0-dev", git = "https://github.com/paritytech/substrate.git", branch = "polkadot-v0.9.26" } +pallet-balances = { version = "4.0.0-dev",git = "https://github.com/paritytech/substrate.git", branch = "polkadot-v0.9.26" } [features] default = ["std"] @@ -39,5 +41,4 @@ std = [ "sp-std/std" ] -runtime-benchmarks = ["frame-benchmarking/runtime-benchmarks"] try-runtime = ["frame-support/try-runtime"] diff --git a/pallets/slashing-voting/src/lib.rs b/pallets/slashing-voting/src/lib.rs index f4c4c10..31c13a3 100644 --- a/pallets/slashing-voting/src/lib.rs +++ b/pallets/slashing-voting/src/lib.rs @@ -1,5 +1,11 @@ #![cfg_attr(not(feature = "std"), no_std)] +#[cfg(test)] +mod mock; + +#[cfg(test)] +mod tests; + use frame_support::traits::Get; use frame_support::traits::ReservableCurrency; use frame_support::BoundedVec; diff --git a/pallets/slashing-voting/src/mock.rs b/pallets/slashing-voting/src/mock.rs new file mode 100644 index 0000000..48306eb --- /dev/null +++ b/pallets/slashing-voting/src/mock.rs @@ -0,0 +1,150 @@ +use crate as pallet_voting; +use frame_system::EnsureRoot; +use frame_support::pallet_prelude::ConstU32; +use frame_support::traits::ConstU128; +use frame_support::traits::{ConstU16, ConstU64}; +use frame_system as system; +use frame_support::parameter_types; +use frame_support::PalletId; +use sp_runtime::{ + testing::Header, + traits::{BlakeTwo256, IdentityLookup, IdentifyAccount, Verify}, + MultiSignature, +}; + +pub type UncheckedExtrinsic = frame_system::mocking::MockUncheckedExtrinsic; +pub type Block = frame_system::mocking::MockBlock; + +pub const UNIT: u128 = 1000000000000; +/// An index to a block. +pub type BlockNumber = u64; + +/// Alias to 512-bit hash when used in the context of a transaction signature on the chain. +pub type Signature = MultiSignature; + +/// Some way of identifying an account on the chain. We intentionally make it equivalent +/// to the public key of our transaction signing scheme. +pub type AccountId = <::Signer as IdentifyAccount>::AccountId; + +/// Balance of an account. +pub type Balance = u128; + +/// Index of a transaction in the chain. +pub type Index = u32; + +/// A hash of some data used by the chain. +pub type Hash = sp_core::H256; + +frame_support::construct_runtime!( + pub enum Test where + Block = Block, + NodeBlock = Block, + UncheckedExtrinsic = UncheckedExtrinsic, + { + System: frame_system::{Pallet, Call, Config, Storage, Event}, + QuadraticVoting: pallet_voting::{Pallet, Call, Storage, Event}, + Balances: pallet_balances::{Pallet, Call, Storage, Config, Event}, + Identity: pallet_identity::{Pallet, Call, Storage, Event}, + } +); + +impl system::Config for Test { + type BaseCallFilter = frame_support::traits::Everything; + type BlockWeights = (); + type BlockLength = (); + type DbWeight = (); + type Origin = Origin; + type Call = Call; + type Index = Index; + type BlockNumber = BlockNumber; + type Hash = Hash; + type Hashing = BlakeTwo256; + type AccountId = AccountId; + type Lookup = IdentityLookup; + type Header = Header; + type Event = Event; + type BlockHashCount = ConstU64<250>; + type Version = (); + type PalletInfo = PalletInfo; + type AccountData = pallet_balances::AccountData; + type OnNewAccount = (); + type OnKilledAccount = (); + type SystemWeightInfo = (); + type SS58Prefix = ConstU16<42>; + type OnSetCode = (); + type MaxConsumers = frame_support::traits::ConstU32<16>; +} + +//let's make identity operations free-of-charge for testing purposes +parameter_types! { + pub const BasicDeposit: Balance = 0; + pub const FieldDeposit: Balance = 0; + pub const SubAccountDeposit: Balance = 0; + pub const MaxSubAccounts: u32 = 100; + pub const MaxAdditionalFields: u32 = 100; + pub const MaxRegistrars: u32 = 20; +} + +impl pallet_identity::Config for Test { + type Event = Event; + type Currency = Balances; + type BasicDeposit = BasicDeposit; + type FieldDeposit = FieldDeposit; + type SubAccountDeposit = SubAccountDeposit; + type MaxSubAccounts = MaxSubAccounts; + type MaxAdditionalFields = MaxAdditionalFields; + type MaxRegistrars = MaxRegistrars; + type Slashed = (); + type ForceOrigin = EnsureRoot; + type RegistrarOrigin = EnsureRoot; + type WeightInfo = pallet_identity::weights::SubstrateWeight; +} + +impl pallet_balances::Config for Test { + type MaxLocks = ConstU32<50>; + type MaxReserves = (); + type ReserveIdentifier = [u8; 8]; + /// The type for recording an account's balance. + type Balance = Balance; + /// The ubiquitous event type. + type Event = Event; + type DustRemoval = (); + type ExistentialDeposit = ConstU128<500>; + type AccountStore = System; + type WeightInfo = pallet_balances::weights::SubstrateWeight; +} + +parameter_types! { + pub const EntryFee: Balance = 30_000 * UNIT; + pub const MaxProposals: u32 = 10u32; + pub const RevealLength: BlockNumber = 50u64; + pub const MinLength: BlockNumber = 100u64; + pub const MaxTokens: u8 = 100u8; + pub const VotingPalletId: PalletId = PalletId(*b"p/v8t1ng"); +} + +pub struct VotingIdentityProvider; +impl pallet_voting::IdentityProvider for VotingIdentityProvider { + fn check_existence(account: &AccountId) -> bool { + Identity::identity(account).is_some() + } +} + +impl pallet_voting::Config for Test { + type Event = Event; + type IdentityProvider = VotingIdentityProvider; + type Currency = Balances; + type BasicDeposit = EntryFee; + type MaxProposals = MaxProposals; + type Public = ::Signer; + type Signature = MultiSignature; + type RevealLength = RevealLength; + type MinLength = MinLength; + type MaxVotingTokens = MaxTokens; + type PalletId = VotingPalletId; +} + +// Build genesis storage according to the mock runtime. +pub fn new_test_ext() -> sp_io::TestExternalities { + system::GenesisConfig::default().build_storage::().unwrap().into() +} diff --git a/pallets/slashing-voting/src/tests.rs b/pallets/slashing-voting/src/tests.rs new file mode 100644 index 0000000..0de6ba0 --- /dev/null +++ b/pallets/slashing-voting/src/tests.rs @@ -0,0 +1,11 @@ +use crate::{mock::*, Error}; +use frame_support::{assert_noop, assert_ok}; + + +#[test] +fn it_works_for_default_value() { + new_test_ext().execute_with(|| { + // Dispatch a signed extrinsic. + assert!(true); + }); +} diff --git a/pallets/slashing-voting/src/types.rs b/pallets/slashing-voting/src/types.rs index 2018ad4..5d7711e 100644 --- a/pallets/slashing-voting/src/types.rs +++ b/pallets/slashing-voting/src/types.rs @@ -46,16 +46,6 @@ pub enum Vote { No, } -/// To generate signature -/// ``` -/// fn generate() -> String { -/// let pair: sp_core::sr25519::Pair = Pair::from_string("//Alice", None).unwrap(); -/// let payload = (Vote::No, 10u32).encode(); -/// let payload: [u8; 6] = payload.try_into().unwrap(); -/// let signed = pair.sign(&payload).0; -/// format!("{:02x?}", signed) -/// } -/// ``` #[derive(Clone, Eq, PartialEq, RuntimeDebug, Encode, Decode, TypeInfo)] pub struct Commit { diff --git a/runtime/Cargo.toml b/runtime/Cargo.toml index 96c0e48..974d475 100644 --- a/runtime/Cargo.toml +++ b/runtime/Cargo.toml @@ -107,6 +107,7 @@ try-runtime = [ "pallet-grandpa/try-runtime", "pallet-randomness-collective-flip/try-runtime", "pallet-sudo/try-runtime", + "pallet-slashing-voting/try-runtime", "pallet-timestamp/try-runtime", "pallet-transaction-payment/try-runtime", ] diff --git a/runtime/src/lib.rs b/runtime/src/lib.rs index fe79820..d454cb1 100644 --- a/runtime/src/lib.rs +++ b/runtime/src/lib.rs @@ -410,7 +410,6 @@ mod benches { [frame_system, SystemBench::] [pallet_balances, Balances] [pallet_timestamp, Timestamp] - [pallet_template, TemplateModule] ); }