1import type {IKeyringPair} from '@polkadot/types/types';2import {usingPlaygrounds, itSub, expect, Pallets, requirePalletsOrSkip, describeGov} from '@unique/test-utils/util.js';3import {Event} from '@unique/test-utils';4import {democracyLaunchPeriod, democracyVotingPeriod, democracyEnactmentPeriod, clearCouncil, clearTechComm, clearFellowship} from './util.js';5import type {ICounselors, ITechComms} from './util.js';67describeGov('Governance: Initialization', () => {8 let donor: IKeyringPair;9 let sudoer: IKeyringPair;10 let counselors: ICounselors;11 let techcomms: ITechComms;12 let coreDevs: any;1314 const expectedAlexFellowRank = 7;15 const expectedFellowRank = 6;1617 before(async function() {18 await usingPlaygrounds(async (helper, privateKey) => {19 requirePalletsOrSkip(this, helper, [Pallets.Democracy, Pallets.Council, Pallets.TechnicalCommittee]);2021 const councilMembers = await helper.council.membership.getMembers();22 const techcommMembers = await helper.technicalCommittee.membership.getMembers();23 expect(councilMembers.length == 0, 'The Council must be empty before the Gov Init');24 expect(techcommMembers.length == 0, 'The Technical Commettee must be empty before the Gov Init');2526 donor = await privateKey({url: import.meta.url});27 sudoer = await privateKey('//Alice');2829 const counselorsNum = 5;30 const techCommsNum = 3;31 const coreDevsNum = 2;32 const [33 alex,34 ildar,35 charu,36 filip,37 irina,3839 greg,40 andy,41 constantine,4243 yaroslav,44 daniel,45 ] = await helper.arrange.createAccounts(new Array(counselorsNum + techCommsNum + coreDevsNum).fill(10_000n), donor);4647 counselors = {48 alex,49 ildar,50 charu,51 filip,52 irina,53 };5455 techcomms = {56 greg,57 andy,58 constantine,59 };6061 coreDevs = {62 yaroslav: yaroslav,63 daniel: daniel,64 };65 });66 });6768 itSub('Initialize Governance', async ({helper}) => {69 const promoteFellow = (fellow: string, promotionsNum: number) => new Array(promotionsNum).fill(helper.fellowship.collective.promoteCall(fellow));7071 const expectFellowRank = async (fellow: string, expectedRank: number) => {72 expect(await helper.fellowship.collective.getMemberRank(fellow)).to.be.equal(expectedRank);73 };7475 console.log('\t- Setup the Prime of the Council via sudo');76 await helper.getSudo().utility.batchAll(sudoer, [77 helper.council.membership.addMemberCall(counselors.alex.address),78 helper.council.membership.setPrimeCall(counselors.alex.address),7980 helper.fellowship.collective.addMemberCall(counselors.alex.address),81 ...promoteFellow(counselors.alex.address, expectedAlexFellowRank),82 ]);8384 let councilMembers = await helper.council.membership.getMembers();85 const councilPrime = await helper.council.collective.getPrimeMember();86 const alexFellowRank = await helper.fellowship.collective.getMemberRank(counselors.alex.address);87 expect(councilMembers).to.be.deep.equal([counselors.alex.address]);88 expect(councilPrime).to.be.equal(counselors.alex.address);89 expect(alexFellowRank).to.be.equal(expectedAlexFellowRank);9091 console.log('\t- The Council Prime initializes the Technical Commettee');92 const councilProposalThreshold = 1;9394 await helper.council.collective.propose(95 counselors.alex,96 helper.utility.batchAllCall([97 helper.technicalCommittee.membership.addMemberCall(techcomms.greg.address),98 helper.technicalCommittee.membership.addMemberCall(techcomms.andy.address),99 helper.technicalCommittee.membership.addMemberCall(techcomms.constantine.address),100101 helper.technicalCommittee.membership.setPrimeCall(techcomms.greg.address),102 ]),103 councilProposalThreshold,104 );105106 const techCommMembers = await helper.technicalCommittee.membership.getMembers();107 const techCommPrime = await helper.technicalCommittee.membership.getPrimeMember();108 const expectedTechComms = [techcomms.greg.address, techcomms.andy.address, techcomms.constantine.address];109 expect(techCommMembers.length).to.be.equal(expectedTechComms.length);110 expect(techCommMembers).to.containSubset(expectedTechComms);111 expect(techCommPrime).to.be.equal(techcomms.greg.address);112113 console.log('\t- The Council Prime initiates a referendum to add counselors');114 const returnPreimageHash = true;115 const preimageHash = await helper.preimage.notePreimageFromCall(counselors.alex, helper.utility.batchAllCall([116 helper.council.membership.addMemberCall(counselors.ildar.address),117 helper.council.membership.addMemberCall(counselors.charu.address),118 helper.council.membership.addMemberCall(counselors.filip.address),119 helper.council.membership.addMemberCall(counselors.irina.address),120121 helper.fellowship.collective.addMemberCall(counselors.charu.address),122 helper.fellowship.collective.addMemberCall(counselors.ildar.address),123 helper.fellowship.collective.addMemberCall(counselors.irina.address),124 helper.fellowship.collective.addMemberCall(counselors.filip.address),125 helper.fellowship.collective.addMemberCall(techcomms.greg.address),126 helper.fellowship.collective.addMemberCall(techcomms.andy.address),127 helper.fellowship.collective.addMemberCall(techcomms.constantine.address),128 helper.fellowship.collective.addMemberCall(coreDevs.yaroslav.address),129 helper.fellowship.collective.addMemberCall(coreDevs.daniel.address),130131 ...promoteFellow(counselors.charu.address, expectedFellowRank),132 ...promoteFellow(counselors.ildar.address, expectedFellowRank),133 ...promoteFellow(counselors.irina.address, expectedFellowRank),134 ...promoteFellow(counselors.filip.address, expectedFellowRank),135 ...promoteFellow(techcomms.greg.address, expectedFellowRank),136 ...promoteFellow(techcomms.andy.address, expectedFellowRank),137 ...promoteFellow(techcomms.constantine.address, expectedFellowRank),138 ...promoteFellow(coreDevs.yaroslav.address, expectedFellowRank),139 ...promoteFellow(coreDevs.daniel.address, expectedFellowRank),140 ]), returnPreimageHash);141142 await helper.council.collective.propose(143 counselors.alex,144 helper.democracy.externalProposeDefaultWithPreimageCall(preimageHash),145 councilProposalThreshold,146 );147148 console.log('\t- The referendum is being decided');149 const startedEvent = await helper.wait.expectEvent(democracyLaunchPeriod, Event.Democracy.Started);150151 await helper.democracy.vote(counselors.filip, startedEvent.referendumIndex, {152 Standard: {153 vote: {154 aye: true,155 conviction: 1,156 },157 balance: 10_000n,158 },159 });160161 const passedReferendumEvent = await helper.wait.expectEvent(democracyVotingPeriod, Event.Democracy.Passed);162 expect(passedReferendumEvent.referendumIndex).to.be.equal(startedEvent.referendumIndex);163164 await helper.wait.expectEvent(democracyEnactmentPeriod, Event.Scheduler.Dispatched);165166 councilMembers = await helper.council.membership.getMembers();167 const expectedCounselors = [168 counselors.alex.address,169 counselors.ildar.address,170 counselors.charu.address,171 counselors.filip.address,172 counselors.irina.address,173 ];174 expect(councilMembers.length).to.be.equal(expectedCounselors.length);175 expect(councilMembers).to.containSubset(expectedCounselors);176177 await expectFellowRank(counselors.ildar.address, expectedFellowRank);178 await expectFellowRank(counselors.charu.address, expectedFellowRank);179 await expectFellowRank(counselors.filip.address, expectedFellowRank);180 await expectFellowRank(counselors.irina.address, expectedFellowRank);181 await expectFellowRank(techcomms.greg.address, expectedFellowRank);182 await expectFellowRank(techcomms.andy.address, expectedFellowRank);183 await expectFellowRank(techcomms.constantine.address, expectedFellowRank);184 await expectFellowRank(coreDevs.yaroslav.address, expectedFellowRank);185 await expectFellowRank(coreDevs.daniel.address, expectedFellowRank);186 });187188 after(async function() {189 await clearFellowship(sudoer);190 await clearTechComm(sudoer);191 await clearCouncil(sudoer);192 });193});