From 833564a998740304d6f4b190a830f493bab3198f Mon Sep 17 00:00:00 2001 From: bgallois <benjamin@gallois.cc> Date: Thu, 20 Jun 2024 11:18:51 +0200 Subject: [PATCH] add missing doc --- distance-oracle/src/lib.rs | 6 +- docs/api/runtime-calls.md | 90 +++++++++++++++------ pallets/certification/src/types.rs | 2 +- pallets/distance/src/median.rs | 2 + pallets/membership/src/lib.rs | 9 ++- pallets/oneshot-account/src/check_nonce.rs | 1 + pallets/smith-members/src/lib.rs | 13 ++- primitives/distance/src/lib.rs | 1 + primitives/membership/src/lib.rs | 3 +- resources/metadata.scale | Bin 148323 -> 150794 bytes 10 files changed, 91 insertions(+), 36 deletions(-) diff --git a/distance-oracle/src/lib.rs b/distance-oracle/src/lib.rs index 53a7503ea..965ed8b20 100644 --- a/distance-oracle/src/lib.rs +++ b/distance-oracle/src/lib.rs @@ -49,6 +49,7 @@ impl subxt::config::Config for RuntimeConfig { type Signature = subxt::ext::sp_runtime::MultiSignature; } +/// Represents a tipping amount. #[derive(Copy, Clone, Debug, Default, Encode)] pub struct Tip { #[codec(compact)] @@ -67,6 +68,7 @@ impl From<u64> for Tip { } } +/// Represents configuration parameters. pub struct Settings { pub evaluation_result_dir: PathBuf, pub rpc_url: String, @@ -81,6 +83,7 @@ impl Default for Settings { } } +/// Asynchronously runs a computation using the provided client and saves the result to a file. pub async fn run_and_save(client: &api::Client, settings: Settings) { let Some((evaluation, current_pool_index, evaluation_result_path)) = run(client, &settings, true).await @@ -138,7 +141,8 @@ pub async fn run_and_save(client: &api::Client, settings: Settings) { }); } -/// Returns `Option<(evaluation, current_pool_index, evaluation_result_path)>` +/// Asynchronously runs a computation based on the provided client and settings. +/// Returns `Option<(evaluation, current_pool_index, evaluation_result_path)>`. pub async fn run( client: &api::Client, settings: &Settings, diff --git a/docs/api/runtime-calls.md b/docs/api/runtime-calls.md index 320e6a185..efdbb573c 100644 --- a/docs/api/runtime-calls.md +++ b/docs/api/runtime-calls.md @@ -28,7 +28,7 @@ Taking 0.0107 % of a block. </details> -unlink the identity associated with the account +Unlink the identity associated with the account. ### Scheduler - 2 @@ -430,7 +430,7 @@ receiver: T::IdtyIndex </details> -Invite a WoT member to try becoming a Smith +Invite a member of the Web of Trust to attempt becoming a Smith. #### accept_invitation - 1 @@ -443,7 +443,7 @@ Taking 0.0122 % of a block. </details> -Accept an invitation (must have been invited first) +Accept an invitation to become a Smith (must have been invited first). #### certify_smith - 2 @@ -457,7 +457,7 @@ receiver: T::IdtyIndex </details> -Certify an invited smith which can lead the certified to become a Smith +Certify an invited Smith, which can lead the certified to become a Smith. ### AuthorityMembers - 11 @@ -472,7 +472,7 @@ Taking 0.0165 % of a block. </details> -ask to leave the set of validators two sessions after +Request to leave the set of validators two sessions later. #### go_online - 1 @@ -485,7 +485,7 @@ Taking 0.0188 % of a block. </details> -ask to join the set of validators two sessions after +Request to join the set of validators two sessions later. #### set_session_keys - 2 @@ -499,7 +499,7 @@ keys: T::Keys </details> -declare new session keys to replace current ones +Declare new session keys to replace current ones. #### remove_member_from_blacklist - 4 @@ -513,6 +513,7 @@ member_id: T::MemberId </details> +Remove a member from the blacklist. remove an identity from the blacklist ### Grandpa - 16 @@ -774,7 +775,7 @@ Taking 0.0218 % of a block. </details> -Claim Universal Dividends +Claim Universal Dividends. #### transfer_ud - 1 @@ -804,7 +805,7 @@ value: BalanceOf<T> </details> -Transfer some liquid free balance to another account, in milliUD. +Transfer some liquid free balance to another account in milliUD and keep the account alive. ### Identity - 41 @@ -901,7 +902,15 @@ inc: bool </details> -change sufficient ref count for given key +Change sufficient reference count for a given key. + +This function allows a privileged root origin to increment or decrement the sufficient +reference count associated with a specified owner key. + +- `origin` - The origin of the call. It must be root. +- `owner_key` - The account whose sufficient reference count will be modified. +- `inc` - A boolean indicating whether to increment (`true`) or decrement (`false`) the count. + #### link_account - 8 @@ -916,7 +925,14 @@ payload_sig: T::Signature </details> -Link an account to an identity +Link an account to an identity. + +This function links a specified account to an identity, requiring both the account and the +identity to sign the operation. + +- `origin` - The origin of the call, which must have an associated identity index. +- `account_id` - The account ID to link, which must sign the payload. +- `payload_sig` - The signature with the linked identity. ### Certification - 43 @@ -961,7 +977,9 @@ receiver: T::IdtyIndex </details> -remove a certification (only root) +Remove one certification given the issuer and the receiver. + +- `origin`: Must be `Root`. #### remove_all_certs_received_by - 2 @@ -975,7 +993,9 @@ idty_index: T::IdtyIndex </details> -remove all certifications received by an identity (only root) +Remove all certifications received by an identity. + +- `origin`: Must be `Root`. ### Distance - 44 @@ -990,9 +1010,11 @@ Taking 0.0325 % of a block. </details> -Request caller identity to be evaluated -positive evaluation will result in claim/renew membership -negative evaluation will result in slash for caller +Request evaluation of the caller's identity distance. + +This function allows the caller to request an evaluation of their distance. +A positive evaluation will lead to claiming or renewing membership, while a negative +evaluation will result in slashing for the caller. #### request_distance_evaluation_for - 4 @@ -1006,8 +1028,10 @@ target: T::IdtyIndex </details> -Request target identity to be evaluated -only possible for unvalidated identity +Request evaluation of a target identity's distance. + +This function allows the caller to request an evaluation of a specific target identity's distance. +This action is only permitted for unvalidated identities. #### update_evaluation - 1 @@ -1021,8 +1045,10 @@ computation_result: ComputationResult </details> -(Inherent) Push an evaluation result to the pool -this is called internally by validators (= inherent) +Push an evaluation result to the pool. + +This inherent function is called internally by validators to push an evaluation result +to the evaluation pool. #### force_update_evaluation - 2 @@ -1037,7 +1063,11 @@ computation_result: ComputationResult </details> -Force push an evaluation result to the pool +Force push an evaluation result to the pool. + +It is primarily used for testing purposes. + +- `origin`: Must be `Root`. #### force_valid_distance_status - 3 @@ -1051,7 +1081,11 @@ identity: <T as pallet_identity::Config>::IdtyIndex </details> -Force set the distance evaluation status of an identity +Force set the distance evaluation status of an identity. + +It is primarily used for testing purposes. + +- `origin`: Must be `Root`. ### AtomicSwap - 50 @@ -1307,7 +1341,7 @@ salt: H256 </details> -Request a randomness +Request randomness. ### Proxy - 53 @@ -2161,7 +2195,7 @@ member_id: T::MemberId </details> -remove an identity from the set of authorities +Remove a member from the set of validators. ### Grandpa - 16 @@ -2269,7 +2303,13 @@ names: Vec<IdtyName> </details> -remove identity names from storage +Remove identity names from storage. + +This function allows a privileged root origin to remove multiple identity names from storage +in bulk. + +- `origin` - The origin of the call. It must be root. +- `names` - A vector containing the identity names to be removed from storage. ### Utility - 54 diff --git a/pallets/certification/src/types.rs b/pallets/certification/src/types.rs index a12f6b435..5a158f8a9 100644 --- a/pallets/certification/src/types.rs +++ b/pallets/certification/src/types.rs @@ -20,7 +20,7 @@ use codec::{Decode, Encode}; use frame_support::pallet_prelude::*; use scale_info::TypeInfo; -/// Reprensent the certification metadata attached to an identity. +/// Represents the certification metadata attached to an identity. #[derive(Encode, Decode, Clone, Copy, PartialEq, Eq, RuntimeDebug, TypeInfo)] pub struct IdtyCertMeta<BlockNumber: Default> { /// Number of certifications issued by this identity. diff --git a/pallets/distance/src/median.rs b/pallets/distance/src/median.rs index feab0d863..5569d6f26 100644 --- a/pallets/distance/src/median.rs +++ b/pallets/distance/src/median.rs @@ -17,6 +17,7 @@ use frame_support::pallet_prelude::*; use sp_std::cmp::Ordering; +/// Represents a median accumulator. #[derive(Clone, Debug, Decode, Default, Encode, TypeInfo)] pub struct MedianAcc< T: Clone + Decode + Encode + Ord + TypeInfo, @@ -35,6 +36,7 @@ pub struct MedianAcc< fn type_info() -> scale_info::Type<scale_info::form::MetaForm> {} }*/ +/// Represents the result of a median calculation. #[derive(Clone, Debug, Eq, PartialEq)] pub enum MedianResult<T: Clone + Ord> { One(T), diff --git a/pallets/membership/src/lib.rs b/pallets/membership/src/lib.rs index 83950eb83..860d3bd25 100644 --- a/pallets/membership/src/lib.rs +++ b/pallets/membership/src/lib.rs @@ -57,15 +57,16 @@ impl<IdtyId, AccountId> SetupBenchmark<IdtyId, AccountId> for () { fn add_cert(_issuer: &IdtyId, _receiver: &IdtyId) {} } +/// Represent reasons for the removal of membership. #[derive(Encode, Decode, Clone, PartialEq, Eq, RuntimeDebug, TypeInfo)] pub enum MembershipRemovalReason { - // reach end of life + /// Indicates membership was removed because it reached the end of its life. Expired, - // was explicitly revoked + /// Indicates membership was explicitly revoked. Revoked, - // received certs count passed below threshold + /// Indicates membership was removed because the received certifications count fell below the threshold. NotEnoughCerts, - // system reasons (consumers, authority members, or root) + /// Indicates membership was removed due to system reasons (e.g., consumers, authority members, or root). System, } diff --git a/pallets/oneshot-account/src/check_nonce.rs b/pallets/oneshot-account/src/check_nonce.rs index 3f3654531..0f1a2fccf 100644 --- a/pallets/oneshot-account/src/check_nonce.rs +++ b/pallets/oneshot-account/src/check_nonce.rs @@ -25,6 +25,7 @@ use sp_runtime::{ transaction_validity::{TransactionValidity, TransactionValidityError}, }; +/// Wrapper around `frame_system::CheckNonce<T>`. #[derive(Encode, Decode, Clone, Eq, PartialEq, TypeInfo)] #[scale_info(skip_type_params(Runtime))] pub struct CheckNonce<T: Config>(pub frame_system::CheckNonce<T>); diff --git a/pallets/smith-members/src/lib.rs b/pallets/smith-members/src/lib.rs index 9cede1d7c..b9bf58af2 100644 --- a/pallets/smith-members/src/lib.rs +++ b/pallets/smith-members/src/lib.rs @@ -71,22 +71,27 @@ pub use pallet::*; use pallet_authority_members::SessionIndex; pub use types::*; +/// Reasons for the removal of a Smith identity. #[derive(Encode, Decode, Clone, PartialEq, Eq, RuntimeDebug, TypeInfo)] pub enum SmithRemovalReason { + /// Membership was lost due to expiration or other reasons. LostMembership, + /// Smith was offline for too long. OfflineTooLong, + /// Smith was blacklisted. Blacklisted, } +/// Possible statuses of a Smith identity. #[derive(Encode, Decode, Copy, Clone, PartialEq, Eq, RuntimeDebug, TypeInfo)] pub enum SmithStatus { - /// The identity has been invited by a smith but has not accepted yet + /// The identity has been invited by a Smith but has not accepted yet. Invited, - /// The identity has accepted to eventually become a smith + /// The identity has accepted to eventually become a Smith. Pending, - /// The identity has reached the requirements to become a smith and can now goGoOnline() or invite/certify other smiths + /// The identity has reached the requirements to become a Smith and can now perform Smith operations. Smith, - /// The identity has been removed from the smiths set but is kept to keep track of its certifications + /// The identity has been removed from the Smiths set but is kept to track its certifications. Excluded, } diff --git a/primitives/distance/src/lib.rs b/primitives/distance/src/lib.rs index 1d4690942..9e67b72f8 100644 --- a/primitives/distance/src/lib.rs +++ b/primitives/distance/src/lib.rs @@ -29,6 +29,7 @@ use std::marker::PhantomData; pub const INHERENT_IDENTIFIER: InherentIdentifier = *b"distanc0"; +/// Represents the result of a distance computation. #[derive(Clone, Decode, Encode, PartialEq, RuntimeDebug, TypeInfo)] pub struct ComputationResult { pub distances: sp_std::vec::Vec<Perbill>, diff --git a/primitives/membership/src/lib.rs b/primitives/membership/src/lib.rs index c98121711..96e37af82 100644 --- a/primitives/membership/src/lib.rs +++ b/primitives/membership/src/lib.rs @@ -27,7 +27,7 @@ use frame_support::pallet_prelude::{RuntimeDebug, Weight}; use scale_info::TypeInfo; use serde::{Deserialize, Serialize}; -/// membership events +/// Represent membership-related events. pub enum Event<IdtyId> { /// A membership was acquired. MembershipAdded(IdtyId), @@ -37,6 +37,7 @@ pub enum Event<IdtyId> { MembershipRenewed(IdtyId), } +/// Represent membership data. #[derive( Encode, Decode, diff --git a/resources/metadata.scale b/resources/metadata.scale index bf88b3ce9a6e05e2a98b8c43493369f717191571..cd7176512ddbd3d7cfa4b633e8d3ef6a071d0813 100644 GIT binary patch delta 5818 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 delta 3421 zcmeC0#re36a|3r4)1K1FyjgmanO3-MZpt#Ta$4h=SC(0ls*tD<o*$x+o0^-HTBJ~t zuTWA{sgRVKoS&PSm#&bg5S*J?lHrn=oSa%v5}ygul30?NpU1$+a%M9BQqjp~OXVhq zF4bm~o!q!ogtZu?dh+b0`ja;-cAG4?%!cJkVsZB5&}F(}iD@ONMJnm}@%ec<nR%%U zj4T&GQgfH-u!5x~pI@fNbRcE&_htH%)t75C?wEXcxy<B6nnIK7mRmBiY`(MnwH{lF zb53Gr?sP{sCSl%Uosy!&yyCRfqWIF3$rG--O*Xl{gpqaf&FiL<bFTAFR{H3+x%x&S zD>F++(d74c6(`-d(q>tboROH9o~lq>nwFNCoSB+eqEM8YrjVRpnpdKbmS3cho>`Wf zr;wdmIr-TGPbQX%$%YT*K%UwB@=*t)3QI>(YHofRDAbZui%K%nGLyl<p`ekUms6=w zl%HRsIr;PxYi5=&MUy$78t|Y<fWl<%Q)gqIIYFs~rK!aw3dxB%IjKbonJKAxC7C6a zpzu#hRY)yM%qdMQNlkfDkYAixl3A9jFnP~2DTQQ^=k<$H^HR&95mua$S#TyVH9Zlg zNS+()3y8Us-#xQ3=YU&Ql30|UT7uKE8DK9I<QErbCgr3~e(+p^v2yaC=XSgt2Q)nM zGE$3D^GY-oCfmGFWxY_6ky$*s`h^OQhOI&-Om6b!7nMvbYbN`>)Si6!WhfKNoyk(K z%)x>8@YORJ(EymQ6BUXQ^HTD2^HPh8LDJh5IT+7BVPu#t@s?5FBR8?27~#mwyp+@m zP`DJ9=9eVu1f`~x=A{Idrk18MGITPtFt8*jq@|`7E0iZ@mVi<$C=QFjil)za%V^4& zGyU9KM(OFV-!dB1Pf);NHaOWT6qh8HloqSFRup6wr55{x(m1QY78VAU9T0uRsl~;a z`FRR(C&9u>0iqwAG!k=)Eu2e>K!FtuQP0RAAi%)Dz`&x^qEK9tUzA#`P?C|VkPK0z zfMV+Oz3&($8Ba{V{*F<TGpSM`v$(i4wP<=Q2a^o*83o_zjT}r0lmDu7vqAFZ^wjr^ zN{mmYcfMy-kW5NV%P#_@Oo(eTixt2QN==!5`aPqoS59Vei9%)`EMu3JWaJlRmSm<D zyZD1Mq$5IvkpblE1O>1bNOo07L`Y8#&=i@T_kock3ZkI2Bt0J#^hio%e8J^OF#{tD ztH44~G*v*t5L(V;rhuXp%1KEqNmOylNleZLnFqF<Vfw=lj55>D-C|VUuKJPjsj#qz z0yI<=LR}ORb3yrax*;o*xR4971UPD@=d&_Nv0P<T2$?>Sl}V|-G%vF(wWv5TM<FG% z43yPU6f{!uQ;QYy@=Fv-60=hkGV@CE6%vynr2r^$;4zz$T3k|8nhYxP6!Oy)a`W?2 zD>XIzQY%V=QbF02fkA?Wfh9x%Bm#0-5m>YoTqsC@1Vd9iAZlFTYLbgm!SXr*iN#Q3 ziWwOsSy&iYA{0Pk=mr%tRx&aE5t+V(jVYh;&2$lVCRMT06a{3v6be#{GV@cW2e32A zFfN#$%g&_2qLEvyIej5JlN95I>3i6jH0nVD8licaCB*@$MWHDY3NM&J36p_=N0d<^ zBqLQJuM}Jh<fkc=f>eRx2ohxA6blLUVujR-f}+&o;?xv{%seD5p)SRtj0&z5iMa(i zsa6V}X$qD3r3&Sl#Tg)TQY#9=K)S#t!K1KPp**uBLm^QiH?bl!w=`FwpeQvt6P(NP z)4)pei&9dH3P52GikIBXoSe*17afJ<jQsrKR0Tr=1B2;b*qM|W89<ptnvr4pQ4S^r zMuzFSoJ<C)II=q^4S<VVP&u1Ay@``4S-As}K4FOfl0e}KA?Zqxi%F{f0z@HPDlaiN z734v<09dVpMsa3tK~AMYqC#<MiKYoCDR`!oRC<DnGkA&c22$~)7Qy_7W=KgsxIO|I z5AuCpYDEdB0!+>H<y=e(Il7Dx_ax=yCuhTA15}M?q(bv=8cauKYB9($Ak&gkVTFT2 zVu=E%G*<u_z*x(~$jT^T;+&tCmRXb=08Uc^0ve#w>w`kT^g?bX@#%WpOx6ODj0zB0 z1xT?oy_TCvgI@#Oa7cw#PMXuVb2G`ZSTZUEOuxg;B+p!)kw5)EH<JU4DoDtkhbfu) zfP(LI8D1vI>8E*^MCA26Kw;zz%^wg81O$vg*6T7tRBA99O?T&IQkZ^<m&r&KqeMq4 zS3q^60;p`6uENKZ?yX9EKvgParocif6<iyjgi`kOV|+~7j0)2~@-Z1Q#!O#W!YIxm zAOOltEJvoh@G}`spTp1OBh{kdjNC>jR>(~)NlZypNUEI9E5M{AT!1d0R5{&8fJxQ5 z1YH7LkS8YPq$=d+=`r>)G0HLuXn+id1ra|eh-9HbBsu+q0FyoA8E`GalvFvrMv%#n zmBkYz-N?bD#Fm_zS(chI{g)t<o#qk+m(n6|aRf?(Wr;bNDWHZ(ewsp}0!kBSdbJRf zp$N+g1y4w01(cc!LG^IT^asLB64MognZ$8RYumVjG8@>Ufc*R%BSwZ$77hjm+~%2! zFqs;kP;dgLYf!CTo{^cH0WK3#GK)(R^O92)ib``*6>>|9OB9k)6_PVjle1G(rq32( zQmhxKPzXrPO953&pkf+QAS)C>nq8?y#S9<d<$ZZZK3pP2Au$iu`~p?=iFu%6wm7w@ zEHwpebwN>Pa;lCeqk;msomHNZpNkMzD9_Bv0Xd~KJg+Dfsw=-pp*Sb8I3qPhp*$ls z53Cx=Ny+)3;<6;QSWm?zGbOYjC9x!xkwJk46f!QEDaejVPc4~#@HV5EoV^3IE(C=n zYKfAf;5=Qgg;9KZvM7@hbBBWC^d3<rh3RWWnZz@BCMX~x0a{_eN{sw8Z~>5AthYqL z5z;_Ga%5()LP~yKszPZoC_s%B3i9)Figos&`vvU%lEm!kx?)U*%nuZNr>BZB$=4U9 zrll68rm7c%f*jN)O3KX1EUCPs5SmvCszs726^cspN-}d(6_QFz6!KD2Q&LkDk}4IF zbHELBcy#9%B_`*jhWKXYIVLBA4a!Lkf*4+`$|%6Vv0k5Lih^%u9=Iw2r)q`#wCU>N zOd{J|#hKz*85yQulwp!%WSGt<%OuapFg;Qh%-bN#B*Mrr{fR77D&vajUUE!Yk_OPm dY5*w0B@`~OLuyKvnCX3TOyb*@$uXtq0RV2us3iaZ -- GitLab