From ff0b50dd28c744aaafc3850cf91598262e1acbee Mon Sep 17 00:00:00 2001 From: zjb0807 <zjb0807@qq.com> Date: Wed, 19 Aug 2020 07:11:20 +0800 Subject: [PATCH] add authority tests (#250) --- authority/src/mock.rs | 31 ++++-- authority/src/tests.rs | 222 ++++++++++++++++++++++++++++++++++++++++- 2 files changed, 246 insertions(+), 7 deletions(-) diff --git a/authority/src/mock.rs b/authority/src/mock.rs index 241e88b..1c699f3 100644 --- a/authority/src/mock.rs +++ b/authority/src/mock.rs @@ -2,7 +2,10 @@ #![cfg(test)] -use frame_support::parameter_types; +use frame_support::{ + parameter_types, + traits::{OnFinalize, OnInitialize}, +}; use frame_system::{ensure_root, ensure_signed, EnsureRoot}; use sp_core::H256; use sp_runtime::{ @@ -12,7 +15,7 @@ use sp_runtime::{ }; use super::*; -use crate as authority; +pub use crate as authority; pub type AccountId = u128; pub type BlockNumber = u64; @@ -34,7 +37,7 @@ impl frame_system::Trait for Runtime { type AccountId = AccountId; type Lookup = IdentityLookup<Self::AccountId>; type Header = Header; - type Event = (); + type Event = Event; type BlockHashCount = BlockHashCount; type MaximumBlockWeight = MaximumBlockWeight; type MaximumBlockLength = MaximumBlockLength; @@ -56,7 +59,7 @@ parameter_types! { pub MaximumSchedulerWeight: u32 = Perbill::from_percent(80) * MaximumBlockWeight::get(); } impl pallet_scheduler::Trait for Runtime { - type Event = (); + type Event = Event; type Origin = Origin; type PalletsOrigin = OriginCaller; type Call = Call; @@ -122,6 +125,14 @@ impl AsOriginId<Origin, OriginCaller> for MockAsOriginId { } fn check_dispatch_from(&self, origin: Origin) -> DispatchResult { ensure_root(origin.clone()).or_else(|_| { + if let OriginCaller::authority(ref sign) = origin.caller() { + if sign.origin == Box::new(Origin::root().caller().clone()) { + return Ok(()); + } else { + return Err(BadOrigin.into()); + } + } + let ok = match self { MockAsOriginId::Root => false, MockAsOriginId::Account1 => ensure_signed(origin)? == 1, @@ -133,7 +144,7 @@ impl AsOriginId<Origin, OriginCaller> for MockAsOriginId { } impl Trait for Runtime { - type Event = (); + type Event = Event; type Origin = Origin; type PalletsOrigin = OriginCaller; type Scheduler = Scheduler; @@ -152,7 +163,7 @@ frame_support::construct_runtime!( UncheckedExtrinsic = UncheckedExtrinsic { System: frame_system::{Module, Call, Event<T>}, - Authority: authority::{Module, Call, Origin<T>}, + Authority: authority::{Module, Call, Origin<T>, Event<T>}, Scheduler: pallet_scheduler::{Module, Call, Storage, Event<T>}, } ); @@ -174,3 +185,11 @@ impl ExtBuilder { t.into() } } + +pub fn run_to_block(n: u64) { + while System::block_number() < n { + Scheduler::on_finalize(System::block_number()); + System::set_block_number(System::block_number() + 1); + Scheduler::on_initialize(System::block_number()); + } +} diff --git a/authority/src/tests.rs b/authority/src/tests.rs index f39e51f..fcaad9f 100644 --- a/authority/src/tests.rs +++ b/authority/src/tests.rs @@ -4,7 +4,11 @@ use super::*; use frame_support::{assert_noop, assert_ok}; -use mock::{Authority, Call, ExtBuilder, MockAsOriginId, Origin}; +use frame_system::RawOrigin; +use mock::{ + authority, run_to_block, Authority, BlockNumber, Call, ExtBuilder, MockAsOriginId, Origin, OriginCaller, Runtime, + System, +}; use sp_runtime::{traits::BadOrigin, Perbill}; #[test] @@ -45,3 +49,219 @@ fn dispatch_as_work() { ); }); } + +#[test] +fn schedule_dispatch_at_work() { + ExtBuilder::default().build().execute_with(|| { + let ensure_root_call = Call::System(frame_system::Call::fill_block(Perbill::one())); + let call = Call::Authority(authority::Call::dispatch_as( + MockAsOriginId::Root, + Box::new(ensure_root_call.clone()), + )); + run_to_block(1); + assert_eq!( + Authority::schedule_dispatch(Origin::root(), DispatchTime::At(1), 0, true, Box::new(call.clone())), + Err(Error::<Runtime>::FailedToSchedule.into()) + ); + + assert_ok!(Authority::schedule_dispatch( + Origin::root(), + DispatchTime::At(2), + 0, + true, + Box::new(call.clone()) + )); + let event = mock::Event::authority(RawEvent::Scheduled( + OriginCaller::authority(DelayedOrigin { + delay: 1, + origin: Box::new(OriginCaller::system(RawOrigin::Root)), + }), + 1, + )); + assert!(System::events().iter().any(|record| record.event == event)); + + run_to_block(2); + let event = mock::Event::pallet_scheduler(pallet_scheduler::RawEvent::Dispatched( + (2, 0), + Some([1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0].to_vec()), + Ok(()), + )); + assert!(System::events().iter().any(|record| record.event == event)); + + // with_delayed_origin = false + assert_ok!(Authority::schedule_dispatch( + Origin::root(), + DispatchTime::At(3), + 0, + false, + Box::new(call.clone()) + )); + let event = mock::Event::authority(RawEvent::Scheduled(OriginCaller::system(RawOrigin::Root), 2)); + assert!(System::events().iter().any(|record| record.event == event)); + + run_to_block(3); + let event = mock::Event::pallet_scheduler(pallet_scheduler::RawEvent::Dispatched( + (3, 0), + Some([0, 0, 2, 0, 0, 0].to_vec()), + Ok(()), + )); + assert!(System::events().iter().any(|record| record.event == event)); + }); +} + +#[test] +fn schedule_dispatch_after_work() { + ExtBuilder::default().build().execute_with(|| { + let ensure_root_call = Call::System(frame_system::Call::fill_block(Perbill::one())); + let call = Call::Authority(authority::Call::dispatch_as( + MockAsOriginId::Root, + Box::new(ensure_root_call.clone()), + )); + run_to_block(1); + assert_eq!( + Authority::schedule_dispatch(Origin::root(), DispatchTime::After(0), 0, true, Box::new(call.clone())), + Err(Error::<Runtime>::FailedToSchedule.into()) + ); + + assert_ok!(Authority::schedule_dispatch( + Origin::root(), + DispatchTime::After(1), + 0, + true, + Box::new(call.clone()) + )); + let event = mock::Event::authority(RawEvent::Scheduled( + OriginCaller::authority(DelayedOrigin { + delay: 1, + origin: Box::new(OriginCaller::system(RawOrigin::Root)), + }), + 1, + )); + assert!(System::events().iter().any(|record| record.event == event)); + + run_to_block(2); + let event = mock::Event::pallet_scheduler(pallet_scheduler::RawEvent::Dispatched( + (2, 0), + Some([1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0].to_vec()), + Ok(()), + )); + assert!(System::events().iter().any(|record| record.event == event)); + + // with_delayed_origin = false + assert_ok!(Authority::schedule_dispatch( + Origin::root(), + DispatchTime::After(1), + 0, + false, + Box::new(call.clone()) + )); + let event = mock::Event::authority(RawEvent::Scheduled(OriginCaller::system(RawOrigin::Root), 2)); + assert!(System::events().iter().any(|record| record.event == event)); + + run_to_block(3); + let event = mock::Event::pallet_scheduler(pallet_scheduler::RawEvent::Dispatched( + (3, 0), + Some([0, 0, 2, 0, 0, 0].to_vec()), + Ok(()), + )); + assert!(System::events().iter().any(|record| record.event == event)); + }); +} + +#[test] +fn fast_track_scheduled_dispatch_work() { + ExtBuilder::default().build().execute_with(|| { + System::set_block_number(1); + //let ensure_root_call = + // Call::System(frame_system::Call::fill_block(Perbill::one())); + // let ensure_signed_call = Call::System(frame_system::Call::remark(vec![])); + assert_ok!(Authority::fast_track_scheduled_dispatch( + Origin::root(), + frame_system::RawOrigin::Root.into(), + 0, + DispatchTime::At(4), + )); + }); +} + +#[test] +fn delay_scheduled_dispatch_work() { + ExtBuilder::default().build().execute_with(|| { + //let ensure_root_call = + // Call::System(frame_system::Call::fill_block(Perbill::one())); + // let ensure_signed_call = Call::System(frame_system::Call::remark(vec![])); + assert_ok!(Authority::delay_scheduled_dispatch( + Origin::root(), + frame_system::RawOrigin::Root.into(), + 0, + 5, + )); + }); +} + +#[test] +fn cancel_scheduled_dispatch_work() { + ExtBuilder::default().build().execute_with(|| { + let ensure_root_call = Call::System(frame_system::Call::fill_block(Perbill::one())); + let call = Call::Authority(authority::Call::dispatch_as( + MockAsOriginId::Root, + Box::new(ensure_root_call.clone()), + )); + run_to_block(1); + assert_ok!(Authority::schedule_dispatch( + Origin::root(), + DispatchTime::At(2), + 0, + true, + Box::new(call.clone()) + )); + let event = mock::Event::authority(RawEvent::Scheduled( + OriginCaller::authority(DelayedOrigin { + delay: 1, + origin: Box::new(OriginCaller::system(RawOrigin::Root)), + }), + 0, + )); + assert!(System::events().iter().any(|record| record.event == event)); + + let schedule_origin = { + let origin: <Runtime as Trait>::Origin = From::from(Origin::root()); + let origin: <Runtime as Trait>::Origin = + From::from(DelayedOrigin::<BlockNumber, <Runtime as Trait>::PalletsOrigin> { + delay: 1, + origin: Box::new(origin.caller().clone()), + }); + origin + }; + + let pallets_origin = schedule_origin.caller().clone(); + assert_ok!(Authority::cancel_scheduled_dispatch(Origin::root(), pallets_origin, 0)); + let event = mock::Event::authority(RawEvent::Cancelled( + OriginCaller::authority(DelayedOrigin { + delay: 1, + origin: Box::new(OriginCaller::system(RawOrigin::Root)), + }), + 0, + )); + println!("{:?}", System::events()); + assert!(System::events().iter().any(|record| record.event == event)); + + assert_ok!(Authority::schedule_dispatch( + Origin::root(), + DispatchTime::At(2), + 0, + false, + Box::new(call.clone()) + )); + let event = mock::Event::authority(RawEvent::Scheduled(OriginCaller::system(RawOrigin::Root), 1)); + assert!(System::events().iter().any(|record| record.event == event)); + + assert_ok!(Authority::cancel_scheduled_dispatch( + Origin::root(), + frame_system::RawOrigin::Root.into(), + 1 + )); + let event = mock::Event::authority(RawEvent::Cancelled(OriginCaller::system(RawOrigin::Root), 1)); + assert!(System::events().iter().any(|record| record.event == event)); + }); +} -- GitLab