feat(wallet): hook transferEth for wallet transfers

This commit is contained in:
Jonathan Rainville 2022-02-01 16:03:47 -05:00
parent 56340bebd1
commit 0f5a6d8599
8 changed files with 119 additions and 35 deletions

View File

@ -78,3 +78,9 @@ method loadTransactions*(self: Controller, address: string, toBlock: Uint256, li
method estimateGas*(self: Controller, from_addr: string, to: string, assetAddress: string, value: string, data: string): string =
result = self.transactionService.estimateGas(from_addr, to, assetAddress, value, data)
method transferEth*(self: Controller, from_addr: string, to_addr: string, value: string,
gas: string, gasPrice: string, maxPriorityFeePerGas: string, maxFeePerGas: string,
password: string, uuid: string): bool =
result = self.transactionService.transferEth(from_addr, to_addr, value, gas, gasPrice,
maxPriorityFeePerGas, maxFeePerGas, password, uuid)

View File

@ -32,6 +32,11 @@ method setTrxHistoryResult*(self: AccessInterface, historyJSON: string) {.base.}
method estimateGas*(self: AccessInterface, from_addr: string, to: string, assetAddress: string, value: string, data: string): string {.base.} =
raise newException(ValueError, "No implementation available")
method transferEth*(self: AccessInterface, from_addr: string, to_addr: string, value: string,
gas: string, gasPrice: string, maxPriorityFeePerGas: string, maxFeePerGas: string,
password: string, uuid: string): bool {.base.} =
raise newException(ValueError, "No implementation available")
type
## Abstract class (concept) which must be implemented by object/s used in this
## module.

View File

@ -43,6 +43,11 @@ method setIsNonArchivalNode*(self: AccessInterface, isNonArchivalNode: bool) {.b
method estimateGas*(self: AccessInterface, from_addr: string, to: string, assetAddress: string, value: string, data: string): string {.base.} =
raise newException(ValueError, "No implementation available")
method transferEth*(self: AccessInterface, from_addr: string, to_addr: string, value: string,
gas: string, gasPrice: string, maxPriorityFeePerGas: string, maxFeePerGas: string,
password: string, uuid: string): bool {.base.} =
raise newException(ValueError, "No implementation available")
# View Delegate Interface
# Delegate for the view must be declared here due to use of QtObject and multi
# inheritance, which is not well supported in Nim.

View File

@ -85,3 +85,9 @@ method estimateGas*(self: Module, from_addr: string, to: string, assetAddress: s
method setIsNonArchivalNode*(self: Module, isNonArchivalNode: bool) =
self.view.setIsNonArchivalNode(isNonArchivalNode)
method transferEth*(self: Module, from_addr: string, to_addr: string, value: string, gas: string,
gasPrice: string, maxPriorityFeePerGas: string, maxFeePerGas: string, password: string,
uuid: string): bool =
result = self.controller.transferEth(from_addr, to_addr, value, gas, gasPrice,
maxPriorityFeePerGas, maxFeePerGas, password, uuid)

View File

@ -103,6 +103,11 @@ QtObject:
read = getIsNonArchivalNode
notify = isNonArchivalNodeChanged
proc estimateGas*(self: View, from_addr: string, to: string, assetAddress: string, value: string, data: string): string {.slot.} =
result = self.delegate.estimateGas(from_addr, to, assetAddress, value, data)
proc transferEth*(self: View, from_addr: string, to_addr: string, value: string, gas: string,
gasPrice: string, maxPriorityFeePerGas: string, maxFeePerGas: string, password: string,
uuid: string): bool {.slot.} =
result = self.delegate.transferEth(from_addr, to_addr, value, gas, gasPrice,
maxPriorityFeePerGas, maxFeePerGas, password, uuid)

View File

@ -143,7 +143,14 @@ QtObject:
)
self.threadpool.start(arg)
proc estimateGas*(self: Service, from_addr: string, to: string, assetAddress: string, value: string, data: string = ""): string {.slot.} =
proc estimateGas*(
self: Service,
from_addr: string,
to: string,
assetAddress: string,
value: string,
data: string = ""
): string {.slot.} =
var response: RpcResponse[JsonNode]
try:
if assetAddress != ZERO_ADDRESS and not assetAddress.isEmptyOrWhitespace:
@ -178,3 +185,36 @@ QtObject:
error "Error estimating gas", msg = e.msg
result = $(%* { "result": "-1", "success": false, "error": { "message": e.msg } })
proc transferEth*(
self: Service,
from_addr: string,
to_addr: string,
value: string,
gas: string,
gasPrice: string,
maxPriorityFeePerGas: string,
maxFeePerGas: string,
password: string,
uuid: string
): bool {.slot.} =
try:
let eip1559Enabled = self.settingsService.isEIP1559Enabled()
eth_utils.validateTransactionInput(from_addr, to_addr, assetAddress = "", value, gas,
gasPrice, data = "", eip1559Enabled, maxPriorityFeePerGas, maxFeePerGas, uuid)
# TODO move this to another thread
var tx = ens_utils.buildTransaction(parseAddress(from_addr), eth2Wei(parseFloat(value), 18),
gas, gasPrice, eip1559Enabled, maxPriorityFeePerGas, maxFeePerGas)
tx.to = parseAddress(to_addr).some
let json: JsonNode = %tx
let response = eth.sendTransaction($json, password)
if response.error != nil:
raise newException(Exception, response.error.message)
self.trackPendingTransaction(response.result.getStr, from_addr, to_addr,
$PendingTransactionTypeDto.WalletTransfer, data = "")
except Exception as e:
error "Error sending eth transfer transaction", msg = e.msg
return false
return true

View File

@ -68,4 +68,9 @@ QtObject {
function getGasEthValue(gweiValue, gasLimit) {
return profileSectionStore.ensUsernamesStore.getGasEthValue(gweiValue, gasLimit)
}
function transferEth(from, to, amount, gasLimit, gasPrice, tipLimit, overallLimit, password, uuid) {
return walletSectionTransactions.transferEth(from, to, amount, gasLimit, gasPrice, tipLimit,
overallLimit, password, uuid);
}
}

View File

@ -37,39 +37,51 @@ ModalPopup {
}
function sendTransaction() {
// Not Refactored Yet
// stack.currentGroup.isPending = true
// let success = false
// if(txtAmount.selectedAsset.address === "" || txtAmount.selectedAsset.address === Constants.zeroAddress){
// success = RootStore.transferEth(
// selectFromAccount.selectedAccount.address,
// selectRecipient.selectedRecipient.address,
// txtAmount.selectedAmount,
// gasSelector.selectedGasLimit,
// gasSelector.eip1599Enabled ? "" : gasSelector.selectedGasPrice,
// gasSelector.selectedTipLimit,
// gasSelector.selectedOverallLimit,
// transactionSigner.enteredPassword,
// stack.uuid)
// } else {
// success = RootStore.transferTokens(
// selectFromAccount.selectedAccount.address,
// selectRecipient.selectedRecipient.address,
// txtAmount.selectedAsset.address,
// txtAmount.selectedAmount,
// gasSelector.selectedGasLimit,
// gasSelector.eip1599Enabled ? "" : gasSelector.selectedGasPrice,
// gasSelector.selectedTipLimit,
// gasSelector.selectedOverallLimit,
// transactionSigner.enteredPassword,
// stack.uuid)
// }
stack.currentGroup.isPending = true
let success = false
if(txtAmount.selectedAsset.address === "" || txtAmount.selectedAsset.address === Constants.zeroAddress){
success = root.store.transferEth(
selectFromAccount.selectedAccount.address,
selectRecipient.selectedRecipient.address,
txtAmount.selectedAmount,
gasSelector.selectedGasLimit,
gasSelector.eip1599Enabled ? "" : gasSelector.selectedGasPrice,
gasSelector.selectedTipLimit,
gasSelector.selectedOverallLimit,
transactionSigner.enteredPassword,
stack.uuid)
} else {
// Not Refactored Yet
// success = RootStore.transferTokens(
// selectFromAccount.selectedAccount.address,
// selectRecipient.selectedRecipient.address,
// txtAmount.selectedAsset.address,
// txtAmount.selectedAmount,
// gasSelector.selectedGasLimit,
// gasSelector.eip1599Enabled ? "" : gasSelector.selectedGasPrice,
// gasSelector.selectedTipLimit,
// gasSelector.selectedOverallLimit,
// transactionSigner.enteredPassword,
// stack.uuid)
}
// if(!success){
// //% "Invalid transaction parameters"
// sendingError.text = qsTrId("invalid-transaction-parameters")
// sendingError.open()
// }
if(!success){
//% "Invalid transaction parameters"
sendingError.text = qsTrId("invalid-transaction-parameters")
sendingError.open()
} else {
// TODO remove this else once the thread and connection are back
stack.currentGroup.isPending = false
//% "Transaction pending..."
Global.toastMessage.title = qsTrId("ens-transaction-pending")
Global.toastMessage.source = Style.svg("loading")
Global.toastMessage.iconColor = Style.current.primary
Global.toastMessage.iconRotates = true
// Refactor this
// Global.toastMessage.link = `${walletModel.utilsView.etherscanLink}/${response.result}`
Global.toastMessage.open()
root.close()
}
}
TransactionStackView {