12345678910111213141516import {IKeyringPair} from '@polkadot/types/types';17import {IEthCrossAccountId} from '../util/playgrounds/types';18import {usingEthPlaygrounds, itEth, expect, EthUniqueHelper} from './util';1920async function recordEthFee(helper: EthUniqueHelper, userAddress: string, call: () => Promise<any>) {21 const before = await helper.balance.getSubstrate(helper.address.ethToSubstrate(userAddress));22 await call();23 await helper.wait.newBlocks(1);24 const after = await helper.balance.getSubstrate(helper.address.ethToSubstrate(userAddress));2526 expect(after < before).to.be.true;2728 return before - after;29}3031describe('Add collection admins', () => {32 let donor: IKeyringPair;3334 before(async function() {35 await usingEthPlaygrounds(async (_helper, privateKey) => {36 donor = await privateKey({filename: __filename});37 });38 });3940 itEth('Add admin by owner', async ({helper}) => {41 const owner = await helper.eth.createAccountWithBalance(donor);42 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');43 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);4445 const newAdmin = helper.eth.createAccount();4647 await collectionEvm.methods.addCollectionAdmin(newAdmin).send();48 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);49 expect(adminList[0].asEthereum.toString().toLocaleLowerCase())50 .to.be.eq(newAdmin.toLocaleLowerCase());51 });5253 itEth.skip('Add substrate admin by owner', async ({helper}) => {54 const owner = await helper.eth.createAccountWithBalance(donor);55 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');56 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);5758 const [newAdmin] = await helper.arrange.createAccounts([10n], donor);59 await collectionEvm.methods.addCollectionAdminSubstrate(newAdmin.addressRaw).send();6061 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);62 expect(adminList[0].asSubstrate.toString().toLocaleLowerCase())63 .to.be.eq(newAdmin.address.toLocaleLowerCase());64 });6566 itEth('Verify owner or admin', async ({helper}) => {67 const owner = await helper.eth.createAccountWithBalance(donor);68 const {collectionAddress} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');6970 const newAdmin = helper.eth.createAccount();71 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);72 73 expect(await collectionEvm.methods.isOwnerOrAdmin(newAdmin).call()).to.be.false;74 await collectionEvm.methods.addCollectionAdmin(newAdmin).send();75 expect(await collectionEvm.methods.isOwnerOrAdmin(newAdmin).call()).to.be.true;76 });77 78 itEth.skip('Check adminlist', async ({helper}) => {79 const owner = await helper.eth.createAccountWithBalance(donor);80 81 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');82 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);83 84 const admin1 = helper.eth.createAccount();85 const [admin2] = await helper.arrange.createAccounts([10n], donor);86 await collectionEvm.methods.addCollectionAdmin(admin1).send();87 await collectionEvm.methods.addCollectionAdminSubstrate(admin2.addressRaw).send();8889 const adminListRpc = await helper.collection.getAdmins(collectionId);90 let adminListEth = await collectionEvm.methods.collectionAdmins().call();91 adminListEth = adminListEth.map((element: IEthCrossAccountId) => {92 return helper.address.convertCrossAccountFromEthCrossAcoount(element);93 });94 expect(adminListRpc).to.be.like(adminListEth);95 }); 96 97 itEth('(!negative tests!) Add admin by ADMIN is not allowed', async ({helper}) => {98 const owner = await helper.eth.createAccountWithBalance(donor);99 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');100101 const admin = await helper.eth.createAccountWithBalance(donor);102 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);103 await collectionEvm.methods.addCollectionAdmin(admin).send();104105 const user = helper.eth.createAccount();106 await expect(collectionEvm.methods.addCollectionAdmin(user).call({from: admin}))107 .to.be.rejectedWith('NoPermission');108109 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);110 expect(adminList.length).to.be.eq(1);111 expect(adminList[0].asEthereum.toString().toLocaleLowerCase())112 .to.be.eq(admin.toLocaleLowerCase());113 });114115 itEth('(!negative tests!) Add admin by USER is not allowed', async ({helper}) => {116 const owner = await helper.eth.createAccountWithBalance(donor);117 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');118119 const notAdmin = await helper.eth.createAccountWithBalance(donor);120 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);121122 const user = helper.eth.createAccount();123 await expect(collectionEvm.methods.addCollectionAdmin(user).call({from: notAdmin}))124 .to.be.rejectedWith('NoPermission');125126 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);127 expect(adminList.length).to.be.eq(0);128 });129130 itEth.skip('(!negative tests!) Add substrate admin by ADMIN is not allowed', async ({helper}) => {131 const owner = await helper.eth.createAccountWithBalance(donor);132 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');133134 const admin = await helper.eth.createAccountWithBalance(donor);135 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);136 await collectionEvm.methods.addCollectionAdmin(admin).send();137138 const [notAdmin] = await helper.arrange.createAccounts([10n], donor);139 await expect(collectionEvm.methods.addCollectionAdminSubstrate(notAdmin.addressRaw).call({from: admin}))140 .to.be.rejectedWith('NoPermission');141142 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);143 expect(adminList.length).to.be.eq(1);144 expect(adminList[0].asEthereum.toString().toLocaleLowerCase())145 .to.be.eq(admin.toLocaleLowerCase());146 });147148 itEth.skip('(!negative tests!) Add substrate admin by USER is not allowed', async ({helper}) => {149 const owner = await helper.eth.createAccountWithBalance(donor);150 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');151152 const notAdmin0 = await helper.eth.createAccountWithBalance(donor);153 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);154 const [notAdmin1] = await helper.arrange.createAccounts([10n], donor);155 await expect(collectionEvm.methods.addCollectionAdminSubstrate(notAdmin1.addressRaw).call({from: notAdmin0}))156 .to.be.rejectedWith('NoPermission');157158 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);159 expect(adminList.length).to.be.eq(0);160 });161});162163describe('Remove collection admins', () => {164 let donor: IKeyringPair;165166 before(async function() {167 await usingEthPlaygrounds(async (_helper, privateKey) => {168 donor = await privateKey({filename: __filename});169 });170 });171172 itEth('Remove admin by owner', async ({helper}) => {173 const owner = await helper.eth.createAccountWithBalance(donor);174 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');175176 const newAdmin = helper.eth.createAccount();177 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);178 await collectionEvm.methods.addCollectionAdmin(newAdmin).send();179180 {181 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);182 expect(adminList.length).to.be.eq(1);183 expect(adminList[0].asEthereum.toString().toLocaleLowerCase())184 .to.be.eq(newAdmin.toLocaleLowerCase());185 }186187 await collectionEvm.methods.removeCollectionAdmin(newAdmin).send();188 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);189 expect(adminList.length).to.be.eq(0);190 });191192 itEth.skip('Remove substrate admin by owner', async ({helper}) => {193 const owner = await helper.eth.createAccountWithBalance(donor);194 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');195196 const [newAdmin] = await helper.arrange.createAccounts([10n], donor);197 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);198 await collectionEvm.methods.addCollectionAdminSubstrate(newAdmin.addressRaw).send();199 {200 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);201 expect(adminList[0].asSubstrate.toString().toLocaleLowerCase())202 .to.be.eq(newAdmin.address.toLocaleLowerCase());203 }204205 await collectionEvm.methods.removeCollectionAdminSubstrate(newAdmin.addressRaw).send();206 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);207 expect(adminList.length).to.be.eq(0);208 });209210 itEth('(!negative tests!) Remove admin by ADMIN is not allowed', async ({helper}) => {211 const owner = await helper.eth.createAccountWithBalance(donor);212 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');213214 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);215216 const admin0 = await helper.eth.createAccountWithBalance(donor);217 await collectionEvm.methods.addCollectionAdmin(admin0).send();218 const admin1 = await helper.eth.createAccountWithBalance(donor);219 await collectionEvm.methods.addCollectionAdmin(admin1).send();220221 await expect(collectionEvm.methods.removeCollectionAdmin(admin1).call({from: admin0}))222 .to.be.rejectedWith('NoPermission');223 {224 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);225 expect(adminList.length).to.be.eq(2);226 expect(adminList.toString().toLocaleLowerCase())227 .to.be.deep.contains(admin0.toLocaleLowerCase())228 .to.be.deep.contains(admin1.toLocaleLowerCase());229 }230 });231232 itEth('(!negative tests!) Remove admin by USER is not allowed', async ({helper}) => {233 const owner = await helper.eth.createAccountWithBalance(donor);234 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');235236 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);237238 const admin = await helper.eth.createAccountWithBalance(donor);239 await collectionEvm.methods.addCollectionAdmin(admin).send();240 const notAdmin = helper.eth.createAccount();241242 await expect(collectionEvm.methods.removeCollectionAdmin(admin).call({from: notAdmin}))243 .to.be.rejectedWith('NoPermission');244 {245 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);246 expect(adminList[0].asEthereum.toString().toLocaleLowerCase())247 .to.be.eq(admin.toLocaleLowerCase());248 expect(adminList.length).to.be.eq(1);249 }250 });251252 itEth.skip('(!negative tests!) Remove substrate admin by ADMIN is not allowed', async ({helper}) => {253 const owner = await helper.eth.createAccountWithBalance(donor);254 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');255256 const [adminSub] = await helper.arrange.createAccounts([10n], donor);257 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);258 await collectionEvm.methods.addCollectionAdminSubstrate(adminSub.addressRaw).send();259 const adminEth = await helper.eth.createAccountWithBalance(donor);260 await collectionEvm.methods.addCollectionAdmin(adminEth).send();261262 await expect(collectionEvm.methods.removeCollectionAdminSubstrate(adminSub.addressRaw).call({from: adminEth}))263 .to.be.rejectedWith('NoPermission');264265 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);266 expect(adminList.length).to.be.eq(2);267 expect(adminList.toString().toLocaleLowerCase())268 .to.be.deep.contains(adminSub.address.toLocaleLowerCase())269 .to.be.deep.contains(adminEth.toLocaleLowerCase());270 });271272 itEth.skip('(!negative tests!) Remove substrate admin by USER is not allowed', async ({helper}) => {273 const owner = await helper.eth.createAccountWithBalance(donor);274 const {collectionAddress, collectionId} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');275276 const [adminSub] = await helper.arrange.createAccounts([10n], donor);277 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);278 await collectionEvm.methods.addCollectionAdminSubstrate(adminSub.addressRaw).send();279 const notAdminEth = await helper.eth.createAccountWithBalance(donor);280281 await expect(collectionEvm.methods.removeCollectionAdminSubstrate(adminSub.addressRaw).call({from: notAdminEth}))282 .to.be.rejectedWith('NoPermission');283284 const adminList = await helper.callRpc('api.rpc.unique.adminlist', [collectionId]);285 expect(adminList.length).to.be.eq(1);286 expect(adminList[0].asSubstrate.toString().toLocaleLowerCase())287 .to.be.eq(adminSub.address.toLocaleLowerCase());288 });289});290291describe('Change owner tests', () => {292 let donor: IKeyringPair;293294 before(async function() {295 await usingEthPlaygrounds(async (_helper, privateKey) => {296 donor = await privateKey({filename: __filename});297 });298 });299300 itEth('Change owner', async ({helper}) => {301 const owner = await helper.eth.createAccountWithBalance(donor);302 const newOwner = await helper.eth.createAccountWithBalance(donor);303 const {collectionAddress} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');304 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);305306 await collectionEvm.methods.changeCollectionOwner(newOwner).send();307308 expect(await collectionEvm.methods.isOwnerOrAdmin(owner).call()).to.be.false;309 expect(await collectionEvm.methods.isOwnerOrAdmin(newOwner).call()).to.be.true;310 });311312 itEth('change owner call fee', async ({helper}) => {313 const owner = await helper.eth.createAccountWithBalance(donor);314 const newOwner = await helper.eth.createAccountWithBalance(donor);315 const {collectionAddress} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');316 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);317 const cost = await recordEthFee(helper, owner, () => collectionEvm.methods.changeCollectionOwner(newOwner).send());318 expect(cost < BigInt(0.2 * Number(helper.balance.getOneTokenNominal())));319 expect(cost > 0);320 });321322 itEth('(!negative tests!) call setOwner by non owner', async ({helper}) => {323 const owner = await helper.eth.createAccountWithBalance(donor);324 const newOwner = await helper.eth.createAccountWithBalance(donor);325 const {collectionAddress} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');326 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);327328 await expect(collectionEvm.methods.changeCollectionOwner(newOwner).send({from: newOwner})).to.be.rejected;329 expect(await collectionEvm.methods.isOwnerOrAdmin(newOwner).call()).to.be.false;330 });331});332333describe('Change substrate owner tests', () => {334 let donor: IKeyringPair;335336 before(async function() {337 await usingEthPlaygrounds(async (_helper, privateKey) => {338 donor = await privateKey({filename: __filename});339 });340 });341342 itEth.skip('Change owner', async ({helper}) => {343 const owner = await helper.eth.createAccountWithBalance(donor);344 const [newOwner] = await helper.arrange.createAccounts([10n], donor);345 const {collectionAddress} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');346 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);347348 expect(await collectionEvm.methods.isOwnerOrAdmin(owner).call()).to.be.true;349 expect(await collectionEvm.methods.isOwnerOrAdminSubstrate(newOwner.addressRaw).call()).to.be.false;350351 await collectionEvm.methods.setOwnerSubstrate(newOwner.addressRaw).send();352353 expect(await collectionEvm.methods.isOwnerOrAdmin(owner).call()).to.be.false;354 expect(await collectionEvm.methods.isOwnerOrAdminSubstrate(newOwner.addressRaw).call()).to.be.true;355 });356357 itEth.skip('change owner call fee', async ({helper}) => {358 const owner = await helper.eth.createAccountWithBalance(donor);359 const [newOwner] = await helper.arrange.createAccounts([10n], donor);360 const {collectionAddress} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');361 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);362363 const cost = await recordEthFee(helper, owner, () => collectionEvm.methods.setOwnerSubstrate(newOwner.addressRaw).send());364 expect(cost < BigInt(0.2 * Number(helper.balance.getOneTokenNominal())));365 expect(cost > 0);366 });367368 itEth.skip('(!negative tests!) call setOwner by non owner', async ({helper}) => {369 const owner = await helper.eth.createAccountWithBalance(donor);370 const otherReceiver = await helper.eth.createAccountWithBalance(donor);371 const [newOwner] = await helper.arrange.createAccounts([10n], donor);372 const {collectionAddress} = await helper.eth.createNFTCollection(owner, 'A', 'B', 'C');373 const collectionEvm = helper.ethNativeContract.collection(collectionAddress, 'nft', owner);374375 await expect(collectionEvm.methods.setOwnerSubstrate(newOwner.addressRaw).send({from: otherReceiver})).to.be.rejected;376 expect(await collectionEvm.methods.isOwnerOrAdminSubstrate(newOwner.addressRaw).call()).to.be.false;377 });378});