mirror of
https://github.com/pezkuwichain/pezkuwi-subxt.git
synced 2026-07-04 12:47:22 +00:00
4dbc9265ee
This function executes the given closure in a context where the test externalities are set. This makes the srml tests easier to write, as the test externalities need to be created anyway.
283 lines
8.2 KiB
Rust
283 lines
8.2 KiB
Rust
// Copyright 2019 Parity Technologies (UK) Ltd.
|
|
// This file is part of Substrate.
|
|
|
|
// Substrate is free software: you can redistribute it and/or modify
|
|
// it under the terms of the GNU General Public License as published by
|
|
// the Free Software Foundation, either version 3 of the License, or
|
|
// (at your option) any later version.
|
|
|
|
// Substrate is distributed in the hope that it will be useful,
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
// GNU General Public License for more details.
|
|
|
|
// You should have received a copy of the GNU General Public License
|
|
// along with Substrate. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
//! Tests for the module.
|
|
|
|
use super::*;
|
|
use mock::*;
|
|
|
|
use support::{assert_ok, assert_noop};
|
|
use sr_primitives::traits::OnInitialize;
|
|
|
|
type ScoredPool = Module<Test>;
|
|
type System = system::Module<Test>;
|
|
type Balances = balances::Module<Test>;
|
|
|
|
const OOB_ERR: &str = "index out of bounds";
|
|
const INDEX_ERR: &str = "index does not match requested account";
|
|
|
|
#[test]
|
|
fn query_membership_works() {
|
|
new_test_ext().execute_with(|| {
|
|
assert_eq!(ScoredPool::members(), vec![20, 40]);
|
|
assert_eq!(Balances::reserved_balance(&31), CandidateDeposit::get());
|
|
assert_eq!(Balances::reserved_balance(&40), CandidateDeposit::get());
|
|
assert_eq!(MEMBERS.with(|m| m.borrow().clone()), vec![20, 40]);
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn submit_candidacy_must_not_work() {
|
|
new_test_ext().execute_with(|| {
|
|
assert_noop!(
|
|
ScoredPool::submit_candidacy(Origin::signed(99)),
|
|
"balance too low to submit candidacy"
|
|
);
|
|
assert_noop!(
|
|
ScoredPool::submit_candidacy(Origin::signed(40)),
|
|
"already a member"
|
|
);
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn submit_candidacy_works() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
let who = 15;
|
|
|
|
// when
|
|
assert_ok!(ScoredPool::submit_candidacy(Origin::signed(who)));
|
|
assert_eq!(fetch_from_pool(15), Some((who, None)));
|
|
|
|
// then
|
|
assert_eq!(Balances::reserved_balance(&who), CandidateDeposit::get());
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn scoring_works() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
let who = 15;
|
|
let score = 99;
|
|
assert_ok!(ScoredPool::submit_candidacy(Origin::signed(who)));
|
|
|
|
// when
|
|
let index = find_in_pool(who).expect("entity must be in pool") as u32;
|
|
assert_ok!(ScoredPool::score(Origin::signed(ScoreOrigin::get()), who, index, score));
|
|
|
|
// then
|
|
assert_eq!(fetch_from_pool(who), Some((who, Some(score))));
|
|
assert_eq!(find_in_pool(who), Some(0)); // must be first element, since highest scored
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn scoring_same_element_with_same_score_works() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
let who = 31;
|
|
let index = find_in_pool(who).expect("entity must be in pool") as u32;
|
|
let score = 2;
|
|
|
|
// when
|
|
assert_ok!(ScoredPool::score(Origin::signed(ScoreOrigin::get()), who, index, score));
|
|
|
|
// then
|
|
assert_eq!(fetch_from_pool(who), Some((who, Some(score))));
|
|
|
|
// must have been inserted right before the `20` element which is
|
|
// of the same score as `31`. so sort order is maintained.
|
|
assert_eq!(find_in_pool(who), Some(1));
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn kicking_works_only_for_authorized() {
|
|
new_test_ext().execute_with(|| {
|
|
let who = 40;
|
|
let index = find_in_pool(who).expect("entity must be in pool") as u32;
|
|
assert_noop!(ScoredPool::kick(Origin::signed(99), who, index), "bad origin");
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn kicking_works() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
let who = 40;
|
|
assert_eq!(Balances::reserved_balance(&who), CandidateDeposit::get());
|
|
assert_eq!(find_in_pool(who), Some(0));
|
|
|
|
// when
|
|
let index = find_in_pool(who).expect("entity must be in pool") as u32;
|
|
assert_ok!(ScoredPool::kick(Origin::signed(KickOrigin::get()), who, index));
|
|
|
|
// then
|
|
assert_eq!(find_in_pool(who), None);
|
|
assert_eq!(ScoredPool::members(), vec![20, 31]);
|
|
assert_eq!(MEMBERS.with(|m| m.borrow().clone()), ScoredPool::members());
|
|
assert_eq!(Balances::reserved_balance(&who), 0); // deposit must have been returned
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn unscored_entities_must_not_be_used_for_filling_members() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
// we submit a candidacy, score will be `None`
|
|
assert_ok!(ScoredPool::submit_candidacy(Origin::signed(15)));
|
|
|
|
// when
|
|
// we remove every scored member
|
|
ScoredPool::pool()
|
|
.into_iter()
|
|
.for_each(|(who, score)| {
|
|
if let Some(_) = score {
|
|
let index = find_in_pool(who).expect("entity must be in pool") as u32;
|
|
assert_ok!(ScoredPool::kick(Origin::signed(KickOrigin::get()), who, index));
|
|
}
|
|
});
|
|
|
|
// then
|
|
// the `None` candidates should not have been filled in
|
|
assert_eq!(ScoredPool::members(), vec![]);
|
|
assert_eq!(MEMBERS.with(|m| m.borrow().clone()), ScoredPool::members());
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn refreshing_works() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
let who = 15;
|
|
assert_ok!(ScoredPool::submit_candidacy(Origin::signed(who)));
|
|
let index = find_in_pool(who).expect("entity must be in pool") as u32;
|
|
assert_ok!(ScoredPool::score(Origin::signed(ScoreOrigin::get()), who, index, 99));
|
|
|
|
// when
|
|
ScoredPool::refresh_members(ScoredPool::pool(), ChangeReceiver::MembershipChanged);
|
|
|
|
// then
|
|
assert_eq!(ScoredPool::members(), vec![15, 40]);
|
|
assert_eq!(MEMBERS.with(|m| m.borrow().clone()), ScoredPool::members());
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn refreshing_happens_every_period() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
System::set_block_number(1);
|
|
assert_ok!(ScoredPool::submit_candidacy(Origin::signed(15)));
|
|
let index = find_in_pool(15).expect("entity must be in pool") as u32;
|
|
assert_ok!(ScoredPool::score(Origin::signed(ScoreOrigin::get()), 15, index, 99));
|
|
assert_eq!(ScoredPool::members(), vec![20, 40]);
|
|
|
|
// when
|
|
System::set_block_number(4);
|
|
ScoredPool::on_initialize(4);
|
|
|
|
// then
|
|
assert_eq!(ScoredPool::members(), vec![15, 40]);
|
|
assert_eq!(MEMBERS.with(|m| m.borrow().clone()), ScoredPool::members());
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn withdraw_candidacy_must_only_work_for_members() {
|
|
new_test_ext().execute_with(|| {
|
|
let who = 77;
|
|
let index = 0;
|
|
assert_noop!( ScoredPool::withdraw_candidacy(Origin::signed(who), index), INDEX_ERR);
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn oob_index_should_abort() {
|
|
new_test_ext().execute_with(|| {
|
|
let who = 40;
|
|
let oob_index = ScoredPool::pool().len() as u32;
|
|
assert_noop!(ScoredPool::withdraw_candidacy(Origin::signed(who), oob_index), OOB_ERR);
|
|
assert_noop!(ScoredPool::score(Origin::signed(ScoreOrigin::get()), who, oob_index, 99), OOB_ERR);
|
|
assert_noop!(ScoredPool::kick(Origin::signed(KickOrigin::get()), who, oob_index), OOB_ERR);
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn index_mismatches_should_abort() {
|
|
new_test_ext().execute_with(|| {
|
|
let who = 40;
|
|
let index = 3;
|
|
assert_noop!(ScoredPool::withdraw_candidacy(Origin::signed(who), index), INDEX_ERR);
|
|
assert_noop!(ScoredPool::score(Origin::signed(ScoreOrigin::get()), who, index, 99), INDEX_ERR);
|
|
assert_noop!(ScoredPool::kick(Origin::signed(KickOrigin::get()), who, index), INDEX_ERR);
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn withdraw_unscored_candidacy_must_work() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
let who = 5;
|
|
|
|
// when
|
|
let index = find_in_pool(who).expect("entity must be in pool") as u32;
|
|
assert_ok!(ScoredPool::withdraw_candidacy(Origin::signed(who), index));
|
|
|
|
// then
|
|
assert_eq!(fetch_from_pool(5), None);
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn withdraw_scored_candidacy_must_work() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
let who = 40;
|
|
assert_eq!(Balances::reserved_balance(&who), CandidateDeposit::get());
|
|
|
|
// when
|
|
let index = find_in_pool(who).expect("entity must be in pool") as u32;
|
|
assert_ok!(ScoredPool::withdraw_candidacy(Origin::signed(who), index));
|
|
|
|
// then
|
|
assert_eq!(fetch_from_pool(who), None);
|
|
assert_eq!(ScoredPool::members(), vec![20, 31]);
|
|
assert_eq!(Balances::reserved_balance(&who), 0);
|
|
});
|
|
}
|
|
|
|
#[test]
|
|
fn candidacy_resubmitting_works() {
|
|
new_test_ext().execute_with(|| {
|
|
// given
|
|
let who = 15;
|
|
|
|
// when
|
|
assert_ok!(ScoredPool::submit_candidacy(Origin::signed(who)));
|
|
assert_eq!(ScoredPool::candidate_exists(who), true);
|
|
let index = find_in_pool(who).expect("entity must be in pool") as u32;
|
|
assert_ok!(ScoredPool::withdraw_candidacy(Origin::signed(who), index));
|
|
assert_eq!(ScoredPool::candidate_exists(who), false);
|
|
assert_ok!(ScoredPool::submit_candidacy(Origin::signed(who)));
|
|
|
|
// then
|
|
assert_eq!(ScoredPool::candidate_exists(who), true);
|
|
});
|
|
}
|