aboutsummaryrefslogtreecommitdiffstats
path: root/app/scripts/controllers
diff options
context:
space:
mode:
Diffstat (limited to 'app/scripts/controllers')
-rw-r--r--app/scripts/controllers/transactions/index.js55
-rw-r--r--app/scripts/controllers/transactions/tx-gas-utils.js11
2 files changed, 59 insertions, 7 deletions
diff --git a/app/scripts/controllers/transactions/index.js b/app/scripts/controllers/transactions/index.js
index 2ce736beb..dc6a043e4 100644
--- a/app/scripts/controllers/transactions/index.js
+++ b/app/scripts/controllers/transactions/index.js
@@ -3,6 +3,17 @@ const ObservableStore = require('obs-store')
const ethUtil = require('ethereumjs-util')
const Transaction = require('ethereumjs-tx')
const EthQuery = require('ethjs-query')
+const abi = require('human-standard-token-abi')
+const abiDecoder = require('abi-decoder')
+abiDecoder.addABI(abi)
+const {
+ TOKEN_METHOD_APPROVE,
+ TOKEN_METHOD_TRANSFER,
+ TOKEN_METHOD_TRANSFER_FROM,
+ SEND_ETHER_ACTION_KEY,
+ DEPLOY_CONTRACT_ACTION_KEY,
+ CONTRACT_INTERACTION_KEY,
+} = require('../../../../ui/app/helpers/constants/transactions.js')
const TransactionStateManager = require('./tx-state-manager')
const TxGasUtil = require('./tx-gas-utils')
const PendingTransactionTracker = require('./pending-tx-tracker')
@@ -180,9 +191,11 @@ class TransactionController extends EventEmitter {
}
txUtils.validateTxParams(normalizedTxParams)
// construct txMeta
+ const { transactionCategory, code } = await this._determineTransactionCategory(txParams)
let txMeta = this.txStateManager.generateTxMeta({
txParams: normalizedTxParams,
type: TRANSACTION_TYPE_STANDARD,
+ transactionCategory,
})
this.addTx(txMeta)
this.emit('newUnapprovedTx', txMeta)
@@ -191,7 +204,7 @@ class TransactionController extends EventEmitter {
// check whether recipient account is blacklisted
recipientBlacklistChecker.checkAccount(txMeta.metamaskNetworkId, normalizedTxParams.to)
// add default tx params
- txMeta = await this.addTxGasDefaults(txMeta)
+ txMeta = await this.addTxGasDefaults(txMeta, code)
} catch (error) {
log.warn(error)
txMeta.loadingDefaults = false
@@ -211,7 +224,7 @@ class TransactionController extends EventEmitter {
@param txMeta {Object} - the txMeta object
@returns {Promise<object>} resolves with txMeta
*/
- async addTxGasDefaults (txMeta) {
+ async addTxGasDefaults (txMeta, code) {
const txParams = txMeta.txParams
// ensure value
txParams.value = txParams.value ? ethUtil.addHexPrefix(txParams.value) : '0x0'
@@ -222,7 +235,7 @@ class TransactionController extends EventEmitter {
}
txParams.gasPrice = ethUtil.addHexPrefix(gasPrice.toString(16))
// set gasLimit
- return await this.txGasUtil.analyzeGasUsage(txMeta)
+ return await this.txGasUtil.analyzeGasUsage(txMeta, code)
}
/**
@@ -556,6 +569,42 @@ class TransactionController extends EventEmitter {
}
/**
+ Returns a "type" for a transaction out of the following list: simpleSend, tokenTransfer, tokenApprove,
+ contractDeployment, contractMethodCall
+ */
+ async _determineTransactionCategory (txParams) {
+ const { data, to } = txParams
+ const { name } = data && abiDecoder.decodeMethod(data) || {}
+ const tokenMethodName = [
+ TOKEN_METHOD_APPROVE,
+ TOKEN_METHOD_TRANSFER,
+ TOKEN_METHOD_TRANSFER_FROM,
+ ].find(tokenMethodName => tokenMethodName === name && name.toLowerCase())
+
+ let result
+ let code
+ if (!txParams.data) {
+ result = SEND_ETHER_ACTION_KEY
+ } else if (tokenMethodName) {
+ result = tokenMethodName
+ } else if (!to) {
+ result = DEPLOY_CONTRACT_ACTION_KEY
+ } else {
+ try {
+ code = await this.query.getCode(to)
+ } catch (e) {
+ log.warn(e)
+ }
+ // For an address with no code, geth will return '0x', and ganache-core v2.2.1 will return '0x0'
+ const codeIsEmpty = !code || code === '0x' || code === '0x0'
+
+ result = codeIsEmpty ? SEND_ETHER_ACTION_KEY : CONTRACT_INTERACTION_KEY
+ }
+
+ return { transactionCategory: result, code }
+ }
+
+ /**
Sets other txMeta statuses to dropped if the txMeta that has been confirmed has other transactions
in the list have the same nonce
diff --git a/app/scripts/controllers/transactions/tx-gas-utils.js b/app/scripts/controllers/transactions/tx-gas-utils.js
index 765551167..2dc461f48 100644
--- a/app/scripts/controllers/transactions/tx-gas-utils.js
+++ b/app/scripts/controllers/transactions/tx-gas-utils.js
@@ -4,6 +4,7 @@ const {
BnMultiplyByFraction,
bnToHex,
} = require('../../lib/util')
+const log = require('loglevel')
const { addHexPrefix } = require('ethereumjs-util')
const SIMPLE_GAS_COST = '0x5208' // Hex for 21000, cost of a simple send.
@@ -24,14 +25,16 @@ class TxGasUtil {
/**
@param txMeta {Object} - the txMeta object
+ @param code {string} - the code at the txs address, as returned by this.query.getCode(to)
@returns {object} the txMeta object with the gas written to the txParams
*/
- async analyzeGasUsage (txMeta) {
+ async analyzeGasUsage (txMeta, code) {
const block = await this.query.getBlockByNumber('latest', false)
let estimatedGasHex
try {
- estimatedGasHex = await this.estimateTxGas(txMeta, block.gasLimit)
+ estimatedGasHex = await this.estimateTxGas(txMeta, block.gasLimit, code)
} catch (err) {
+ log.warn(err)
txMeta.simulationFails = {
reason: err.message,
errorKey: err.errorKey,
@@ -52,9 +55,10 @@ class TxGasUtil {
Estimates the tx's gas usage
@param txMeta {Object} - the txMeta object
@param blockGasLimitHex {string} - hex string of the block's gas limit
+ @param code {string} - the code at the txs address, as returned by this.query.getCode(to)
@returns {string} the estimated gas limit as a hex string
*/
- async estimateTxGas (txMeta, blockGasLimitHex) {
+ async estimateTxGas (txMeta, blockGasLimitHex, code) {
const txParams = txMeta.txParams
// check if gasLimit is already specified
@@ -70,7 +74,6 @@ class TxGasUtil {
// see if we can set the gas based on the recipient
if (hasRecipient) {
- const code = await this.query.getCode(recipient)
// For an address with no code, geth will return '0x', and ganache-core v2.2.1 will return '0x0'
const codeIsEmpty = !code || code === '0x' || code === '0x0'