Session Delayed Para Changes / Actions Queue (#2406)

* initial implementation of lifecycles and upgrades

* clean up a bit

* fix doc comment

* more rigid lifecycle checks

* include paras which are transitioning, and lifecycle query

* format guide

* update api

* update guide

* explicit outgoing state, fix genesis

* handle outgoing with transitioning paras

* do not include transitioning paras in identifier

* Update roadmap/implementers-guide/src/runtime/paras.md

* Update roadmap/implementers-guide/src/runtime/paras.md

* Update roadmap/implementers-guide/src/runtime/paras.md

* Apply suggestions from code review

* Use matches macro

* Correct terms

* Apply suggestions from code review

* actions queue

* Revert "actions queue"

This reverts commit b2e9011ec8937d6c73e99292416c9692aeb30f73.

* collapse onboarding state

* starting actions queue

* consolidate actions queue

* schedule para initialize result

* more actions queue for upgrade/downgrade

* clean up with fully implemented actions queue

* fix tests

* fix scheduler tests

* fix hrmp tests

* fix test

* doc fixes

* fix hrmp test w/ valid para

* Update paras.md

* fix paras registrar

* Update propose_parachain.rs

* fix merge

* Introduce "shared" module

* fix rococo build

* fix up and use shared

* guide updates

* add shared config to common tests

* add shared to test-runtime

* remove println

* fix note

Co-authored-by: Gavin Wood <gavin@parity.io>
This commit is contained in:
Shawn Tabrizi
2021-02-18 23:20:18 -04:00
committed by GitHub
parent 006602eff2
commit a5defa7c7f
20 changed files with 654 additions and 698 deletions
+39 -135
View File
@@ -731,19 +731,31 @@ impl<T: Config> Module<T> {
}
}
#[cfg(test)]
mod tests {
use super::*;
use primitives::v1::{BlockNumber, ValidatorId, CollatorId};
use frame_support::traits::{OnFinalize, OnInitialize};
use primitives::v1::{BlockNumber, ValidatorId, CollatorId, SessionIndex};
use frame_support::{
assert_ok,
traits::{OnFinalize, OnInitialize},
};
use keyring::Sr25519Keyring;
use crate::mock::{new_test_ext, Configuration, Paras, System, Scheduler, MockGenesisConfig};
use crate::mock::{new_test_ext, Configuration, Paras, Shared, System, Scheduler, MockGenesisConfig};
use crate::initializer::SessionChangeNotification;
use crate::configuration::HostConfiguration;
use crate::paras::ParaGenesisArgs;
fn schedule_blank_para(id: ParaId, is_chain: bool) {
assert_ok!(Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
}));
}
fn run_to_block(
to: BlockNumber,
new_session: impl Fn(BlockNumber) -> Option<SessionChangeNotification<BlockNumber>>,
@@ -755,8 +767,13 @@ mod tests {
Paras::initializer_finalize();
if let Some(notification) = new_session(b + 1) {
Paras::initializer_on_new_session(&notification);
Scheduler::initializer_on_new_session(&notification);
let mut notification_with_session_index = notification;
// We will make every session change trigger an action queue. Normally this may require 2 or more session changes.
if notification_with_session_index.session_index == SessionIndex::default() {
notification_with_session_index.session_index = Shared::scheduled_session();
}
Paras::initializer_on_new_session(&notification_with_session_index);
Scheduler::initializer_on_new_session(&notification_with_session_index);
}
System::on_finalize(b);
@@ -816,11 +833,7 @@ mod tests {
let collator = CollatorId::from(Sr25519Keyring::Alice.public());
new_test_ext(genesis_config).execute_with(|| {
Paras::schedule_para_initialize(thread_id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: false,
});
schedule_blank_para(thread_id, false);
assert!(!Paras::is_parathread(thread_id));
@@ -895,11 +908,7 @@ mod tests {
let collator = CollatorId::from(Sr25519Keyring::Alice.public());
new_test_ext(genesis_config).execute_with(|| {
Paras::schedule_para_initialize(thread_id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: false,
});
schedule_blank_para(thread_id, false);
assert!(!Paras::is_parathread(thread_id));
@@ -935,23 +944,9 @@ mod tests {
// threads a, b, and c will be live in next session, but not d.
{
Paras::schedule_para_initialize(thread_a, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: false,
});
Paras::schedule_para_initialize(thread_b, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: false,
});
Paras::schedule_para_initialize(thread_c, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: false,
});
schedule_blank_para(thread_a, false);
schedule_blank_para(thread_b, false);
schedule_blank_para(thread_c, false);
}
// set up a queue as if n_cores was 4 and with some with many retries.
@@ -1041,16 +1036,9 @@ mod tests {
let chain_b = ParaId::from(2);
// ensure that we have 5 groups by registering 2 parachains.
Paras::schedule_para_initialize(chain_a, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: true,
});
Paras::schedule_para_initialize(chain_b, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: true,
});
schedule_blank_para(chain_a, true);
schedule_blank_para(chain_b, true);
run_to_block(1, |number| match number {
1 => Some(SessionChangeNotification {
@@ -1107,21 +1095,10 @@ mod tests {
let chain_c = ParaId::from(3);
// ensure that we have 5 groups by registering 2 parachains.
Paras::schedule_para_initialize(chain_a, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: true,
});
Paras::schedule_para_initialize(chain_b, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: true,
});
Paras::schedule_para_initialize(chain_c, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: false,
});
schedule_blank_para(chain_a, true);
schedule_blank_para(chain_b, true);
schedule_blank_para(chain_c, false);
run_to_block(1, |number| match number {
1 => Some(SessionChangeNotification {
@@ -1170,12 +1147,6 @@ mod tests {
let collator = CollatorId::from(Sr25519Keyring::Alice.public());
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
assert_eq!(default_config().parathread_cores, 3);
@@ -1285,12 +1256,6 @@ mod tests {
let collator = CollatorId::from(Sr25519Keyring::Alice.public());
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
assert_eq!(default_config().parathread_cores, 3);
@@ -1442,12 +1407,6 @@ mod tests {
let chain_b = ParaId::from(2);
let chain_c = ParaId::from(3);
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
assert_eq!(default_config().parathread_cores, 3);
@@ -1552,12 +1511,6 @@ mod tests {
let collator = CollatorId::from(Sr25519Keyring::Alice.public());
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
assert_eq!(default_config().parathread_cores, 3);
@@ -1630,12 +1583,6 @@ mod tests {
let collator = CollatorId::from(Sr25519Keyring::Alice.public());
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
assert_eq!(default_config().parathread_cores, 3);
@@ -1695,12 +1642,6 @@ mod tests {
let chain_a = ParaId::from(1);
let thread_a = ParaId::from(2);
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
schedule_blank_para(chain_a, true);
schedule_blank_para(thread_a, false);
@@ -1798,12 +1739,6 @@ mod tests {
let collator = CollatorId::from(Sr25519Keyring::Alice.public());
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
schedule_blank_para(thread_a, false);
schedule_blank_para(thread_b, false);
@@ -1879,12 +1814,6 @@ mod tests {
let collator = CollatorId::from(Sr25519Keyring::Alice.public());
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
schedule_blank_para(thread_a, false);
schedule_blank_para(thread_b, false);
@@ -1966,12 +1895,6 @@ mod tests {
let chain_a = ParaId::from(1);
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
schedule_blank_para(chain_a, true);
@@ -2029,12 +1952,6 @@ mod tests {
let chain_a = ParaId::from(1);
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
schedule_blank_para(chain_a, true);
@@ -2093,16 +2010,9 @@ mod tests {
let chain_b = ParaId::from(2);
// ensure that we have 5 groups by registering 2 parachains.
Paras::schedule_para_initialize(chain_a, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: true,
});
Paras::schedule_para_initialize(chain_b, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: true,
});
schedule_blank_para(chain_a, true);
schedule_blank_para(chain_b, true);
run_to_block(1, |number| match number {
1 => Some(SessionChangeNotification {
@@ -2127,7 +2037,7 @@ mod tests {
let groups = ValidatorGroups::get();
assert_eq!(groups.len(), 5);
Paras::schedule_para_cleanup(chain_b);
assert_ok!(Paras::schedule_para_cleanup(chain_b));
run_to_end_of_block(2, |number| match number {
2 => Some(SessionChangeNotification {
@@ -2179,12 +2089,6 @@ mod tests {
let collator = CollatorId::from(Sr25519Keyring::Alice.public());
let schedule_blank_para = |id, is_chain| Paras::schedule_para_initialize(id, ParaGenesisArgs {
genesis_head: Vec::new().into(),
validation_code: Vec::new().into(),
parachain: is_chain,
});
new_test_ext(genesis_config).execute_with(|| {
assert_eq!(default_config().parathread_cores, 3);
@@ -2210,7 +2114,7 @@ mod tests {
run_to_block(2, |_| None);
assert_eq!(Scheduler::scheduled().len(), 2);
Paras::schedule_para_cleanup(thread_a);
assert_ok!(Paras::schedule_para_cleanup(thread_a));
// start a new session to activate, 5 validators for 5 cores.
run_to_block(3, |number| match number {