From 7a1280918e13bab5973b69a3f851ecfe57bd6f4a Mon Sep 17 00:00:00 2001 From: Hugo Trentesaux <hugo.trentesaux@lilo.org> Date: Wed, 3 May 2023 12:45:35 +0200 Subject: [PATCH] add tests (nodes/rust/duniter-v2s!151) * fix not enough for transfer * cucumber: add identity validation * wip add revocation test --- .../identity_creation.feature | 22 +++++--- end2end-tests/tests/common/identity.rs | 29 ++++++++++- end2end-tests/tests/common/mod.rs | 5 +- end2end-tests/tests/cucumber_tests.rs | 43 ++++++++++------ pallets/duniter-wot/src/tests.rs | 50 +++++++++++++++++++ 5 files changed, 124 insertions(+), 25 deletions(-) diff --git a/end2end-tests/cucumber-features/identity_creation.feature b/end2end-tests/cucumber-features/identity_creation.feature index 2cc5bcc99..81113d8b1 100644 --- a/end2end-tests/cucumber-features/identity_creation.feature +++ b/end2end-tests/cucumber-features/identity_creation.feature @@ -5,11 +5,21 @@ Feature: Identity creation # - account creation fees (3 ÄžD) # - existential deposit (2 ÄžD) # - transaction fees (below 1 ÄžD) - When alice sends 6 ÄžD to ferdie + When alice sends 6 ÄžD to dave + When bob sends 6 ÄžD to eve # alice last certification is counted from block zero - # then next cert can be done after cert_period + # then next cert can be done after cert_period, which is 15 When 15 block later - When alice creates identity for ferdie - Then ferdie identity should be created - When ferdie confirms his identity with pseudo "Ferdie" - Then ferdie identity should be confirmed + When alice creates identity for dave + Then dave identity should be created + Then dave should be certified by alice + When dave confirms his identity with pseudo "dave" + Then dave identity should be confirmed + When 3 block later + When bob certifies dave + When charlie certifies dave + Then dave should be certified by bob + Then dave should be certified by charlie + When 3 block later + When eve validates dave identity + Then dave identity should be validated diff --git a/end2end-tests/tests/common/identity.rs b/end2end-tests/tests/common/identity.rs index 0f21cb5aa..58e881264 100644 --- a/end2end-tests/tests/common/identity.rs +++ b/end2end-tests/tests/common/identity.rs @@ -72,8 +72,27 @@ pub async fn confirm_identity(client: &Client, from: AccountKeyring, pseudo: Str Ok(()) } -// get identity value from account keyring name -pub async fn get_identity_value(world: &mut DuniterWorld, account: String) -> Result<IdtyValue> { +pub async fn validate_identity(client: &Client, from: AccountKeyring, to: u32) -> Result<()> { + let from = PairSigner::new(from.pair()); + + let _events = create_block_with_extrinsic( + client, + client + .tx() + .create_signed( + &gdev::tx().identity().validate_identity(to), + &from, + BaseExtrinsicParamsBuilder::new(), + ) + .await?, + ) + .await?; + + Ok(()) +} + +// get identity index from account keyring name +pub async fn get_identity_index(world: &mut DuniterWorld, account: String) -> Result<u32> { let account = AccountKeyring::from_str(&account) .expect("unknown account") .to_account_id(); @@ -84,6 +103,12 @@ pub async fn get_identity_value(world: &mut DuniterWorld, account: String) -> Re .ok_or_else(|| anyhow::anyhow!("identity {} has no associated index", account)) .unwrap(); + Ok(identity_index) +} +// get identity value from account keyring name +pub async fn get_identity_value(world: &mut DuniterWorld, account: String) -> Result<IdtyValue> { + let identity_index = get_identity_index(world, account).await.unwrap(); + let identity_value = world .read(&gdev::storage().identity().identities(identity_index)) .await? diff --git a/end2end-tests/tests/common/mod.rs b/end2end-tests/tests/common/mod.rs index c1fd35076..56ccdea5d 100644 --- a/end2end-tests/tests/common/mod.rs +++ b/end2end-tests/tests/common/mod.rs @@ -21,7 +21,10 @@ pub mod cert; pub mod identity; pub mod oneshot; -#[subxt::subxt(runtime_metadata_path = "../resources/metadata.scale")] +#[subxt::subxt( + runtime_metadata_path = "../resources/metadata.scale", + derive_for_all_types = "Eq, PartialEq" +)] pub mod gdev {} use anyhow::anyhow; diff --git a/end2end-tests/tests/cucumber_tests.rs b/end2end-tests/tests/cucumber_tests.rs index cd7876032..094932d4b 100644 --- a/end2end-tests/tests/cucumber_tests.rs +++ b/end2end-tests/tests/cucumber_tests.rs @@ -313,6 +313,15 @@ async fn confirm_identity(world: &mut DuniterWorld, from: String, pseudo: String common::identity::confirm_identity(world.client(), from, pseudo).await } +#[when(regex = r#"([a-zA-Z]+) validates ([a-zA-Z]+) identity"#)] +async fn validate_identity(world: &mut DuniterWorld, from: String, to: String) -> Result<()> { + // input names to keyrings + let from = AccountKeyring::from_str(&from).expect("unknown from"); + let to: u32 = common::identity::get_identity_index(world, to).await?; + + common::identity::validate_identity(world.client(), from, to).await +} + // ===== then ==== #[then(regex = r"([a-zA-Z]+) should have (\d+) (ÄžD|cÄžD)")] @@ -430,28 +439,30 @@ async fn should_be_certified_by( use gdev::runtime_types::pallet_identity::types::IdtyStatus; -#[then(regex = r"([a-zA-Z]+) identity should be created")] -async fn identity_should_be_created(world: &mut DuniterWorld, receiver: String) -> Result<()> { - let identity_value = common::identity::get_identity_value(world, receiver).await?; +// status from string +impl FromStr for IdtyStatus { + type Err = String; - match identity_value.status { - IdtyStatus::Created => Ok(()), - IdtyStatus::ConfirmedByOwner | IdtyStatus::Validated => { - Err(anyhow::anyhow!("status not created").into()) + fn from_str(input: &str) -> std::result::Result<IdtyStatus, String> { + match input { + "created" => Ok(IdtyStatus::Created), + "confirmed" => Ok(IdtyStatus::ConfirmedByOwner), + "validated" => Ok(IdtyStatus::Validated), + _ => Err(format!("'{input}' does not match a status")), } } } -#[then(regex = r"([a-zA-Z]+) identity should be confirmed")] -async fn identity_should_be_confirmed(world: &mut DuniterWorld, name: String) -> Result<()> { +#[then(regex = r"([a-zA-Z]+) identity should be ([a-zA-Z ]+)")] +async fn identity_status_should_be( + world: &mut DuniterWorld, + name: String, + status: String, +) -> Result<()> { let identity_value = common::identity::get_identity_value(world, name).await?; - - match identity_value.status { - IdtyStatus::ConfirmedByOwner => Ok(()), - IdtyStatus::Created | IdtyStatus::Validated => { - Err(anyhow::anyhow!("status not confirmed by owner").into()) - } - } + let expected_status = IdtyStatus::from_str(&status)?; + assert_eq!(identity_value.status, expected_status); + Ok(()) } // ============================================================ diff --git a/pallets/duniter-wot/src/tests.rs b/pallets/duniter-wot/src/tests.rs index 1f40cab21..3c51f2f6b 100644 --- a/pallets/duniter-wot/src/tests.rs +++ b/pallets/duniter-wot/src/tests.rs @@ -251,6 +251,56 @@ fn test_confirm_idty_ok() { }); } +#[test] +fn test_revoke_idty() { + new_test_ext(5, 1).execute_with(|| { + run_to_block(2); + + // Alice identity can not be revoked because she's smith + assert_noop!( + Identity::revoke_identity( + RuntimeOrigin::signed(1), + 1, + 1, + TestSignature( + 1, + ( + REVOCATION_PAYLOAD_PREFIX, + RevocationPayload { + idty_index: 1u32, + genesis_hash: System::block_hash(0), + } + ) + .encode() + ) + ), + pallet_duniter_wot::Error::<Test, Instance2>::NotAllowedToRemoveIdty + ); + + // Anyone should be able to submit Bob revocation certificate + assert_ok!(Identity::revoke_identity( + RuntimeOrigin::signed(42), + 2, + 2, + TestSignature( + 2, + ( + REVOCATION_PAYLOAD_PREFIX, + RevocationPayload { + idty_index: 2u32, + genesis_hash: System::block_hash(0), + } + ) + .encode() + ) + )); + + System::assert_has_event(RuntimeEvent::Identity( + pallet_identity::Event::IdtyRemoved { idty_index: 2 }, + )); + }); +} + #[test] fn test_idty_membership_expire_them_requested() { new_test_ext(3, 2).execute_with(|| { -- GitLab