From 1bfde6203f120c82081321b358851430d147947d Mon Sep 17 00:00:00 2001 From: Michal Iskierko Date: Thu, 28 Mar 2024 22:23:40 +0100 Subject: [PATCH] feat(@desktop/communitytokens): Move community tokens logic to status-go. Nim part is only responsible for catching the signal about handled transaction and update UI. Added CommunityTokenTransactionStatusChangedSignal. Issue #4351 --- .../core/signals/remote_signals/community.nim | 24 + .../signals/remote_signals/signal_type.nim | 1 + src/app/core/signals/signals_manager.nim | 1 + .../main/communities/tokens/controller.nim | 12 +- .../main/communities/tokens/module.nim | 49 +- .../service/community_tokens/async_tasks.nim | 6 +- .../community_tokens/dto/community_token.nim | 3 - .../dto/deployment_parameters.nim | 17 +- .../service/community_tokens/service.nim | 437 ++++++------------ src/backend/community_tokens.nim | 12 +- 10 files changed, 226 insertions(+), 336 deletions(-) diff --git a/src/app/core/signals/remote_signals/community.nim b/src/app/core/signals/remote_signals/community.nim index 5397e408c9..841d98785e 100644 --- a/src/app/core/signals/remote_signals/community.nim +++ b/src/app/core/signals/remote_signals/community.nim @@ -2,6 +2,7 @@ import json, tables import base import ../../../../app_service/service/community/dto/[community] +import ../../../../app_service/service/community_tokens/dto/community_token import ../../../../app_service/service/chat/dto/[chat] import signal_type @@ -63,6 +64,15 @@ type DiscordChannelImportFinishedSignal* = ref object of Signal communityId*: string channelId*: string +type CommunityTokenTransactionStatusChangedSignal* = ref object of Signal + transactionType*: string + success*: bool + hash*: string + communityToken*: CommunityTokenDto + ownerToken*: CommunityTokenDto + masterToken*: CommunityTokenDto + errorString*: string + proc fromEvent*(T: type CommunitySignal, event: JsonNode): CommunitySignal = result = CommunitySignal() result.signalType = SignalType.CommunityFound @@ -226,3 +236,17 @@ proc downloadingHistoryArchivesFinishedFromEvent*(T: type HistoryArchivesSignal, result = HistoryArchivesSignal() result.communityId = event["event"]{"communityId"}.getStr() result.signalType = SignalType.DownloadingHistoryArchivesFinished + +proc fromEvent*(T: type CommunityTokenTransactionStatusChangedSignal, event: JsonNode): CommunityTokenTransactionStatusChangedSignal = + result = CommunityTokenTransactionStatusChangedSignal() + result.transactionType = event["event"]{"transactionType"}.getStr() + result.success = event["event"]{"success"}.getBool() + result.hash = event["event"]{"hash"}.getStr() + if event["event"].hasKey("communityToken"): + result.communityToken = toCommunityTokenDto(event["event"]{"communityToken"}) + if event["event"].hasKey("ownerToken"): + result.ownerToken = toCommunityTokenDto(event["event"]{"ownerToken"}) + if event["event"].hasKey("masterToken"): + result.masterToken = toCommunityTokenDto(event["event"]{"masterToken"}) + result.errorString = event["event"]{"errorString"}.getStr() + result.signalType = SignalType.CommunityTokenTransactionStatusChanged \ No newline at end of file diff --git a/src/app/core/signals/remote_signals/signal_type.nim b/src/app/core/signals/remote_signals/signal_type.nim index 4e4e4157fb..eaa93bc6ce 100644 --- a/src/app/core/signals/remote_signals/signal_type.nim +++ b/src/app/core/signals/remote_signals/signal_type.nim @@ -60,6 +60,7 @@ type SignalType* {.pure.} = enum LocalPairing = "localPairing" DBReEncryptionStarted = "db.reEncryption.started" DBReEncryptionFinished = "db.reEncryption.finished" + CommunityTokenTransactionStatusChanged = "communityToken.communityTokenTransactionStatusChanged" Unknown proc event*(self:SignalType):string = diff --git a/src/app/core/signals/signals_manager.nim b/src/app/core/signals/signals_manager.nim index 0afe1d0dc4..aa1f318e29 100644 --- a/src/app/core/signals/signals_manager.nim +++ b/src/app/core/signals/signals_manager.nim @@ -129,6 +129,7 @@ QtObject: of SignalType.WakuBackedUpWatchOnlyAccount: WakuBackedUpWatchOnlyAccountSignal.fromEvent(jsonSignal) # pairing of SignalType.LocalPairing: LocalPairingSignal.fromEvent(jsonSignal) + of SignalType.CommunityTokenTransactionStatusChanged: CommunityTokenTransactionStatusChangedSignal.fromEvent(jsonSignal) else: Signal() result.signalType = signalType diff --git a/src/app/modules/main/communities/tokens/controller.nim b/src/app/modules/main/communities/tokens/controller.nim index db126fbba3..73f3ffd1d7 100644 --- a/src/app/modules/main/communities/tokens/controller.nim +++ b/src/app/modules/main/communities/tokens/controller.nim @@ -106,15 +106,13 @@ proc init*(self: Controller) = self.events.on(SIGNAL_COMMUNITY_TOKENS_CHANGED) do(e:Args): self.communityTokensService.getAllCommunityTokensAsync() -proc deployContract*(self: Controller, communityId: string, addressFrom: string, password: string, deploymentParams: DeploymentParameters, tokenMetadata: CommunityTokensMetadataDto, tokenImageCropInfoJson: string, chainId: int) = - self.communityTokensService.deployContract(communityId, addressFrom, password, deploymentParams, tokenMetadata, tokenImageCropInfoJson, chainId) +proc deployContract*(self: Controller, communityId: string, addressFrom: string, password: string, deploymentParams: DeploymentParameters, chainId: int) = + self.communityTokensService.deployContract(communityId, addressFrom, password, deploymentParams, chainId) proc deployOwnerContracts*(self: Controller, communityId: string, addressFrom: string, password: string, - ownerDeploymentParams: DeploymentParameters, ownerTokenMetadata: CommunityTokensMetadataDto, - masterDeploymentParams: DeploymentParameters, masterTokenMetadata: CommunityTokensMetadataDto, - tokenImageCropInfoJson: string, chainId: int) = - self.communityTokensService.deployOwnerContracts(communityId, addressFrom, password, ownerDeploymentParams, ownerTokenMetadata, - masterDeploymentParams, masterTokenMetadata, tokenImageCropInfoJson, chainId) + ownerDeploymentParams: DeploymentParameters, masterDeploymentParams: DeploymentParameters, chainId: int) = + self.communityTokensService.deployOwnerContracts(communityId, addressFrom, password, ownerDeploymentParams, + masterDeploymentParams, chainId) proc removeCommunityToken*(self: Controller, communityId: string, chainId: int, address: string) = self.communityTokensService.removeCommunityToken(communityId, chainId, address) diff --git a/src/app/modules/main/communities/tokens/module.nim b/src/app/modules/main/communities/tokens/module.nim index fc89e12aee..f296114cf5 100644 --- a/src/app/modules/main/communities/tokens/module.nim +++ b/src/app/modules/main/communities/tokens/module.nim @@ -37,16 +37,12 @@ type tempChainId: int tempContractAddress: string tempDeploymentParams: DeploymentParameters - tempTokenMetadata: CommunityTokensMetadataDto - tempTokenImageCropInfoJson: string tempWalletAddresses: seq[string] tempContractAction: ContractAction tempContractUniqueKey: string tempAmount: Uint256 tempOwnerDeploymentParams: DeploymentParameters tempMasterDeploymentParams: DeploymentParameters - tempOwnerTokenMetadata: CommunityTokensMetadataDto - tempMasterTokenMetadata: CommunityTokensMetadataDto tempOwnerTokenCommunity: CommunityDto proc newCommunityTokensModule*( @@ -71,8 +67,6 @@ method resetTempValues(self:Module) = self.tempAddressFrom = "" self.tempCommunityId = "" self.tempDeploymentParams = DeploymentParameters() - self.tempTokenMetadata = CommunityTokensMetadataDto() - self.tempTokenImageCropInfoJson = "" self.tempChainId = 0 self.tempContractAddress = "" self.tempWalletAddresses = @[] @@ -80,6 +74,8 @@ method resetTempValues(self:Module) = self.tempTokenAndAmountList = @[] self.tempWalletAndAmountList = @[] self.tempContractUniqueKey = "" + self.tempOwnerDeploymentParams = DeploymentParameters() + self.tempMasterDeploymentParams = DeploymentParameters() method load*(self: Module) = singletonInstance.engine.setRootContextProperty("communityTokensModule", self.viewVariant) @@ -186,9 +182,10 @@ method deployCollectibles*(self: Module, communityId: string, fromAddress: strin self.tempDeploymentParams.tokenUri = utl.changeCommunityKeyCompression(communityId) & "/" self.tempDeploymentParams.ownerTokenAddress = ownerTokenAddress self.tempDeploymentParams.masterTokenAddress = masterTokenAddress - self.tempTokenMetadata.tokenType = TokenType.ERC721 - self.tempTokenMetadata.description = description - self.tempTokenImageCropInfoJson = imageCropInfoJson + self.tempDeploymentParams.tokenType = TokenType.ERC721 + self.tempDeploymentParams.description = description + self.tempDeploymentParams.croppedImageJson = imageCropInfoJson + self.tempDeploymentParams.communityId = communityId self.tempContractAction = ContractAction.Deploy self.authenticate() @@ -196,8 +193,12 @@ proc createOwnerAndMasterDeploymentParams(self: Module, communityId: string): (D let communityDto = self.controller.getCommunityById(communityId) let commName = communityDto.name let commNameShort = try: commName[0 .. 2].toUpper except: commName.toUpper - return (DeploymentParameters(name: "Owner-" & commName, symbol: "OWN" & commNameShort, supply: stint.u256("1"), infiniteSupply: false, transferable: true, remoteSelfDestruct: false, tokenUri: utl.changeCommunityKeyCompression(communityId) & "/"), - DeploymentParameters(name: "TMaster-" & commName, symbol: "TM" & commNameShort, infiniteSupply: true, transferable: false, remoteSelfDestruct: true, tokenUri: utl.changeCommunityKeyCompression(communityId) & "/")) + return (DeploymentParameters(name: "Owner-" & commName, symbol: "OWN" & commNameShort, supply: stint.u256("1"), + infiniteSupply: false, transferable: true, remoteSelfDestruct: false, + tokenUri: utl.changeCommunityKeyCompression(communityId) & "/", communityId: communityId), + DeploymentParameters(name: "TMaster-" & commName, symbol: "TM" & commNameShort, infiniteSupply: true, + transferable: false, remoteSelfDestruct: true, + tokenUri: utl.changeCommunityKeyCompression(communityId) & "/", communityId: communityId)) method deployOwnerToken*(self: Module, communityId: string, fromAddress: string, ownerName: string, ownerSymbol: string, ownerDescription: string, masterName: string, masterSymbol: string, masterDescription: string, chainId: int, imageCropInfoJson: string) = @@ -209,12 +210,15 @@ method deployOwnerToken*(self: Module, communityId: string, fromAddress: string, self.tempAddressFrom = fromAddress self.tempCommunityId = communityId self.tempChainId = chainId + let croppedImage = imageCropInfoJson.parseJson + let base65Image = singletonInstance.utils.formatImagePath(croppedImage["imagePath"].getStr) (self.tempOwnerDeploymentParams, self.tempMasterDeploymentParams) = self.createOwnerAndMasterDeploymentParams(communityId) - self.tempOwnerTokenMetadata.description = ownerDescription - self.tempOwnerTokenMetadata.tokenType = TokenType.ERC721 - self.tempMasterTokenMetadata.description = masterDescription - self.tempMasterTokenMetadata.tokenType = TokenType.ERC721 - self.tempTokenImageCropInfoJson = imageCropInfoJson + self.tempOwnerDeploymentParams.description = ownerDescription + self.tempOwnerDeploymentParams.tokenType = TokenType.ERC721 + self.tempOwnerDeploymentParams.base64image = base65Image + self.tempMasterDeploymentParams.description = masterDescription + self.tempMasterDeploymentParams.tokenType = TokenType.ERC721 + self.tempMasterDeploymentParams.base64image = base65Image self.tempContractAction = ContractAction.DeployOwnerToken self.authenticate() @@ -235,9 +239,10 @@ method deployAssets*(self: Module, communityId: string, fromAddress: string, nam self.tempDeploymentParams.tokenUri = utl.changeCommunityKeyCompression(communityId) & "/" self.tempDeploymentParams.ownerTokenAddress = ownerTokenAddress self.tempDeploymentParams.masterTokenAddress = masterTokenAddress - self.tempTokenMetadata.tokenType = TokenType.ERC20 - self.tempTokenMetadata.description = description - self.tempTokenImageCropInfoJson = imageCropInfoJson + self.tempDeploymentParams.tokenType = TokenType.ERC20 + self.tempDeploymentParams.description = description + self.tempDeploymentParams.croppedImageJson = imageCropInfoJson + self.tempDeploymentParams.communityId = communityId self.tempContractAction = ContractAction.Deploy self.authenticate() @@ -251,7 +256,7 @@ method onUserAuthenticated*(self: Module, password: string) = #TODO signalize somehow else: if self.tempContractAction == ContractAction.Deploy: - self.controller.deployContract(self.tempCommunityId, self.tempAddressFrom, password, self.tempDeploymentParams, self.tempTokenMetadata, self.tempTokenImageCropInfoJson, self.tempChainId) + self.controller.deployContract(self.tempCommunityId, self.tempAddressFrom, password, self.tempDeploymentParams, self.tempChainId) elif self.tempContractAction == ContractAction.Airdrop: self.controller.airdropTokens(self.tempCommunityId, password, self.tempTokenAndAmountList, self.tempWalletAddresses, self.tempAddressFrom) elif self.tempContractAction == ContractAction.SelfDestruct: @@ -260,9 +265,7 @@ method onUserAuthenticated*(self: Module, password: string) = self.controller.burnTokens(self.tempCommunityId, password, self.tempContractUniqueKey, self.tempAmount, self.tempAddressFrom) elif self.tempContractAction == ContractAction.DeployOwnerToken: self.controller.deployOwnerContracts(self.tempCommunityId, self.tempAddressFrom, password, - self.tempOwnerDeploymentParams, self.tempOwnerTokenMetadata, - self.tempMasterDeploymentParams, self.tempMasterTokenMetadata, - self.tempTokenImageCropInfoJson, self.tempChainId) + self.tempOwnerDeploymentParams, self.tempMasterDeploymentParams, self.tempChainId) elif self.tempContractAction == ContractAction.SetSigner: self.controller.setSigner(password, self.tempCommunityId, self.tempChainId, self.tempContractAddress, self.tempAddressFrom) diff --git a/src/app_service/service/community_tokens/async_tasks.nim b/src/app_service/service/community_tokens/async_tasks.nim index cd14699ca5..54e379c332 100644 --- a/src/app_service/service/community_tokens/async_tasks.nim +++ b/src/app_service/service/community_tokens/async_tasks.nim @@ -44,11 +44,7 @@ const asyncGetDeployOwnerContractsFeesTask: Task = proc(argEncoded: string) {.gc let response = eth.suggestedFees(arg.chainId).result feeTable[arg.chainId] = response.toSuggestedFeesDto() - # get deployment signature - let signatureResponse = community_tokens.createCommunityTokenDeploymentSignature(arg.chainId, arg.addressFrom, arg.communityId) - let signature = signatureResponse.result.getStr() - - let deployGas = community_tokens.deployOwnerTokenEstimate(arg.chainId, arg.addressFrom, arg.ownerParams, arg.masterParams, signature, arg.communityId, arg.signerPubKey).result.getInt + let deployGas = community_tokens.deployOwnerTokenEstimate(arg.chainId, arg.addressFrom, arg.ownerParams, arg.masterParams, arg.communityId, arg.signerPubKey).result.getInt gasTable[(arg.chainId, "")] = deployGas arg.finish(%* { "feeTable": tableToJsonArray(feeTable), diff --git a/src/app_service/service/community_tokens/dto/community_token.nim b/src/app_service/service/community_tokens/dto/community_token.nim index a6011499c9..2b1faa8864 100644 --- a/src/app_service/service/community_tokens/dto/community_token.nim +++ b/src/app_service/service/community_tokens/dto/community_token.nim @@ -25,7 +25,6 @@ type infiniteSupply*: bool transferable*: bool remoteSelfDestruct*: bool - tokenUri*: string chainId*: int deployState*: DeployState image*: string @@ -45,7 +44,6 @@ proc toJsonNode*(self: CommunityTokenDto): JsonNode = "infiniteSupply": self.infiniteSupply, "transferable": self.transferable, "remoteSelfDestruct": self.remoteSelfDestruct, - "tokenUri": self.tokenUri, "chainId": self.chainId, "deployState": self.deployState.int, "image": self.image, @@ -70,7 +68,6 @@ proc toCommunityTokenDto*(jsonObj: JsonNode): CommunityTokenDto = discard jsonObj.getProp("infiniteSupply", result.infiniteSupply) discard jsonObj.getProp("transferable", result.transferable) discard jsonObj.getProp("remoteSelfDestruct", result.remoteSelfDestruct) - discard jsonObj.getProp("tokenUri", result.tokenUri) discard jsonObj.getProp("chainId", result.chainId) var deployStateInt: int discard jsonObj.getProp("deployState", deployStateInt) diff --git a/src/app_service/service/community_tokens/dto/deployment_parameters.nim b/src/app_service/service/community_tokens/dto/deployment_parameters.nim index db4d616ba6..b4e78c4982 100644 --- a/src/app_service/service/community_tokens/dto/deployment_parameters.nim +++ b/src/app_service/service/community_tokens/dto/deployment_parameters.nim @@ -1,4 +1,6 @@ import json, stint +import ../../../../backend/interpret/cropped_image +import ../../../common/types type DeploymentParameters* = object @@ -9,9 +11,14 @@ type transferable*: bool remoteSelfDestruct*: bool tokenUri*: string - decimals*: int ownerTokenAddress*: string masterTokenAddress*: string + description*: string + communityId*: string + croppedImageJson*: string + base64image*: string + tokenType*: TokenType + decimals*: int proc `%`*(x: DeploymentParameters): JsonNode = result = newJobject() @@ -24,4 +31,10 @@ proc `%`*(x: DeploymentParameters): JsonNode = result["tokenUri"] = %x.tokenUri result["decimals"] = %x.decimals result["ownerTokenAddress"] = %x.ownerTokenAddress - result["masterTokenAddress"] = %x.masterTokenAddress \ No newline at end of file + result["masterTokenAddress"] = %x.masterTokenAddress + result["description"] = %x.description + result["communityId"] = %x.communityId + if x.croppedImageJson != "": + result["croppedImage"] = %newCroppedImage(x.croppedImageJson) + result["base64image"] = %x.base64image + result["tokenType"] = %x.tokenType \ No newline at end of file diff --git a/src/app_service/service/community_tokens/service.nim b/src/app_service/service/community_tokens/service.nim index b59c82fd5c..26c2c901d7 100644 --- a/src/app_service/service/community_tokens/service.nim +++ b/src/app_service/service/community_tokens/service.nim @@ -339,6 +339,19 @@ QtObject: result.tokenOwners1SecTimer.setSingleShot(true) signalConnect(result.tokenOwners1SecTimer, "timeout()", result, "onFetchTempTokenOwners()", 2) + # cache functions + proc updateCommunityTokenCache(self: Service, chainId: int, address: string, tokenToUpdate: CommunityTokenDto) = + for i in 0..self.communityTokensCache.len-1: + if self.communityTokensCache[i].chainId == chainId and self.communityTokensCache[i].address == address: + self.communityTokensCache[i] = tokenToUpdate + return + + proc removeCommunityTokenAndUpdateCache(self: Service, chainId: int, contractAddress: string) = + discard tokens_backend.removeCommunityToken(chainId, contractAddress) + self.communityTokensCache = self.communityTokensCache.filter(x => ((x.chainId != chainId) or (x.address != contractAddress))) + + # end of cache functions + proc processReceivedCollectiblesWalletEvent(self: Service, jsonMessage: string, accounts: seq[string]) = try: let dataMessageJson = parseJson(jsonMessage) @@ -455,65 +468,104 @@ QtObject: except Exception as e: error "Error registering community token received notification", msg=e.msg - proc processSetSignerTransactionEvent(self: Service, transactionArgs: TransactionMinedArgs) = + proc processSetSignerTransactionEvent(self: Service, signalArgs: CommunityTokenTransactionStatusChangedSignal) = try: - if not transactionArgs.success: - error "Signer not set" - let contractDetails = transactionArgs.data.parseJson().toContractDetails() - if transactionArgs.success: - # promoteSelfToControlNode will be moved to status-go in next phase - discard communities_backend.promoteSelfToControlNode(contractDetails.communityId) - let finaliseStatusArgs = FinaliseOwnershipStatusArgs(isPending: false, communityId: contractDetails.communityId) - self.events.emit(SIGNAL_FINALISE_OWNERSHIP_STATUS, finaliseStatusArgs) + let chainId = signalArgs.communityToken.chainId + let communityId = signalArgs.communityToken.communityId - let data = SetSignerArgs(status: if transactionArgs.success: ContractTransactionStatus.Completed else: ContractTransactionStatus.Failed, - chainId: transactionArgs.chainId, - transactionHash: transactionArgs.transactionHash, - communityId: contractDetails.communityId) + if signalArgs.success: + let finaliseStatusArgs = FinaliseOwnershipStatusArgs(isPending: false, communityId: communityId) + self.events.emit(SIGNAL_FINALISE_OWNERSHIP_STATUS, finaliseStatusArgs) + else: + error "Signer not set" + + let data = SetSignerArgs(status: if signalArgs.success: ContractTransactionStatus.Completed else: ContractTransactionStatus.Failed, + chainId: chainId, + transactionHash: signalArgs.hash, + communityId: communityId) self.events.emit(SIGNAL_SET_SIGNER_STATUS, data) - let response = if transactionArgs.success: tokens_backend.registerReceivedOwnershipNotification(contractDetails.communityId) else: tokens_backend.registerSetSignerFailedNotification(contractDetails.communityId) + # TODO move AC notifications to status-go + let response = if signalArgs.success: tokens_backend.registerReceivedOwnershipNotification(communityId) else: tokens_backend.registerSetSignerFailedNotification(communityId) checkAndEmitACNotificationsFromResponse(self.events, response.result{"activityCenterNotifications"}) - let notificationToSetRead = self.acService.getNotificationForTypeAndCommunityId(notification.ActivityCenterNotificationType.OwnerTokenReceived, contractDetails.communityId) + let notificationToSetRead = self.acService.getNotificationForTypeAndCommunityId(notification.ActivityCenterNotificationType.OwnerTokenReceived, communityId) if notificationToSetRead != nil: self.acService.markActivityCenterNotificationRead(notificationToSetRead.id) except Exception as e: error "Error processing set signer transaction", msg=e.msg - # cache functions - proc saveCommunityTokenAndUpdateCache(self: Service, tokenToSave: CommunityTokenDto, croppedImageJson: string): CommunityTokenDto = - let savedTokenJson = tokens_backend.saveCommunityToken(tokenToSave, croppedImageJson) - let savedToken = savedTokenJson.result.toCommunityTokenDto() - self.communityTokensCache.add(savedToken) - return savedToken + proc processAirdropTransactionEvent(self: Service, signalArgs: CommunityTokenTransactionStatusChangedSignal) = + try: + let transactionStatus = if signalArgs.success: ContractTransactionStatus.Completed else: ContractTransactionStatus.Failed + let data = AirdropArgs(communityToken: signalArgs.communityToken, transactionHash: signalArgs.hash, status: transactionStatus) + self.events.emit(SIGNAL_AIRDROP_STATUS, data) - proc updateCommunityTokenSupplyAndUpdateCache(self: Service, chainId: int, contractAddress: string, supply: Uint256) = - discard updateCommunityTokenSupply(chainId, contractAddress, supply) - for i in 0..self.communityTokensCache.len-1: - if self.communityTokensCache[i].chainId == chainId and self.communityTokensCache[i].address == contractAddress: - self.communityTokensCache[i].supply = supply - return + # update owners list if airdrop was successfull + if signalArgs.success: + self.tempTokenOwnersToFetch = signalArgs.communityToken + self.tokenOwners1SecTimer.start() + except Exception as e: + error "Error processing airdrop pending transaction event", msg=e.msg - proc updateCommunityTokenStateAndUpdateCache(self: Service, chainId: int, contractAddress: string, deployState: DeployState) = - discard updateCommunityTokenState(chainId, contractAddress, deployState) - for i in 0..self.communityTokensCache.len-1: - if self.communityTokensCache[i].chainId == chainId and self.communityTokensCache[i].address == contractAddress: - self.communityTokensCache[i].deployState = deployState - return + proc processRemoteDestructEvent(self: Service, signalArgs: CommunityTokenTransactionStatusChangedSignal) = + try: + let transactionStatus = if signalArgs.success: ContractTransactionStatus.Completed else: ContractTransactionStatus.Failed + let data = RemoteDestructArgs(communityToken: signalArgs.communityToken, transactionHash: signalArgs.hash, status: transactionStatus, remoteDestructAddresses: @[]) + self.events.emit(SIGNAL_REMOTE_DESTRUCT_STATUS, data) - proc updateCommunityTokenAddressAndUpdateCache(self: Service, chainId: int, contractAddress: string, newAddress: string) = - discard updateCommunityTokenAddress(chainId, contractAddress, newAddress) - for i in 0..self.communityTokensCache.len-1: - if self.communityTokensCache[i].chainId == chainId and self.communityTokensCache[i].address == contractAddress: - self.communityTokensCache[i].address = newAddress - return + # update owners list if remote destruct was successfull + if signalArgs.success: + self.tempTokenOwnersToFetch = signalArgs.communityToken + self.tokenOwners1SecTimer.start() + except Exception as e: + error "Error processing collectible self destruct pending transaction event", msg=e.msg - proc removeCommunityTokenAndUpdateCache(self: Service, chainId: int, contractAddress: string) = - discard tokens_backend.removeCommunityToken(chainId, contractAddress) - self.communityTokensCache = self.communityTokensCache.filter(x => ((x.chainId != chainId) or (x.address != contractAddress))) - - # end of cache functions + proc processBurnEvent(self: Service, signalArgs: CommunityTokenTransactionStatusChangedSignal) = + try: + let transactionStatus = if signalArgs.success: ContractTransactionStatus.Completed else: ContractTransactionStatus.Failed + if signalArgs.success: + self.updateCommunityTokenCache(signalArgs.communityToken.chainId, signalArgs.communityToken.address, signalArgs.communityToken) + let data = RemoteDestructArgs(communityToken: signalArgs.communityToken, transactionHash: signalArgs.hash, status: transactionStatus) + self.events.emit(SIGNAL_BURN_STATUS, data) + except Exception as e: + error "Error processing collectible burn pending transaction event", msg=e.msg + + proc processDeployCommunityToken(self: Service, signalArgs: CommunityTokenTransactionStatusChangedSignal) = + try: + let deployState = if signalArgs.success: DeployState.Deployed else: DeployState.Failed + let tokenDto = signalArgs.communityToken + if not signalArgs.success: + error "Community contract not deployed", chainId=tokenDto.chainId, address=tokenDto.address + self.updateCommunityTokenCache(tokenDto.chainId, tokenDto.address, tokenDto) + let data = CommunityTokenDeployedStatusArgs(communityId: tokenDto.communityId, contractAddress: tokenDto.address, + deployState: deployState, chainId: tokenDto.chainId, + transactionHash: signalArgs.hash) + self.events.emit(SIGNAL_COMMUNITY_TOKEN_DEPLOY_STATUS, data) + except Exception as e: + error "Error processing community token deployment pending transaction event", msg=e.msg + + proc processDeployOwnerToken(self: Service, signalArgs: CommunityTokenTransactionStatusChangedSignal) = + try: + let deployState = if signalArgs.success: DeployState.Deployed else: DeployState.Failed + let ownerToken = signalArgs.ownerToken + let masterToken = signalArgs.masterToken + if not signalArgs.success: + error "Owner token contract not deployed", chainId=ownerToken.chainId, address=ownerToken.address + + let temporaryMasterContractAddress = signalArgs.hash & "-master" + let temporaryOwnerContractAddress = signalArgs.hash & "-owner" + self.updateCommunityTokenCache(ownerToken.chainId, temporaryOwnerContractAddress, ownerToken) + self.updateCommunityTokenCache(ownerToken.chainId, temporaryMasterContractAddress, masterToken) + + let data = OwnerTokenDeployedStatusArgs(communityId: ownerToken.communityId, chainId: ownerToken.chainId, + ownerContractAddress: ownerToken.address, + masterContractAddress: masterToken.address, + deployState: deployState, + transactionHash: signalArgs.hash) + self.events.emit(SIGNAL_OWNER_TOKEN_DEPLOY_STATUS, data) + except Exception as e: + error "Error processing owner token deployment pending transaction event", msg=e.msg proc init*(self: Service) = self.getAllCommunityTokensAsync() @@ -527,133 +579,23 @@ QtObject: elif data.eventType == tokens_backend.eventCommunityTokenReceived: self.processReceivedCommunityTokenWalletEvent(data.message, data.accounts) - self.events.on(PendingTransactionTypeDto.SetSignerPublicKey.event) do(e: Args): - let receivedData = TransactionMinedArgs(e) - self.processSetSignerTransactionEvent(receivedData) - - self.events.on(PendingTransactionTypeDto.DeployCommunityToken.event) do(e: Args): - var receivedData = TransactionMinedArgs(e) - try: - let deployState = if receivedData.success: DeployState.Deployed else: DeployState.Failed - let tokenDto = toCommunityTokenDto(parseJson(receivedData.data)) - if not receivedData.success: - error "Community contract not deployed", chainId=tokenDto.chainId, address=tokenDto.address - try: - self.updateCommunityTokenStateAndUpdateCache(tokenDto.chainId, tokenDto.address, deployState) - # now add community token to community and publish update - let response = tokens_backend.addCommunityToken(tokenDto.communityId, tokenDto.chainId, tokenDto.address) - if response.error != nil: - let error = Json.decode($response.error, RpcError) - raise newException(RpcException, "error adding community token: " & error.message) - except RpcException: - error "Error updating community contract state", message = getCurrentExceptionMsg() - let data = CommunityTokenDeployedStatusArgs(communityId: tokenDto.communityId, contractAddress: tokenDto.address, - deployState: deployState, chainId: tokenDto.chainId, - transactionHash: receivedData.transactionHash) - self.events.emit(SIGNAL_COMMUNITY_TOKEN_DEPLOY_STATUS, data) - except Exception as e: - error "Error processing community token deployment pending transaction event", msg=e.msg, receivedData - - self.events.on(PendingTransactionTypeDto.DeployOwnerToken.event) do(e: Args): - var receivedData = TransactionMinedArgs(e) - try: - let deployState = if receivedData.success: DeployState.Deployed else: DeployState.Failed - let ownerTransactionDetails = toOwnerTokenDeploymentTransactionDetails(parseJson(receivedData.data)) - if not receivedData.success: - warn "Owner contracts not deployed", chainId=ownerTransactionDetails.ownerToken.chainId, address=ownerTransactionDetails.ownerToken.address - var masterContractAddress = ownerTransactionDetails.masterToken.address - var ownerContractAddress = ownerTransactionDetails.ownerToken.address - - try: - # get master token address from transaction logs - if receivedData.success: - var response = tokens_backend.getOwnerTokenContractAddressFromHash(ownerTransactionDetails.ownerToken.chainId, receivedData.transactionHash) - ownerContractAddress = response.result.getStr() - if ownerContractAddress == "": - raise newException(RpcException, "owner contract address is empty") - response = tokens_backend.getMasterTokenContractAddressFromHash(ownerTransactionDetails.masterToken.chainId, receivedData.transactionHash) - masterContractAddress = response.result.getStr() - if masterContractAddress == "": - raise newException(RpcException, "master contract address is empty") - - debug "Minted owner token contract address:", ownerContractAddress - debug "Minted master token contract address:", masterContractAddress - - # update master token address - self.updateCommunityTokenAddressAndUpdateCache(ownerTransactionDetails.masterToken.chainId, ownerTransactionDetails.masterToken.address, masterContractAddress) - # update owner token address - self.updateCommunityTokenAddressAndUpdateCache(ownerTransactionDetails.ownerToken.chainId, ownerTransactionDetails.ownerToken.address, ownerContractAddress) - #update db state for owner and master token - self.updateCommunityTokenStateAndUpdateCache(ownerTransactionDetails.ownerToken.chainId, ownerContractAddress, deployState) - self.updateCommunityTokenStateAndUpdateCache(ownerTransactionDetails.masterToken.chainId, masterContractAddress, deployState) - # now add owner token to community and publish update - var response = tokens_backend.addCommunityToken(ownerTransactionDetails.communityId, ownerTransactionDetails.ownerToken.chainId, ownerContractAddress) - if response.error != nil: - let error = Json.decode($response.error, RpcError) - raise newException(RpcException, "error adding owner token: " & error.message) - - # now add master token to community and publish update - response = tokens_backend.addCommunityToken(ownerTransactionDetails.communityId, ownerTransactionDetails.masterToken.chainId, masterContractAddress) - if response.error != nil: - let error = Json.decode($response.error, RpcError) - raise newException(RpcException, "error adding master token: " & error.message) - except RpcException: - error "Error updating owner contracts state", message = getCurrentExceptionMsg() - - let data = OwnerTokenDeployedStatusArgs(communityId: ownerTransactionDetails.communityId, chainId: ownerTransactionDetails.ownerToken.chainId, - ownerContractAddress: ownerContractAddress, - masterContractAddress: masterContractAddress, - deployState: deployState, - transactionHash: receivedData.transactionHash) - self.events.emit(SIGNAL_OWNER_TOKEN_DEPLOY_STATUS, data) - except Exception as e: - error "Error processing Owner token deployment pending transaction event", msg=e.msg, receivedData - - self.events.on(PendingTransactionTypeDto.AirdropCommunityToken.event) do(e: Args): - let receivedData = TransactionMinedArgs(e) - try: - let tokenDto = toCommunityTokenDto(parseJson(receivedData.data)) - let transactionStatus = if receivedData.success: ContractTransactionStatus.Completed else: ContractTransactionStatus.Failed - let data = AirdropArgs(communityToken: tokenDto, transactionHash: receivedData.transactionHash, status: transactionStatus) - self.events.emit(SIGNAL_AIRDROP_STATUS, data) - - # update owners list if airdrop was successfull - if receivedData.success: - self.tempTokenOwnersToFetch = tokenDto - self.tokenOwners1SecTimer.start() - except Exception as e: - error "Error processing Collectible airdrop pending transaction event", msg=e.msg, receivedData - - self.events.on(PendingTransactionTypeDto.RemoteDestructCollectible.event) do(e: Args): - let receivedData = TransactionMinedArgs(e) - try: - let remoteDestructTransactionDetails = toRemoteDestroyTransactionDetails(parseJson(receivedData.data)) - let tokenDto = self.getCommunityToken(remoteDestructTransactionDetails.chainId, remoteDestructTransactionDetails.contractAddress) - let transactionStatus = if receivedData.success: ContractTransactionStatus.Completed else: ContractTransactionStatus.Failed - let data = RemoteDestructArgs(communityToken: tokenDto, transactionHash: receivedData.transactionHash, status: transactionStatus, remoteDestructAddresses: @[]) - self.events.emit(SIGNAL_REMOTE_DESTRUCT_STATUS, data) - - # update owners list if remote destruct was successfull - if receivedData.success: - self.tempTokenOwnersToFetch = tokenDto - self.tokenOwners1SecTimer.start() - except Exception as e: - error "Error processing Collectible self destruct pending transaction event", msg=e.msg, receivedData - - self.events.on(PendingTransactionTypeDto.BurnCommunityToken.event) do(e: Args): - let receivedData = TransactionMinedArgs(e) - try: - let tokenDto = toCommunityTokenDto(parseJson(receivedData.data)) - let transactionStatus = if receivedData.success: ContractTransactionStatus.Completed else: ContractTransactionStatus.Failed - if receivedData.success: - try: - self.updateCommunityTokenSupplyAndUpdateCache(tokenDto.chainId, tokenDto.address, tokenDto.supply) - except RpcException: - error "Error updating collectibles supply", message = getCurrentExceptionMsg() - let data = RemoteDestructArgs(communityToken: tokenDto, transactionHash: receivedData.transactionHash, status: transactionStatus) - self.events.emit(SIGNAL_BURN_STATUS, data) - except Exception as e: - error "Error processing Collectible burn pending transaction event", msg=e.msg, receivedData + self.events.on(SignalType.CommunityTokenTransactionStatusChanged.event) do(e: Args): + let receivedData = CommunityTokenTransactionStatusChangedSignal(e) + if receivedData.errorString != "": + error "Community token transaction has finished but the system error occured. Probably state of the token in database is broken.", + errorString=receivedData.errorString, transactionHash=receivedData.hash, transactionSuccess=receivedData.success + if receivedData.transactionType == $PendingTransactionTypeDto.SetSignerPublicKey: + self.processSetSignerTransactionEvent(receivedData) + elif receivedData.transactionType == $PendingTransactionTypeDto.AirdropCommunityToken: + self.processAirdropTransactionEvent(receivedData) + elif receivedData.transactionType == $PendingTransactionTypeDto.RemoteDestructCollectible: + self.processRemoteDestructEvent(receivedData) + elif receivedData.transactionType == $PendingTransactionTypeDto.BurnCommunityToken: + self.processBurnEvent(receivedData) + elif receivedData.transactionType == $PendingTransactionTypeDto.DeployCommunityToken: + self.processDeployCommunityToken(receivedData) + elif receivedData.transactionType == $PendingTransactionTypeDto.DeployOwnerToken: + self.processDeployOwnerToken(receivedData) proc buildTransactionDataDto(self: Service, addressFrom: string, chainId: int, contractAddress: string): TransactionDataDto = let gasUnits = self.tempGasTable.getOrDefault((chainId, contractAddress), 0) @@ -666,45 +608,6 @@ QtObject: if suggestedFees.eip1559Enabled: $suggestedFees.maxPriorityFeePerGas else: "", if suggestedFees.eip1559Enabled: $suggestedFees.maxFeePerGasM else: "") - proc createCommunityToken(self: Service, deploymentParams: DeploymentParameters, tokenMetadata: CommunityTokensMetadataDto, - chainId: int, contractAddress: string, communityId: string, addressFrom: string, privilegesLevel: PrivilegesLevel): CommunityTokenDto = - result.tokenType = tokenMetadata.tokenType - result.communityId = communityId - result.address = contractAddress - result.name = deploymentParams.name - result.symbol = deploymentParams.symbol - result.description = tokenMetadata.description - result.supply = stint.parse($deploymentParams.supply, Uint256) - result.infiniteSupply = deploymentParams.infiniteSupply - result.transferable = deploymentParams.transferable - result.remoteSelfDestruct = deploymentParams.remoteSelfDestruct - result.tokenUri = deploymentParams.tokenUri - result.chainId = chainId - result.deployState = DeployState.InProgress - result.decimals = deploymentParams.decimals - result.deployer = addressFrom - result.privilegesLevel = privilegesLevel - - proc saveTokenToDbAndWatchTransaction*(self:Service, communityToken: CommunityTokenDto, croppedImageJson: string, - transactionHash: string, addressFrom: string, watchTransaction: bool) = - var croppedImage = croppedImageJson.parseJson - croppedImage{"imagePath"} = newJString(singletonInstance.utils.formatImagePath(croppedImage["imagePath"].getStr)) - - let addedCommunityToken = self.saveCommunityTokenAndUpdateCache(communityToken, $croppedImage) - let data = CommunityTokenDeploymentArgs(communityToken: addedCommunityToken, transactionHash: transactionHash) - self.events.emit(SIGNAL_COMMUNITY_TOKEN_DEPLOYMENT_STARTED, data) - - if watchTransaction: - # observe transaction state - self.transactionService.watchTransaction( - transactionHash, - addressFrom, - addedCommunityToken.address, - $PendingTransactionTypeDto.DeployCommunityToken, - $addedCommunityToken.toJsonNode(), - addedCommunityToken.chainId, - ) - proc temporaryMasterContractAddress*(ownerContractTransactionHash: string): string = return ownerContractTransactionHash & "-master" @@ -712,9 +615,7 @@ QtObject: return ownerContractTransactionHash & "-owner" proc deployOwnerContracts*(self: Service, communityId: string, addressFrom: string, password: string, - ownerDeploymentParams: DeploymentParameters, ownerTokenMetadata: CommunityTokensMetadataDto, - masterDeploymentParams: DeploymentParameters, masterTokenMetadata: CommunityTokensMetadataDto, - croppedImageJson: string, chainId: int) = + ownerDeploymentParams: DeploymentParameters, masterDeploymentParams: DeploymentParameters, chainId: int) = try: let txData = self.buildTransactionDataDto(addressFrom, chainId, "") if txData.source == parseAddress(ZERO_ADDRESS): @@ -723,70 +624,52 @@ QtObject: # set my pub key as signer let signerPubKey = singletonInstance.userProfile.getPubKey() - # get deployment signature - let signatureResponse = tokens_backend.createCommunityTokenDeploymentSignature(chainId, addressFrom, communityId) - let signature = signatureResponse.result.getStr() - # deploy contract let response = tokens_backend.deployOwnerToken(chainId, %ownerDeploymentParams, %masterDeploymentParams, - signature, communityId, signerPubKey, %txData, common_utils.hashPassword(password)) + signerPubKey, %txData, common_utils.hashPassword(password)) let transactionHash = response.result["transactionHash"].getStr() + let deployedOwnerToken = toCommunityTokenDto(response.result["ownerToken"]) + let deployedMasterToken = toCommunityTokenDto(response.result["masterToken"]) debug "Deployment transaction hash ", transactionHash=transactionHash - var ownerToken = self.createCommunityToken(ownerDeploymentParams, ownerTokenMetadata, chainId, temporaryOwnerContractAddress(transactionHash), communityId, addressFrom, PrivilegesLevel.Owner) - var masterToken = self.createCommunityToken(masterDeploymentParams, masterTokenMetadata, chainId, temporaryMasterContractAddress(transactionHash), communityId, addressFrom, PrivilegesLevel.Master) + self.communityTokensCache.add(deployedOwnerToken) + self.communityTokensCache.add(deployedMasterToken) - var croppedImage = croppedImageJson.parseJson - ownerToken.image = croppedImage{"imagePath"}.getStr - masterToken.image = croppedImage{"imagePath"}.getStr - - let addedOwnerToken = self.saveCommunityTokenAndUpdateCache(ownerToken, "") - let addedMasterToken = self.saveCommunityTokenAndUpdateCache(masterToken, "") - - let data = OwnerTokenDeploymentArgs(ownerToken: addedOwnerToken, masterToken: addedMasterToken, transactionHash: transactionHash) + let data = OwnerTokenDeploymentArgs(ownerToken: deployedOwnerToken, masterToken: deployedMasterToken, transactionHash: transactionHash) self.events.emit(SIGNAL_OWNER_TOKEN_DEPLOYMENT_STARTED, data) - let transactionDetails = OwnerTokenDeploymentTransactionDetails(ownerToken: (chainId, addedOwnerToken.address), - masterToken: (chainId, addedMasterToken.address), communityId: addedOwnerToken.communityId) - - self.transactionService.watchTransaction( - transactionHash, - addressFrom, - addedOwnerToken.address, - $PendingTransactionTypeDto.DeployOwnerToken, - $(%transactionDetails), - chainId, - ) except RpcException: error "Error deploying owner contract", message = getCurrentExceptionMsg() let data = OwnerTokenDeployedStatusArgs(communityId: communityId, deployState: DeployState.Failed) self.events.emit(SIGNAL_OWNER_TOKEN_DEPLOY_STATUS, data) - proc deployContract*(self: Service, communityId: string, addressFrom: string, password: string, deploymentParams: DeploymentParameters, tokenMetadata: CommunityTokensMetadataDto, croppedImageJson: string, chainId: int) = + proc deployContract*(self: Service, communityId: string, addressFrom: string, password: string, deploymentParams: DeploymentParameters, chainId: int) = try: let txData = self.buildTransactionDataDto(addressFrom, chainId, "") if txData.source == parseAddress(ZERO_ADDRESS): return var response: RpcResponse[JsonNode] - case tokenMetadata.tokenType + case deploymentParams.tokenType of TokenType.ERC721: response = tokens_backend.deployCollectibles(chainId, %deploymentParams, %txData, common_utils.hashPassword(password)) of TokenType.ERC20: response = tokens_backend.deployAssets(chainId, %deploymentParams, %txData, common_utils.hashPassword(password)) else: - error "Contract deployment error - unknown token type", tokenType=tokenMetadata.tokenType + error "Contract deployment error - unknown token type", tokenType=deploymentParams.tokenType return let contractAddress = response.result["contractAddress"].getStr() let transactionHash = response.result["transactionHash"].getStr() + let deployedCommunityToken = toCommunityTokenDto(response.result["communityToken"]) debug "Deployed contract address ", contractAddress=contractAddress debug "Deployment transaction hash ", transactionHash=transactionHash - var communityToken = self.createCommunityToken(deploymentParams, tokenMetadata, chainId, contractAddress, communityId, addressFrom, PrivilegesLevel.Community) - - self.saveTokenToDbAndWatchTransaction(communityToken, croppedImageJson, transactionHash, addressFrom, true) + # add to cache + self.communityTokensCache.add(deployedCommunityToken) + let data = CommunityTokenDeploymentArgs(communityToken: deployedCommunityToken, transactionHash: transactionHash) + self.events.emit(SIGNAL_COMMUNITY_TOKEN_DEPLOYMENT_STARTED, data) except RpcException: error "Error deploying contract", message = getCurrentExceptionMsg() @@ -882,8 +765,7 @@ QtObject: let burnTransactions = self.transactionService.getPendingTransactionsForType(PendingTransactionTypeDto.BurnCommunityToken) for transaction in burnTransactions: try: - let communityToken = toCommunityTokenDto(parseJson(transaction.additionalData)) - if communityToken.chainId == chainId and communityToken.address == contractAddress: + if transaction.chainId == chainId and transaction.to == contractAddress: return ContractTransactionStatus.InProgress except Exception: discard @@ -893,9 +775,9 @@ QtObject: try: let remoteDestructTransactions = self.transactionService.getPendingTransactionsForType(PendingTransactionTypeDto.RemoteDestructCollectible) for transaction in remoteDestructTransactions: - let remoteDestructTransactionDetails = toRemoteDestroyTransactionDetails(parseJson(transaction.additionalData)) - if remoteDestructTransactionDetails.chainId == chainId and remoteDestructTransactionDetails.contractAddress == contractAddress: - return remoteDestructTransactionDetails.addresses + if transaction.chainId == chainId and transaction.to == contractAddress: + let burntAddresses = to(transaction.additionalData.parseJson(), seq[string]) + return burntAddresses except Exception: error "Error getting contract owner", message = getCurrentExceptionMsg() @@ -910,18 +792,23 @@ QtObject: error "Error getting contract owner name", message = getCurrentExceptionMsg() proc getRemainingSupply*(self: Service, chainId: int, contractAddress: string): Uint256 = + let token = self.getCommunityToken(chainId, contractAddress) + if token.deployState != DeployState.Deployed: + return token.supply try: let response = tokens_backend.remainingSupply(chainId, contractAddress) return stint.parse(response.result.getStr(), Uint256) except RpcException: error "Error getting remaining supply", message = getCurrentExceptionMsg() # if there is an exception probably community token is not minted yet - return self.getCommunityToken(chainId, contractAddress).supply + return token.supply proc getRemoteDestructedAmount*(self: Service, chainId: int, contractAddress: string): Uint256 = try: - let tokenType = self.getCommunityToken(chainId, contractAddress).tokenType - if tokenType != TokenType.ERC721: + let token = self.getCommunityToken(chainId, contractAddress) + let tokenType = token.tokenType + let tokenState = token.deployState + if tokenType != TokenType.ERC721 or tokenState != DeployState.Deployed: return stint.parse("0", Uint256) let response = tokens_backend.remoteDestructedAmount(chainId, contractAddress) return stint.parse(response.result.getStr(), Uint256) @@ -941,16 +828,6 @@ QtObject: var data = AirdropArgs(communityToken: collectibleAndAmount.communityToken, transactionHash: transactionHash, status: ContractTransactionStatus.InProgress) self.events.emit(SIGNAL_AIRDROP_STATUS, data) - - # observe transaction state - self.transactionService.watchTransaction( - transactionHash, - addressFrom, - collectibleAndAmount.communityToken.address, - $PendingTransactionTypeDto.AirdropCommunityToken, - $collectibleAndAmount.communityToken.toJsonNode(), - collectibleAndAmount.communityToken.chainId, - ) except RpcException: error "Error airdropping tokens", message = getCurrentExceptionMsg() @@ -1073,29 +950,20 @@ QtObject: let contract = self.findContractByUniqueId(contractUniqueKey) let tokenIds = self.getTokensToBurn(walletAndAmounts, contract) if len(tokenIds) == 0: + debug "No token ids to remote burn", walletAndAmounts=walletAndAmounts return + var addresses: seq[string] = @[] + for walletAndAmount in walletAndAmounts: + addresses.add(walletAndAmount.walletAddress) let txData = self.buildTransactionDataDto(addressFrom, contract.chainId, contract.address) debug "Remote destruct collectibles ", chainId=contract.chainId, address=contract.address, tokens=tokenIds - let response = tokens_backend.remoteBurn(contract.chainId, contract.address, %txData, common_utils.hashPassword(password), tokenIds) + let response = tokens_backend.remoteBurn(contract.chainId, contract.address, %txData, common_utils.hashPassword(password), + tokenIds, $(%addresses)) let transactionHash = response.result.getStr() debug "Remote destruct transaction hash ", transactionHash=transactionHash - var transactionDetails = RemoteDestroyTransactionDetails(chainId: contract.chainId, contractAddress: contract.address) - for walletAndAmount in walletAndAmounts: - transactionDetails.addresses.add(walletAndAmount.walletAddress) - - var data = RemoteDestructArgs(communityToken: contract, transactionHash: transactionHash, status: ContractTransactionStatus.InProgress, remoteDestructAddresses: transactionDetails.addresses) + var data = RemoteDestructArgs(communityToken: contract, transactionHash: transactionHash, status: ContractTransactionStatus.InProgress, remoteDestructAddresses: addresses) self.events.emit(SIGNAL_REMOTE_DESTRUCT_STATUS, data) - - # observe transaction state - self.transactionService.watchTransaction( - transactionHash, - addressFrom, - contract.address, - $PendingTransactionTypeDto.RemoteDestructCollectible, - $(%transactionDetails), - contract.chainId, - ) except Exception as e: error "Remote self destruct error", msg = e.msg @@ -1147,17 +1015,6 @@ QtObject: var data = RemoteDestructArgs(communityToken: contract, transactionHash: transactionHash, status: ContractTransactionStatus.InProgress) self.events.emit(SIGNAL_BURN_STATUS, data) - - contract.supply = contract.supply - amount # save with changed supply - # observe transaction state - self.transactionService.watchTransaction( - transactionHash, - addressFrom, - contract.address, - $PendingTransactionTypeDto.BurnCommunityToken, - $contract.toJsonNode(), - contract.chainId, - ) except Exception as e: error "Burn error", msg = e.msg diff --git a/src/backend/community_tokens.nim b/src/backend/community_tokens.nim index 8014fa6dc1..8e434cdc52 100644 --- a/src/backend/community_tokens.nim +++ b/src/backend/community_tokens.nim @@ -60,8 +60,8 @@ proc estimateMintTokens*(chainId: int, contractAddress: string, fromAddress: str let payload = %* [chainId, contractAddress, fromAddress, walletAddresses, amount.toString(10)] return core.callPrivateRPC("communitytokens_estimateMintTokens", payload) -proc remoteBurn*(chainId: int, contractAddress: string, txData: JsonNode, hashedPassword: string, tokenIds: seq[UInt256]): RpcResponse[JsonNode] = - let payload = %* [chainId, contractAddress, txData, hashedPassword, tokenIds.map(x => x.toString(10))] +proc remoteBurn*(chainId: int, contractAddress: string, txData: JsonNode, hashedPassword: string, tokenIds: seq[UInt256], additionalData: string): RpcResponse[JsonNode] = + let payload = %* [chainId, contractAddress, txData, hashedPassword, tokenIds.map(x => x.toString(10)), additionalData] return core.callPrivateRPC("communitytokens_remoteBurn", payload) proc estimateRemoteBurn*(chainId: int, contractAddress: string, fromAddress: string, tokenIds: seq[UInt256]): RpcResponse[JsonNode] = @@ -96,12 +96,12 @@ proc remoteDestructedAmount*(chainId: int, contractAddress: string): RpcResponse let payload = %*[chainId, contractAddress] return core.callPrivateRPC("communitytokens_remoteDestructedAmount", payload) -proc deployOwnerTokenEstimate*(chainId: int, addressFrom: string, ownerParams: JsonNode, masterParams: JsonNode, signature: string, communityId: string, signerPubKey: string): RpcResponse[JsonNode] = - let payload = %*[chainId, addressFrom, ownerParams, masterParams, signature, communityId, signerPubKey] +proc deployOwnerTokenEstimate*(chainId: int, addressFrom: string, ownerParams: JsonNode, masterParams: JsonNode, communityId: string, signerPubKey: string): RpcResponse[JsonNode] = + let payload = %*[chainId, addressFrom, ownerParams, masterParams, communityId, signerPubKey] return core.callPrivateRPC("communitytokens_deployOwnerTokenEstimate", payload) -proc deployOwnerToken*(chainId: int, ownerParams: JsonNode, masterParams: JsonNode, signature: string, communityId: string, signerPubKey: string, txData: JsonNode, hashedPassword: string): RpcResponse[JsonNode] = - let payload = %*[chainId, ownerParams, masterParams, signature, communityId, signerPubKey, txData, hashedPassword] +proc deployOwnerToken*(chainId: int, ownerParams: JsonNode, masterParams: JsonNode, signerPubKey: string, txData: JsonNode, hashedPassword: string): RpcResponse[JsonNode] = + let payload = %*[chainId, ownerParams, masterParams, signerPubKey, txData, hashedPassword] return core.callPrivateRPC("communitytokens_deployOwnerToken", payload) proc getMasterTokenContractAddressFromHash*(chainId: int, transactionHash: string): RpcResponse[JsonNode] =