feat: identify if a token is being approved and estimate gas for contract trxs

This commit is contained in:
Richard Ramos 2020-10-19 10:32:25 -04:00 committed by Iuri Matias
parent 5ff809b6b8
commit 6c641eff42
5 changed files with 62 additions and 32 deletions

View File

@ -265,14 +265,14 @@ QtObject:
read = getAccountList read = getAccountList
notify = accountListChanged notify = accountListChanged
proc estimateGas*(self: WalletView, from_addr: string, to: string, assetAddress: string, value: string): string {.slot.} = proc estimateGas*(self: WalletView, from_addr: string, to: string, assetAddress: string, value: string, data: string = ""): string {.slot.} =
var var
response: int response: int
success: bool success: bool
if assetAddress != ZERO_ADDRESS and not assetAddress.isEmptyOrWhitespace: if assetAddress != ZERO_ADDRESS and not assetAddress.isEmptyOrWhitespace:
response = self.status.wallet.estimateTokenGas(from_addr, to, assetAddress, value, success) response = self.status.wallet.estimateTokenGas(from_addr, to, assetAddress, value, success)
else: else:
response = self.status.wallet.estimateGas(from_addr, to, value, success) response = self.status.wallet.estimateGas(from_addr, to, value, data, success)
result = $(%* { "result": %response, "success": %success }) result = $(%* { "result": %response, "success": %success })
proc transactionWasSent*(self: WalletView, txResult: string) {.signal.} proc transactionWasSent*(self: WalletView, txResult: string) {.signal.}
@ -522,6 +522,16 @@ QtObject:
proc isKnownTokenContract*(self: WalletView, address: string): bool {.slot.} = proc isKnownTokenContract*(self: WalletView, address: string): bool {.slot.} =
return self.status.wallet.getKnownTokenContract(parseAddress(address)) != nil return self.status.wallet.getKnownTokenContract(parseAddress(address)) != nil
proc decodeTokenApproval*(self: WalletView, tokenAddress: string, data: string): string {.slot.} =
let amount = data[74..len(data)-1]
let token = getToken(tokenAddress)
if(token != nil):
let amountDec = $hex2Token(amount, token.decimals)
return $(%* {"symbol": token.symbol, "amount": amountDec})
return """{"error":"Unknown token address"}""";
proc isHistoryFetched*(self: WalletView, address: string): bool {.slot.} = proc isHistoryFetched*(self: WalletView, address: string): bool {.slot.} =
return self.currentTransactions.rowCount() > 0 return self.currentTransactions.rowCount() > 0

View File

@ -1,4 +1,4 @@
import json, chronicles, strformat, stint, strutils import json, chronicles, strformat, stint, strutils, sequtils
import core, wallet import core, wallet
import ./eth/contracts import ./eth/contracts
import web3/[ethtypes, conversions] import web3/[ethtypes, conversions]
@ -101,6 +101,9 @@ proc getTokensBalances*(accounts: openArray[string], tokens: openArray[string]):
return %* {} return %* {}
response["result"] response["result"]
proc getToken*(tokenAddress: string): Erc20Contract =
getErc20Contracts().concat(getCustomTokens()).getErc20ContractByAddress(tokenAddress.parseAddress)
proc getTokenBalance*(tokenAddress: string, account: string): string = proc getTokenBalance*(tokenAddress: string, account: string): string =
var postfixedAccount: string = account var postfixedAccount: string = account
postfixedAccount.removePrefix("0x") postfixedAccount.removePrefix("0x")

View File

@ -70,10 +70,11 @@ proc buildTokenTransaction(self: WalletModel, source, to, assetAddress: Address,
proc getKnownTokenContract*(self: WalletModel, address: Address): Erc20Contract = proc getKnownTokenContract*(self: WalletModel, address: Address): Erc20Contract =
getErc20Contracts().concat(getCustomTokens()).getErc20ContractByAddress(address) getErc20Contracts().concat(getCustomTokens()).getErc20ContractByAddress(address)
proc estimateGas*(self: WalletModel, source, to, value: string, success: var bool): int = proc estimateGas*(self: WalletModel, source, to, value, data: string, success: var bool): int =
var tx = transactions.buildTransaction( var tx = transactions.buildTransaction(
parseAddress(source), parseAddress(source),
eth2Wei(parseFloat(value), 18) eth2Wei(parseFloat(value), 18),
data = data
) )
tx.to = parseAddress(to).some tx.to = parseAddress(to).some
let response = eth.estimateGas(tx, success) let response = eth.estimateGas(tx, success)

View File

@ -114,32 +114,32 @@ Rectangle {
} }
} else if (request.type === Constants.web3SendAsyncReadOnly && } else if (request.type === Constants.web3SendAsyncReadOnly &&
request.payload.method === "eth_sendTransaction") { request.payload.method === "eth_sendTransaction") {
const sendDialog = sendTransactionModalComponent.createObject(browserWindow); walletModel.setFocusedAccountByAddress(request.payload.params[0].from)
var acc = walletModel.focusedAccount
const value = utilsModel.wei2Token(request.payload.params[0].value, 18)
_walletModel.setFocusedAccountByAddress(request.payload.params[0].from) const sendDialog = sendTransactionModalComponent.createObject(browserWindow, {
var acc = _walletModel.focusedAccount trxData:request.payload.params[0].data,
sendDialog.selectedAccount = { selectedAccount: {
name: acc.name, name: acc.name,
address: request.payload.params[0].from, address: request.payload.params[0].from,
iconColor: acc.iconColor, iconColor: acc.iconColor,
assets: acc.assets assets: acc.assets
} },
sendDialog.selectedRecipient = { selectedRecipient: {
address: request.payload.params[0].to, address: request.payload.params[0].to,
identicon: _chatsModel.generateIdenticon(request.payload.params[0].to), identicon: chatsModel.generateIdenticon(request.payload.params[0].to),
name: _chatsModel.activeChannel.name, name: chatsModel.activeChannel.name,
type: RecipientSelector.Type.Address type: RecipientSelector.Type.Address
}; },
// TODO get this from data selectedAsset: {
sendDialog.selectedAsset = { name: "ETH",
name: "ETH", symbol: "ETH",
symbol: "ETH", address: Constants.zeroAddress
address: Constants.zeroAddress },
}; selectedFiatAmount: "42", // TODO calculate that
const value = _utilsModel.wei2Token(request.payload.params[0].value, 18) selectedAmount: value
sendDialog.selectedAmount = value });
// TODO calculate that
sendDialog.selectedFiatAmount = "42";
// TODO change sendTransaction function to the postMessage one // TODO change sendTransaction function to the postMessage one
sendDialog.sendTransaction = function (selectedGasLimit, selectedGasPrice, enteredPassword) { sendDialog.sendTransaction = function (selectedGasLimit, selectedGasPrice, enteredPassword) {
@ -180,6 +180,7 @@ Rectangle {
sendDialog.destroy() sendDialog.destroy()
} }
sendDialog.estimateGas()
sendDialog.open(); sendDialog.open();
walletModel.getGasPricePredictions() walletModel.getGasPricePredictions()
} else if (request.type === Constants.web3SendAsyncReadOnly && ["eth_sign", "personal_sign", "eth_signTypedData", "eth_signTypedData_v3"].indexOf(request.payload.method) > -1) { } else if (request.type === Constants.web3SendAsyncReadOnly && ["eth_sign", "personal_sign", "eth_signTypedData", "eth_signTypedData_v3"].indexOf(request.payload.method) > -1) {

View File

@ -13,6 +13,8 @@ ModalPopup {
property var selectedAmount property var selectedAmount
property var selectedFiatAmount property var selectedFiatAmount
property string trxData: ""
property alias transactionSigner: transactionSigner property alias transactionSigner: transactionSigner
property var sendTransaction: function(selectedGasLimit, selectedGasPrice, enteredPassword) { property var sendTransaction: function(selectedGasLimit, selectedGasPrice, enteredPassword) {
@ -38,6 +40,10 @@ ModalPopup {
root.close() root.close()
} }
function estimateGas(){
gasSelector.estimateGas()
}
id: root id: root
//% "Send" //% "Send"
@ -68,7 +74,14 @@ ModalPopup {
TransactionFormGroup { TransactionFormGroup {
id: group1 id: group1
//% "Send" //% "Send"
headerText: qsTrId("command-button-send") headerText: {
if(trxData.startsWith("0x095ea7b3")){
const approveData = JSON.parse(walletModel.decodeTokenApproval(selectedRecipient.address, trxData))
if(approveData.symbol)
return qsTr("Authorize %1 %2").arg(approveData.amount).arg(approveData.symbol)
}
return qsTrId("command-button-send");
}
//% "Preview" //% "Preview"
footerText: qsTrId("preview") footerText: qsTrId("preview")
@ -87,6 +100,7 @@ ModalPopup {
} }
function estimateGas() { function estimateGas() {
console.log("CALLING ESTIMATE GAS")
if (!(root.selectedAccount && root.selectedAccount.address && if (!(root.selectedAccount && root.selectedAccount.address &&
root.selectedRecipient && root.selectedRecipient.address && root.selectedRecipient && root.selectedRecipient.address &&
root.selectedAsset && root.selectedAsset.address && root.selectedAsset && root.selectedAsset.address &&
@ -96,7 +110,8 @@ ModalPopup {
root.selectedAccount.address, root.selectedAccount.address,
root.selectedRecipient.address, root.selectedRecipient.address,
root.selectedAsset.address, root.selectedAsset.address,
root.selectedAmount)) root.selectedAmount,
trxData))
if (!gasEstimate.success) { if (!gasEstimate.success) {
//% "Error estimating gas: %1" //% "Error estimating gas: %1"