git.delta.rocks / unique-network / refs/commits / 69f287a4abbd

difftreelog

Use only getAccounts method

Max Andreev2023-04-11parent: #ba41614.patch.diff
in: master
to make sure: there are no any active stakes before each test

1 file changed

modifiedtests/src/sub/appPromotion/appPromotion.test.tsdiffbeforeafterboth
28let accounts: IKeyringPair[];28let accounts: IKeyringPair[];
29let usedAccounts: IKeyringPair[] = [];29let usedAccounts: IKeyringPair[] = [];
3030
31function getAccount(accountsNumber: number) {31async function getAccounts(accountsNumber: number, balance?: bigint) {
32 const accs = accounts.splice(0, accountsNumber);32 let accs: IKeyringPair[] = [];
33 if (balance) {
34 await usingPlaygrounds(async (helper) => {
35 accs = await helper.arrange.createAccounts(new Array(accountsNumber).fill(balance), donor);
36 });
37 } else {
38 accs = accounts.splice(0, accountsNumber);
39 }
33 usedAccounts.push(...accs);40 usedAccounts.push(...accs);
34 return accs;41 return accs;
35}42}
63 }70 }
64 await Promise.all(unstakeTxs);71 await Promise.all(unstakeTxs);
65 usedAccounts = [];72 usedAccounts = [];
73 expect(await helper.staking.getTotalStaked()).to.eq(0n); // there are no active stakes after each test
66 });74 });
67 });75 });
6876
69 describe('stake extrinsic', () => {77 describe('stake extrinsic', () => {
70 itSub('should "lock" staking balance, add it to "staked" map, and increase "totalStaked" amount', async ({helper}) => {78 itSub('should "lock" staking balance, add it to "staked" map, and increase "totalStaked" amount', async ({helper}) => {
71 const [staker, recepient] = getAccount(2);79 const [staker, recepient] = await getAccounts(2);
72 const totalStakedBefore = await helper.staking.getTotalStaked();80 const totalStakedBefore = await helper.staking.getTotalStaked();
7381
74 // Minimum stake amount is 100:82 // Minimum stake amount is 100:
98 {unstake: 'unstakeAll' as const},106 {unstake: 'unstakeAll' as const},
99 {unstake: 'unstakePartial' as const},107 {unstake: 'unstakePartial' as const},
100 ].map(testCase => {108 ].map(testCase => {
101 itSub('should allow to create maximum 10 stakes for account', async ({helper}) => {109 itSub(`[${testCase.unstake}] should allow to create maximum 10 stakes for account`, async ({helper}) => {
102 const [staker] = await helper.arrange.createAccounts([2000n], donor);110 const [staker] = await getAccounts(1, 2000n);
103 const ONE_STAKE = 100n * nominal;111 const ONE_STAKE = 100n * nominal;
104 for (let i = 0; i < 10; i++) {112 for (let i = 0; i < 10; i++) {
105 await helper.staking.stake(staker, ONE_STAKE);113 await helper.staking.stake(staker, ONE_STAKE);
135 });143 });
136144
137 itSub('should allow to stake() if balance is locked with different id', async ({helper}) => {145 itSub('should allow to stake() if balance is locked with different id', async ({helper}) => {
138 const [staker] = getAccount(1);146 const [staker] = await getAccounts(1);
139147
140 // staker has tokens locked with vesting id:148 // staker has tokens locked with vesting id:
141 await helper.balance.vestedTransfer(donor, staker.address, {start: 0n, period: 1n, periodCount: 1n, perPeriod: 200n * nominal});149 await helper.balance.vestedTransfer(donor, staker.address, {start: 0n, period: 1n, periodCount: 1n, perPeriod: 200n * nominal});
168 });176 });
169177
170 itSub('should not allow to stake(), if stake amount is more than total free balance minus locked by staking', async ({helper}) => {178 itSub('should not allow to stake(), if stake amount is more than total free balance minus locked by staking', async ({helper}) => {
171 const [staker] = getAccount(1);179 const [staker] = await getAccounts(1);
172180
173 // Can't stake full balance because Alice needs to pay some fee181 // Can't stake full balance because Alice needs to pay some fee
174 await expect(helper.staking.stake(staker, 1000n * nominal)).to.be.rejected; // With('Arithmetic')182 await expect(helper.staking.stake(staker, 1000n * nominal)).to.be.rejected; // With('Arithmetic')
180 });188 });
181189
182 itSub('for different accounts in one block is possible', async ({helper}) => {190 itSub('for different accounts in one block is possible', async ({helper}) => {
183 const crowd = getAccount(4);191 const crowd = await getAccounts(4);
184192
185 const crowdStartsToStake = crowd.map(user => helper.staking.stake(user, 100n * nominal));193 const crowdStartsToStake = crowd.map(user => helper.staking.stake(user, 100n * nominal));
186 await expect(Promise.all(crowdStartsToStake)).to.be.fulfilled;194 await expect(Promise.all(crowdStartsToStake)).to.be.fulfilled;
196 {method: 'unstakePartial' as const},204 {method: 'unstakePartial' as const},
197 ].map(testCase => {205 ].map(testCase => {
198 itSub(`[${testCase.method}] should move tokens to "pendingUnstake" and subtract it from totalStaked`, async ({helper}) => {206 itSub(`[${testCase.method}] should move tokens to "pendingUnstake" and subtract it from totalStaked`, async ({helper}) => {
199 const [staker, recepient] = getAccount(2);207 const [staker, recepient] = await getAccounts(2);
200 const totalStakedBefore = await helper.staking.getTotalStaked();208 const totalStakedBefore = await helper.staking.getTotalStaked();
201 const STAKE_AMOUNT = 900n * nominal;209 const STAKE_AMOUNT = 900n * nominal;
202210
222 {method: 'unstakePartial' as const},230 {method: 'unstakePartial' as const},
223 ].map(testCase => {231 ].map(testCase => {
224 itSub(`[${testCase.method}] should unlock balance after unlocking period ends and remove it from "pendingUnstake"`, async ({helper}) => {232 itSub(`[${testCase.method}] should unlock balance after unlocking period ends and remove it from "pendingUnstake"`, async ({helper}) => {
225 const [staker] = getAccount(1);233 const [staker] = await getAccounts(1);
226 await helper.staking.stake(staker, 100n * nominal);234 await helper.staking.stake(staker, 100n * nominal);
227 testCase.method === 'unstakeAll'235 testCase.method === 'unstakeAll'
228 ? await helper.staking.unstakeAll(staker)236 ? await helper.staking.unstakeAll(staker)
245 {method: 'unstakePartial' as const},253 {method: 'unstakePartial' as const},
246 ].map(testCase => {254 ].map(testCase => {
247 itSub(`[${testCase.method}] should successfully unstake multiple stakes`, async ({helper}) => {255 itSub(`[${testCase.method}] should successfully unstake multiple stakes`, async ({helper}) => {
248 const [staker] = getAccount(1);256 const [staker] = await getAccounts(1);
249 await helper.staking.stake(staker, 100n * nominal);257 await helper.staking.stake(staker, 100n * nominal);
250 await helper.staking.stake(staker, 200n * nominal);258 await helper.staking.stake(staker, 200n * nominal);
251 await helper.staking.stake(staker, 300n * nominal);259 await helper.staking.stake(staker, 300n * nominal);
285 {method: 'unstakePartial' as const},293 {method: 'unstakePartial' as const},
286 ].map(testCase => {294 ].map(testCase => {
287 itSub(`[${testCase.method}] should not have any effects if no active stakes`, async ({helper}) => {295 itSub(`[${testCase.method}] should not have any effects if no active stakes`, async ({helper}) => {
288 const [staker] = getAccount(1);296 const [staker] = await getAccounts(1);
289297
290 // unstake has no effect if no stakes at all298 // unstake has no effect if no stakes at all
291 testCase.method === 'unstakeAll'299 testCase.method === 'unstakeAll'
319 {method: 'unstakePartial' as const},327 {method: 'unstakePartial' as const},
320 ].map(testCase => {328 ].map(testCase => {
321 itSub(`[${testCase.method}] should create different pending-unlock for each unlocking stake`, async ({helper}) => {329 itSub(`[${testCase.method}] should create different pending-unlock for each unlocking stake`, async ({helper}) => {
322 const [staker] = getAccount(1);330 const [staker] = await getAccounts(1);
323 await helper.staking.stake(staker, 100n * nominal);331 await helper.staking.stake(staker, 100n * nominal);
324 testCase.method === 'unstakeAll'332 testCase.method === 'unstakeAll'
325 ? await helper.staking.unstakeAll(staker)333 ? await helper.staking.unstakeAll(staker)
342 {method: 'unstakePartial' as const},350 {method: 'unstakePartial' as const},
343 ].map(testCase => {351 ].map(testCase => {
344 itSub(`[${testCase.method}] should be possible for 3 accounts in one block`, async ({helper}) => {352 itSub(`[${testCase.method}] should be possible for 3 accounts in one block`, async ({helper}) => {
345 const stakers = getAccount(3);353 const stakers = await getAccounts(3);
346354
347 await Promise.all(stakers.map(staker => helper.staking.stake(staker, 100n * nominal)));355 await Promise.all(stakers.map(staker => helper.staking.stake(staker, 100n * nominal)));
348 await Promise.all(stakers.map(staker => {356 await Promise.all(stakers.map(staker => {
360368
361 itSub('should not be possible for more than 3 accounts in one block', async ({helper}) => {369 itSub('should not be possible for more than 3 accounts in one block', async ({helper}) => {
362 if (!await helper.arrange.isDevNode()) {370 if (!await helper.arrange.isDevNode()) {
363 const stakers = getAccount(10);371 const stakers = await getAccounts(10);
364372
365 await Promise.all(stakers.map(staker => helper.staking.stake(staker, 100n * nominal)));373 await Promise.all(stakers.map(staker => helper.staking.stake(staker, 100n * nominal)));
366 const unstakingResults = await Promise.allSettled(stakers.map((staker, i) => {374 const unstakingResults = await Promise.allSettled(stakers.map((staker, i) => {
375 });383 });
376384
377 itSub('Cannot partially unstake more than staked', async ({helper}) => {385 itSub('Cannot partially unstake more than staked', async ({helper}) => {
378 const [staker] = getAccount(1);386 const [staker] = await getAccounts(1);
379 // Staker stakes 300:387 // Staker stakes 300:
380 await helper.staking.stake(staker, 100n * nominal);388 await helper.staking.stake(staker, 100n * nominal);
381 await helper.staking.stake(staker, 200n * nominal);389 await helper.staking.stake(staker, 200n * nominal);
395 });403 });
396404
397 itSub('Can partially unstake arbitrary amount', async ({helper}) => {405 itSub('Can partially unstake arbitrary amount', async ({helper}) => {
398 const [staker] = getAccount(1);406 const [staker] = await getAccounts(1);
399 await helper.staking.stake(staker, 100n * nominal);407 await helper.staking.stake(staker, 100n * nominal);
400 await helper.staking.stake(staker, 200n * nominal);408 await helper.staking.stake(staker, 200n * nominal);
401409
429 });437 });
430438
431 itSub('can mix different type of unstakes', async ({helper}) => {439 itSub('can mix different type of unstakes', async ({helper}) => {
432 const [staker] = getAccount(1);440 const [staker] = await getAccounts(1);
433 await helper.staking.stake(staker, 100n * nominal);441 await helper.staking.stake(staker, 100n * nominal);
434 await helper.staking.stake(staker, 200n * nominal);442 await helper.staking.stake(staker, 200n * nominal);
435443
454 describe('collection sponsoring', () => {462 describe('collection sponsoring', () => {
455 itSub('should actually sponsor transactions', async ({helper}) => {463 itSub('should actually sponsor transactions', async ({helper}) => {
456 const api = helper.getApi();464 const api = helper.getApi();
457 const [collectionOwner, tokenSender, receiver] = getAccount(3);465 const [collectionOwner, tokenSender, receiver] = await getAccounts(3);
458 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'Name', description: 'Description', tokenPrefix: 'Prefix', limits: {sponsorTransferTimeout: 0}});466 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'Name', description: 'Description', tokenPrefix: 'Prefix', limits: {sponsorTransferTimeout: 0}});
459 const token = await collection.mintToken(collectionOwner, {Substrate: tokenSender.address});467 const token = await collection.mintToken(collectionOwner, {Substrate: tokenSender.address});
460 await helper.signTransaction(palletAdmin, api.tx.appPromotion.sponsorCollection(collection.collectionId));468 await helper.signTransaction(palletAdmin, api.tx.appPromotion.sponsorCollection(collection.collectionId));
471479
472 itSub('can not be set by non admin', async ({helper}) => {480 itSub('can not be set by non admin', async ({helper}) => {
473 const api = helper.getApi();481 const api = helper.getApi();
474 const [collectionOwner, nonAdmin] = getAccount(2);482 const [collectionOwner, nonAdmin] = await getAccounts(2);
475483
476 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion'});484 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion'});
477485
481489
482 itSub('should set pallet address as confirmed admin', async ({helper}) => {490 itSub('should set pallet address as confirmed admin', async ({helper}) => {
483 const api = helper.getApi();491 const api = helper.getApi();
484 const [collectionOwner, oldSponsor] = getAccount(2);492 const [collectionOwner, oldSponsor] = await getAccounts(2);
485493
486 // Can set sponsoring for collection without sponsor494 // Can set sponsoring for collection without sponsor
487 const collectionWithoutSponsor = await helper.nft.mintCollection(collectionOwner, {name: 'No-sponsor', description: 'New Collection', tokenPrefix: 'Promotion'});495 const collectionWithoutSponsor = await helper.nft.mintCollection(collectionOwner, {name: 'No-sponsor', description: 'New Collection', tokenPrefix: 'Promotion'});
503511
504 itSub('can be overwritten by collection owner', async ({helper}) => {512 itSub('can be overwritten by collection owner', async ({helper}) => {
505 const api = helper.getApi();513 const api = helper.getApi();
506 const [collectionOwner, newSponsor] = getAccount(2);514 const [collectionOwner, newSponsor] = await getAccounts(2);
507 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion'});515 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion'});
508 const collectionId = collection.collectionId;516 const collectionId = collection.collectionId;
509517
520 });528 });
521529
522 itSub('should not overwrite collection limits set by the owner earlier', async ({helper}) => {530 itSub('should not overwrite collection limits set by the owner earlier', async ({helper}) => {
531 const [owner] = await getAccounts(1);
523 const api = helper.getApi();532 const api = helper.getApi();
524 const limits = {ownerCanDestroy: true, ownerCanTransfer: true, sponsorTransferTimeout: 0};533 const limits = {ownerCanDestroy: true, ownerCanTransfer: true, sponsorTransferTimeout: 0};
525 const collectionWithLimits = await helper.nft.mintCollection(getAccount(1)[0], {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion', limits});534 const collectionWithLimits = await helper.nft.mintCollection(owner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion', limits});
526535
527 await expect(helper.signTransaction(palletAdmin, api.tx.appPromotion.sponsorCollection(collectionWithLimits.collectionId))).to.be.fulfilled;536 await expect(helper.signTransaction(palletAdmin, api.tx.appPromotion.sponsorCollection(collectionWithLimits.collectionId))).to.be.fulfilled;
528 expect((await collectionWithLimits.getData())?.raw.limits).to.be.deep.contain(limits);537 expect((await collectionWithLimits.getData())?.raw.limits).to.be.deep.contain(limits);
529 });538 });
530539
531 itSub('should reject transaction if collection doesn\'t exist', async ({helper}) => {540 itSub('should reject transaction if collection doesn\'t exist', async ({helper}) => {
532 const api = helper.getApi();541 const api = helper.getApi();
533 const [collectionOwner] = getAccount(1);542 const [collectionOwner] = await getAccounts(1);
534543
535 // collection has never existed544 // collection has never existed
536 await expect(helper.signTransaction(palletAdmin, api.tx.appPromotion.sponsorCollection(999999999))).to.be.rejected;545 await expect(helper.signTransaction(palletAdmin, api.tx.appPromotion.sponsorCollection(999999999))).to.be.rejected;
545 describe('stopSponsoringCollection', () => {554 describe('stopSponsoringCollection', () => {
546 itSub('can not be called by non-admin', async ({helper}) => {555 itSub('can not be called by non-admin', async ({helper}) => {
547 const api = helper.getApi();556 const api = helper.getApi();
548 const [collectionOwner, nonAdmin] = getAccount(2);557 const [collectionOwner, nonAdmin] = await getAccounts(2);
549 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion'});558 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion'});
550559
551 await expect(helper.signTransaction(palletAdmin, api.tx.appPromotion.sponsorCollection(collection.collectionId))).to.be.fulfilled;560 await expect(helper.signTransaction(palletAdmin, api.tx.appPromotion.sponsorCollection(collection.collectionId))).to.be.fulfilled;
556565
557 itSub('should set sponsoring as disabled', async ({helper}) => {566 itSub('should set sponsoring as disabled', async ({helper}) => {
558 const api = helper.getApi();567 const api = helper.getApi();
559 const [collectionOwner, recepient] = getAccount(2);568 const [collectionOwner, recepient] = await getAccounts(2);
560 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion', limits: {sponsorTransferTimeout: 0}});569 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion', limits: {sponsorTransferTimeout: 0}});
561 const token = await collection.mintToken(collectionOwner, {Substrate: collectionOwner.address});570 const token = await collection.mintToken(collectionOwner, {Substrate: collectionOwner.address});
562571
574583
575 itSub('should not affect collection which is not sponsored by pallete', async ({helper}) => {584 itSub('should not affect collection which is not sponsored by pallete', async ({helper}) => {
576 const api = helper.getApi();585 const api = helper.getApi();
577 const [collectionOwner] = getAccount(1);586 const [collectionOwner] = await getAccounts(1);
578 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion', pendingSponsor: collectionOwner.address});587 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion', pendingSponsor: collectionOwner.address});
579 await collection.confirmSponsorship(collectionOwner);588 await collection.confirmSponsorship(collectionOwner);
580589
584 });593 });
585594
586 itSub('should reject transaction if collection does not exist', async ({helper}) => {595 itSub('should reject transaction if collection does not exist', async ({helper}) => {
587 const [collectionOwner] = getAccount(1);596 const [collectionOwner] = await getAccounts(1);
588 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion'});597 const collection = await helper.nft.mintCollection(collectionOwner, {name: 'New', description: 'New Collection', tokenPrefix: 'Promotion'});
589598
590 await collection.burn(collectionOwner);599 await collection.burn(collectionOwner);
658 });667 });
659668
660 itEth('can not be set by non admin', async ({helper}) => {669 itEth('can not be set by non admin', async ({helper}) => {
661 const [nonAdmin] = getAccount(1);670 const [nonAdmin] = await getAccounts(1);
662 const contractOwner = (await helper.eth.createAccountWithBalance(donor, 1000n)).toLowerCase();671 const contractOwner = (await helper.eth.createAccountWithBalance(donor, 1000n)).toLowerCase();
663 const flipper = await helper.eth.deployFlipper(contractOwner); // await deployFlipper(web3, contractOwner);672 const flipper = await helper.eth.deployFlipper(contractOwner); // await deployFlipper(web3, contractOwner);
664 const contractHelper = await helper.ethNativeContract.contractHelpers(contractOwner);673 const contractHelper = await helper.ethNativeContract.contractHelpers(contractOwner);
740 });749 });
741750
742 itEth('can not be called by non-admin', async ({helper}) => {751 itEth('can not be called by non-admin', async ({helper}) => {
743 const [nonAdmin] = getAccount(1);752 const [nonAdmin] = await getAccounts(1);
744 const contractOwner = (await helper.eth.createAccountWithBalance(donor, 1000n)).toLowerCase();753 const contractOwner = (await helper.eth.createAccountWithBalance(donor, 1000n)).toLowerCase();
745 const flipper = await helper.eth.deployFlipper(contractOwner);754 const flipper = await helper.eth.deployFlipper(contractOwner);
746755
750 });759 });
751760
752 itEth('should not affect a contract which is not sponsored by pallete', async ({helper}) => {761 itEth('should not affect a contract which is not sponsored by pallete', async ({helper}) => {
753 const [nonAdmin] = getAccount(1);762 const [nonAdmin] = await getAccounts(1);
754 const contractOwner = (await helper.eth.createAccountWithBalance(donor, 1000n)).toLowerCase();763 const contractOwner = (await helper.eth.createAccountWithBalance(donor, 1000n)).toLowerCase();
755 const flipper = await helper.eth.deployFlipper(contractOwner);764 const flipper = await helper.eth.deployFlipper(contractOwner);
756 const contractHelper = await helper.ethNativeContract.contractHelpers(contractOwner);765 const contractHelper = await helper.ethNativeContract.contractHelpers(contractOwner);
762771
763 describe('payoutStakers', () => {772 describe('payoutStakers', () => {
764 itSub('can not be called by non admin', async ({helper}) => {773 itSub('can not be called by non admin', async ({helper}) => {
765 const [nonAdmin] = getAccount(1);774 const [nonAdmin] = await getAccounts(1);
766 await expect(helper.admin.payoutStakers(nonAdmin, 100)).to.be.rejectedWith('appPromotion.NoPermission');775 await expect(helper.admin.payoutStakers(nonAdmin, 100)).to.be.rejectedWith('appPromotion.NoPermission');
767 });776 });
768777
769 itSub('should increase total staked', async ({helper}) => {778 itSub('should increase total staked', async ({helper}) => {
770 const [staker] = getAccount(1);779 const [staker] = await getAccounts(1);
771 const totalStakedBefore = await helper.staking.getTotalStaked();780 const totalStakedBefore = await helper.staking.getTotalStaked();
772 await helper.staking.stake(staker, 100n * nominal);781 await helper.staking.stake(staker, 100n * nominal);
773782
784 });793 });
785794
786 itSub('should credit 0.05% for staking period', async ({helper}) => {795 itSub('should credit 0.05% for staking period', async ({helper}) => {
787 const [staker] = getAccount(1);796 const [staker] = await getAccounts(1);
788797
789 await waitPromotionPeriodDoesntEnd(helper);798 await waitPromotionPeriodDoesntEnd(helper);
790799
810 });819 });
811820
812 itSub('shoud be paid for more than one period if payments was missed', async ({helper}) => {821 itSub('shoud be paid for more than one period if payments was missed', async ({helper}) => {
813 const [staker] = getAccount(1);822 const [staker] = await getAccounts(1);
814823
815 await helper.staking.stake(staker, 100n * nominal);824 await helper.staking.stake(staker, 100n * nominal);
816 // wait for two rewards are available:825 // wait for two rewards are available:
829838
830 itSub('should not be credited for pending-unstaked tokens', async ({helper}) => {839 itSub('should not be credited for pending-unstaked tokens', async ({helper}) => {
831 // staker unstakes before rewards been payed840 // staker unstakes before rewards been payed
832 const [staker] = getAccount(1);841 const [staker] = await getAccounts(1);
833 await helper.staking.stake(staker, 100n * nominal);842 await helper.staking.stake(staker, 100n * nominal);
834 const [stake] = await helper.staking.getTotalStakedPerBlock({Substrate: staker.address});843 const [stake] = await helper.staking.getTotalStakedPerBlock({Substrate: staker.address});
835 await helper.wait.forRelayBlockNumber(rewardAvailableInBlock(stake.block) + LOCKING_PERIOD);844 await helper.wait.forRelayBlockNumber(rewardAvailableInBlock(stake.block) + LOCKING_PERIOD);
844 });853 });
845854
846 itSub('should bring compound interest', async ({helper}) => {855 itSub('should bring compound interest', async ({helper}) => {
847 const [staker] = getAccount(1);856 const [staker] = await getAccounts(1);
848857
849 await helper.staking.stake(staker, 100n * nominal);858 await helper.staking.stake(staker, 100n * nominal);
850859
862 });871 });
863872
864 itSub('can calculate reward for tiny stake', async ({helper}) => {873 itSub('can calculate reward for tiny stake', async ({helper}) => {
865 const [staker] = getAccount(1);874 const [staker] = await getAccounts(1);
866 await helper.staking.stake(staker, 100n * nominal);875 await helper.staking.stake(staker, 100n * nominal);
867 await helper.staking.stake(staker, 100n * nominal);876 await helper.staking.stake(staker, 100n * nominal);
868 await helper.staking.unstakePartial(staker, 100n * nominal - 1n);877 await helper.staking.unstakePartial(staker, 100n * nominal - 1n);
875 });884 });
876885
877 itSub('can eventually pay all rewards', async ({helper}) => {886 itSub('can eventually pay all rewards', async ({helper}) => {
878 const stakers = getAccount(30);887 const stakers = await getAccounts(30);
879 // Create 30 stakes:888 // Create 30 stakes:
880 await Promise.all(stakers.map(staker => helper.staking.stake(staker, 100n * nominal)));889 await Promise.all(stakers.map(staker => helper.staking.stake(staker, 100n * nominal)));
881890
888 unstakingTxs.push(helper.staking.unstakePartial(staker, 100n * nominal - 1n));897 unstakingTxs.push(helper.staking.unstakePartial(staker, 100n * nominal - 1n));
889 }898 }
890899
891 const [staker] = getAccount(1);900 const [staker] = await getAccounts(1);
892 await helper.staking.stake(staker, 100n * nominal);901 await helper.staking.stake(staker, 100n * nominal);
893 const [stake] = await helper.staking.getTotalStakedPerBlock({Substrate: staker.address});902 const [stake] = await helper.staking.getTotalStakedPerBlock({Substrate: staker.address});
894 await helper.wait.forRelayBlockNumber(rewardAvailableInBlock(stake.block));903 await helper.wait.forRelayBlockNumber(rewardAvailableInBlock(stake.block));
909 const unstakeParams = testCase.method === 'unstakePartial'918 const unstakeParams = testCase.method === 'unstakePartial'
910 ? [100n * nominal - 1n]919 ? [100n * nominal - 1n]
911 : [];920 : [];
912 const [staker] = getAccount(1);921 const [staker] = await getAccounts(1);
913 await helper.staking.stake(staker, 100n * nominal);922 await helper.staking.stake(staker, 100n * nominal);
914 await helper.staking.stake(staker, 200n * nominal);923 await helper.staking.stake(staker, 200n * nominal);
915 const {result} = await helper.executeExtrinsic(staker, `api.tx.appPromotion.${testCase.method}`, unstakeParams);924 const {result} = await helper.executeExtrinsic(staker, `api.tx.appPromotion.${testCase.method}`, unstakeParams);
923 });932 });
924933
925 itSub('stake', async ({helper}) => {934 itSub('stake', async ({helper}) => {
926 const [staker] = getAccount(1);935 const [staker] = await getAccounts(1);
927 const {result} = await helper.executeExtrinsic(staker, 'api.tx.appPromotion.stake', [100n * nominal]);936 const {result} = await helper.executeExtrinsic(staker, 'api.tx.appPromotion.stake', [100n * nominal]);
928937
929 const event = result.events.find(e => e.event.section === 'appPromotion' && e.event.method === 'Stake');938 const event = result.events.find(e => e.event.section === 'appPromotion' && e.event.method === 'Stake');
935944
936 // Flaky945 // Flaky
937 itSub.skip('payoutStakers', async ({helper}) => {946 itSub.skip('payoutStakers', async ({helper}) => {
938 const [staker1, staker2] = getAccount(2);947 const [staker1, staker2] = await getAccounts(2);
939 const STAKE1 = 100n * nominal;948 const STAKE1 = 100n * nominal;
940 const STAKE2 = 200n * nominal;949 const STAKE2 = 200n * nominal;
941 await helper.staking.stake(staker1, STAKE1);950 await helper.staking.stake(staker1, STAKE1);