Skip to content
This repository was archived by the owner on Nov 15, 2023. It is now read-only.
Merged
Changes from 1 commit
Commits
Show all changes
55 commits
Select commit Hold shift + click to select a range
62dc0d7
New Society
gavofyork Apr 30, 2022
135009c
More logic drafting
gavofyork Apr 30, 2022
01c6834
More work
gavofyork May 3, 2022
a6577e0
Building
gavofyork May 3, 2022
feb7d6b
Some tests
gavofyork May 3, 2022
f7ce7e3
Fixes
gavofyork May 4, 2022
841c732
Improvements to the voting process
gavofyork May 4, 2022
8b997cd
More tests
gavofyork May 4, 2022
3f9fdbd
Test number 20
gavofyork May 4, 2022
98f4060
Tests
gavofyork May 4, 2022
3f6ba74
30 tests
gavofyork May 4, 2022
89c4bf6
Another test]
gavofyork May 5, 2022
db636be
All tests enabled
gavofyork May 5, 2022
d6abcb9
Minor stuff
gavofyork May 5, 2022
f8360a8
generate_storage_alias: Rewrite as proc macro attribute
bkchr May 10, 2022
43cf8c1
Maintenance operations don't pay fee
gavofyork May 10, 2022
0fbf6b5
Merge remote-tracking branch 'origin/master' into gav-society-v2
gavofyork May 10, 2022
287269d
Merge remote-tracking branch 'origin/bkchr-storage-alias-proc-macro' …
gavofyork May 10, 2022
b12cbb2
Fix compilation and FMT
bkchr May 10, 2022
249b664
Moare fixes
bkchr May 10, 2022
0763482
Merge remote-tracking branch 'origin/bkchr-storage-alias-proc-macro' …
gavofyork May 10, 2022
676595c
Migrations
gavofyork May 11, 2022
0fe52d8
Fix tests and add migration testing
gavofyork May 11, 2022
27abee7
Introduce lazy-cleanup and avoid unbounded prefix removal
gavofyork May 11, 2022
adccb66
Fixes
gavofyork May 18, 2022
06700bd
Merge remote-tracking branch 'origin/master' into gav-society-v2
gavofyork May 31, 2022
aefd6db
Fixes
gavofyork Jun 1, 2022
1bbc803
Merge remote-tracking branch 'origin/master' into gav-society-v2
gavofyork Jun 1, 2022
be940c1
[WIP][Society] Adding benchmarking to the v2. (#11776)
arturgontijo Dec 3, 2022
0f4f927
Merge branch 'master' into gav-society-v2
gavofyork Dec 3, 2022
3f20f36
Fix Cargo
gavofyork Dec 5, 2022
db9990f
Fixes
gavofyork Dec 7, 2022
6218e32
Merge remote-tracking branch 'origin/master' into gav-society-v2
gavofyork Dec 7, 2022
d9dce35
Fixes
gavofyork Dec 7, 2022
4c60eef
Spelling
gavofyork Dec 8, 2022
fc1d682
Merge branch 'master' into gav-society-v2
gavofyork Jan 21, 2023
e1214b3
Merge remote-tracking branch 'origin/master' into gav-society-v2
gavofyork Jun 11, 2023
3f119f1
Fix benchmarks
gavofyork Jun 12, 2023
59d1545
Merge remote-tracking branch 'origin/master' into gav-society-v2
gavofyork Jun 12, 2023
2440062
Another fix
gavofyork Jun 12, 2023
7811ac1
Remove println
gavofyork Jun 12, 2023
687d914
Society migration
gavofyork Jun 12, 2023
4841585
Merge remote-tracking branch 'origin/master' into gav-society-v2
Jun 13, 2023
1864679
Merge branch 'gav-society-v2' of github.com:paritytech/substrate into…
gavofyork Jun 13, 2023
ab1eafd
Fixes
gavofyork Jun 13, 2023
c01e8bc
Docs
gavofyork Jun 13, 2023
3d3b43c
Docs
gavofyork Jun 13, 2023
3b73c57
Remove accidental addition.
gavofyork Jun 13, 2023
e51eebf
Fixes
gavofyork Jun 13, 2023
43ea1db
Clippy
gavofyork Jun 14, 2023
bfed684
Fixes
gavofyork Jun 14, 2023
ba534a6
Docs
gavofyork Jun 14, 2023
1528a58
Improve try_runtime test
gavofyork Jun 15, 2023
af65cf7
Use pallet storage version
gavofyork Jun 15, 2023
308e646
Fix up society cargo toml file
gavofyork Jun 15, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
More work
  • Loading branch information
gavofyork committed May 3, 2022
commit 01c68345f0b7d35789d1147c4ae08be6448892f3
100 changes: 70 additions & 30 deletions frame/society/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,6 @@
//! At any point, a user in the society can be one of a:
//! * Bidder - A user who has submitted intention of joining the society.
//! * Candidate - A user who will be voted on to join the society.
//! * Suspended Candidate - A user who failed to win a vote.
//! * Member - A user who is a member of the society.
//! * Suspended Member - A member of the society who has accumulated too many strikes
//! or failed their membership challenge.
Expand Down Expand Up @@ -413,16 +412,21 @@ pub type PayoutsFor<T, I> = BoundedVec<

/// Information concerning a member.
#[derive(Encode, Decode, Copy, Clone, PartialEq, Eq, RuntimeDebug, TypeInfo)]
pub struct MemberRecord<Balance, BlockNumber, MaxPayouts> {
pub struct MemberRecord {
rank: Rank,
strikes: StrikeCount,
vouching: Option<VouchingStatus>,
paid: Balance,
index: u32,
}

/// Information concerning a member.
#[derive(Default, Encode, Decode, Copy, Clone, PartialEq, Eq, RuntimeDebug, TypeInfo)]
pub struct PayoutRecord<Balance, BlockNumber, MaxPayouts> {
paid: Balance,
payouts: BoundedVec<(BlockNumber, Balance), MaxPayouts>,
}

pub type MemberRecordFor<T, I> = MemberRecord<
pub type PayoutRecordFor<T, I> = PayoutRecord<
BalanceOf<T, I>,
<T as frame_system::Config>::BlockNumber,
<T as Config<I>>::MaxPayouts,
Expand Down Expand Up @@ -451,6 +455,21 @@ pub struct GroupParams<Balance> {

pub type GroupParamsFor<T> = GroupParams<BalanceOf<T, I>>;

pub type FactionIndex = u32;

pub enum Faction {
Society,
Splinter(FactionIndex),
}

/// A group is just the rank of a faction.
pub struct Group {
faction: Faction,
rank: Rank,
}

//TODO: Ranks cannot be indexed linearly. Should just be done as Groups DAG.

#[frame_support::pallet]
pub mod pallet {
use super::*;
Expand Down Expand Up @@ -567,6 +586,8 @@ pub mod pallet {
NoDefender,
/// Group doesn't exist.
NotGroup,
/// The member is already elevated to this rank.
AlreadyElevated,
}

#[pallet::event]
Expand Down Expand Up @@ -607,6 +628,8 @@ pub mod pallet {
Unfounded { founder: T::AccountId },
/// Some funds were deposited into the society account.
Deposit { value: BalanceOf<T, I> },
/// A \[member\] got elevated to \[rank\].
Elevated { member: T::AccountId, rank: Rank },
}

/// Old name generated by `decl_event`.
Expand All @@ -622,23 +645,25 @@ pub mod pallet {
pub type Pot<T: Config<I>, I: 'static = ()> = StorageValue<_, BalanceOf<T, I>, ValueQuery>;

/// The first member.
// TODO: Rename to `Faction` as a map on `FactionIndex`.
#[pallet::storage]
pub type Founder<T: Config<I>, I: 'static = ()> = StorageValue<_, T::AccountId>;

/// The most primary from the most recently approved members.
/// The most primary from the most recently approved rank 0 members in the society.
#[pallet::storage]
pub type Head<T: Config<I>, I: 'static = ()> = StorageValue<_, T::AccountId>;

/// A hash of the rules of this society concerning membership. Can only be set once and
/// only by the founder.
// TODO: Should be a map with rules for each rank and faction.
// TODO: Rename to `GroupMeta` as a map on `GroupIndex` and include `name: String`.
#[pallet::storage]
pub type Rules<T: Config<I>, I: 'static = ()> = StorageValue<_, T::Hash>;

/// The current members and their rank. Doesn't include `SuspendedMembers`.
#[pallet::storage]
pub type Members<T: Config<I>, I: 'static = ()> =
StorageMap<_, Twox64Concat, T::AccountId, MemberRecordFor<T>, OptionQuery>;
StorageMap<_, Twox64Concat, T::AccountId, MemberRecord, OptionQuery>;
/*
// TODO: Migrate from:
pub(super) type Vouching<T: Config<I>, I: 'static = ()> =
Expand All @@ -649,20 +674,29 @@ pub mod pallet {
StorageValue<_, Vec<T::AccountId>, ValueQuery>;
*/

/// The number of items in `Membership` currently. (Doesn't include `SuspendedMembers`.)
/// Information regarding rank-0 payouts, past and future.
#[pallet::storage]
pub type Payouts<T: Config<I>, I: 'static = ()> =
StorageMap<_, Twox64Concat, T::AccountId, PayoutRecordFor<T, I>, ValueQuery>;
/*
// TODO: Migrate from:
pub(super) type Payouts<T: Config<I>, I: 'static = ()> = ???
*/

/// The number of items in `Members` currently. (Doesn't include `SuspendedMembers`.)
#[pallet::storage]
pub type MemberCount<T: Config<I>, I: 'static = ()> = StorageValue<_, u32, ValueQuery>;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't instead Members be CountedStorageMap?


/// The current items in `Membership` keyed by their unique index. Keys are densely populated
/// The current items in `Members` keyed by their unique index. Keys are densely populated
/// `0..MemberCount` (does not include `MemberCount`).
#[pallet::storage]
pub type MemberByIndex<T: Config<I>, I: 'static = ()> =
StorageMap<_, Twox64Concat, u32, T::AccountId, OptionQuery>;

/// The set of suspended members.
/// The set of suspended members, with their old membership record.
#[pallet::storage]
pub type SuspendedMembers<T: Config<I>, I: 'static = ()> =
StorageMap<_, Twox64Concat, T::AccountId, MemberRecordFor<T>, OptionQuery>;
StorageMap<_, Twox64Concat, T::AccountId, MemberRecord, OptionQuery>;

/// The number of rounds which have passed.
#[pallet::storage]
Expand Down Expand Up @@ -1019,7 +1053,7 @@ pub mod pallet {
#[pallet::weight(T::BlockWeights::get().max_block / 10)]
pub fn payout(origin: OriginFor<T>) -> DispatchResult {
let who = ensure_signed(origin)?;
let mut record = Members::<T, I>::get(&who).ok_or(Error::<T, I>::NotMember)?;
let mut record = Payouts::<T, I>::get(&who).ok_or(Error::<T, I>::NotMember)?;

if let Some((when, amount)) = record.payouts.first() {
if when <= &<frame_system::Pallet<T>>::block_number() {
Expand All @@ -1033,18 +1067,24 @@ pub mod pallet {
Err(Error::<T, I>::NoPayout)?
}

/// Repay the payment previously given to the member with the signed origin, and elevate
/// them from rank 0 to rank 1.
/// Repay the payment previously given to the member with the signed origin, remove any
/// pending payments, and elevate them from rank 0 to rank 1.
#[pallet::weight(T::BlockWeights::get().max_block / 10)]
pub fn repay(origin: OriginFor<T>) -> DispatchResult {
todo!()
}
pub fn waive_repay(origin: OriginFor<T>) -> DispatchResult {
let who = ensure_signed(origin)?;
let mut record = Members::<T, I>::get(&who).ok_or(Error::<T, I>::NotMember)?;
let mut payout_record = Payouts::<T, I>::get(&who).ok_or(Error::<T, I>::NotMember)?;
ensure!(record.rank == 0, Error::<T, I>::AlreadyElevated);

/// Remove the payment owed to the member with the signed origin, and elevate them from
/// rank 0 to rank 1.
#[pallet::weight(T::BlockWeights::get().max_block / 10)]
pub fn waive(origin: OriginFor<T>) -> DispatchResult {
todo!()
T::Currency::transfer(&who, &Self::account_id(), payout_record.paid, AllowDeath)?;
payout_record.payouts.clear();
record.rank = 1;
Members::<T, I>::insert(&who, record);
Payouts::<T, I>::insert(&who, payout_record);

Self::deposit_event(Event::<T, I>::Elevated { member: who, rank: 1 });

Ok(())
}

/// Found the society.
Expand Down Expand Up @@ -1080,7 +1120,7 @@ pub mod pallet {
// This should never fail in the context of this function...
let params = GroupParams { max_members, max_intake, max_strikes, candidate_deposit };
Parameters::<T, I>::put(params);
Self::insert_member(&founder, 1, BoundedVec::new())?;
Self::insert_member(&founder, 1)?;
Head::<T, I>::put(&founder);
Founder::<T, I>::put(&founder);
Rules::<T, I>::put(T::Hashing::hash(&rules));
Expand Down Expand Up @@ -1150,9 +1190,10 @@ pub mod pallet {

if forgive {
// Try to add member back to society. Can fail with `MaxMembers` limit.
Self::reinstate_member(&who, record.rank, record.payouts)?;
Self::reinstate_member(&who, record.rank)?;
} else {
Self::unreserve_payout(record.payouts.into_iter().map(|x| x.1).sum());
let mut payout_record = Payouts::<T, I>::take(&who);
Self::unreserve_payout(payout_record.payouts.into_iter().map(|x| x.1).sum());
}

SuspendedMembers::<T, I>::remove(&who);
Expand Down Expand Up @@ -1514,12 +1555,11 @@ impl<T: Config<I>, I: 'static> Pallet<T, I> {
///
/// NOTE: Generally you should not use this, and instead use `add_new_member` or
/// `reinstate_member`, whose names clearly match the desired intention.
fn insert_member(who: &T::AccountId, rank: Rank, payouts: PayoutsFor<T>) -> DispatchResult {
fn insert_member(who: &T::AccountId, rank: Rank) -> DispatchResult {
let params = Parameters::<T, I>::get().ok_or(Error::<T, I>::NotGroup);
ensure!(MemberCount::get() < params.max_members as usize, Error::<T, I>::MaxMembers);
let index = MemberCount::<T, I>::mutate(|i| { i.saturating_accrue(1); *i - 1 });
let paid = Zero::zero();
let record = MemberRecord { rank, strikes: 0, vouching: None, paid, index, payouts };
let record = MemberRecord { rank, strikes: 0, vouching: None, index };
Members::<T, I>::insert(who, record);
MemberByIndex::<T, I>::insert(index, who);
Ok(())
Expand All @@ -1531,14 +1571,14 @@ impl<T: Config<I>, I: 'static> Pallet<T, I> {
///
/// The `payouts` value must be exactly as it was prior to suspension since no further funds
/// will be reserved.
fn reinstate_member(who: &T::AccountId, rank: Rank, payouts: PayoutsFor<T>) -> DispatchResult {
Self::insert_member(who, rank, payouts)
fn reinstate_member(who: &T::AccountId, rank: Rank) -> DispatchResult {
Self::insert_member(who, rank)
}

/// Add a member to the sorted members list. If the user is already a member, do nothing.
/// Can fail when `MaxMember` limit is reached, but in that case it has no side-effects.
fn add_new_member(who: &T::AccountId, rank: Rank) -> DispatchResult {
Self::insert_member(who, rank, Default::default())
Self::insert_member(who, rank)
}

/// Induct a new member into the set.
Expand Down