aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorThomas <thomas.b.huang@gmail.com>2018-05-17 15:01:36 +0800
committerThomas <thomas.b.huang@gmail.com>2018-05-17 15:01:36 +0800
commit770379c3da4f625b265d752d45423d179dfc0b9d (patch)
treedb908a8fa5f4979ffcac4436d2227294d0df94e4
parent5e80bc4cb93277c8b3952345a6cb4cc055248b94 (diff)
parent708422432c634ffbd4c73388f980c43f766b3355 (diff)
downloadtangerine-wallet-browser-770379c3da4f625b265d752d45423d179dfc0b9d.tar
tangerine-wallet-browser-770379c3da4f625b265d752d45423d179dfc0b9d.tar.gz
tangerine-wallet-browser-770379c3da4f625b265d752d45423d179dfc0b9d.tar.bz2
tangerine-wallet-browser-770379c3da4f625b265d752d45423d179dfc0b9d.tar.lz
tangerine-wallet-browser-770379c3da4f625b265d752d45423d179dfc0b9d.tar.xz
tangerine-wallet-browser-770379c3da4f625b265d752d45423d179dfc0b9d.tar.zst
tangerine-wallet-browser-770379c3da4f625b265d752d45423d179dfc0b9d.zip
Merge branch 'develop' into testing
-rw-r--r--app/scripts/controllers/network/enums.js26
-rw-r--r--app/scripts/controllers/network/network.js121
-rw-r--r--app/scripts/controllers/network/util.js36
-rw-r--r--app/scripts/controllers/transactions/lib/tx-state-history-helper.js21
-rw-r--r--app/scripts/controllers/transactions/tx-state-manager.js2
-rw-r--r--app/scripts/first-time-state.js9
-rw-r--r--app/scripts/lib/setupRaven.js42
-rw-r--r--app/scripts/metamask-controller.js1
-rw-r--r--docs/send-screen-QA-checklist.md96
-rw-r--r--old-ui/app/app.js3
-rw-r--r--test/unit/network-contoller-test.js30
-rw-r--r--test/unit/tx-state-history-helper-test.js139
-rw-r--r--test/unit/tx-state-history-helper.js46
-rw-r--r--test/unit/tx-state-manager-test.js9
-rw-r--r--ui/app/actions.js18
-rw-r--r--ui/app/app.js13
-rw-r--r--ui/app/components/app-header/app-header.component.js44
-rw-r--r--ui/app/components/pages/settings/settings.js2
-rw-r--r--ui/app/components/pages/unlock-page/unlock-page.component.js1
-rw-r--r--ui/app/components/pages/unlock-page/unlock-page.container.js2
-rw-r--r--ui/app/components/pending-tx/confirm-send-ether.js14
-rw-r--r--ui/app/css/itcss/components/account-menu.scss4
-rw-r--r--ui/app/css/itcss/components/header.scss4
-rw-r--r--ui/app/first-time/init-menu.js2
-rw-r--r--ui/app/select-app.js5
-rw-r--r--ui/index.js9
26 files changed, 371 insertions, 328 deletions
diff --git a/app/scripts/controllers/network/enums.js b/app/scripts/controllers/network/enums.js
index 4f29e301b..9da7f309c 100644
--- a/app/scripts/controllers/network/enums.js
+++ b/app/scripts/controllers/network/enums.js
@@ -13,20 +13,6 @@ const RINKEBY_DISPLAY_NAME = 'Rinkeby'
const KOVAN_DISPLAY_NAME = 'Kovan'
const MAINNET_DISPLAY_NAME = 'Main Ethereum Network'
-const MAINNET_RPC_URL = 'https://mainnet.infura.io/metamask'
-const ROPSTEN_RPC_URL = 'https://ropsten.infura.io/metamask'
-const KOVAN_RPC_URL = 'https://kovan.infura.io/metamask'
-const RINKEBY_RPC_URL = 'https://rinkeby.infura.io/metamask'
-const LOCALHOST_RPC_URL = 'http://localhost:8545'
-
-const MAINNET_RPC_URL_BETA = 'https://mainnet.infura.io/metamask2'
-const ROPSTEN_RPC_URL_BETA = 'https://ropsten.infura.io/metamask2'
-const KOVAN_RPC_URL_BETA = 'https://kovan.infura.io/metamask2'
-const RINKEBY_RPC_URL_BETA = 'https://rinkeby.infura.io/metamask2'
-
-const DEFAULT_NETWORK = 'rinkeby'
-const OLD_UI_NETWORK_TYPE = 'network'
-const BETA_UI_NETWORK_TYPE = 'networkBeta'
module.exports = {
ROPSTEN,
@@ -41,16 +27,4 @@ module.exports = {
RINKEBY_DISPLAY_NAME,
KOVAN_DISPLAY_NAME,
MAINNET_DISPLAY_NAME,
- MAINNET_RPC_URL,
- ROPSTEN_RPC_URL,
- KOVAN_RPC_URL,
- RINKEBY_RPC_URL,
- LOCALHOST_RPC_URL,
- MAINNET_RPC_URL_BETA,
- ROPSTEN_RPC_URL_BETA,
- KOVAN_RPC_URL_BETA,
- RINKEBY_RPC_URL_BETA,
- DEFAULT_NETWORK,
- OLD_UI_NETWORK_TYPE,
- BETA_UI_NETWORK_TYPE,
}
diff --git a/app/scripts/controllers/network/network.js b/app/scripts/controllers/network/network.js
index 2f5b81cd2..93fde7c57 100644
--- a/app/scripts/controllers/network/network.js
+++ b/app/scripts/controllers/network/network.js
@@ -14,52 +14,40 @@ const {
RINKEBY,
KOVAN,
MAINNET,
- OLD_UI_NETWORK_TYPE,
- DEFAULT_NETWORK,
+ LOCALHOST,
} = require('./enums')
-const { getNetworkEndpoints } = require('./util')
+const LOCALHOST_RPC_URL = 'http://localhost:8545'
const INFURA_PROVIDER_TYPES = [ROPSTEN, RINKEBY, KOVAN, MAINNET]
+const env = process.env.METAMASK_ENV
+const METAMASK_DEBUG = process.env.METAMASK_DEBUG
+const testMode = (METAMASK_DEBUG || env === 'test')
+
+const defaultProviderConfig = {
+ type: testMode ? RINKEBY : MAINNET,
+}
+
module.exports = class NetworkController extends EventEmitter {
- constructor (config) {
+ constructor (opts = {}) {
super()
- this._networkEndpointVersion = OLD_UI_NETWORK_TYPE
- this._networkEndpoints = getNetworkEndpoints(OLD_UI_NETWORK_TYPE)
- this._defaultRpc = this._networkEndpoints[DEFAULT_NETWORK]
-
- config.provider.rpcTarget = this.getRpcAddressForType(config.provider.type, config.provider)
+ // parse options
+ const providerConfig = opts.provider || defaultProviderConfig
+ // create stores
+ this.providerStore = new ObservableStore(providerConfig)
this.networkStore = new ObservableStore('loading')
- this.providerStore = new ObservableStore(config.provider)
this.store = new ComposedStore({ provider: this.providerStore, network: this.networkStore })
+ // create event emitter proxy
this._proxy = createEventEmitterProxy()
this.on('networkDidChange', this.lookupNetwork)
}
- async setNetworkEndpoints (version) {
- if (version === this._networkEndpointVersion) {
- return
- }
-
- this._networkEndpointVersion = version
- this._networkEndpoints = getNetworkEndpoints(version)
- this._defaultRpc = this._networkEndpoints[DEFAULT_NETWORK]
- const { type } = this.getProviderConfig()
-
- return this.setProviderType(type, true)
- }
-
initializeProvider (_providerParams) {
this._baseProviderParams = _providerParams
const { type, rpcTarget } = this.providerStore.getState()
- // map rpcTarget to rpcUrl
- const opts = {
- type,
- rpcUrl: rpcTarget,
- }
- this._configureProvider(opts)
+ this._configureProvider({ type, rpcTarget })
this._proxy.on('block', this._logBlock.bind(this))
this._proxy.on('error', this.verifyNetwork.bind(this))
this.ethQuery = new EthQuery(this._proxy)
@@ -96,45 +84,27 @@ module.exports = class NetworkController extends EventEmitter {
})
}
- setRpcTarget (rpcUrl) {
- this.providerStore.updateState({
+ setRpcTarget (rpcTarget) {
+ const providerConfig = {
type: 'rpc',
- rpcTarget: rpcUrl,
- })
- this._switchNetwork({ rpcUrl })
- }
-
- getCurrentRpcAddress () {
- const provider = this.getProviderConfig()
- if (!provider) return null
- return this.getRpcAddressForType(provider.type)
- }
-
- async setProviderType (type, forceUpdate = false) {
- assert(type !== 'rpc', `NetworkController.setProviderType - cannot connect by type "rpc"`)
- // skip if type already matches
- if (type === this.getProviderConfig().type && !forceUpdate) {
- return
+ rpcTarget,
}
+ this.providerStore.updateState(providerConfig)
+ this._switchNetwork(providerConfig)
+ }
- const rpcTarget = this.getRpcAddressForType(type)
- assert(rpcTarget, `NetworkController - unknown rpc address for type "${type}"`)
- this.providerStore.updateState({ type, rpcTarget })
- this._switchNetwork({ type })
+ async setProviderType (type) {
+ assert.notEqual(type, 'rpc', `NetworkController - cannot call "setProviderType" with type 'rpc'. use "setRpcTarget"`)
+ assert(INFURA_PROVIDER_TYPES.includes(type) || type === LOCALHOST, `NetworkController - Unknown rpc type "${type}"`)
+ const providerConfig = { type }
+ this.providerStore.updateState(providerConfig)
+ this._switchNetwork(providerConfig)
}
getProviderConfig () {
return this.providerStore.getState()
}
- getRpcAddressForType (type, provider = this.getProviderConfig()) {
- if (this._networkEndpoints[type]) {
- return this._networkEndpoints[type]
- }
-
- return provider && provider.rpcTarget ? provider.rpcTarget : this._defaultRpc
- }
-
//
// Private
//
@@ -146,32 +116,27 @@ module.exports = class NetworkController extends EventEmitter {
}
_configureProvider (opts) {
- // type-based rpc endpoints
- const { type } = opts
- if (type) {
- // type-based infura rpc endpoints
- const isInfura = INFURA_PROVIDER_TYPES.includes(type)
- opts.rpcUrl = this.getRpcAddressForType(type)
- if (isInfura) {
- this._configureInfuraProvider(opts)
- // other type-based rpc endpoints
- } else {
- this._configureStandardProvider(opts)
- }
+ const { type, rpcTarget } = opts
+ // infura type-based endpoints
+ const isInfura = INFURA_PROVIDER_TYPES.includes(type)
+ if (isInfura) {
+ this._configureInfuraProvider(opts)
+ // other type-based rpc endpoints
+ } else if (type === LOCALHOST) {
+ this._configureStandardProvider({ rpcUrl: LOCALHOST_RPC_URL })
// url-based rpc endpoints
+ } else if (type === 'rpc'){
+ this._configureStandardProvider({ rpcUrl: rpcTarget })
} else {
- this._configureStandardProvider(opts)
+ throw new Error(`NetworkController - _configureProvider - unknown type "${type}"`)
}
}
- _configureInfuraProvider (opts) {
- log.info('_configureInfuraProvider', opts)
- const infuraProvider = createInfuraProvider({
- network: opts.type,
- })
+ _configureInfuraProvider ({ type }) {
+ log.info('_configureInfuraProvider', type)
+ const infuraProvider = createInfuraProvider({ network: type })
const infuraSubprovider = new SubproviderFromProvider(infuraProvider)
const providerParams = extend(this._baseProviderParams, {
- rpcUrl: opts.rpcUrl,
engineParams: {
pollingInterval: 8000,
blockTrackerProvider: infuraProvider,
diff --git a/app/scripts/controllers/network/util.js b/app/scripts/controllers/network/util.js
index 4f38ccda4..261dae721 100644
--- a/app/scripts/controllers/network/util.js
+++ b/app/scripts/controllers/network/util.js
@@ -3,7 +3,6 @@ const {
RINKEBY,
KOVAN,
MAINNET,
- LOCALHOST,
ROPSTEN_CODE,
RINKEYBY_CODE,
KOVAN_CODE,
@@ -11,17 +10,6 @@ const {
RINKEBY_DISPLAY_NAME,
KOVAN_DISPLAY_NAME,
MAINNET_DISPLAY_NAME,
- MAINNET_RPC_URL,
- ROPSTEN_RPC_URL,
- KOVAN_RPC_URL,
- RINKEBY_RPC_URL,
- LOCALHOST_RPC_URL,
- MAINNET_RPC_URL_BETA,
- ROPSTEN_RPC_URL_BETA,
- KOVAN_RPC_URL_BETA,
- RINKEBY_RPC_URL_BETA,
- OLD_UI_NETWORK_TYPE,
- BETA_UI_NETWORK_TYPE,
} = require('./enums')
const networkToNameMap = {
@@ -34,32 +22,8 @@ const networkToNameMap = {
[KOVAN_CODE]: KOVAN_DISPLAY_NAME,
}
-const networkEndpointsMap = {
- [OLD_UI_NETWORK_TYPE]: {
- [LOCALHOST]: LOCALHOST_RPC_URL,
- [MAINNET]: MAINNET_RPC_URL,
- [ROPSTEN]: ROPSTEN_RPC_URL,
- [KOVAN]: KOVAN_RPC_URL,
- [RINKEBY]: RINKEBY_RPC_URL,
- },
- [BETA_UI_NETWORK_TYPE]: {
- [LOCALHOST]: LOCALHOST_RPC_URL,
- [MAINNET]: MAINNET_RPC_URL_BETA,
- [ROPSTEN]: ROPSTEN_RPC_URL_BETA,
- [KOVAN]: KOVAN_RPC_URL_BETA,
- [RINKEBY]: RINKEBY_RPC_URL_BETA,
- },
-}
-
const getNetworkDisplayName = key => networkToNameMap[key]
-const getNetworkEndpoints = (networkType = OLD_UI_NETWORK_TYPE) => {
- return {
- ...networkEndpointsMap[networkType],
- }
-}
-
module.exports = {
getNetworkDisplayName,
- getNetworkEndpoints,
}
diff --git a/app/scripts/controllers/transactions/lib/tx-state-history-helper.js b/app/scripts/controllers/transactions/lib/tx-state-history-helper.js
index 59a4b562c..4562568e9 100644
--- a/app/scripts/controllers/transactions/lib/tx-state-history-helper.js
+++ b/app/scripts/controllers/transactions/lib/tx-state-history-helper.js
@@ -25,26 +25,31 @@ function migrateFromSnapshotsToDiffs (longHistory) {
}
/**
- generates an array of history objects sense the previous state.
- The object has the keys opp(the operation preformed),
- path(the key and if a nested object then each key will be seperated with a `/`)
- value
- with the first entry having the note
+ Generates an array of history objects sense the previous state.
+ The object has the keys
+ op (the operation performed),
+ path (the key and if a nested object then each key will be seperated with a `/`)
+ value
+ with the first entry having the note and a timestamp when the change took place
@param previousState {object} - the previous state of the object
@param newState {object} - the update object
@param note {string} - a optional note for the state change
- @reurns {array}
+ @returns {array}
*/
function generateHistoryEntry (previousState, newState, note) {
const entry = jsonDiffer.compare(previousState, newState)
// Add a note to the first op, since it breaks if we append it to the entry
- if (note && entry[0]) entry[0].note = note
+ if (entry[0]) {
+ if (note) entry[0].note = note
+
+ entry[0].timestamp = Date.now()
+ }
return entry
}
/**
Recovers previous txMeta state obj
- @return {object}
+ @returns {object}
*/
function replayHistory (_shortHistory) {
const shortHistory = clone(_shortHistory)
diff --git a/app/scripts/controllers/transactions/tx-state-manager.js b/app/scripts/controllers/transactions/tx-state-manager.js
index 380214c1d..00e837571 100644
--- a/app/scripts/controllers/transactions/tx-state-manager.js
+++ b/app/scripts/controllers/transactions/tx-state-manager.js
@@ -158,7 +158,7 @@ class TransactionStateManager extends EventEmitter {
/**
updates the txMeta in the list and adds a history entry
@param txMeta {Object} - the txMeta to update
- @param [note] {string} - a not about the update for history
+ @param [note] {string} - a note about the update for history
*/
updateTx (txMeta, note) {
// validate txParams
diff --git a/app/scripts/first-time-state.js b/app/scripts/first-time-state.js
index c49d89288..13119bc04 100644
--- a/app/scripts/first-time-state.js
+++ b/app/scripts/first-time-state.js
@@ -1,7 +1,3 @@
-// test and development environment variables
-const env = process.env.METAMASK_ENV
-const METAMASK_DEBUG = process.env.METAMASK_DEBUG
-const { DEFAULT_NETWORK, MAINNET } = require('./controllers/network/enums')
/**
* @typedef {Object} FirstTimeState
@@ -14,11 +10,6 @@ const { DEFAULT_NETWORK, MAINNET } = require('./controllers/network/enums')
*/
const initialState = {
config: {},
- NetworkController: {
- provider: {
- type: (METAMASK_DEBUG || env === 'test') ? DEFAULT_NETWORK : MAINNET,
- },
- },
}
module.exports = initialState
diff --git a/app/scripts/lib/setupRaven.js b/app/scripts/lib/setupRaven.js
index b1b67f771..d164827ab 100644
--- a/app/scripts/lib/setupRaven.js
+++ b/app/scripts/lib/setupRaven.js
@@ -25,7 +25,7 @@ function setupRaven(opts) {
const report = opts.data
try {
// handle error-like non-error exceptions
- nonErrorException(report)
+ rewriteErrorLikeExceptions(report)
// simplify certain complex error messages (e.g. Ethjs)
simplifyErrorMessages(report)
// modify report urls
@@ -42,27 +42,35 @@ function setupRaven(opts) {
return Raven
}
-function nonErrorException(report) {
- // handle errors that lost their error-ness in serialization
- if (report.message.includes('Non-Error exception captured with keys: message')) {
- if (!(report.extra && report.extra.__serialized__)) return
- report.message = `Non-Error Exception: ${report.extra.__serialized__.message}`
- }
+function rewriteErrorLikeExceptions(report) {
+ // handle errors that lost their error-ness in serialization (e.g. dnode)
+ rewriteErrorMessages(report, (errorMessage) => {
+ if (!errorMessage.includes('Non-Error exception captured with keys:')) return errorMessage
+ if (!(report.extra && report.extra.__serialized__ && report.extra.__serialized__.message)) return errorMessage
+ return `Non-Error Exception: ${report.extra.__serialized__.message}`
+ })
}
function simplifyErrorMessages(report) {
+ rewriteErrorMessages(report, (errorMessage) => {
+ // simplify ethjs error messages
+ errorMessage = extractEthjsErrorMessage(errorMessage)
+ // simplify 'Transaction Failed: known transaction'
+ if (errorMessage.indexOf('Transaction Failed: known transaction') === 0) {
+ // cut the hash from the error message
+ errorMessage = 'Transaction Failed: known transaction'
+ }
+ return errorMessage
+ })
+}
+
+function rewriteErrorMessages(report, rewriteFn) {
+ // rewrite top level message
+ report.message = rewriteFn(report.message)
+ // rewrite each exception message
if (report.exception && report.exception.values) {
report.exception.values.forEach(item => {
- let errorMessage = item.value
- // simplify ethjs error messages
- errorMessage = extractEthjsErrorMessage(errorMessage)
- // simplify 'Transaction Failed: known transaction'
- if (errorMessage.indexOf('Transaction Failed: known transaction') === 0) {
- // cut the hash from the error message
- errorMessage = 'Transaction Failed: known transaction'
- }
- // finalize
- item.value = errorMessage
+ item.value = rewriteFn(item.value)
})
}
}
diff --git a/app/scripts/metamask-controller.js b/app/scripts/metamask-controller.js
index a90acb4d5..a6b5d3453 100644
--- a/app/scripts/metamask-controller.js
+++ b/app/scripts/metamask-controller.js
@@ -355,7 +355,6 @@ module.exports = class MetamaskController extends EventEmitter {
submitPassword: nodeify(keyringController.submitPassword, keyringController),
// network management
- setNetworkEndpoints: nodeify(networkController.setNetworkEndpoints, networkController),
setProviderType: nodeify(networkController.setProviderType, networkController),
setCustomRpc: nodeify(this.setCustomRpc, this),
diff --git a/docs/send-screen-QA-checklist.md b/docs/send-screen-QA-checklist.md
new file mode 100644
index 000000000..52167b50b
--- /dev/null
+++ b/docs/send-screen-QA-checklist.md
@@ -0,0 +1,96 @@
+# Send screen QA checklist:
+
+This checklist can be to guide QA of the send screen. It can also be used to guide e2e tests for the send screen.
+
+Once all of these are QA verified on master, resolutions to any bugs related to the send screen should include and update to this list.
+
+Additional features or functionality on the send screen should include an update to this list.
+
+## Send Eth mode
+ - [ ] **Header** _It should:_
+ - [ ] have title "Send ETH"
+ - [ ] have sub title "Only send ETH to an Ethereum address."
+ - [ ] return user to main screen when top right X is clicked
+ - [ ] **From row** _It should:_
+ - [ ] show the currently selected account by default
+ - [ ] show a dropdown with all of the users accounts
+ - [ ] contain the following info for each account: identicon, account name, balance in ETH, balance in current currency
+ - [ ] change the account selected in the dropdown (but not the app-wide selected account) when one in the dropdown is clicked
+ - [ ] close the dropdown, without changing the dropdown selected account, when the dropdown is open and then a click happens outside it
+ - [ ] **To row** _It should:_
+ - [ ] Show a placeholder with the text 'Recipient Address' by default
+ - [ ] Show, when clicked, a dropdown list of all 'to accounts': the users accounts, plus any other accounts they have previously sent to
+ - [ ] Show account address, and account name if it exists, of each item in the dropdown list
+ - [ ] Show a dropdown list of all to accounts (see above) whose address matches an address currently being typed in
+ - [ ] Set the input text to the address of an account clicked in the dropdown list, and also hide the dropdown
+ - [ ] Hide the dropdown without changing what is in the input if the user clicks outside the dropdown list while it is open
+ - [ ] Select the text in the input (i.e. the address) if an address is displayed and then clicked
+ - [ ] Show a 'required' error if the dropdown is opened but no account is selected
+ - [ ] Show an 'invalid address' error if text is entered in the input that cannot be a valid hex address or ens address
+ - [ ] Support ens names. (enter dinodan.eth on mainnet) After entering the plain text address, the hex address should appear in the input with a green checkmark beside
+ - [ ] Should show a 'no such address' error if a non-existent ens address is entered
+ - [ ] **Amount row** _It should:_
+ - [ ] allow user to enter any rational number >= 0
+ - [ ] allow user to copy and paste into the field
+ - [ ] show an insufficient funds error if an amount > balance - gas fee
+ - [ ] display 'ETH' after the number amount. The position of 'ETH' should change as the length of the input amount text changes
+ - [ ] display the value of the amount of ETH in the current currency, formatted in that currency
+ - [ ] show a 'max' but if amount < balance - gas fee
+ - [ ] show no max button or error if amount === balance - gas fee
+ - [ ] set the amount to balance - gas fee if the 'max' button is clicked
+ - [ ] **Gas Fee Display row** _It should:_
+ - [ ] Default to the fee given by the estimated gas price
+ - [ ] display the fee in ETH and the current currency
+ - [ ] update when changes are made using the customize gas modal
+ - [ ] **Cancel button** _It should:_
+ - [ ] Take the user back to the main screen
+ - [ ] **submit button** _It should:_
+ - [ ] be disabled if no recipient address is provided or if any field is in error
+ - [ ] sign a transaction with the info in the above form, and display the details of that transaction on the confirm screen
+
+## Send token mode
+- [ ] **Header** _It should:_
+ - [ ] have title "Send Tokens"
+ - [ ] have sub title "Only send [token symbol] to an Ethereum address."
+ - [ ] return user to main screen when top right X is clicked
+- [ ] **From row** _It should:_
+ - [ ] Behave the same as 'Send ETH mode' (see above)
+- [ ] **To row** _It should:_
+ - [ ] Behave the same as 'Send ETH mode' (see above)
+- [ ] **Amount row** _It should:_
+ - [ ] allow user to enter any rational number >= 0
+ - [ ] allow user to copy and paste into the field
+ - [ ] show an 'insufficient tokens' error if an amount > token balance
+ - [ ] show an 'insufficient funds' error if an gas fee > eth balance
+ - [ ] display [token symbol] after the number amount. The position of [token symbol] should change as the length of the input amount text changes
+ - [ ] display the value of the amount of tokens in the current currency, formatted in that currency
+ - [ ] show a 'max' but if amount < token balance
+ - [ ] show no max button or error if amount === token balance
+ - [ ] set the amount to token balance if the 'max' button is clicked
+- [ ] **Gas Fee Display row** _It should:_
+ - [ ] Behave the same as 'Send ETH mode' (see above)
+- [ ] **Cancel button** _It should:_
+ - [ ] Take the user back to the main screen
+- [ ] **submit button** _It should:_
+ - [ ] be disabled if no recipient address is provided or if any field is in error
+ - [ ] sign a token transaction with the info in the above form, and display the details of that transaction on the confirm screen
+
+## Edit send Eth mode
+ - [ ] Say 'Editing transaction' in the header
+ - [ ] display a button to go back to the confirmation screen without applying update
+ - [ ] say 'update transaction' on the submit button
+ - [ ] update the existing transaction, instead of signing a new one, when clicking the submit button
+ - [ ] Otherwise, behave the same as 'Send ETH mode' (see above)
+
+## Edit send token mode
+ - [ ] Behave the same as 'Edit send Eth mode' (see above)
+
+## Specific cases to test
+ - [ ] Send eth to a hex address
+ - [ ] Send eth to an ENS address
+ - [ ] Donate to the faucet at https://faucet.metamask.io/ and edit the transaction before confirming
+ - [ ] Send a token that is available on the 'Add Token' screen search to a hex address
+ - [ ] Create a custom token at https://tokenfactory.surge.sh/ and send it to a hex address
+ - [ ] Send a token to an ENS address
+ - [ ] Create a token transaction using https://tokenfactory.surge.sh/#/, and edit the transaction before confirming
+ - [ ] Send each of MKR, EOS and ICON using myetherwallet, and edit the transaction before confirming
diff --git a/old-ui/app/app.js b/old-ui/app/app.js
index 3aa845b3a..2378a1a0a 100644
--- a/old-ui/app/app.js
+++ b/old-ui/app/app.js
@@ -35,7 +35,6 @@ const HDCreateVaultComplete = require('./keychains/hd/create-vault-complete')
const HDRestoreVaultScreen = require('./keychains/hd/restore-vault')
const RevealSeedConfirmation = require('./keychains/hd/recover-seed/confirmation')
const AccountDropdowns = require('./components/account-dropdowns').AccountDropdowns
-const { BETA_UI_NETWORK_TYPE } = require('../../app/scripts/controllers/network/enums')
module.exports = connect(mapStateToProps)(App)
@@ -409,7 +408,6 @@ App.prototype.renderDropdown = function () {
closeMenu: () => this.setState({ isMainMenuOpen: !isOpen }),
onClick: () => {
this.props.dispatch(actions.setFeatureFlag('betaUI', true, 'BETA_UI_NOTIFICATION_MODAL'))
- .then(() => this.props.dispatch(actions.setNetworkEndpoints(BETA_UI_NETWORK_TYPE)))
},
}, 'Try Beta!'),
])
@@ -472,7 +470,6 @@ App.prototype.renderPrimary = function () {
onClick: () => {
global.platform.openExtensionInBrowser()
props.dispatch(actions.setFeatureFlag('betaUI', true, 'BETA_UI_NOTIFICATION_MODAL'))
- .then(() => props.dispatch(actions.setNetworkEndpoints(BETA_UI_NETWORK_TYPE)))
},
style: {
fontSize: '0.8em',
diff --git a/test/unit/network-contoller-test.js b/test/unit/network-contoller-test.js
index 2b905718b..2d590a3f6 100644
--- a/test/unit/network-contoller-test.js
+++ b/test/unit/network-contoller-test.js
@@ -3,17 +3,15 @@ const nock = require('nock')
const NetworkController = require('../../app/scripts/controllers/network')
const {
getNetworkDisplayName,
- getNetworkEndpoints,
} = require('../../app/scripts/controllers/network/util')
const { createTestProviderTools } = require('../stub/provider')
const providerResultStub = {}
-const provider = createTestProviderTools({ scaffold: providerResultStub }).provider
describe('# Network Controller', function () {
let networkController
const noop = () => {}
- const networkControllerProviderInit = {
+ const networkControllerProviderConfig = {
getAccounts: noop,
}
@@ -24,11 +22,9 @@ describe('# Network Controller', function () {
.post('/metamask')
.reply(200)
- networkController = new NetworkController({
- provider,
- })
+ networkController = new NetworkController()
- networkController.initializeProvider(networkControllerProviderInit, provider)
+ networkController.initializeProvider(networkControllerProviderConfig)
})
afterEach(function () {
@@ -38,7 +34,7 @@ describe('# Network Controller', function () {
describe('network', function () {
describe('#provider', function () {
it('provider should be updatable without reassignment', function () {
- networkController.initializeProvider(networkControllerProviderInit, provider)
+ networkController.initializeProvider(networkControllerProviderConfig)
const proxy = networkController._proxy
proxy.setTarget({ test: true, on: () => {} })
assert.ok(proxy.test)
@@ -59,12 +55,6 @@ describe('# Network Controller', function () {
})
})
- describe('#getRpcAddressForType', function () {
- it('should return the right rpc address', function () {
- const rpcTarget = networkController.getRpcAddressForType('mainnet')
- assert.equal(rpcTarget, 'https://mainnet.infura.io/metamask', 'returns the right rpcAddress')
- })
- })
describe('#setProviderType', function () {
it('should update provider.type', function () {
networkController.setProviderType('mainnet')
@@ -76,16 +66,11 @@ describe('# Network Controller', function () {
const loading = networkController.isNetworkLoading()
assert.ok(loading, 'network is loading')
})
- it('should set the right rpcTarget', function () {
- networkController.setProviderType('mainnet')
- const rpcTarget = networkController.getProviderConfig().rpcTarget
- assert.equal(rpcTarget, 'https://mainnet.infura.io/metamask', 'returns the right rpcAddress')
- })
})
})
})
-describe('# Network utils', () => {
+describe('Network utils', () => {
it('getNetworkDisplayName should return the correct network name', () => {
const tests = [
{
@@ -114,9 +99,4 @@ describe('# Network utils', () => {
tests.forEach(({ input, expected }) => assert.equal(getNetworkDisplayName(input), expected))
})
-
- it('getNetworkEndpoints should return the correct endpoints', () => {
- assert.equal(getNetworkEndpoints('networkBeta').ropsten, 'https://ropsten.infura.io/metamask2')
- assert.equal(getNetworkEndpoints('network').rinkeby, 'https://rinkeby.infura.io/metamask')
- })
})
diff --git a/test/unit/tx-state-history-helper-test.js b/test/unit/tx-state-history-helper-test.js
index 35e9ef188..5ad014dbb 100644
--- a/test/unit/tx-state-history-helper-test.js
+++ b/test/unit/tx-state-history-helper-test.js
@@ -1,26 +1,129 @@
const assert = require('assert')
-const clone = require('clone')
const txStateHistoryHelper = require('../../app/scripts/controllers/transactions/lib/tx-state-history-helper')
+const testVault = require('../data/v17-long-history.json')
-describe('deepCloneFromTxMeta', function () {
- it('should clone deep', function () {
- const input = {
- foo: {
- bar: {
- bam: 'baz'
+describe ('Transaction state history helper', function () {
+
+ describe('#snapshotFromTxMeta', function () {
+ it('should clone deep', function () {
+ const input = {
+ foo: {
+ bar: {
+ bam: 'baz'
+ }
}
}
- }
- const output = txStateHistoryHelper.snapshotFromTxMeta(input)
- assert('foo' in output, 'has a foo key')
- assert('bar' in output.foo, 'has a bar key')
- assert('bam' in output.foo.bar, 'has a bar key')
- assert.equal(output.foo.bar.bam, 'baz', 'has a baz value')
+ const output = txStateHistoryHelper.snapshotFromTxMeta(input)
+ assert('foo' in output, 'has a foo key')
+ assert('bar' in output.foo, 'has a bar key')
+ assert('bam' in output.foo.bar, 'has a bar key')
+ assert.equal(output.foo.bar.bam, 'baz', 'has a baz value')
+ })
+
+ it('should remove the history key', function () {
+ const input = { foo: 'bar', history: 'remembered' }
+ const output = txStateHistoryHelper.snapshotFromTxMeta(input)
+ assert(typeof output.history, 'undefined', 'should remove history')
+ })
})
- it('should remove the history key', function () {
- const input = { foo: 'bar', history: 'remembered' }
- const output = txStateHistoryHelper.snapshotFromTxMeta(input)
- assert(typeof output.history, 'undefined', 'should remove history')
+ describe('#migrateFromSnapshotsToDiffs', function () {
+ it('migrates history to diffs and can recover original values', function () {
+ testVault.data.TransactionController.transactions.forEach((tx, index) => {
+ const newHistory = txStateHistoryHelper.migrateFromSnapshotsToDiffs(tx.history)
+ newHistory.forEach((newEntry, index) => {
+ if (index === 0) {
+ assert.equal(Array.isArray(newEntry), false, 'initial history item IS NOT a json patch obj')
+ } else {
+ assert.equal(Array.isArray(newEntry), true, 'non-initial history entry IS a json patch obj')
+ }
+ const oldEntry = tx.history[index]
+ const historySubset = newHistory.slice(0, index + 1)
+ const reconstructedValue = txStateHistoryHelper.replayHistory(historySubset)
+ assert.deepEqual(oldEntry, reconstructedValue, 'was able to reconstruct old entry from diffs')
+ })
+ })
+ })
+ })
+
+ describe('#replayHistory', function () {
+ it('replaying history does not mutate the original obj', function () {
+ const initialState = { test: true, message: 'hello', value: 1 }
+ const diff1 = [{
+ "op": "replace",
+ "path": "/message",
+ "value": "haay",
+ }]
+ const diff2 = [{
+ "op": "replace",
+ "path": "/value",
+ "value": 2,
+ }]
+ const history = [initialState, diff1, diff2]
+
+ const beforeStateSnapshot = JSON.stringify(initialState)
+ const latestState = txStateHistoryHelper.replayHistory(history)
+ const afterStateSnapshot = JSON.stringify(initialState)
+
+ assert.notEqual(initialState, latestState, 'initial state is not the same obj as the latest state')
+ assert.equal(beforeStateSnapshot, afterStateSnapshot, 'initial state is not modified during run')
+ })
+ })
+
+ describe('#generateHistoryEntry', function () {
+
+ function generateHistoryEntryTest(note) {
+
+ const prevState = {
+ someValue: 'value 1',
+ foo: {
+ bar: {
+ bam: 'baz'
+ }
+ }
+ }
+
+ const nextState = {
+ newPropRoot: 'new property - root',
+ someValue: 'value 2',
+ foo: {
+ newPropFirstLevel: 'new property - first level',
+ bar: {
+ bam: 'baz'
+ }
+ }
+ }
+
+ const before = new Date().getTime()
+ const result = txStateHistoryHelper.generateHistoryEntry(prevState, nextState, note)
+ const after = new Date().getTime()
+
+ assert.ok(Array.isArray(result))
+ assert.equal(result.length, 3)
+
+ const expectedEntry1 = { op: 'add', path: '/foo/newPropFirstLevel', value: 'new property - first level' }
+ assert.equal(result[0].op, expectedEntry1.op)
+ assert.equal(result[0].path, expectedEntry1.path)
+ assert.equal(result[0].value, expectedEntry1.value)
+ assert.equal(result[0].value, expectedEntry1.value)
+ if (note)
+ assert.equal(result[0].note, note)
+
+ assert.ok(result[0].timestamp >= before && result[0].timestamp <= after)
+
+ const expectedEntry2 = { op: 'replace', path: '/someValue', value: 'value 2' }
+ assert.deepEqual(result[1], expectedEntry2)
+
+ const expectedEntry3 = { op: 'add', path: '/newPropRoot', value: 'new property - root' }
+ assert.deepEqual(result[2], expectedEntry3)
+ }
+
+ it('should generate history entries', function () {
+ generateHistoryEntryTest()
+ })
+
+ it('should add note to first entry', function () {
+ generateHistoryEntryTest('custom note')
+ })
})
-})
+}) \ No newline at end of file
diff --git a/test/unit/tx-state-history-helper.js b/test/unit/tx-state-history-helper.js
deleted file mode 100644
index 35f7dac57..000000000
--- a/test/unit/tx-state-history-helper.js
+++ /dev/null
@@ -1,46 +0,0 @@
-const assert = require('assert')
-const txStateHistoryHelper = require('../../app/scripts/controllers/transactions/lib/tx-state-history-helper')
-const testVault = require('../data/v17-long-history.json')
-
-
-describe('tx-state-history-helper', function () {
- it('migrates history to diffs and can recover original values', function () {
- testVault.data.TransactionController.transactions.forEach((tx, index) => {
- const newHistory = txStateHistoryHelper.migrateFromSnapshotsToDiffs(tx.history)
- newHistory.forEach((newEntry, index) => {
- if (index === 0) {
- assert.equal(Array.isArray(newEntry), false, 'initial history item IS NOT a json patch obj')
- } else {
- assert.equal(Array.isArray(newEntry), true, 'non-initial history entry IS a json patch obj')
- }
- const oldEntry = tx.history[index]
- const historySubset = newHistory.slice(0, index + 1)
- const reconstructedValue = txStateHistoryHelper.replayHistory(historySubset)
- assert.deepEqual(oldEntry, reconstructedValue, 'was able to reconstruct old entry from diffs')
- })
- })
- })
-
- it('replaying history does not mutate the original obj', function () {
- const initialState = { test: true, message: 'hello', value: 1 }
- const diff1 = [{
- "op": "replace",
- "path": "/message",
- "value": "haay",
- }]
- const diff2 = [{
- "op": "replace",
- "path": "/value",
- "value": 2,
- }]
- const history = [initialState, diff1, diff2]
-
- const beforeStateSnapshot = JSON.stringify(initialState)
- const latestState = txStateHistoryHelper.replayHistory(history)
- const afterStateSnapshot = JSON.stringify(initialState)
-
- assert.notEqual(initialState, latestState, 'initial state is not the same obj as the latest state')
- assert.equal(beforeStateSnapshot, afterStateSnapshot, 'initial state is not modified during run')
- })
-
-})
diff --git a/test/unit/tx-state-manager-test.js b/test/unit/tx-state-manager-test.js
index e5fe68d0b..179542f90 100644
--- a/test/unit/tx-state-manager-test.js
+++ b/test/unit/tx-state-manager-test.js
@@ -176,14 +176,21 @@ describe('TransactionStateManager', function () {
assert.deepEqual(updatedTx.history[0], txStateHistoryHelper.snapshotFromTxMeta(updatedTx), 'first history item is initial state')
// modify value and updateTx
updatedTx.txParams.gasPrice = desiredGasPrice
+ const before = new Date().getTime()
txStateManager.updateTx(updatedTx)
+ const after = new Date().getTime()
// check updated value
const result = txStateManager.getTx('1')
assert.equal(result.txParams.gasPrice, desiredGasPrice, 'gas price updated')
// validate history was updated
assert.equal(result.history.length, 2, 'two history items (initial + diff)')
+ assert.equal(result.history[1].length, 1, 'two history state items (initial + diff)')
+
const expectedEntry = { op: 'replace', path: '/txParams/gasPrice', value: desiredGasPrice }
- assert.deepEqual(result.history[1], [expectedEntry], 'two history items (initial + diff)')
+ assert.deepEqual(result.history[1][0].op, expectedEntry.op, 'two history items (initial + diff) operation')
+ assert.deepEqual(result.history[1][0].path, expectedEntry.path, 'two history items (initial + diff) path')
+ assert.deepEqual(result.history[1][0].value, expectedEntry.value, 'two history items (initial + diff) value')
+ assert.ok(result.history[1][0].timestamp >= before && result.history[1][0].timestamp <= after)
})
})
diff --git a/ui/app/actions.js b/ui/app/actions.js
index 9c4de9551..2d238b2f8 100644
--- a/ui/app/actions.js
+++ b/ui/app/actions.js
@@ -271,7 +271,6 @@ var actions = {
SET_MOUSE_USER_STATE: 'SET_MOUSE_USER_STATE',
// Network
- setNetworkEndpoints,
updateNetworkEndpointType,
UPDATE_NETWORK_ENDPOINT_TYPE: 'UPDATE_NETWORK_ENDPOINT_TYPE',
@@ -1924,23 +1923,6 @@ function setLocaleMessages (localeMessages) {
}
}
-function setNetworkEndpoints (networkEndpointType) {
- return dispatch => {
- log.debug('background.setNetworkEndpoints')
- return new Promise((resolve, reject) => {
- background.setNetworkEndpoints(networkEndpointType, err => {
- if (err) {
- dispatch(actions.displayWarning(err.message))
- return reject(err)
- }
-
- dispatch(actions.updateNetworkEndpointType(networkEndpointType))
- resolve(networkEndpointType)
- })
- })
- }
-}
-
function updateNetworkEndpointType (networkEndpointType) {
return {
type: actions.UPDATE_NETWORK_ENDPOINT_TYPE,
diff --git a/ui/app/app.js b/ui/app/app.js
index 5bc571c64..f840cc34e 100644
--- a/ui/app/app.js
+++ b/ui/app/app.js
@@ -1,7 +1,7 @@
const { Component } = require('react')
const PropTypes = require('prop-types')
const connect = require('react-redux').connect
-const { Route, Switch, withRouter, matchPath } = require('react-router-dom')
+const { Route, Switch, withRouter } = require('react-router-dom')
const { compose } = require('recompose')
const h = require('react-hyperscript')
const actions = require('./actions')
@@ -83,15 +83,6 @@ class App extends Component {
)
}
- renderAppHeader () {
- const { location } = this.props
- const isInitializing = matchPath(location.pathname, {
- path: INITIALIZE_ROUTE, exact: false,
- })
-
- return isInitializing ? null : h(AppHeader)
- }
-
render () {
const {
isLoading,
@@ -128,7 +119,7 @@ class App extends Component {
// global modal
h(Modal, {}, []),
- this.renderAppHeader(),
+ h(AppHeader),
// sidebar
this.renderSidebar(),
diff --git a/ui/app/components/app-header/app-header.component.js b/ui/app/components/app-header/app-header.component.js
index cf36e0d79..62b04562a 100644
--- a/ui/app/components/app-header/app-header.component.js
+++ b/ui/app/components/app-header/app-header.component.js
@@ -1,9 +1,13 @@
import React, { Component } from 'react'
import PropTypes from 'prop-types'
import classnames from 'classnames'
+import { matchPath } from 'react-router-dom'
-const { ENVIRONMENT_TYPE_NOTIFICATION } = require('../../../../app/scripts/lib/enums')
-const { DEFAULT_ROUTE, CONFIRM_TRANSACTION_ROUTE } = require('../../routes')
+const {
+ ENVIRONMENT_TYPE_NOTIFICATION,
+ ENVIRONMENT_TYPE_POPUP,
+} = require('../../../../app/scripts/lib/enums')
+const { DEFAULT_ROUTE, INITIALIZE_ROUTE, CONFIRM_TRANSACTION_ROUTE } = require('../../routes')
const Identicon = require('../identicon')
const NetworkIndicator = require('../network')
@@ -36,13 +40,23 @@ class AppHeader extends Component {
: hideNetworkDropdown()
}
+ isConfirming () {
+ const { location } = this.props
+
+ return Boolean(matchPath(location.pathname, {
+ path: CONFIRM_TRANSACTION_ROUTE, exact: false,
+ }))
+ }
+
renderAccountMenu () {
const { isUnlocked, toggleAccountMenu, selectedAddress } = this.props
return isUnlocked && (
<div
- className="account-menu__icon"
- onClick={toggleAccountMenu}
+ className={classnames('account-menu__icon', {
+ 'account-menu__icon--disabled': this.isConfirming(),
+ })}
+ onClick={() => this.isConfirming() || toggleAccountMenu()}
>
<Identicon
address={selectedAddress}
@@ -52,6 +66,26 @@ class AppHeader extends Component {
)
}
+ hideAppHeader () {
+ const { location } = this.props
+
+ const isInitializing = Boolean(matchPath(location.pathname, {
+ path: INITIALIZE_ROUTE, exact: false,
+ }))
+
+ if (isInitializing) {
+ return true
+ }
+
+ if (window.METAMASK_UI_TYPE === ENVIRONMENT_TYPE_NOTIFICATION) {
+ return true
+ }
+
+ if (window.METAMASK_UI_TYPE === ENVIRONMENT_TYPE_POPUP && this.isConfirming()) {
+ return true
+ }
+ }
+
render () {
const {
network,
@@ -61,7 +95,7 @@ class AppHeader extends Component {
isUnlocked,
} = this.props
- if (window.METAMASK_UI_TYPE === ENVIRONMENT_TYPE_NOTIFICATION) {
+ if (this.hideAppHeader()) {
return null
}
diff --git a/ui/app/components/pages/settings/settings.js b/ui/app/components/pages/settings/settings.js
index bdefe56f8..f58ac7ddf 100644
--- a/ui/app/components/pages/settings/settings.js
+++ b/ui/app/components/pages/settings/settings.js
@@ -12,7 +12,6 @@ const SimpleDropdown = require('../../dropdowns/simple-dropdown')
const ToggleButton = require('react-toggle-button')
const { REVEAL_SEED_ROUTE } = require('../../../routes')
const locales = require('../../../../../app/_locales/index.json')
-const { OLD_UI_NETWORK_TYPE } = require('../../../../../app/scripts/controllers/network/enums')
const getInfuraCurrencyOptions = () => {
const sortedCurrencies = infuraCurrencies.objects.sort((a, b) => {
@@ -349,7 +348,6 @@ const mapDispatchToProps = dispatch => {
updateCurrentLocale: key => dispatch(actions.updateCurrentLocale(key)),
setFeatureFlagToBeta: () => {
return dispatch(actions.setFeatureFlag('betaUI', false, 'OLD_UI_NOTIFICATION_MODAL'))
- .then(() => dispatch(actions.setNetworkEndpoints(OLD_UI_NETWORK_TYPE)))
},
showResetAccountConfirmationModal: () => {
return dispatch(actions.showModal({ name: 'CONFIRM_RESET_ACCOUNT' }))
diff --git a/ui/app/components/pages/unlock-page/unlock-page.component.js b/ui/app/components/pages/unlock-page/unlock-page.component.js
index d5e2a3224..0976d9506 100644
--- a/ui/app/components/pages/unlock-page/unlock-page.component.js
+++ b/ui/app/components/pages/unlock-page/unlock-page.component.js
@@ -175,7 +175,6 @@ UnlockPage.propTypes = {
isUnlocked: PropTypes.bool,
t: PropTypes.func,
useOldInterface: PropTypes.func,
- setNetworkEndpoints: PropTypes.func,
}
export default UnlockPage
diff --git a/ui/app/components/pages/unlock-page/unlock-page.container.js b/ui/app/components/pages/unlock-page/unlock-page.container.js
index 9788a18ea..18fed9b2e 100644
--- a/ui/app/components/pages/unlock-page/unlock-page.container.js
+++ b/ui/app/components/pages/unlock-page/unlock-page.container.js
@@ -6,7 +6,6 @@ const {
tryUnlockMetamask,
forgotPassword,
markPasswordForgotten,
- setNetworkEndpoints,
} = require('../../../actions')
import UnlockPage from './unlock-page.component'
@@ -23,7 +22,6 @@ const mapDispatchToProps = dispatch => {
forgotPassword: () => dispatch(forgotPassword()),
tryUnlockMetamask: password => dispatch(tryUnlockMetamask(password)),
markPasswordForgotten: () => dispatch(markPasswordForgotten()),
- setNetworkEndpoints: type => dispatch(setNetworkEndpoints(type)),
}
}
diff --git a/ui/app/components/pending-tx/confirm-send-ether.js b/ui/app/components/pending-tx/confirm-send-ether.js
index 16dbd273b..c07c96ccc 100644
--- a/ui/app/components/pending-tx/confirm-send-ether.js
+++ b/ui/app/components/pending-tx/confirm-send-ether.js
@@ -28,6 +28,10 @@ const currencies = require('currency-formatter/currencies')
const { MIN_GAS_PRICE_HEX } = require('../send/send-constants')
const { SEND_ROUTE, DEFAULT_ROUTE } = require('../../routes')
+const {
+ ENVIRONMENT_TYPE_POPUP,
+ ENVIRONMENT_TYPE_NOTIFICATION,
+} = require('../../../../app/scripts/lib/enums')
ConfirmSendEther.contextTypes = {
t: PropTypes.func,
@@ -293,6 +297,14 @@ ConfirmSendEther.prototype.editTransaction = function (txMeta) {
history.push(SEND_ROUTE)
}
+ConfirmSendEther.prototype.renderNetworkDisplay = function () {
+ const windowType = window.METAMASK_UI_TYPE
+
+ return (windowType === ENVIRONMENT_TYPE_NOTIFICATION || windowType === ENVIRONMENT_TYPE_POPUP)
+ ? h(NetworkDisplay)
+ : null
+}
+
ConfirmSendEther.prototype.render = function () {
const {
currentCurrency,
@@ -358,7 +370,7 @@ ConfirmSendEther.prototype.render = function () {
visibility: !txMeta.lastGasPrice ? 'initial' : 'hidden',
},
}, 'Edit'),
- window.METAMASK_UI_TYPE === 'notification' && h(NetworkDisplay),
+ this.renderNetworkDisplay(),
]),
h('.page-container__title', title),
h('.page-container__subtitle', subtitle),
diff --git a/ui/app/css/itcss/components/account-menu.scss b/ui/app/css/itcss/components/account-menu.scss
index 824b2ddb6..657760ab5 100644
--- a/ui/app/css/itcss/components/account-menu.scss
+++ b/ui/app/css/itcss/components/account-menu.scss
@@ -23,6 +23,10 @@
&__icon {
margin-left: 20px;
cursor: pointer;
+
+ &--disabled {
+ cursor: initial;
+ }
}
&__header {
diff --git a/ui/app/css/itcss/components/header.scss b/ui/app/css/itcss/components/header.scss
index cef61d0e2..3ccfd5c15 100644
--- a/ui/app/css/itcss/components/header.scss
+++ b/ui/app/css/itcss/components/header.scss
@@ -82,10 +82,6 @@
display: flex;
flex-flow: row nowrap;
align-items: center;
-
- .identicon {
- cursor: pointer;
- }
}
}
diff --git a/ui/app/first-time/init-menu.js b/ui/app/first-time/init-menu.js
index 6cb548bb9..c20ba2d77 100644
--- a/ui/app/first-time/init-menu.js
+++ b/ui/app/first-time/init-menu.js
@@ -10,7 +10,6 @@ const getCaretCoordinates = require('textarea-caret')
const { RESTORE_VAULT_ROUTE, DEFAULT_ROUTE } = require('../routes')
const { getEnvironmentType } = require('../../../app/scripts/lib/util')
const { ENVIRONMENT_TYPE_POPUP } = require('../../../app/scripts/lib/enums')
-const { OLD_UI_NETWORK_TYPE } = require('../../../app/scripts/controllers/network/enums')
class InitializeMenuScreen extends Component {
constructor (props) {
@@ -190,7 +189,6 @@ class InitializeMenuScreen extends Component {
showOldUI () {
this.props.dispatch(actions.setFeatureFlag('betaUI', false, 'OLD_UI_NOTIFICATION_MODAL'))
- .then(() => this.props.dispatch(actions.setNetworkEndpoints(OLD_UI_NETWORK_TYPE)))
}
}
diff --git a/ui/app/select-app.js b/ui/app/select-app.js
index 808f9ba56..f2e8e8d10 100644
--- a/ui/app/select-app.js
+++ b/ui/app/select-app.js
@@ -6,8 +6,7 @@ const { HashRouter } = require('react-router-dom')
const App = require('./app')
const OldApp = require('../../old-ui/app/app')
const { autoAddToBetaUI } = require('./selectors')
-const { setFeatureFlag, setNetworkEndpoints } = require('./actions')
-const { BETA_UI_NETWORK_TYPE } = require('../../app/scripts/controllers/network/enums')
+const { setFeatureFlag } = require('./actions')
const I18nProvider = require('./i18n-provider')
function mapStateToProps (state) {
@@ -24,11 +23,9 @@ function mapDispatchToProps (dispatch) {
return {
setFeatureFlagWithModal: () => {
return dispatch(setFeatureFlag('betaUI', true, 'BETA_UI_NOTIFICATION_MODAL'))
- .then(() => dispatch(setNetworkEndpoints(BETA_UI_NETWORK_TYPE)))
},
setFeatureFlagWithoutModal: () => {
return dispatch(setFeatureFlag('betaUI', true))
- .then(() => dispatch(setNetworkEndpoints(BETA_UI_NETWORK_TYPE)))
},
}
}
diff --git a/ui/index.js b/ui/index.js
index 075faf66d..bd9ecc28b 100644
--- a/ui/index.js
+++ b/ui/index.js
@@ -5,11 +5,6 @@ const actions = require('./app/actions')
const configureStore = require('./app/store')
const txHelper = require('./lib/tx-helper')
const { fetchLocale } = require('./i18n-helper')
-const {
- OLD_UI_NETWORK_TYPE,
- BETA_UI_NETWORK_TYPE,
-} = require('../app/scripts/controllers/network/enums')
-
const log = require('loglevel')
module.exports = launchMetamaskUi
@@ -55,10 +50,6 @@ async function startApp (metamaskState, accountManager, opts) {
networkVersion: opts.networkVersion,
})
- const useBetaUi = metamaskState.featureFlags.betaUI
- const networkEndpointType = useBetaUi ? BETA_UI_NETWORK_TYPE : OLD_UI_NETWORK_TYPE
- store.dispatch(actions.setNetworkEndpoints(networkEndpointType))
-
// if unconfirmed txs, start on txConf page
const unapprovedTxsAll = txHelper(metamaskState.unapprovedTxs, metamaskState.unapprovedMsgs, metamaskState.unapprovedPersonalMsgs, metamaskState.unapprovedTypedMessages, metamaskState.network)
const numberOfUnapprivedTx = unapprovedTxsAll.length