diff --git a/.eslintignore b/.eslintignore index a07416923..659550cc7 100644 --- a/.eslintignore +++ b/.eslintignore @@ -3,14 +3,9 @@ node_modules/** dist/** builds/** -test-builds/** +test-*/** docs/** coverage/ -app/scripts/lib/extension-instance.js app/scripts/chromereload.js app/vendor/** - -ui/lib/blockies.js - -package-lock.json diff --git a/.eslintrc.js b/.eslintrc.js index 8ea5865e8..6c5058390 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -44,8 +44,32 @@ module.exports = { /* TODO: Remove these when upgrading to `@metamask/eslint-config@2` */ 'array-callback-return': 'error', 'callback-return': 'error', + 'consistent-return': 'error', 'global-require': 'error', 'guard-for-in': 'error', + 'implicit-arrow-linebreak': 'error', + 'import/extensions': ['error', 'never', { 'json': 'always' }], + 'import/no-extraneous-dependencies': 'error', + 'max-statements-per-line': ['error', { 'max': 1 }], + 'no-case-declarations': 'error', + 'no-constant-condition': 'error', + 'no-dupe-else-if': 'error', + 'no-empty': 'error', + 'no-empty-function': 'error', + 'no-eq-null': 'error', + 'no-global-assign': 'error', + 'no-loop-func': 'error', + 'no-negated-condition': 'error', + 'no-nested-ternary': 'error', + 'no-plusplus': ['error', { 'allowForLoopAfterthoughts': true }], + 'no-process-exit': 'error', + 'no-prototype-builtins': 'error', + 'no-template-curly-in-string': 'error', + 'no-useless-catch': 'error', + 'no-useless-concat': 'error', + 'prefer-rest-params': 'error', + 'prefer-spread': 'error', + 'require-unicode-regexp': 'error', /* End v2 rules */ 'arrow-parens': 'error', 'no-tabs': 'error', @@ -95,11 +119,22 @@ module.exports = { 'logical': 'parens-new-line', 'prop': 'parens-new-line', }], + + 'no-invalid-this': 'off', + 'babel/no-invalid-this': 'error', + 'babel/semi': ['error', 'never'], 'mocha/no-setup-in-describe': 'off', }, overrides: [{ + files: [ + 'test/e2e/**/*.js', + ], + rules: { + 'mocha/no-hooks-for-single-case': 'off', + }, + }, { files: [ 'app/scripts/migrations/*.js', '*.stories.js', @@ -114,6 +149,24 @@ module.exports = { rules: { 'global-require': 'off', }, + }, { + files: [ + 'test/**/*-test.js', + 'test/**/*.spec.js', + ], + rules: { + // Mocha will re-assign `this` in a test context + 'babel/no-invalid-this': 'off', + }, + }, { + files: [ + 'development/**/*.js', + 'test/e2e/benchmark.js', + 'test/helper.js', + ], + rules: { + 'no-process-exit': 'off', + }, }], settings: { diff --git a/.storybook/main.js b/.storybook/main.js index 598003cdd..74acf6fb8 100644 --- a/.storybook/main.js +++ b/.storybook/main.js @@ -1,5 +1,5 @@ module.exports = { - stories: ['../ui/app/components/**/*.stories.js'], + stories: ['../ui/app/**/*.stories.js'], addons: [ '@storybook/addon-knobs', '@storybook/addon-actions', diff --git a/.storybook/webpack.config.js b/.storybook/webpack.config.js index f32a01559..be7dfecea 100644 --- a/.storybook/webpack.config.js +++ b/.storybook/webpack.config.js @@ -29,11 +29,13 @@ module.exports = { ], }, plugins: [ - new CopyWebpackPlugin([ - { - from: path.join('node_modules', '@fortawesome', 'fontawesome-free', 'webfonts'), - to: path.join('fonts', 'fontawesome'), - }, - ]), + new CopyWebpackPlugin({ + patterns: [ + { + from: path.join('node_modules', '@fortawesome', 'fontawesome-free', 'webfonts'), + to: path.join('fonts', 'fontawesome'), + }, + ], + }), ], } diff --git a/app/fonts/Euclid/EuclidCircularB-Bold-WebXL.ttf b/app/fonts/Euclid/EuclidCircularB-Bold-WebXL.ttf new file mode 100644 index 000000000..244ebba0a Binary files /dev/null and b/app/fonts/Euclid/EuclidCircularB-Bold-WebXL.ttf differ diff --git a/app/fonts/Euclid/EuclidCircularB-Regular-WebXL.ttf b/app/fonts/Euclid/EuclidCircularB-Regular-WebXL.ttf new file mode 100644 index 000000000..6cf177fe1 Binary files /dev/null and b/app/fonts/Euclid/EuclidCircularB-Regular-WebXL.ttf differ diff --git a/app/fonts/Euclid/EuclidCircularB-RegularItalic-WebXL.ttf b/app/fonts/Euclid/EuclidCircularB-RegularItalic-WebXL.ttf new file mode 100644 index 000000000..35345ba0f Binary files /dev/null and b/app/fonts/Euclid/EuclidCircularB-RegularItalic-WebXL.ttf differ diff --git a/app/scripts/account-import-strategies/index.js b/app/scripts/account-import-strategies/index.js index 7ff8c262f..9a7bc2f8e 100644 --- a/app/scripts/account-import-strategies/index.js +++ b/app/scripts/account-import-strategies/index.js @@ -8,7 +8,7 @@ const accountImporter = { importAccount (strategy, args) { try { const importer = this.strategies[strategy] - const privateKeyHex = importer.apply(null, args) + const privateKeyHex = importer(...args) return Promise.resolve(privateKeyHex) } catch (e) { return Promise.reject(e) diff --git a/app/scripts/background.js b/app/scripts/background.js index adbd1e40e..c890441c9 100644 --- a/app/scripts/background.js +++ b/app/scripts/background.js @@ -26,7 +26,7 @@ import Migrator from './lib/migrator' import migrations from './migrations' import PortStream from 'extension-port-stream' import createStreamSink from './lib/createStreamSink' -import NotificationManager from './lib/notification-manager.js' +import NotificationManager from './lib/notification-manager' import MetamaskController from './metamask-controller' import rawFirstTimeState from './first-time-state' import setupSentry from './lib/setupSentry' @@ -327,7 +327,7 @@ function setupController (initState, initLangCode) { const isMetaMaskInternalProcess = metamaskInternalProcessHash[processName] if (metamaskBlockedPorts.includes(remotePort.name)) { - return false + return } if (isMetaMaskInternalProcess) { diff --git a/app/scripts/contentscript.js b/app/scripts/contentscript.js index de3066ca8..e7a983a69 100644 --- a/app/scripts/contentscript.js +++ b/app/scripts/contentscript.js @@ -155,8 +155,8 @@ function doctypeCheck () { */ function suffixCheck () { const prohibitedTypes = [ - /\.xml$/, - /\.pdf$/, + /\.xml$/u, + /\.pdf$/u, ] const currentUrl = window.location.pathname for (let i = 0; i < prohibitedTypes.length; i++) { @@ -202,7 +202,7 @@ function blockedDomainCheck () { let currentRegex for (let i = 0; i < blockedDomains.length; i++) { const blockedDomain = blockedDomains[i].replace('.', '\\.') - currentRegex = new RegExp(`(?:https?:\\/\\/)(?:(?!${blockedDomain}).)*$`) + currentRegex = new RegExp(`(?:https?:\\/\\/)(?:(?!${blockedDomain}).)*$`, 'u') if (!currentRegex.test(currentUrl)) { return true } @@ -228,7 +228,7 @@ function redirectToPhishingWarning () { async function domIsReady () { // already loaded if (['interactive', 'complete'].includes(document.readyState)) { - return + return undefined } // wait for load return new Promise((resolve) => window.addEventListener('DOMContentLoaded', resolve, { once: true })) diff --git a/app/scripts/controllers/app-state.js b/app/scripts/controllers/app-state.js index 17bae2973..a9414cea4 100644 --- a/app/scripts/controllers/app-state.js +++ b/app/scripts/controllers/app-state.js @@ -19,7 +19,7 @@ export default class AppStateController extends EventEmitter { super() - this.onInactiveTimeout = onInactiveTimeout || (() => {}) + this.onInactiveTimeout = onInactiveTimeout || (() => undefined) this.store = new ObservableStore(Object.assign({ timeoutMinutes: 0, connectedStatusPopoverHasBeenShown: true, diff --git a/app/scripts/controllers/network/middleware/pending.js b/app/scripts/controllers/network/middleware/pending.js index c869389e7..95e86f3c9 100644 --- a/app/scripts/controllers/network/middleware/pending.js +++ b/app/scripts/controllers/network/middleware/pending.js @@ -5,11 +5,13 @@ export function createPendingNonceMiddleware ({ getPendingNonce }) { return createAsyncMiddleware(async (req, res, next) => { const { method, params } = req if (method !== 'eth_getTransactionCount') { - return next() + next() + return } const [param, blockRef] = params if (blockRef !== 'pending') { - return next() + next() + return } res.result = await getPendingNonce(param) }) @@ -19,12 +21,14 @@ export function createPendingTxMiddleware ({ getPendingTransactionByHash }) { return createAsyncMiddleware(async (req, res, next) => { const { method, params } = req if (method !== 'eth_getTransactionByHash') { - return next() + next() + return } const [hash] = params const txMeta = getPendingTransactionByHash(hash) if (!txMeta) { - return next() + next() + return } res.result = formatTxMetaForRpcResult(txMeta) }) diff --git a/app/scripts/controllers/network/network.js b/app/scripts/controllers/network/network.js index f5efc58bd..f22dbc323 100644 --- a/app/scripts/controllers/network/network.js +++ b/app/scripts/controllers/network/network.js @@ -93,7 +93,8 @@ export default class NetworkController extends EventEmitter { setNetworkState (network, type) { if (network === 'loading') { - return this.networkStore.putState(network) + this.networkStore.putState(network) + return } // type must be defined @@ -101,7 +102,7 @@ export default class NetworkController extends EventEmitter { return } network = networks.networkList[type]?.chainId || network - return this.networkStore.putState(network) + this.networkStore.putState(network) } isNetworkLoading () { @@ -111,7 +112,8 @@ export default class NetworkController extends EventEmitter { lookupNetwork () { // Prevent firing when provider is not defined. if (!this._provider) { - return log.warn('NetworkController - lookupNetwork aborted due to missing provider') + log.warn('NetworkController - lookupNetwork aborted due to missing provider') + return } const { type } = this.providerStore.getState() const ethQuery = new EthQuery(this._provider) @@ -120,7 +122,8 @@ export default class NetworkController extends EventEmitter { const currentNetwork = this.getNetworkState() if (initialNetwork === currentNetwork) { if (err) { - return this.setNetworkState('loading') + this.setNetworkState('loading') + return } log.info('web3.getNetwork returned ' + network) this.setNetworkState(network, type) diff --git a/app/scripts/controllers/permissions/index.js b/app/scripts/controllers/permissions/index.js index a5aeb7b14..f82cb1c75 100644 --- a/app/scripts/controllers/permissions/index.js +++ b/app/scripts/controllers/permissions/index.js @@ -132,7 +132,7 @@ export class PermissionsController { const req = { method: 'eth_accounts' } const res = {} this.permissions.providerMiddlewareFunction( - { origin }, req, res, () => {}, _end, + { origin }, req, res, () => undefined, _end, ) function _end () { @@ -187,7 +187,7 @@ export class PermissionsController { const res = {} this.permissions.providerMiddlewareFunction( - domain, req, res, () => {}, _end, + domain, req, res, () => undefined, _end, ) function _end (_err) { diff --git a/app/scripts/controllers/permissions/permissionsLog.js b/app/scripts/controllers/permissions/permissionsLog.js index f7997f085..3a6f02537 100644 --- a/app/scripts/controllers/permissions/permissionsLog.js +++ b/app/scripts/controllers/permissions/permissionsLog.js @@ -116,7 +116,8 @@ export default class PermissionsLogController { requestedMethods = [ 'eth_accounts' ] } else { // no-op - return next() + next() + return } // call next with a return handler for capturing the response diff --git a/app/scripts/controllers/permissions/permissionsMethodMiddleware.js b/app/scripts/controllers/permissions/permissionsMethodMiddleware.js index 075f67cf8..ec5066b9c 100644 --- a/app/scripts/controllers/permissions/permissionsMethodMiddleware.js +++ b/app/scripts/controllers/permissions/permissionsMethodMiddleware.js @@ -24,12 +24,13 @@ export default function createPermissionsMethodMiddleware ({ // Intercepting eth_accounts requests for backwards compatibility: // The getAccounts call below wraps the rpc-cap middleware, and returns // an empty array in case of errors (such as 4100:unauthorized) - case 'eth_accounts': + case 'eth_accounts': { res.result = await getAccounts() return + } - case 'eth_requestAccounts': + case 'eth_requestAccounts': { if (isProcessingRequestAccounts) { res.error = ethErrors.rpc.resourceUnavailable( @@ -73,19 +74,21 @@ export default function createPermissionsMethodMiddleware ({ } return + } // custom method for getting metadata from the requesting domain, // sent automatically by the inpage provider when it's initialized - case 'wallet_sendDomainMetadata': + case 'wallet_sendDomainMetadata': { if (typeof req.domainMetadata?.name === 'string') { addDomainMetadata(req.origin, req.domainMetadata) } res.result = true return + } // register return handler to send accountsChanged notification - case 'wallet_requestPermissions': + case 'wallet_requestPermissions': { if ('eth_accounts' in req.params?.[0]) { @@ -101,6 +104,7 @@ export default function createPermissionsMethodMiddleware ({ } } break + } default: break diff --git a/app/scripts/controllers/preferences.js b/app/scripts/controllers/preferences.js index 47fa73746..4c0e97ceb 100644 --- a/app/scripts/controllers/preferences.js +++ b/app/scripts/controllers/preferences.js @@ -198,7 +198,7 @@ export default class PreferencesController { ) { const { type, options } = req.params switch (type) { - case 'ERC20': + case 'ERC20': { const result = await this._handleWatchAssetERC20(options) if (result instanceof Error) { end(result) @@ -207,6 +207,7 @@ export default class PreferencesController { end() } return + } default: end(new Error(`Asset of type ${type} not supported`)) return diff --git a/app/scripts/controllers/threebox.js b/app/scripts/controllers/threebox.js index bca43d9f6..726a14ffa 100644 --- a/app/scripts/controllers/threebox.js +++ b/app/scripts/controllers/threebox.js @@ -123,7 +123,7 @@ export default class ThreeBoxController { const threeBoxConfig = await Box.getConfig(this.address) backupExists = threeBoxConfig.spaces && threeBoxConfig.spaces.metamask } catch (e) { - if (e.message.match(/^Error: Invalid response \(404\)/)) { + if (e.message.match(/^Error: Invalid response \(404\)/u)) { backupExists = false } else { throw e diff --git a/app/scripts/controllers/transactions/index.js b/app/scripts/controllers/transactions/index.js index fd9856705..795c7c6ea 100644 --- a/app/scripts/controllers/transactions/index.js +++ b/app/scripts/controllers/transactions/index.js @@ -16,7 +16,7 @@ import { SEND_ETHER_ACTION_KEY, DEPLOY_CONTRACT_ACTION_KEY, CONTRACT_INTERACTION_KEY, -} from '../../../../ui/app/helpers/constants/transactions.js' +} from '../../../../ui/app/helpers/constants/transactions' import TransactionStateManager from './tx-state-manager' import TxGasUtil from './tx-gas-utils' @@ -287,11 +287,11 @@ export default class TransactionController extends EventEmitter { /** * Gets default gas price, or returns `undefined` if gas price is already set * @param {Object} txMeta - The txMeta object - * @returns {Promise} The default gas price + * @returns {Promise} The default gas price */ async _getDefaultGasPrice (txMeta) { if (txMeta.txParams.gasPrice) { - return + return undefined } const gasPrice = await this.query.gasPrice() @@ -560,9 +560,9 @@ export default class TransactionController extends EventEmitter { // It seems that sometimes the numerical values being returned from // this.query.getTransactionReceipt are BN instances and not strings. - const gasUsed = typeof txReceipt.gasUsed !== 'string' - ? txReceipt.gasUsed.toString(16) - : txReceipt.gasUsed + const gasUsed = typeof txReceipt.gasUsed === 'string' + ? txReceipt.gasUsed + : txReceipt.gasUsed.toString(16) txMeta.txReceipt = { ...txReceipt, @@ -684,7 +684,7 @@ export default class TransactionController extends EventEmitter { if (!('retryCount' in txMeta)) { txMeta.retryCount = 0 } - txMeta.retryCount++ + txMeta.retryCount += 1 this.txStateManager.updateTx(txMeta, 'transactions/pending-tx-tracker#event: tx:retry') }) } diff --git a/app/scripts/controllers/transactions/pending-tx-tracker.js b/app/scripts/controllers/transactions/pending-tx-tracker.js index a901707a8..8066a116f 100644 --- a/app/scripts/controllers/transactions/pending-tx-tracker.js +++ b/app/scripts/controllers/transactions/pending-tx-tracker.js @@ -129,7 +129,7 @@ export default class PendingTransactionTracker extends EventEmitter { // Exponential backoff to limit retries at publishing if (txBlockDistance <= Math.pow(2, retryCount) - 1) { - return + return undefined } // Only auto-submit already-signed txs: @@ -239,11 +239,11 @@ export default class PendingTransactionTracker extends EventEmitter { async _checkIfNonceIsTaken (txMeta) { const address = txMeta.txParams.from const completed = this.getCompletedTransactions(address) - return completed.some((other) => + return completed.some( // This is called while the transaction is in-flight, so it is possible that the // list of completed transactions now includes the transaction we were looking at // and if that is the case, don't consider the transaction to have taken its own nonce - !(other.id === txMeta.id) && other.txParams.nonce === txMeta.txParams.nonce, + (other) => !(other.id === txMeta.id) && other.txParams.nonce === txMeta.txParams.nonce, ) } } diff --git a/app/scripts/controllers/transactions/tx-state-manager.js b/app/scripts/controllers/transactions/tx-state-manager.js index b8adf8deb..7de54fb9c 100644 --- a/app/scripts/controllers/transactions/tx-state-manager.js +++ b/app/scripts/controllers/transactions/tx-state-manager.js @@ -164,10 +164,10 @@ export default class TransactionStateManager extends EventEmitter { txMeta.txParams = this.normalizeAndValidateTxParams(txMeta.txParams) } - this.once(`${txMeta.id}:signed`, function () { + this.once(`${txMeta.id}:signed`, () => { this.removeAllListeners(`${txMeta.id}:rejected`) }) - this.once(`${txMeta.id}:rejected`, function () { + this.once(`${txMeta.id}:rejected`, () => { this.removeAllListeners(`${txMeta.id}:signed`) }) // initialize history @@ -424,7 +424,7 @@ export default class TransactionStateManager extends EventEmitter { @param {erroObject} err - error object */ setTxStatusFailed (txId, err) { - const error = !err ? new Error('Internal metamask failure') : err + const error = err || new Error('Internal metamask failure') const txMeta = this.getTx(txId) txMeta.err = { diff --git a/app/scripts/inpage.js b/app/scripts/inpage.js index c7c92face..3cb837373 100644 --- a/app/scripts/inpage.js +++ b/app/scripts/inpage.js @@ -35,7 +35,7 @@ import LocalMessageDuplexStream from 'post-message-stream' import { initProvider } from '@metamask/inpage-provider' // TODO:deprecate:2020 -import setupWeb3 from './lib/setupWeb3.js' +import setupWeb3 from './lib/setupWeb3' restoreContextAfterImports() diff --git a/app/scripts/lib/ComposableObservableStore.js b/app/scripts/lib/ComposableObservableStore.js index 3f8b99af4..3fb90b4b6 100644 --- a/app/scripts/lib/ComposableObservableStore.js +++ b/app/scripts/lib/ComposableObservableStore.js @@ -25,7 +25,7 @@ export default class ComposableObservableStore extends ObservableStore { this.config = config this.removeAllListeners() for (const key in config) { - if (config.hasOwnProperty(key)) { + if (Object.prototype.hasOwnProperty.call(config, key)) { config[key].subscribe((state) => { this.updateState({ [key]: state }) }) @@ -42,7 +42,7 @@ export default class ComposableObservableStore extends ObservableStore { getFlatState () { let flatState = {} for (const key in this.config) { - if (this.config.hasOwnProperty(key)) { + if (Object.prototype.hasOwnProperty.call(this.config, key)) { const controller = this.config[key] const state = controller.getState ? controller.getState() : controller.state flatState = { ...flatState, ...state } diff --git a/app/scripts/lib/account-tracker.js b/app/scripts/lib/account-tracker.js index 974920ee4..4ce0d692e 100644 --- a/app/scripts/lib/account-tracker.js +++ b/app/scripts/lib/account-tracker.js @@ -256,7 +256,8 @@ export default class AccountTracker { ethContract.balances(addresses, ethBalance, (error, result) => { if (error) { log.warn(`MetaMask - Account Tracker single call balance fetch failed`, error) - return Promise.all(addresses.map(this._updateAccount.bind(this))) + Promise.all(addresses.map(this._updateAccount.bind(this))) + return } addresses.forEach((address, index) => { const balance = bnToHex(result[index]) diff --git a/app/scripts/lib/background-metametrics.js b/app/scripts/lib/background-metametrics.js index a9baa79b7..7af1125c1 100644 --- a/app/scripts/lib/background-metametrics.js +++ b/app/scripts/lib/background-metametrics.js @@ -2,9 +2,6 @@ import { getBackgroundMetaMetricState } from '../../../ui/app/selectors' import { sendMetaMetricsEvent } from '../../../ui/app/helpers/utils/metametrics.util' export default function backgroundMetaMetricsEvent (metaMaskState, version, eventData) { - - eventData.eventOpts['category'] = 'Background' - const stateEventData = getBackgroundMetaMetricState({ metamask: metaMaskState }) if (stateEventData.participateInMetaMetrics) { sendMetaMetricsEvent({ diff --git a/app/scripts/lib/createMethodMiddleware.js b/app/scripts/lib/createMethodMiddleware.js index a2b466be1..7a98ce531 100644 --- a/app/scripts/lib/createMethodMiddleware.js +++ b/app/scripts/lib/createMethodMiddleware.js @@ -14,7 +14,7 @@ export default function createMethodMiddleware ({ origin, sendMetrics }) { return function methodMiddleware (req, res, next, end) { switch (req.method) { - case 'metamask_logInjectedWeb3Usage': + case 'metamask_logInjectedWeb3Usage': { const { action, name } = req.params[0] @@ -32,6 +32,7 @@ export default function createMethodMiddleware ({ origin, sendMetrics }) { res.result = true break + } default: return next() diff --git a/app/scripts/lib/decrypt-message-manager.js b/app/scripts/lib/decrypt-message-manager.js index ca308090f..d6986f52f 100644 --- a/app/scripts/lib/decrypt-message-manager.js +++ b/app/scripts/lib/decrypt-message-manager.js @@ -5,7 +5,7 @@ import { ethErrors } from 'eth-json-rpc-errors' import createId from './random-id' import { MESSAGE_TYPE } from './enums' -const hexRe = /^[0-9A-Fa-f]+$/g +const hexRe = /^[0-9A-Fa-f]+$/ug import log from 'loglevel' /** @@ -65,7 +65,8 @@ export default class DecryptMessageManager extends EventEmitter { getUnapprovedMsgs () { return this.messages.filter((msg) => msg.status === 'unapproved') .reduce((result, msg) => { - result[msg.id] = msg; return result + result[msg.id] = msg + return result }, {}) } @@ -82,19 +83,24 @@ export default class DecryptMessageManager extends EventEmitter { addUnapprovedMessageAsync (msgParams, req) { return new Promise((resolve, reject) => { if (!msgParams.from) { - return reject(new Error('MetaMask Decryption: from field is required.')) + reject(new Error('MetaMask Decryption: from field is required.')) + return } const msgId = this.addUnapprovedMessage(msgParams, req) this.once(`${msgId}:finished`, (data) => { switch (data.status) { case 'decrypted': - return resolve(data.rawData) + resolve(data.rawData) + return case 'rejected': - return reject(ethErrors.provider.userRejectedRequest('MetaMask Decryption: User denied message decryption.')) + reject(ethErrors.provider.userRejectedRequest('MetaMask Decryption: User denied message decryption.')) + return case 'errored': - return reject(new Error('This message cannot be decrypted')) + reject(new Error('This message cannot be decrypted')) + return default: - return reject(new Error(`MetaMask Decryption: Unknown problem: ${JSON.stringify(msgParams)}`)) + reject(new Error(`MetaMask Decryption: Unknown problem: ${JSON.stringify(msgParams)}`)) + return } }) }) @@ -248,7 +254,7 @@ export default class DecryptMessageManager extends EventEmitter { _setMsgStatus (msgId, status) { const msg = this.getMsg(msgId) if (!msg) { - throw new Error('DecryptMessageManager - Message not found for id: "${msgId}".') + throw new Error(`DecryptMessageManager - Message not found for id: "${msgId}".`) } msg.status = status this._updateMsg(msg) diff --git a/app/scripts/lib/encryption-public-key-manager.js b/app/scripts/lib/encryption-public-key-manager.js index 92f09057c..7550a26e3 100644 --- a/app/scripts/lib/encryption-public-key-manager.js +++ b/app/scripts/lib/encryption-public-key-manager.js @@ -62,7 +62,8 @@ export default class EncryptionPublicKeyManager extends EventEmitter { getUnapprovedMsgs () { return this.messages.filter((msg) => msg.status === 'unapproved') .reduce((result, msg) => { - result[msg.id] = msg; return result + result[msg.id] = msg + return result }, {}) } @@ -79,17 +80,21 @@ export default class EncryptionPublicKeyManager extends EventEmitter { addUnapprovedMessageAsync (address, req) { return new Promise((resolve, reject) => { if (!address) { - return reject(new Error('MetaMask Message: address field is required.')) + reject(new Error('MetaMask Message: address field is required.')) + return } const msgId = this.addUnapprovedMessage(address, req) this.once(`${msgId}:finished`, (data) => { switch (data.status) { case 'received': - return resolve(data.rawData) + resolve(data.rawData) + return case 'rejected': - return reject(ethErrors.provider.userRejectedRequest('MetaMask EncryptionPublicKey: User denied message EncryptionPublicKey.')) + reject(ethErrors.provider.userRejectedRequest('MetaMask EncryptionPublicKey: User denied message EncryptionPublicKey.')) + return default: - return reject(new Error(`MetaMask EncryptionPublicKey: Unknown problem: ${JSON.stringify(address)}`)) + reject(new Error(`MetaMask EncryptionPublicKey: Unknown problem: ${JSON.stringify(address)}`)) + return } }) }) @@ -243,7 +248,7 @@ export default class EncryptionPublicKeyManager extends EventEmitter { _setMsgStatus (msgId, status) { const msg = this.getMsg(msgId) if (!msg) { - throw new Error('EncryptionPublicKeyManager - Message not found for id: "${msgId}".') + throw new Error(`EncryptionPublicKeyManager - Message not found for id: "${msgId}".`) } msg.status = status this._updateMsg(msg) diff --git a/app/scripts/lib/ens-ipfs/setup.js b/app/scripts/lib/ens-ipfs/setup.js index d1fc42674..e543a2d66 100644 --- a/app/scripts/lib/ens-ipfs/setup.js +++ b/app/scripts/lib/ens-ipfs/setup.js @@ -1,6 +1,6 @@ import urlUtil from 'url' import extension from 'extensionizer' -import resolveEnsToIpfsContentId from './resolver.js' +import resolveEnsToIpfsContentId from './resolver' const supportedTopLevelDomains = ['eth'] diff --git a/app/scripts/lib/freezeGlobals.js b/app/scripts/lib/freezeGlobals.js index 6599088d6..b17a84781 100644 --- a/app/scripts/lib/freezeGlobals.js +++ b/app/scripts/lib/freezeGlobals.js @@ -30,11 +30,11 @@ function freeze (target, key, value, enumerable = true) { configurable: false, writable: false, } - if (value !== undefined) { + if (value === undefined) { + target[key] = deepFreeze(target[key]) + } else { opts.value = deepFreeze(value) opts.enumerable = enumerable - } else { - target[key] = deepFreeze(target[key]) } Object.defineProperty(target, key, opts) diff --git a/app/scripts/lib/get-first-preferred-lang-code.js b/app/scripts/lib/get-first-preferred-lang-code.js index 00e50d7f4..d4bb61a8f 100644 --- a/app/scripts/lib/get-first-preferred-lang-code.js +++ b/app/scripts/lib/get-first-preferred-lang-code.js @@ -40,7 +40,7 @@ export default async function getFirstPreferredLangCode () { const firstPreferredLangCode = userPreferredLocaleCodes .map((code) => code.toLowerCase().replace('_', '-')) - .find((code) => existingLocaleCodes.hasOwnProperty(code)) + .find((code) => Object.prototype.hasOwnProperty.call(existingLocaleCodes, code)) return existingLocaleCodes[firstPreferredLangCode] || 'en' } diff --git a/app/scripts/lib/message-manager.js b/app/scripts/lib/message-manager.js index b2de1eeab..6c74b017a 100644 --- a/app/scripts/lib/message-manager.js +++ b/app/scripts/lib/message-manager.js @@ -64,7 +64,8 @@ export default class MessageManager extends EventEmitter { getUnapprovedMsgs () { return this.messages.filter((msg) => msg.status === 'unapproved') .reduce((result, msg) => { - result[msg.id] = msg; return result + result[msg.id] = msg + return result }, {}) } @@ -225,7 +226,7 @@ export default class MessageManager extends EventEmitter { _setMsgStatus (msgId, status) { const msg = this.getMsg(msgId) if (!msg) { - throw new Error('MessageManager - Message not found for id: "${msgId}".') + throw new Error(`MessageManager - Message not found for id: "${msgId}".`) } msg.status = status this._updateMsg(msg) diff --git a/app/scripts/lib/nodeify.js b/app/scripts/lib/nodeify.js index 5d4eb8c4d..074fba3bb 100644 --- a/app/scripts/lib/nodeify.js +++ b/app/scripts/lib/nodeify.js @@ -15,9 +15,7 @@ const callbackNoop = function (err) { * */ export default function nodeify (fn, context) { - return function () { - // parse arguments - const args = [].slice.call(arguments) + return function (...args) { const lastArg = args[args.length - 1] const lastArgIsCallback = typeof lastArg === 'function' let callback diff --git a/app/scripts/lib/personal-message-manager.js b/app/scripts/lib/personal-message-manager.js index 067c696bd..7770e8106 100644 --- a/app/scripts/lib/personal-message-manager.js +++ b/app/scripts/lib/personal-message-manager.js @@ -5,7 +5,7 @@ import { ethErrors } from 'eth-json-rpc-errors' import createId from './random-id' import { MESSAGE_TYPE } from './enums' -const hexRe = /^[0-9A-Fa-f]+$/g +const hexRe = /^[0-9A-Fa-f]+$/ug import log from 'loglevel' /** @@ -68,7 +68,8 @@ export default class PersonalMessageManager extends EventEmitter { getUnapprovedMsgs () { return this.messages.filter((msg) => msg.status === 'unapproved') .reduce((result, msg) => { - result[msg.id] = msg; return result + result[msg.id] = msg + return result }, {}) } @@ -85,17 +86,21 @@ export default class PersonalMessageManager extends EventEmitter { addUnapprovedMessageAsync (msgParams, req) { return new Promise((resolve, reject) => { if (!msgParams.from) { - return reject(new Error('MetaMask Message Signature: from field is required.')) + reject(new Error('MetaMask Message Signature: from field is required.')) + return } const msgId = this.addUnapprovedMessage(msgParams, req) this.once(`${msgId}:finished`, (data) => { switch (data.status) { case 'signed': - return resolve(data.rawSig) + resolve(data.rawSig) + return case 'rejected': - return reject(ethErrors.provider.userRejectedRequest('MetaMask Message Signature: User denied message signature.')) + reject(ethErrors.provider.userRejectedRequest('MetaMask Message Signature: User denied message signature.')) + return default: - return reject(new Error(`MetaMask Message Signature: Unknown problem: ${JSON.stringify(msgParams)}`)) + reject(new Error(`MetaMask Message Signature: Unknown problem: ${JSON.stringify(msgParams)}`)) + return } }) }) diff --git a/app/scripts/lib/random-id.js b/app/scripts/lib/random-id.js index f7abc4169..eebba0619 100644 --- a/app/scripts/lib/random-id.js +++ b/app/scripts/lib/random-id.js @@ -3,5 +3,6 @@ const MAX = Number.MAX_SAFE_INTEGER let idCounter = Math.round(Math.random() * MAX) export default function createRandomId () { idCounter = idCounter % MAX + // eslint-disable-next-line no-plusplus return idCounter++ } diff --git a/app/scripts/lib/setupSentry.js b/app/scripts/lib/setupSentry.js index a6d1bb9b2..c974aafd8 100644 --- a/app/scripts/lib/setupSentry.js +++ b/app/scripts/lib/setupSentry.js @@ -72,7 +72,7 @@ export default function setupSentry ({ release, getState }) { let sentryTarget if (METAMASK_DEBUG) { - return + return undefined } else if (METAMASK_ENVIRONMENT === 'production') { if (!process.env.SENTRY_DSN) { throw new Error(`Missing SENTRY_DSN environment variable in production environment`) diff --git a/app/scripts/lib/setupWeb3.js b/app/scripts/lib/setupWeb3.js index da5d8d422..b795d2921 100644 --- a/app/scripts/lib/setupWeb3.js +++ b/app/scripts/lib/setupWeb3.js @@ -3,7 +3,7 @@ // TODO:deprecate:2020 // Delete this file -import 'web3/dist/web3.min.js' +import 'web3/dist/web3.min' const shouldLogUsage = !([ 'docs.metamask.io', diff --git a/app/scripts/lib/typed-message-manager.js b/app/scripts/lib/typed-message-manager.js index 3f5da3db1..38762a97a 100644 --- a/app/scripts/lib/typed-message-manager.js +++ b/app/scripts/lib/typed-message-manager.js @@ -61,7 +61,8 @@ export default class TypedMessageManager extends EventEmitter { getUnapprovedMsgs () { return this.messages.filter((msg) => msg.status === 'unapproved') .reduce((result, msg) => { - result[msg.id] = msg; return result + result[msg.id] = msg + return result }, {}) } @@ -154,7 +155,7 @@ export default class TypedMessageManager extends EventEmitter { }, 'Signing data must be valid EIP-712 typed data.') break case 'V3': - case 'V4': + case 'V4': { assert.equal(typeof params.data, 'string', '"params.data" must be a string.') let data assert.doesNotThrow(() => { @@ -167,6 +168,7 @@ export default class TypedMessageManager extends EventEmitter { const activeChainId = parseInt(this.networkController.getNetworkState()) chainId && assert.equal(chainId, activeChainId, `Provided chainId "${chainId}" must match the active chainId "${activeChainId}"`) break + } default: assert.fail(`Unknown typed data version "${params.version}"`) } @@ -291,7 +293,7 @@ export default class TypedMessageManager extends EventEmitter { _setMsgStatus (msgId, status) { const msg = this.getMsg(msgId) if (!msg) { - throw new Error('TypedMessageManager - Message not found for id: "${msgId}".') + throw new Error(`TypedMessageManager - Message not found for id: "${msgId}".`) } msg.status = status this._updateMsg(msg) diff --git a/app/scripts/lib/util.js b/app/scripts/lib/util.js index dfd3bc54c..ab8653669 100644 --- a/app/scripts/lib/util.js +++ b/app/scripts/lib/util.js @@ -55,19 +55,19 @@ const getEnvironmentType = (url = window.location.href) => getEnvironmentTypeMem */ const getPlatform = (_) => { const ua = window.navigator.userAgent - if (ua.search('Firefox') !== -1) { - return PLATFORM_FIREFOX - } else { + if (ua.search('Firefox') === -1) { if (window && window.chrome && window.chrome.ipcRenderer) { return PLATFORM_BRAVE - } else if (ua.search('Edge') !== -1) { - return PLATFORM_EDGE - } else if (ua.search('OPR') !== -1) { - return PLATFORM_OPERA - } else { - return PLATFORM_CHROME } + if (ua.search('Edge') !== -1) { + return PLATFORM_EDGE + } + if (ua.search('OPR') !== -1) { + return PLATFORM_OPERA + } + return PLATFORM_CHROME } + return PLATFORM_FIREFOX } /** @@ -135,12 +135,12 @@ function BnMultiplyByFraction (targetBN, numerator, denominator) { /** * Returns an Error if extension.runtime.lastError is present * this is a workaround for the non-standard error object that's used - * @returns {Error} + * @returns {Error|undefined} */ function checkForError () { const lastError = extension.runtime.lastError if (!lastError) { - return + return undefined } // if it quacks like an Error, its an Error if (lastError.stack && lastError.message) { diff --git a/app/scripts/metamask-controller.js b/app/scripts/metamask-controller.js index b0866ce08..cd3729784 100644 --- a/app/scripts/metamask-controller.js +++ b/app/scripts/metamask-controller.js @@ -24,7 +24,7 @@ import createOriginMiddleware from './lib/createOriginMiddleware' import createTabIdMiddleware from './lib/createTabIdMiddleware' import createOnboardingMiddleware from './lib/createOnboardingMiddleware' import providerAsMiddleware from 'eth-json-rpc-middleware/providerAsMiddleware' -import { setupMultiplex } from './lib/stream-utils.js' +import { setupMultiplex } from './lib/stream-utils' import KeyringController from 'eth-keyring-controller' import EnsController from './controllers/ens' import NetworkController from './controllers/network' @@ -47,7 +47,6 @@ import { PermissionsController } from './controllers/permissions' import getRestrictedMethods from './controllers/permissions/restrictedMethods' import nodeify from './lib/nodeify' import accountImporter from './account-import-strategies' -import getBuyEthUrl from './lib/buy-eth-url' import selectChainId from './lib/select-chain-id' import { Mutex } from 'await-semaphore' import { version } from '../manifest/_base.json' @@ -449,7 +448,6 @@ export default class MetamaskController extends EventEmitter { setCurrentLocale: this.setCurrentLocale.bind(this), markPasswordForgotten: this.markPasswordForgotten.bind(this), unMarkPasswordForgotten: this.unMarkPasswordForgotten.bind(this), - buyEth: this.buyEth.bind(this), safelistPhishingDomain: this.safelistPhishingDomain.bind(this), getRequestAccountTabIds: (cb) => cb(null, this.getRequestAccountTabIds()), getOpenMetamaskTabsIds: (cb) => cb(null, this.getOpenMetamaskTabsIds()), @@ -601,8 +599,6 @@ export default class MetamaskController extends EventEmitter { this.selectFirstIdentity() } return vault - } catch (err) { - throw err } finally { releaseLock() } @@ -658,8 +654,6 @@ export default class MetamaskController extends EventEmitter { this.preferencesController.setAddresses(accounts) this.selectFirstIdentity() return vault - } catch (err) { - throw err } finally { releaseLock() } @@ -714,15 +708,16 @@ export default class MetamaskController extends EventEmitter { Object.keys(accountTokens).forEach((address) => { const checksummedAddress = ethUtil.toChecksumAddress(address) filteredAccountTokens[checksummedAddress] = {} - Object.keys(accountTokens[address]).forEach( - (networkType) => (filteredAccountTokens[checksummedAddress][networkType] = networkType !== 'mainnet' ? - accountTokens[address][networkType] : - accountTokens[address][networkType].filter(({ address }) => { - const tokenAddress = ethUtil.toChecksumAddress(address) - return contractMap[tokenAddress] ? contractMap[tokenAddress].erc20 : true - }) - ), - ) + Object.keys(accountTokens[address]).forEach((networkType) => { + filteredAccountTokens[checksummedAddress][networkType] = networkType === 'mainnet' + ? ( + accountTokens[address][networkType].filter(({ address }) => { + const tokenAddress = ethUtil.toChecksumAddress(address) + return contractMap[tokenAddress] ? contractMap[tokenAddress].erc20 : true + }) + ) + : accountTokens[address][networkType] + }) }) const preferences = { @@ -1349,7 +1344,7 @@ export default class MetamaskController extends EventEmitter { * Triggers the callback in newUnsignedTypedMessage. * * @param {Object} msgParams - The params passed to eth_signTypedData. - * @returns {Object} - Full state update. + * @returns {Object|undefined} - Full state update. */ async signTypedMessage (msgParams) { log.info('MetaMaskController - eth_signTypedData') @@ -1372,6 +1367,7 @@ export default class MetamaskController extends EventEmitter { } catch (error) { log.info('MetaMaskController - eth_signTypedData failed.', error) this.typedMessageManager.errorMessage(msgId, error) + return undefined } } @@ -1401,13 +1397,9 @@ export default class MetamaskController extends EventEmitter { * @returns {Object} - MetaMask state */ async createCancelTransaction (originalTxId, customGasPrice) { - try { - await this.txController.createCancelTransaction(originalTxId, customGasPrice) - const state = await this.getState() - return state - } catch (error) { - throw error - } + await this.txController.createCancelTransaction(originalTxId, customGasPrice) + const state = await this.getState() + return state } async createSpeedUpTransaction (originalTxId, customGasPrice, customGasLimit) { @@ -1526,7 +1518,7 @@ export default class MetamaskController extends EventEmitter { const api = this.getApi() const dnode = Dnode(api) // report new active controller connection - this.activeControllerConnections++ + this.activeControllerConnections += 1 this.emit('controllerConnectionChanged', this.activeControllerConnections) // connect dnode api to remote connection pump( @@ -1535,7 +1527,7 @@ export default class MetamaskController extends EventEmitter { outStream, (err) => { // report new active controller connection - this.activeControllerConnections-- + this.activeControllerConnections -= 1 this.emit('controllerConnectionChanged', this.activeControllerConnections) // report any error if (err) { @@ -1850,6 +1842,7 @@ export default class MetamaskController extends EventEmitter { customVariables, eventOpts: { action, + category: 'Background', name, }, }, @@ -1884,24 +1877,6 @@ export default class MetamaskController extends EventEmitter { } } - /** - * A method for forwarding the user to the easiest way to obtain ether, - * or the network "gas" currency, for the current selected network. - * - * @param {string} address - The address to fund. - * @param {string} amount - The amount of ether desired, as a base 10 string. - */ - buyEth (address, amount) { - if (!amount) { - amount = '5' - } - const network = this.networkController.getNetworkState() - const url = getBuyEthUrl({ network, address, amount }) - if (url) { - this.platform.openTab({ url }) - } - } - // network /** * A method for selecting a custom URL for an ethereum RPC provider and updating it diff --git a/app/scripts/migrations/002.js b/app/scripts/migrations/002.js index ce172365a..a726d01e3 100644 --- a/app/scripts/migrations/002.js +++ b/app/scripts/migrations/002.js @@ -14,7 +14,9 @@ export default { versionedData.data.config.provider.type = 'rpc' versionedData.data.config.provider.rpcTarget = 'https://rpc.metamask.io/' } - } catch (e) {} + } catch (_) { + // empty + } return Promise.resolve(versionedData) }, } diff --git a/app/scripts/migrations/003.js b/app/scripts/migrations/003.js index 15c9b2070..9584fb889 100644 --- a/app/scripts/migrations/003.js +++ b/app/scripts/migrations/003.js @@ -14,7 +14,9 @@ export default { if (versionedData.data.config.provider.rpcTarget === oldTestRpc) { versionedData.data.config.provider.rpcTarget = newTestRpc } - } catch (e) {} + } catch (_) { + // empty + } return Promise.resolve(versionedData) }, } diff --git a/app/scripts/migrations/004.js b/app/scripts/migrations/004.js index 358cbbea7..d2d3136f3 100644 --- a/app/scripts/migrations/004.js +++ b/app/scripts/migrations/004.js @@ -25,7 +25,9 @@ export default { break // No default } - } catch (_) {} + } catch (_) { + // empty + } return Promise.resolve(safeVersionedData) }, } diff --git a/app/scripts/migrations/019.js b/app/scripts/migrations/019.js index e87bdad62..aa1e8a6cc 100644 --- a/app/scripts/migrations/019.js +++ b/app/scripts/migrations/019.js @@ -72,7 +72,7 @@ function getHighestContinuousFrom (txList, startPoint) { let highest = startPoint while (nonces.includes(highest)) { - highest++ + highest += 1 } return highest diff --git a/app/scripts/phishing-detect.js b/app/scripts/phishing-detect.js index f0ab55d00..f3333fb5e 100644 --- a/app/scripts/phishing-detect.js +++ b/app/scripts/phishing-detect.js @@ -3,7 +3,7 @@ import dnode from 'dnode' import { EventEmitter } from 'events' import PortStream from 'extension-port-stream' import extension from 'extensionizer' -import { setupMultiplex } from './lib/stream-utils.js' +import { setupMultiplex } from './lib/stream-utils' import { getEnvironmentType } from './lib/util' import ExtensionPlatform from './platforms/extension' diff --git a/app/scripts/ui.js b/app/scripts/ui.js index 3a76a5f4e..ab05303ef 100644 --- a/app/scripts/ui.js +++ b/app/scripts/ui.js @@ -24,7 +24,7 @@ import Eth from 'ethjs' import EthQuery from 'eth-query' import launchMetaMaskUi from '../../ui' import StreamProvider from 'web3-stream-provider' -import { setupMultiplex } from './lib/stream-utils.js' +import { setupMultiplex } from './lib/stream-utils' import log from 'loglevel' start().catch(log.error) @@ -62,7 +62,8 @@ async function start () { const container = document.getElementById('app-content') initializeUi(tab, container, connectionStream, (err, store) => { if (err) { - return displayCriticalError(container, err) + displayCriticalError(container, err) + return } const state = store.getState() @@ -102,7 +103,8 @@ async function queryCurrentActiveTab (windowType) { function initializeUi (activeTab, container, connectionStream, cb) { connectToAccountManager(connectionStream, (err, backgroundConnection) => { if (err) { - return cb(err) + cb(err) + return } launchMetaMaskUi({ diff --git a/development/build/scripts.js b/development/build/scripts.js index 6f206ee57..0831dbf69 100644 --- a/development/build/scripts.js +++ b/development/build/scripts.js @@ -25,7 +25,7 @@ module.exports = createScriptTasks const dependencies = Object.keys((packageJSON && packageJSON.dependencies) || {}) const materialUIDependencies = ['@material-ui/core'] -const reactDepenendencies = dependencies.filter((dep) => dep.match(/react/)) +const reactDepenendencies = dependencies.filter((dep) => dep.match(/react/u)) const d3Dependencies = ['c3', 'd3'] const externalDependenciesMap = { @@ -365,7 +365,7 @@ function getEnvironment ({ devMode, test }) { return 'testing' } else if (process.env.CIRCLE_BRANCH === 'master') { return 'production' - } else if (/^Version-v(\d+)[.](\d+)[.](\d+)/.test(process.env.CIRCLE_BRANCH)) { + } else if (/^Version-v(\d+)[.](\d+)[.](\d+)/u.test(process.env.CIRCLE_BRANCH)) { return 'release-candidate' } else if (process.env.CIRCLE_BRANCH === 'develop') { return 'staging' diff --git a/development/metamaskbot-build-announce.js b/development/metamaskbot-build-announce.js index 788929fb3..2414901de 100755 --- a/development/metamaskbot-build-announce.js +++ b/development/metamaskbot-build-announce.js @@ -81,10 +81,7 @@ async function start () { const summaryPlatform = 'chrome' const summaryPage = 'home' let commentBody - if (!benchmarkResults[summaryPlatform]) { - console.log(`No results for ${summaryPlatform} found; skipping benchmark`) - commentBody = artifactsBody - } else { + if (benchmarkResults[summaryPlatform]) { try { const summaryPageLoad = Math.round(parseFloat(benchmarkResults[summaryPlatform][summaryPage].average.load)) const summaryPageLoadMarginOfError = Math.round(parseFloat(benchmarkResults[summaryPlatform][summaryPage].marginOfError.load)) @@ -147,6 +144,9 @@ async function start () { console.error(`Error constructing benchmark results: '${error}'`) commentBody = artifactsBody } + } else { + console.log(`No results for ${summaryPlatform} found; skipping benchmark`) + commentBody = artifactsBody } const JSON_PAYLOAD = JSON.stringify({ body: commentBody }) diff --git a/development/mock-3box.js b/development/mock-3box.js index 89cf20ab1..37ff02c7b 100644 --- a/development/mock-3box.js +++ b/development/mock-3box.js @@ -50,7 +50,7 @@ class Mock3Box { }, } }, - logout: () => {}, + logout: () => undefined, }) } diff --git a/development/sentry-publish.js b/development/sentry-publish.js index 81034374e..650ac37fd 100644 --- a/development/sentry-publish.js +++ b/development/sentry-publish.js @@ -25,12 +25,14 @@ async function start () { // check if version has artifacts or not const versionHasArtifacts = versionAlreadyExists && await checkIfVersionHasArtifacts() - if (!versionHasArtifacts) { - // upload sentry source and sourcemaps - await exec(`./development/sentry-upload-artifacts.sh --release ${VERSION}`) - } else { + if (versionHasArtifacts) { console.log(`Version "${VERSION}" already has artifacts on Sentry, skipping sourcemap upload`) + return } + + // upload sentry source and sourcemaps + await exec(`./development/sentry-upload-artifacts.sh --release ${VERSION}`) + } async function checkIfAuthWorks () { diff --git a/development/sourcemap-validator.js b/development/sourcemap-validator.js index 7be473110..cfb569138 100644 --- a/development/sourcemap-validator.js +++ b/development/sourcemap-validator.js @@ -49,7 +49,9 @@ async function validateSourcemapForFile ({ buildName }) { try { const filePath = path.join(__dirname, `/../dist/${platform}/`, `${buildName}`) rawBuild = await fsAsync.readFile(filePath, 'utf8') - } catch (err) {} + } catch (_) { + // empty + } if (!rawBuild) { throw new Error(`SourcemapValidator - failed to load source file for "${buildName}"`) } @@ -58,12 +60,16 @@ async function validateSourcemapForFile ({ buildName }) { try { const filePath = path.join(__dirname, `/../dist/sourcemaps/`, `${buildName}.map`) rawSourceMap = await fsAsync.readFile(filePath, 'utf8') - } catch (err) {} + } catch (_) { + // empty + } // attempt to load in dev mode try { const filePath = path.join(__dirname, `/../dist/${platform}/`, `${buildName}.map`) rawSourceMap = await fsAsync.readFile(filePath, 'utf8') - } catch (err) {} + } catch (_) { + // empty + } if (!rawSourceMap) { throw new Error(`SourcemapValidator - failed to load sourcemaps for "${buildName}"`) } @@ -85,7 +91,7 @@ async function validateSourcemapForFile ({ buildName }) { const matchesPerLine = buildLines.map((line) => indicesOf(targetString, line)) matchesPerLine.forEach((matchIndices, lineIndex) => { matchIndices.forEach((matchColumn) => { - sampleCount++ + sampleCount += 1 const position = { line: lineIndex + 1, column: matchColumn } const result = consumer.originalPositionFor(position) // warn if source content is missing diff --git a/development/static-server.js b/development/static-server.js index fff4103c4..368c186e9 100644 --- a/development/static-server.js +++ b/development/static-server.js @@ -61,7 +61,7 @@ const main = async () => { } while (args.length) { - if (/^(--port|-p)$/i.test(args[0])) { + if (/^(--port|-p)$/u.test(args[0])) { if (args[1] === undefined) { throw new Error('Missing port argument') } diff --git a/development/verify-locale-strings.js b/development/verify-locale-strings.js index 990ed95f4..3b9e72bf3 100644 --- a/development/verify-locale-strings.js +++ b/development/verify-locale-strings.js @@ -97,6 +97,7 @@ async function getLocale (code) { log.error(`Error opening your locale ("${code}") file: `, e) } process.exit(1) + return undefined } } @@ -111,6 +112,7 @@ async function writeLocale (code, locale) { log.error(`Error writing your locale ("${code}") file: `, e) } process.exit(1) + return undefined } } @@ -156,6 +158,8 @@ async function verifyLocale (code, fix = false) { } return true } + + return false } async function verifyEnglishLocale (fix = false) { @@ -165,11 +169,11 @@ async function verifyEnglishLocale (fix = false) { // match "t(`...`)" because constructing message keys from template strings // prevents this script from finding the messages, and then inappropriately // deletes them - const templateStringRegex = /\bt\(`.*`\)/g + const templateStringRegex = /\bt\(`.*`\)/ug const templateUsage = [] // match the keys from the locale file - const keyRegex = /'(\w+)'|"(\w+)"/g + const keyRegex = /'(\w+)'|"(\w+)"/ug const usedMessages = new Set() for await (const fileContents of getFileContents(javascriptFiles)) { for (const match of matchAll.call(fileContents, keyRegex)) { diff --git a/package.json b/package.json index c20828989..516212e52 100644 --- a/package.json +++ b/package.json @@ -202,7 +202,7 @@ "chalk": "^3.0.0", "chromedriver": "^79.0.0", "concurrently": "^5.2.0", - "copy-webpack-plugin": "^5.1.1", + "copy-webpack-plugin": "^6.0.3", "coveralls": "^3.0.0", "css-loader": "^2.1.1", "del": "^3.0.0", diff --git a/test/e2e/.eslintrc.js b/test/e2e/.eslintrc.js deleted file mode 100644 index d84a4b2fb..000000000 --- a/test/e2e/.eslintrc.js +++ /dev/null @@ -1,5 +0,0 @@ -module.exports = { - rules: { - 'mocha/no-hooks-for-single-case': 'off', - }, -} diff --git a/test/e2e/address-book.spec.js b/test/e2e/address-book.spec.js index f9fc7d5be..fdd0b6b28 100644 --- a/test/e2e/address-book.spec.js +++ b/test/e2e/address-book.spec.js @@ -152,7 +152,7 @@ describe('MetaMask', function () { it('balance renders', async function () { const balance = await driver.findElement(By.css('[data-testid="wallet-balance"] .list-item__heading')) - await driver.wait(until.elementTextMatches(balance, /25\s*ETH/)) + await driver.wait(until.elementTextMatches(balance, /25\s*ETH/u)) await driver.delay(regularDelayMs) }) }) @@ -202,7 +202,7 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/u), 10000) }) }) @@ -239,7 +239,7 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues, /-2\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txValues, /-2\s*ETH/u), 10000) }) }) }) diff --git a/test/e2e/benchmark.js b/test/e2e/benchmark.js index 52008bb40..f34436328 100644 --- a/test/e2e/benchmark.js +++ b/test/e2e/benchmark.js @@ -92,7 +92,7 @@ async function isWritable (directory) { } async function getFirstParentDirectoryThatExists (directory) { - while (true) { + for (;;) { try { await fs.access(directory, fsConstants.F_OK) return directory @@ -117,7 +117,7 @@ async function main () { let existingParentDirectory while (args.length) { - if (/^(--pages|-p)$/i.test(args[0])) { + if (/^(--pages|-p)$/u.test(args[0])) { if (args[1] === undefined) { throw new Error('Missing pages argument') } @@ -128,7 +128,7 @@ async function main () { } } args.splice(0, 2) - } else if (/^(--samples|-s)$/i.test(args[0])) { + } else if (/^(--samples|-s)$/u.test(args[0])) { if (args[1] === undefined) { throw new Error('Missing number of samples') } @@ -137,7 +137,7 @@ async function main () { throw new Error(`Invalid 'samples' argument given: '${args[1]}'`) } args.splice(0, 2) - } else if (/^(--out|-o)$/i.test(args[0])) { + } else if (/^(--out|-o)$/u.test(args[0])) { if (args[1] === undefined) { throw new Error('Missing output filename') } diff --git a/test/e2e/ethereum-on.spec.js b/test/e2e/ethereum-on.spec.js index e7412ac68..8c0426a0d 100644 --- a/test/e2e/ethereum-on.spec.js +++ b/test/e2e/ethereum-on.spec.js @@ -89,11 +89,11 @@ describe('MetaMask', function () { }) it('gets the current accounts address', async function () { - const addressInput = await driver.findElement(By.css('.qr-ellip-address')) + const addressInput = await driver.findElement(By.css('.readonly-input__input')) publicAddress = await addressInput.getAttribute('value') const accountModal = await driver.findElement(By.css('span .modal')) - await driver.clickElement(By.css('.account-modal-close')) + await driver.clickElement(By.css('.account-modal__close')) await driver.wait(until.stalenessOf(accountModal)) await driver.delay(regularDelayMs) diff --git a/test/e2e/fixture-server.js b/test/e2e/fixture-server.js index 608955f76..f923c0a26 100644 --- a/test/e2e/fixture-server.js +++ b/test/e2e/fixture-server.js @@ -44,7 +44,7 @@ class FixtureServer { return } - return new Promise((resolve, reject) => { + await new Promise((resolve, reject) => { this._server.close() this._server.once('error', reject) this._server.once('close', resolve) diff --git a/test/e2e/from-import-ui.spec.js b/test/e2e/from-import-ui.spec.js index 7a112c722..b0eab48e4 100644 --- a/test/e2e/from-import-ui.spec.js +++ b/test/e2e/from-import-ui.spec.js @@ -99,24 +99,24 @@ describe('Using MetaMask with an existing account', function () { it('shows the correct account address', async function () { await driver.clickElement(By.css('[data-testid="account-options-menu-button"]')) await driver.clickElement(By.css('[data-testid="account-options-menu__account-details"]')) - await driver.findVisibleElement(By.css('.qr-wrapper')) + await driver.findVisibleElement(By.css('.qr-code__wrapper')) await driver.delay(regularDelayMs) - const [address] = await driver.findElements(By.css('input.qr-ellip-address')) + const [address] = await driver.findElements(By.css('.readonly-input__input')) assert.equal(await address.getAttribute('value'), testAddress) - await driver.clickElement(By.css('.account-modal-close')) + await driver.clickElement(By.css('.account-modal__close')) await driver.delay(largeDelayMs) }) it('shows a QR code for the account', async function () { await driver.clickElement(By.css('[data-testid="account-options-menu-button"]')) await driver.clickElement(By.css('[data-testid="account-options-menu__account-details"]')) - await driver.findVisibleElement(By.css('.qr-wrapper')) + await driver.findVisibleElement(By.css('.qr-code__wrapper')) const detailModal = await driver.findElement(By.css('span .modal')) await driver.delay(regularDelayMs) - await driver.clickElement(By.css('.account-modal-close')) + await driver.clickElement(By.css('.account-modal__close')) await driver.wait(until.stalenessOf(detailModal)) await driver.delay(regularDelayMs) }) @@ -223,7 +223,7 @@ describe('Using MetaMask with an existing account', function () { const txValues = await driver.findElements(By.css('.transaction-list-item__primary-currency')) assert.equal(txValues.length, 1) - assert.ok(/-1\s*ETH/.test(await txValues[0].getText())) + assert.ok(/-1\s*ETH/u.test(await txValues[0].getText())) }) }) diff --git a/test/e2e/incremental-security.spec.js b/test/e2e/incremental-security.spec.js index 82e3fc0e0..1e1a30349 100644 --- a/test/e2e/incremental-security.spec.js +++ b/test/e2e/incremental-security.spec.js @@ -95,12 +95,12 @@ describe('MetaMask', function () { }) it('gets the current accounts address', async function () { - const addressInput = await driver.findElement(By.css('.qr-ellip-address')) + const addressInput = await driver.findElement(By.css('.readonly-input__input')) publicAddress = await addressInput.getAttribute('value') const accountModal = await driver.findElement(By.css('span .modal')) - await driver.clickElement(By.css('.account-modal-close')) + await driver.clickElement(By.css('.account-modal__close')) await driver.wait(until.stalenessOf(accountModal)) await driver.delay(regularDelayMs) @@ -127,7 +127,7 @@ describe('MetaMask', function () { await driver.clickElement(By.css('#send')) const txStatus = await driver.findElement(By.css('#success')) - await driver.wait(until.elementTextMatches(txStatus, /Success/), 15000) + await driver.wait(until.elementTextMatches(txStatus, /Success/u), 15000) }) it('switches back to MetaMask', async function () { @@ -136,7 +136,7 @@ describe('MetaMask', function () { it('should have the correct amount of eth', async function () { const balances = await driver.findElements(By.css('.currency-display-component__text')) - await driver.wait(until.elementTextMatches(balances[0], /1/), 15000) + await driver.wait(until.elementTextMatches(balances[0], /1/u), 15000) const balance = await balances[0].getText() assert.equal(balance, '1') @@ -193,7 +193,7 @@ describe('MetaMask', function () { it('should have the correct amount of eth', async function () { const balances = await driver.findElements(By.css('.currency-display-component__text')) - await driver.wait(until.elementTextMatches(balances[0], /1/), 15000) + await driver.wait(until.elementTextMatches(balances[0], /1/u), 15000) const balance = await balances[0].getText() assert.equal(balance, '1') diff --git a/test/e2e/metamask-responsive-ui.spec.js b/test/e2e/metamask-responsive-ui.spec.js index 0b7e8b4d4..b2d8e9c5e 100644 --- a/test/e2e/metamask-responsive-ui.spec.js +++ b/test/e2e/metamask-responsive-ui.spec.js @@ -167,7 +167,7 @@ describe('MetaMask', function () { it('balance renders', async function () { const balance = await driver.findElement(By.css('[data-testid="eth-overview__primary-currency"]')) - await driver.wait(until.elementTextMatches(balance, /100\s*ETH/)) + await driver.wait(until.elementTextMatches(balance, /100\s*ETH/u)) await driver.delay(regularDelayMs) }) }) @@ -218,7 +218,7 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/u), 10000) }) }) }) diff --git a/test/e2e/metamask-ui.spec.js b/test/e2e/metamask-ui.spec.js index 15d0198cd..bb13c0646 100644 --- a/test/e2e/metamask-ui.spec.js +++ b/test/e2e/metamask-ui.spec.js @@ -121,11 +121,11 @@ describe('MetaMask', function () { it('shows the QR code for the account', async function () { await driver.clickElement(By.css('[data-testid="account-options-menu-button"]')) await driver.clickElement(By.css('[data-testid="account-options-menu__account-details"]')) - await driver.findVisibleElement(By.css('.qr-wrapper')) + await driver.findVisibleElement(By.css('.qr-code__wrapper')) await driver.delay(regularDelayMs) const accountModal = await driver.findElement(By.css('span .modal')) - await driver.clickElement(By.css('.account-modal-close')) + await driver.clickElement(By.css('.account-modal__close')) await driver.wait(until.stalenessOf(accountModal)) await driver.delay(regularDelayMs) @@ -208,7 +208,7 @@ describe('MetaMask', function () { it('balance renders', async function () { const balance = await driver.findElement(By.css('[data-testid="wallet-balance"] .list-item__heading')) - await driver.wait(until.elementTextMatches(balance, /100\s*ETH/)) + await driver.wait(until.elementTextMatches(balance, /100\s*ETH/u)) await driver.delay(regularDelayMs) }) }) @@ -273,7 +273,7 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/u), 10000) }) }) @@ -312,7 +312,7 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/u), 10000) }) }) @@ -360,7 +360,7 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txValues, /-1\s*ETH/u), 10000) }) }) @@ -463,7 +463,7 @@ describe('MetaMask', function () { }, 10000) const txValue = await driver.findClickableElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValue, /-3\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txValue, /-3\s*ETH/u), 10000) }) it('the transaction has the expected gas price', async function () { @@ -471,7 +471,7 @@ describe('MetaMask', function () { await txValue.click() const popoverCloseButton = await driver.findClickableElement(By.css('.popover-header__button')) const txGasPrice = await driver.findElement(By.css('[data-testid="transaction-breakdown__gas-price"]')) - await driver.wait(until.elementTextMatches(txGasPrice, /^10$/), 10000) + await driver.wait(until.elementTextMatches(txGasPrice, /^10$/u), 10000) await popoverCloseButton.click() }) }) @@ -654,7 +654,7 @@ describe('MetaMask', function () { }, 10000) const txAction = await driver.findElements(By.css('.list-item__heading')) - await driver.wait(until.elementTextMatches(txAction[0], /Contract\sDeployment/), 10000) + await driver.wait(until.elementTextMatches(txAction[0], /Contract\sDeployment/u), 10000) await driver.delay(regularDelayMs) }) @@ -663,20 +663,20 @@ describe('MetaMask', function () { await driver.delay(regularDelayMs) let contractStatus = await driver.findElement(By.css('#contractStatus')) - await driver.wait(until.elementTextMatches(contractStatus, /Deployed/), 15000) + await driver.wait(until.elementTextMatches(contractStatus, /Deployed/u), 15000) await driver.clickElement(By.css('#depositButton')) await driver.delay(largeDelayMs) contractStatus = await driver.findElement(By.css('#contractStatus')) - await driver.wait(until.elementTextMatches(contractStatus, /Deposit\sinitiated/), 10000) + await driver.wait(until.elementTextMatches(contractStatus, /Deposit\sinitiated/u), 10000) await driver.switchToWindow(extension) await driver.delay(largeDelayMs * 2) await driver.findElements(By.css('.transaction-list-item')) const txListValue = await driver.findClickableElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txListValue, /-4\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txListValue, /-4\s*ETH/u), 10000) await txListValue.click() await driver.delay(regularDelayMs) @@ -718,7 +718,7 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElements(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues[0], /-4\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txValues[0], /-4\s*ETH/u), 10000) }) it('calls and confirms a contract method where ETH is received', async function () { @@ -743,7 +743,7 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues, /-0\s*ETH/), 10000) + await driver.wait(until.elementTextMatches(txValues, /-0\s*ETH/u), 10000) await driver.closeAllWindowHandlesExcept([extension, dapp]) await driver.switchToWindow(extension) @@ -752,9 +752,9 @@ describe('MetaMask', function () { it('renders the correct ETH balance', async function () { const balance = await driver.findElement(By.css('[data-testid="eth-overview__primary-currency"]')) await driver.delay(regularDelayMs) - await driver.wait(until.elementTextMatches(balance, /^87.*\s*ETH.*$/), 10000) + await driver.wait(until.elementTextMatches(balance, /^87.*\s*ETH.*$/u), 10000) const tokenAmount = await balance.getText() - assert.ok(/^87.*\s*ETH.*$/.test(tokenAmount)) + assert.ok(/^87.*\s*ETH.*$/u.test(tokenAmount)) await driver.delay(regularDelayMs) }) }) @@ -797,7 +797,7 @@ describe('MetaMask', function () { await driver.delay(tinyDelayMs) const tokenContractAddress = await driver.findElement(By.css('#tokenAddress')) - await driver.wait(until.elementTextMatches(tokenContractAddress, /0x/)) + await driver.wait(until.elementTextMatches(tokenContractAddress, /0x/u)) tokenAddress = await tokenContractAddress.getText() await driver.delay(regularDelayMs) @@ -830,9 +830,9 @@ describe('MetaMask', function () { it('renders the balance for the new token', async function () { const balance = await driver.findElement(By.css('.wallet-overview .token-overview__primary-balance')) - await driver.wait(until.elementTextMatches(balance, /^10\s*TST\s*$/)) + await driver.wait(until.elementTextMatches(balance, /^10\s*TST\s*$/u)) const tokenAmount = await balance.getText() - assert.ok(/^10\s*TST\s*$/.test(tokenAmount)) + assert.ok(/^10\s*TST\s*$/u.test(tokenAmount)) await driver.delay(regularDelayMs) }) }) @@ -887,7 +887,7 @@ describe('MetaMask', function () { const confirmDataText = await confirmDataDiv.getText() await driver.delay(regularDelayMs) - assert(confirmDataText.match(/0xa9059cbb0000000000000000000000002f318c334780961fb129d2a6c30d0763d9a5c97/)) + assert(confirmDataText.match(/0xa9059cbb0000000000000000000000002f318c334780961fb129d2a6c30d0763d9a5c97/u)) await driver.clickElement(By.xpath(`//li[contains(text(), 'Details')]`)) await driver.delay(regularDelayMs) @@ -906,10 +906,10 @@ describe('MetaMask', function () { const txValues = await driver.findElements(By.css('.transaction-list-item__primary-currency')) assert.equal(txValues.length, 1) - await driver.wait(until.elementTextMatches(txValues[0], /-1\s*TST/), 10000) + await driver.wait(until.elementTextMatches(txValues[0], /-1\s*TST/u), 10000) const txStatuses = await driver.findElements(By.css('.list-item__heading')) - await driver.wait(until.elementTextMatches(txStatuses[0], /Send\sTST/i), 10000) + await driver.wait(until.elementTextMatches(txStatuses[0], /Send\sTST/u), 10000) }) }) @@ -931,7 +931,7 @@ describe('MetaMask', function () { await driver.findElements(By.css('.transaction-list__pending-transactions')) const txListValue = await driver.findClickableElement(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txListValue, /-1.5\s*TST/), 10000) + await driver.wait(until.elementTextMatches(txListValue, /-1.5\s*TST/u), 10000) await txListValue.click() await driver.delay(regularDelayMs) @@ -987,12 +987,12 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElements(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues[0], /-1.5\s*TST/)) + await driver.wait(until.elementTextMatches(txValues[0], /-1.5\s*TST/u)) const txStatuses = await driver.findElements(By.css('.list-item__heading')) - await driver.wait(until.elementTextMatches(txStatuses[0], /Send\sTST/), 10000) + await driver.wait(until.elementTextMatches(txStatuses[0], /Send\sTST/u), 10000) const tokenBalanceAmount = await driver.findElements(By.css('.token-overview__primary-balance')) - await driver.wait(until.elementTextMatches(tokenBalanceAmount[0], /7.5\s*TST/), 10000) + await driver.wait(until.elementTextMatches(tokenBalanceAmount[0], /7.5\s*TST/u), 10000) }) }) @@ -1019,7 +1019,7 @@ describe('MetaMask', function () { }, 10000) const [txtListHeading] = await driver.findElements(By.css('.transaction-list-item .list-item__heading')) - await driver.wait(until.elementTextMatches(txtListHeading, /Approve TST spend limit/)) + await driver.wait(until.elementTextMatches(txtListHeading, /Approve TST spend limit/u)) await driver.clickElement(By.css('.transaction-list-item')) await driver.delay(regularDelayMs) }) @@ -1034,7 +1034,7 @@ describe('MetaMask', function () { const confirmDataDiv = await driver.findElement(By.css('.confirm-approve-content__data__data-block')) const confirmDataText = await confirmDataDiv.getText() - assert(confirmDataText.match(/0x095ea7b30000000000000000000000009bc5baf874d2da8d216ae9f137804184ee5afef4/)) + assert(confirmDataText.match(/0x095ea7b30000000000000000000000009bc5baf874d2da8d216ae9f137804184ee5afef4/u)) }) it('opens the gas edit modal', async function () { @@ -1105,7 +1105,7 @@ describe('MetaMask', function () { }, 10000) const txStatuses = await driver.findElements(By.css('.list-item__heading')) - await driver.wait(until.elementTextMatches(txStatuses[0], /Approve TST spend limit/)) + await driver.wait(until.elementTextMatches(txStatuses[0], /Approve TST spend limit/u)) }) }) @@ -1130,7 +1130,7 @@ describe('MetaMask', function () { }, 10000) const [txListValue] = await driver.findElements(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txListValue, /-1.5\s*TST/)) + await driver.wait(until.elementTextMatches(txListValue, /-1.5\s*TST/u)) await driver.clickElement(By.css('.transaction-list-item')) await driver.delay(regularDelayMs) }) @@ -1148,9 +1148,9 @@ describe('MetaMask', function () { }, 10000) const txValues = await driver.findElements(By.css('.transaction-list-item__primary-currency')) - await driver.wait(until.elementTextMatches(txValues[0], /-1.5\s*TST/)) + await driver.wait(until.elementTextMatches(txValues[0], /-1.5\s*TST/u)) const txStatuses = await driver.findElements(By.css('.list-item__heading')) - await driver.wait(until.elementTextMatches(txStatuses[0], /Send TST/)) + await driver.wait(until.elementTextMatches(txStatuses[0], /Send TST/u)) }) }) @@ -1176,7 +1176,7 @@ describe('MetaMask', function () { }, 10000) const [txtListHeading] = await driver.findElements(By.css('.transaction-list-item .list-item__heading')) - await driver.wait(until.elementTextMatches(txtListHeading, /Approve TST spend limit/)) + await driver.wait(until.elementTextMatches(txtListHeading, /Approve TST spend limit/u)) await driver.clickElement(By.css('.transaction-list-item')) await driver.delay(regularDelayMs) }) @@ -1203,7 +1203,7 @@ describe('MetaMask', function () { }, 10000) const txStatuses = await driver.findElements(By.css('.list-item__heading')) - await driver.wait(until.elementTextMatches(txStatuses[0], /Approve TST spend limit/)) + await driver.wait(until.elementTextMatches(txStatuses[0], /Approve TST spend limit/u)) }) }) @@ -1244,7 +1244,7 @@ describe('MetaMask', function () { it('renders the balance for the chosen token', async function () { const balance = await driver.findElement(By.css('.token-overview__primary-balance')) - await driver.wait(until.elementTextMatches(balance, /0\s*BAT/)) + await driver.wait(until.elementTextMatches(balance, /0\s*BAT/u)) await driver.delay(regularDelayMs) }) }) diff --git a/test/e2e/mock-3box/server.js b/test/e2e/mock-3box/server.js index 9d6bc7372..c4fe9d9c7 100644 --- a/test/e2e/mock-3box/server.js +++ b/test/e2e/mock-3box/server.js @@ -32,6 +32,7 @@ const server = http.createServer(requestHandler) server.listen(port, (err) => { if (err) { - return console.log('mock 3box server error: ', err) + console.log('mock 3box server error: ', err) + return } }) diff --git a/test/e2e/permissions.spec.js b/test/e2e/permissions.spec.js index 8ec86b3cb..cd6cef453 100644 --- a/test/e2e/permissions.spec.js +++ b/test/e2e/permissions.spec.js @@ -90,11 +90,11 @@ describe('MetaMask', function () { }) it('gets the current accounts address', async function () { - const addressInput = await driver.findElement(By.css('.qr-ellip-address')) + const addressInput = await driver.findElement(By.css('.readonly-input__input')) publicAddress = await addressInput.getAttribute('value') const accountModal = await driver.findElement(By.css('span .modal')) - await driver.clickElement(By.css('.account-modal-close')) + await driver.clickElement(By.css('.account-modal__close')) await driver.wait(until.stalenessOf(accountModal)) await driver.delay(regularDelayMs) diff --git a/test/e2e/send-edit.spec.js b/test/e2e/send-edit.spec.js index c3e60f1c2..ddf9bfde4 100644 --- a/test/e2e/send-edit.spec.js +++ b/test/e2e/send-edit.spec.js @@ -205,7 +205,7 @@ describe('Using MetaMask with an existing account', function () { const txValues = await driver.findElements(By.css('.transaction-list-item__primary-currency')) assert.equal(txValues.length, 1) - assert.ok(/-2.2\s*ETH/.test(await txValues[0].getText())) + assert.ok(/-2.2\s*ETH/u.test(await txValues[0].getText())) }) }) }) diff --git a/test/e2e/signature-request.spec.js b/test/e2e/signature-request.spec.js index 6e2a558ec..4ad70e15e 100644 --- a/test/e2e/signature-request.spec.js +++ b/test/e2e/signature-request.spec.js @@ -124,11 +124,11 @@ describe('MetaMask', function () { await driver.clickElement(By.css('[data-testid="account-options-menu__account-details"]')) await driver.delay(regularDelayMs) - const addressInput = await driver.findElement(By.css('.qr-ellip-address')) + const addressInput = await driver.findElement(By.css('.readonly-input__input')) const newPublicAddress = await addressInput.getAttribute('value') const accountModal = await driver.findElement(By.css('span .modal')) - await driver.clickElement(By.css('.account-modal-close')) + await driver.clickElement(By.css('.account-modal__close')) await driver.wait(until.stalenessOf(accountModal)) await driver.delay(regularDelayMs) diff --git a/test/e2e/tests/localization.spec.js b/test/e2e/tests/localization.spec.js index e3d4520ca..127d432bd 100644 --- a/test/e2e/tests/localization.spec.js +++ b/test/e2e/tests/localization.spec.js @@ -20,7 +20,7 @@ describe('Localization', function () { await passwordField.sendKeys(Key.ENTER) const secondaryBalance = await driver.findElement(By.css('[data-testid="eth-overview__secondary-currency"]')) const secondaryBalanceText = await secondaryBalance.getText() - const [fiatAmount, fiatUnit] = secondaryBalanceText.trim().split(/\s+/) + const [fiatAmount, fiatUnit] = secondaryBalanceText.trim().split(/\s+/u) assert.ok(fiatAmount.startsWith('₱')) assert.equal(fiatUnit, 'PHP') }, diff --git a/test/e2e/threebox.spec.js b/test/e2e/threebox.spec.js index e7affbfeb..6d46e0377 100644 --- a/test/e2e/threebox.spec.js +++ b/test/e2e/threebox.spec.js @@ -97,7 +97,7 @@ describe('MetaMask', function () { it('balance renders', async function () { const balance = await driver.findElement(By.css('[data-testid="wallet-balance"] .list-item__heading')) - await driver.wait(until.elementTextMatches(balance, /25\s*ETH/)) + await driver.wait(until.elementTextMatches(balance, /25\s*ETH/u)) await driver.delay(regularDelayMs) }) }) @@ -203,7 +203,7 @@ describe('MetaMask', function () { it('balance renders', async function () { const balance = await driver2.findElement(By.css('[data-testid="wallet-balance"] .list-item__heading')) - await driver2.wait(until.elementTextMatches(balance, /25\s*ETH/)) + await driver2.wait(until.elementTextMatches(balance, /25\s*ETH/u)) await driver2.delay(regularDelayMs) }) }) diff --git a/test/e2e/webdriver/driver.js b/test/e2e/webdriver/driver.js index daf3a1acc..6ae17bdcf 100644 --- a/test/e2e/webdriver/driver.js +++ b/test/e2e/webdriver/driver.js @@ -180,7 +180,9 @@ class Driver { await fs.writeFile(`${filepathBase}-screenshot.png`, screenshot, { encoding: 'base64' }) const htmlSource = await this.driver.getPageSource() await fs.writeFile(`${filepathBase}-dom.html`, htmlSource) - const uiState = await this.driver.executeScript(() => window.getCleanAppState()) + const uiState = await this.driver.executeScript( + () => window.getCleanAppState && window.getCleanAppState(), + ) await fs.writeFile(`${filepathBase}-state.json`, JSON.stringify(uiState, null, 2)) } diff --git a/test/e2e/webdriver/index.js b/test/e2e/webdriver/index.js index 652e27283..8972d54a6 100644 --- a/test/e2e/webdriver/index.js +++ b/test/e2e/webdriver/index.js @@ -45,7 +45,7 @@ async function setupFetchMocking (driver) { return { json: async () => clone(fetchMockResponses.ethGasBasic) } } else if (url.match(/http(s?):\/\/ethgasstation\.info\/json\/predictTable.*/u)) { return { json: async () => clone(fetchMockResponses.ethGasPredictTable) } - } else if (url.match(/chromeextensionmm/)) { + } else if (url.match(/chromeextensionmm/u)) { return { json: async () => clone(fetchMockResponses.metametrics) } } return window.origFetch(...args) diff --git a/test/helper.js b/test/helper.js index ea44bee48..50ec1f2d8 100644 --- a/test/helper.js +++ b/test/helper.js @@ -80,7 +80,7 @@ require('abortcontroller-polyfill/dist/polyfill-patch-fetch') window.localStorage = {} // override metamask-logo -window.requestAnimationFrame = () => {} +window.requestAnimationFrame = () => undefined // crypto.getRandomValues if (!window.crypto) { diff --git a/test/lib/render-helpers.js b/test/lib/render-helpers.js index 3671ad129..2224c2165 100644 --- a/test/lib/render-helpers.js +++ b/test/lib/render-helpers.js @@ -27,7 +27,7 @@ export function mountWithRouter (component, store = {}, pathname = '/') { context: { router, t: (str) => str, - metricsEvent: () => {}, + metricsEvent: () => undefined, store, }, childContextTypes: { diff --git a/test/unit-global/frozenPromise.js b/test/unit-global/frozenPromise.js index 05f1defe7..594c1350a 100644 --- a/test/unit-global/frozenPromise.js +++ b/test/unit-global/frozenPromise.js @@ -1,7 +1,3 @@ - -/* eslint-disable no-native-reassign */ - -// this is what we're testing import '../../app/scripts/lib/freezeGlobals' import assert from 'assert' @@ -10,6 +6,7 @@ describe('Promise global is immutable', function () { it('throws when reassinging promise (syntax 1)', function () { try { + // eslint-disable-next-line no-global-assign,no-native-reassign Promise = {} assert.fail('did not throw error') } catch (err) { @@ -28,7 +25,7 @@ describe('Promise global is immutable', function () { it('throws when mutating existing Promise property', function () { try { - Promise.all = () => {} + Promise.all = () => undefined assert.fail('did not throw error') } catch (err) { assert.ok(err, 'did throw error') diff --git a/test/unit/app/controllers/cached-balances-test.js b/test/unit/app/controllers/cached-balances-test.js index 272334dc5..f954da63f 100644 --- a/test/unit/app/controllers/cached-balances-test.js +++ b/test/unit/app/controllers/cached-balances-test.js @@ -9,7 +9,7 @@ describe('CachedBalancesController', function () { getNetwork: () => Promise.resolve(17), accountTracker: { store: { - subscribe: () => {}, + subscribe: () => undefined, }, }, initState: { @@ -32,7 +32,7 @@ describe('CachedBalancesController', function () { const controller = new CachedBalancesController({ accountTracker: { store: { - subscribe: () => {}, + subscribe: () => undefined, }, }, initState: { @@ -75,7 +75,7 @@ describe('CachedBalancesController', function () { const controller = new CachedBalancesController({ accountTracker: { store: { - subscribe: () => {}, + subscribe: () => undefined, }, }, initState: { diff --git a/test/unit/app/controllers/detect-tokens-test.js b/test/unit/app/controllers/detect-tokens-test.js index ee2418856..83ca9eb01 100644 --- a/test/unit/app/controllers/detect-tokens-test.js +++ b/test/unit/app/controllers/detect-tokens-test.js @@ -14,7 +14,7 @@ describe('DetectTokensController', function () { const sandbox = sinon.createSandbox() let keyringMemStore, network, preferences - const noop = () => {} + const noop = () => undefined const networkControllerProviderConfig = { getAccounts: noop, @@ -24,7 +24,7 @@ describe('DetectTokensController', function () { nock('https://api.infura.io') - .get(/.*/) + .get(/.*/u) .reply(200) keyringMemStore = new ObservableStore({ isUnlocked: false }) diff --git a/test/unit/app/controllers/ens-controller-test.js b/test/unit/app/controllers/ens-controller-test.js index 1176b8b42..cf57bdf1f 100644 --- a/test/unit/app/controllers/ens-controller-test.js +++ b/test/unit/app/controllers/ens-controller-test.js @@ -1,7 +1,6 @@ import assert from 'assert' import sinon from 'sinon' import ObservableStore from 'obs-store' -import HttpProvider from 'ethjs-provider-http' import EnsController from '../../../../app/scripts/controllers/ens' const ZERO_ADDRESS = '0x0000000000000000000000000000000000000000' @@ -10,11 +9,10 @@ const ZERO_X_ERROR_ADDRESS = '0x' describe('EnsController', function () { describe('#constructor', function () { it('should construct the controller given a provider and a network', async function () { - const provider = new HttpProvider('https://ropsten.infura.io') const currentNetworkId = '3' const networkStore = new ObservableStore(currentNetworkId) const ens = new EnsController({ - provider, + provider: { }, networkStore, }) diff --git a/test/unit/app/controllers/metamask-controller-test.js b/test/unit/app/controllers/metamask-controller-test.js index 746b098d3..92be16f51 100644 --- a/test/unit/app/controllers/metamask-controller-test.js +++ b/test/unit/app/controllers/metamask-controller-test.js @@ -19,7 +19,7 @@ import proxyquire from 'proxyquire' class ThreeBoxControllerMock { constructor () { this.store = { - subscribe: () => {}, + subscribe: () => undefined, getState: () => ({}), } this.init = threeBoxSpies.init @@ -78,7 +78,7 @@ const CUSTOM_RPC_URL = 'http://localhost:8545' describe('MetaMaskController', function () { let metamaskController const sandbox = sinon.createSandbox() - const noop = () => {} + const noop = () => undefined beforeEach(function () { @@ -92,12 +92,12 @@ describe('MetaMaskController', function () { nock('https://api.infura.io') .persist() - .get(/.*/) + .get(/.*/u) .reply(200) nock('https://min-api.cryptocompare.com') .persist() - .get(/.*/) + .get(/.*/u) .reply(200, '{"JPY":12415.9}') metamaskController = new MetaMaskController({ @@ -113,7 +113,7 @@ describe('MetaMaskController', function () { }, }, initState: cloneDeep(firstTimeState), - platform: { showTransactionNotification: () => {} }, + platform: { showTransactionNotification: () => undefined }, }) // disable diagnostics metamaskController.diagnostics = null @@ -819,7 +819,8 @@ describe('MetaMaskController', function () { const { promise, resolve } = deferredPromise() const streamTest = createThoughStream((chunk, _, cb) => { if (chunk.name !== 'phishing') { - return cb() + cb() + return } assert.equal(chunk.data.hostname, (new URL(phishingMessageSender.url)).hostname) resolve() diff --git a/test/unit/app/controllers/network/network-controller-test.js b/test/unit/app/controllers/network/network-controller-test.js index 08164d99d..be1c7f536 100644 --- a/test/unit/app/controllers/network/network-controller-test.js +++ b/test/unit/app/controllers/network/network-controller-test.js @@ -6,7 +6,7 @@ import { getNetworkDisplayName } from '../../../../../app/scripts/controllers/ne describe('NetworkController', function () { describe('controller', function () { let networkController - const noop = () => {} + const noop = () => undefined const networkControllerProviderConfig = { getAccounts: noop, } diff --git a/test/unit/app/controllers/permissions/mocks.js b/test/unit/app/controllers/permissions/mocks.js index 5302d9f61..65b311182 100644 --- a/test/unit/app/controllers/permissions/mocks.js +++ b/test/unit/app/controllers/permissions/mocks.js @@ -20,7 +20,7 @@ import { * - Immutable mock values like Ethereum accounts and expected states */ -export const noop = () => {} +export const noop = () => undefined /** * Mock Permissions Controller and Middleware diff --git a/test/unit/app/controllers/preferences-controller-test.js b/test/unit/app/controllers/preferences-controller-test.js index 5d711f1c8..f0091d35a 100644 --- a/test/unit/app/controllers/preferences-controller-test.js +++ b/test/unit/app/controllers/preferences-controller-test.js @@ -372,7 +372,7 @@ describe('preferences controller', function () { beforeEach(function () { req = { params: {} } res = {} - asy = { next: () => {}, end: () => {} } + asy = { next: () => undefined, end: () => undefined } stubNext = sandbox.stub(asy, 'next') stubEnd = sandbox.stub(asy, 'end').returns(0) stubHandleWatchAssetERC20 = sandbox.stub(preferencesController, '_handleWatchAssetERC20') @@ -382,7 +382,7 @@ describe('preferences controller', function () { }) it('shouldn not do anything if method not corresponds', async function () { - const asy = { next: () => {}, end: () => {} } + const asy = { next: () => undefined, end: () => undefined } const stubNext = sandbox.stub(asy, 'next') const stubEnd = sandbox.stub(asy, 'end').returns(0) req.method = 'metamask' @@ -391,7 +391,7 @@ describe('preferences controller', function () { sandbox.assert.called(stubNext) }) it('should do something if method is supported', async function () { - const asy = { next: () => {}, end: () => {} } + const asy = { next: () => undefined, end: () => undefined } const stubNext = sandbox.stub(asy, 'next') const stubEnd = sandbox.stub(asy, 'end').returns(0) req.method = 'metamask_watchAsset' @@ -415,7 +415,7 @@ describe('preferences controller', function () { assert.deepEqual(res, {}) }) it('should trigger handle add asset if type supported', async function () { - const asy = { next: () => {}, end: () => {} } + const asy = { next: () => undefined, end: () => undefined } req.method = 'metamask_watchAsset' req.params.type = 'ERC20' await preferencesController.requestWatchAsset(req, res, asy.next, asy.end) @@ -442,7 +442,7 @@ describe('preferences controller', function () { req.params.options = { address, symbol, decimals, image } sandbox.stub(preferencesController, '_validateERC20AssetParams').returns(true) - preferencesController.openPopup = async () => {} + preferencesController.openPopup = async () => undefined await preferencesController._handleWatchAssetERC20(req.params.options) const suggested = preferencesController.getSuggestedTokens() @@ -478,46 +478,16 @@ describe('preferences controller', function () { assert.ok(assetImages[address], `set image correctly`) }) it('should validate ERC20 asset correctly', async function () { - const validateSpy = sandbox.spy(preferencesController._validateERC20AssetParams) - try { - validateSpy({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABC', decimals: 0 }) - } catch (e) {} - assert.equal(validateSpy.threw(), false, 'correct options object') - const validateSpyAddress = sandbox.spy(preferencesController._validateERC20AssetParams) - try { - validateSpyAddress({ symbol: 'ABC', decimals: 0 }) - } catch (e) {} - assert.equal(validateSpyAddress.threw(), true, 'options object with no address') - const validateSpySymbol = sandbox.spy(preferencesController._validateERC20AssetParams) - try { - validateSpySymbol({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', decimals: 0 }) - } catch (e) {} - assert.equal(validateSpySymbol.threw(), true, 'options object with no symbol') - const validateSpyDecimals = sandbox.spy(preferencesController._validateERC20AssetParams) - try { - validateSpyDecimals({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABC' }) - } catch (e) {} - assert.equal(validateSpyDecimals.threw(), true, 'options object with no decimals') - const validateSpyInvalidSymbol = sandbox.spy(preferencesController._validateERC20AssetParams) - try { - validateSpyInvalidSymbol({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABCDEFGHI', decimals: 0 }) - } catch (e) {} - assert.equal(validateSpyInvalidSymbol.threw(), true, 'options object with invalid symbol') - const validateSpyInvalidDecimals1 = sandbox.spy(preferencesController._validateERC20AssetParams) - try { - validateSpyInvalidDecimals1({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABCDEFGHI', decimals: -1 }) - } catch (e) {} - assert.equal(validateSpyInvalidDecimals1.threw(), true, 'options object with decimals less than zero') - const validateSpyInvalidDecimals2 = sandbox.spy(preferencesController._validateERC20AssetParams) - try { - validateSpyInvalidDecimals2({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABCDEFGHI', decimals: 38 }) - } catch (e) {} - assert.equal(validateSpyInvalidDecimals2.threw(), true, 'options object with decimals more than 36') - const validateSpyInvalidAddress = sandbox.spy(preferencesController._validateERC20AssetParams) - try { - validateSpyInvalidAddress({ rawAddress: '0x123', symbol: 'ABC', decimals: 0 }) - } catch (e) {} - assert.equal(validateSpyInvalidAddress.threw(), true, 'options object with address invalid') + const validate = preferencesController._validateERC20AssetParams + + assert.doesNotThrow(() => validate({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABC', decimals: 0 })) + assert.throws(() => validate({ symbol: 'ABC', decimals: 0 }), 'missing address should fail') + assert.throws(() => validate({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', decimals: 0 }), 'missing symbol should fail') + assert.throws(() => validate({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABC' }), 'missing decimals should fail') + assert.throws(() => validate({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABCDEFGHI', decimals: 0 }), 'invalid symbol should fail') + assert.throws(() => validate({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABC', decimals: -1 }), 'decimals < 0 should fail') + assert.throws(() => validate({ rawAddress: '0xd26114cd6EE289AccF82350c8d8487fedB8A0C07', symbol: 'ABC', decimals: 38 }), 'decimals > 36 should fail') + assert.throws(() => validate({ rawAddress: '0x123', symbol: 'ABC', decimals: 0 }), 'invalid address should fail') }) }) diff --git a/test/unit/app/controllers/transactions/pending-tx-tracker-test.js b/test/unit/app/controllers/transactions/pending-tx-tracker-test.js index facc0bb12..000ad263d 100644 --- a/test/unit/app/controllers/transactions/pending-tx-tracker-test.js +++ b/test/unit/app/controllers/transactions/pending-tx-tracker-test.js @@ -147,15 +147,15 @@ describe('PendingTransactionTracker', function () { }, nonceTracker: { getGlobalLock: async () => { - return { releaseLock: () => {} } + return { releaseLock: () => undefined } }, }, getPendingTransactions: () => txList, getCompletedTransactions: () => { return [] }, - publishTransaction: () => {}, - confirmTransaction: () => {}, + publishTransaction: () => undefined, + confirmTransaction: () => undefined, }) const checkPendingTxStub = sinon.stub(pendingTxTracker, '_checkPendingTx').resolves() diff --git a/test/unit/app/controllers/transactions/tx-controller-test.js b/test/unit/app/controllers/transactions/tx-controller-test.js index e9d229aba..b3649a9b3 100644 --- a/test/unit/app/controllers/transactions/tx-controller-test.js +++ b/test/unit/app/controllers/transactions/tx-controller-test.js @@ -13,7 +13,7 @@ import { SEND_ETHER_ACTION_KEY, DEPLOY_CONTRACT_ACTION_KEY, CONTRACT_INTERACTION_KEY, -} from '../../../../../ui/app/helpers/constants/transactions.js' +} from '../../../../../ui/app/helpers/constants/transactions' import { createTestProviderTools, getTestAccounts } from '../../../../stub/provider' @@ -47,7 +47,7 @@ describe('Transaction Controller', function () { ethTx.sign(fromAccount.key) resolve() }), - getPermittedAccounts: () => {}, + getPermittedAccounts: () => undefined, }) txController.nonceTracker.getNonceLock = () => Promise.resolve({ nextNonce: 0, releaseLock: noop }) }) diff --git a/test/unit/app/controllers/transactions/tx-gas-util-test.js b/test/unit/app/controllers/transactions/tx-gas-util-test.js index 615a25527..21ba62746 100644 --- a/test/unit/app/controllers/transactions/tx-gas-util-test.js +++ b/test/unit/app/controllers/transactions/tx-gas-util-test.js @@ -9,7 +9,7 @@ describe('txUtils', function () { before(function () { txUtils = new TxUtils(new Proxy({}, { get: () => { - return () => {} + return () => undefined }, })) }) diff --git a/test/unit/app/message-manager-test.js b/test/unit/app/message-manager-test.js index 8c499c97d..66eef7b10 100644 --- a/test/unit/app/message-manager-test.js +++ b/test/unit/app/message-manager-test.js @@ -14,9 +14,6 @@ describe('Message Manager', function () { assert.ok(Array.isArray(result)) assert.equal(result.length, 0) }) - it('should also return transactions from local storage if any', function () { - - }) }) describe('#addMsg', function () { diff --git a/test/unit/app/nodeify-test.js b/test/unit/app/nodeify-test.js index a70446ef0..c8d1c46d9 100644 --- a/test/unit/app/nodeify-test.js +++ b/test/unit/app/nodeify-test.js @@ -16,9 +16,10 @@ describe('nodeify', function () { if (!err) { assert.equal(res, 'barbaz') done() - } else { - done(new Error(err.toString())) + return } + + done(new Error(err.toString())) }) }) @@ -37,7 +38,8 @@ describe('nodeify', function () { try { nodified((err, result) => { if (err) { - return done(new Error(`should not have thrown any error: ${err.message}`)) + done(new Error(`should not have thrown any error: ${err.message}`)) + return } assert.equal(42, result, 'got expected result') }) @@ -54,7 +56,8 @@ describe('nodeify', function () { try { nodified((err, result) => { if (result) { - return done(new Error('should not have returned any result')) + done(new Error('should not have returned any result')) + return } assert.ok(err, 'got expected error') assert.ok(err.message.includes('boom!'), 'got expected error message') diff --git a/test/unit/app/personal-message-manager-test.js b/test/unit/app/personal-message-manager-test.js index 9e5aaaba1..d95ca5e14 100644 --- a/test/unit/app/personal-message-manager-test.js +++ b/test/unit/app/personal-message-manager-test.js @@ -14,9 +14,6 @@ describe('Personal Message Manager', function () { assert.ok(Array.isArray(result)) assert.equal(result.length, 0) }) - it('should also return transactions from local storage if any', function () { - - }) }) describe('#addMsg', function () { diff --git a/test/unit/migrations/023-test.js b/test/unit/migrations/023-test.js index 821057bf8..362b4dbe2 100644 --- a/test/unit/migrations/023-test.js +++ b/test/unit/migrations/023-test.js @@ -38,8 +38,10 @@ let nonDeletableCount = 0 let status while (transactions.length <= 100) { status = txStates[Math.floor(Math.random() * Math.floor(txStates.length - 1))] + // This is an old migration, let's allow it + // eslint-disable-next-line no-loop-func if (!deletableTxStates.find((s) => s === status)) { - nonDeletableCount++ + nonDeletableCount += 1 } transactions.push({ status }) } @@ -65,7 +67,7 @@ describe('storage is migrated successfully and the proper transactions are remov const migratedTransactions = migratedData.data.TransactionController.transactions migratedTransactions.forEach((tx) => { if (!deletableTxStates.find((s) => s === tx.status)) { - leftoverNonDeletableTxCount++ + leftoverNonDeletableTxCount += 1 } }) assert.equal(leftoverNonDeletableTxCount, nonDeletableCount, "migration shouldn't delete transactions we want to keep") diff --git a/test/unit/migrations/030-test.js b/test/unit/migrations/030-test.js index f575e4bcb..6d0271f0d 100644 --- a/test/unit/migrations/030-test.js +++ b/test/unit/migrations/030-test.js @@ -1,5 +1,5 @@ import assert from 'assert' -import migrationTemplate from '../../../app/scripts/migrations/030.js' +import migrationTemplate from '../../../app/scripts/migrations/030' const storage = { meta: {}, diff --git a/test/unit/migrations/migrator-test.js b/test/unit/migrations/migrator-test.js index c54866ec0..a3dc2fbb7 100644 --- a/test/unit/migrations/migrator-test.js +++ b/test/unit/migrations/migrator-test.js @@ -50,7 +50,7 @@ describe('migrations', function () { migrationNumbers = fileNames .reduce((acc, filename) => { const name = filename.split('.')[0] - if (/^\d+$/.test(name)) { + if (/^\d+$/u.test(name)) { acc.push(name) } return acc @@ -70,7 +70,7 @@ describe('migrations', function () { const testNumbers = fileNames .reduce((acc, filename) => { const name = filename.split('-test.')[0] - if (/^\d+$/.test(name)) { + if (/^\d+$/u.test(name)) { acc.push(name) } return acc diff --git a/test/unit/ui/app/actions.spec.js b/test/unit/ui/app/actions.spec.js index 6eb2e6007..c25586950 100644 --- a/test/unit/ui/app/actions.spec.js +++ b/test/unit/ui/app/actions.spec.js @@ -19,7 +19,7 @@ const mockStore = (state = defaultState) => configureStore(middleware)(state) describe('Actions', function () { - const noop = () => {} + const noop = () => undefined const currentNetworkId = '42' diff --git a/test/unit/ui/app/reducers/app.spec.js b/test/unit/ui/app/reducers/app.spec.js index cd135d220..027f574f2 100644 --- a/test/unit/ui/app/reducers/app.spec.js +++ b/test/unit/ui/app/reducers/app.spec.js @@ -167,6 +167,23 @@ describe('App State', function () { }) + it('clears account details', function () { + const exportPrivKeyModal = { + accountDetail: { + subview: 'export', + accountExport: 'completed', + privateKey: 'a-priv-key', + }, + } + + const state = { ...metamaskState, appState: { ...exportPrivKeyModal } } + const newState = reduceApp(state, { + type: actions.CLEAR_ACCOUNT_DETAILS, + }) + + assert.deepStrictEqual(newState.accountDetail, {}) + }) + it('shoes account page', function () { const state = reduceApp(metamaskState, { type: actions.SHOW_ACCOUNTS_PAGE, diff --git a/ui/app/components/app/account-list-item/account-list-item.js b/ui/app/components/app/account-list-item/account-list-item.js new file mode 100644 index 000000000..7e001f7d6 --- /dev/null +++ b/ui/app/components/app/account-list-item/account-list-item.js @@ -0,0 +1,51 @@ +import React from 'react' +import PropTypes from 'prop-types' +import { checksumAddress } from '../../../helpers/utils/util' +import Identicon from '../../ui/identicon' +import AccountMismatchWarning from '../../ui/account-mismatch-warning/account-mismatch-warning.component' + +export default function AccountListItem ({ + account, + className, + displayAddress = false, + handleClick, + icon = null, +}) { + const { name, address, balance } = account || {} + + return ( +
handleClick && handleClick({ name, address, balance })} + > + +
+ + +
{ name || address }
+ + {icon &&
{ icon }
} + + +
+ + {displayAddress && name && ( +
+ { checksumAddress(address) } +
+ )} +
+ ) +} + +AccountListItem.propTypes = { + account: PropTypes.object, + className: PropTypes.string, + displayAddress: PropTypes.bool, + handleClick: PropTypes.func, + icon: PropTypes.node, +} diff --git a/ui/app/components/app/account-list-item/index.js b/ui/app/components/app/account-list-item/index.js new file mode 100644 index 000000000..1759f6597 --- /dev/null +++ b/ui/app/components/app/account-list-item/index.js @@ -0,0 +1 @@ +export { default } from './account-list-item' diff --git a/ui/app/components/app/account-list-item/index.scss b/ui/app/components/app/account-list-item/index.scss new file mode 100644 index 000000000..dcc08d9b5 --- /dev/null +++ b/ui/app/components/app/account-list-item/index.scss @@ -0,0 +1,26 @@ +.account-list-item { + &__top-row { + display: flex; + margin-top: 10px; + margin-left: 8px; + position: relative; + } + + &__account-name { + font-size: 16px; + margin-left: 8px; + } + + &__icon { + position: absolute; + right: 12px; + top: 1px; + } + + &__account-address { + margin-left: 35px; + width: 80%; + overflow: hidden; + text-overflow: ellipsis; + } +} diff --git a/ui/app/pages/send/account-list-item/tests/account-list-item-component.test.js b/ui/app/components/app/account-list-item/tests/account-list-item-component.test.js similarity index 75% rename from ui/app/pages/send/account-list-item/tests/account-list-item-component.test.js rename to ui/app/components/app/account-list-item/tests/account-list-item-component.test.js index a2949511a..ee4ef3c89 100644 --- a/ui/app/pages/send/account-list-item/tests/account-list-item-component.test.js +++ b/ui/app/components/app/account-list-item/tests/account-list-item-component.test.js @@ -3,9 +3,8 @@ import assert from 'assert' import { shallow } from 'enzyme' import sinon from 'sinon' import * as utils from '../../../../helpers/utils/util' -import Identicon from '../../../../components/ui/identicon' -import UserPreferencedCurrencyDisplay from '../../../../components/app/user-preferenced-currency-display' -import AccountListItem from '../account-list-item.component' +import Identicon from '../../../ui/identicon' +import AccountListItem from '../account-list-item' describe('AccountListItem Component', function () { let wrapper, propsMethodSpies, checksumAddressStub @@ -22,11 +21,7 @@ describe('AccountListItem Component', function () { } /> @@ -113,36 +108,5 @@ describe('AccountListItem Component', function () { wrapper.setProps({ account: { address: 'someAddressButNoName' } }) assert.equal(wrapper.find('.account-list-item__account-address').length, 0) }) - - it('should render a CurrencyDisplay with the correct props if displayBalance is true', function () { - wrapper.setProps({ displayBalance: true }) - assert.equal(wrapper.find(UserPreferencedCurrencyDisplay).length, 2) - assert.deepEqual( - wrapper.find(UserPreferencedCurrencyDisplay).at(0).props(), - { - type: 'PRIMARY', - value: 'mockBalance', - hideTitle: true, - }, - ) - }) - - it('should only render one CurrencyDisplay if showFiat is false', function () { - wrapper.setProps({ showFiat: false, displayBalance: true }) - assert.equal(wrapper.find(UserPreferencedCurrencyDisplay).length, 1) - assert.deepEqual( - wrapper.find(UserPreferencedCurrencyDisplay).at(0).props(), - { - type: 'PRIMARY', - value: 'mockBalance', - hideTitle: true, - }, - ) - }) - - it('should not render a CurrencyDisplay if displayBalance is false', function () { - wrapper.setProps({ displayBalance: false }) - assert.equal(wrapper.find(UserPreferencedCurrencyDisplay).length, 0) - }) }) }) diff --git a/ui/app/components/app/account-panel.js b/ui/app/components/app/account-panel.js deleted file mode 100644 index 36517f474..000000000 --- a/ui/app/components/app/account-panel.js +++ /dev/null @@ -1,63 +0,0 @@ -import PropTypes from 'prop-types' -import React, { Component } from 'react' -import Identicon from '../ui/identicon' -import { addressSummary, formatBalance } from '../../helpers/utils/util' - -export default class AccountPanel extends Component { - static propTypes = { - identity: PropTypes.object, - account: PropTypes.object, - isFauceting: PropTypes.bool, - } - - static defaultProps = { - identity: {}, - account: {}, - isFauceting: false, - } - - render () { - const { identity, account, isFauceting } = this.props - - const panelState = { - key: `accountPanel${identity.address}`, - identiconKey: identity.address, - identiconLabel: identity.name || '', - attributes: [ - { - key: 'ADDRESS', - value: addressSummary(identity.address), - }, - balanceOrFaucetingIndication(account, isFauceting), - ], - } - - return ( -
-
- - {panelState.identiconLabel.substring(0, 7) + '...'} -
-
- {panelState.attributes.map((attr, index) => ( -
- - {attr.value} -
- ))} -
-
- ) - } -} - -function balanceOrFaucetingIndication (account) { - return { - key: 'BALANCE', - value: formatBalance(account.balance), - } -} diff --git a/ui/app/components/app/app-header/tests/app-header.test.js b/ui/app/components/app/app-header/tests/app-header.test.js index 0ada978da..ece8e498c 100644 --- a/ui/app/components/app/app-header/tests/app-header.test.js +++ b/ui/app/components/app/app-header/tests/app-header.test.js @@ -30,7 +30,7 @@ describe('App Header', function () { , { context: { t: (str) => str, - metricsEvent: () => {}, + metricsEvent: () => undefined, }, }, ) @@ -54,8 +54,8 @@ describe('App Header', function () { const network = wrapper.find({ network: 'test' }) network.simulate('click', { - preventDefault: () => {}, - stopPropagation: () => {}, + preventDefault: () => undefined, + stopPropagation: () => undefined, }) assert(props.showNetworkDropdown.calledOnce) @@ -66,8 +66,8 @@ describe('App Header', function () { const network = wrapper.find({ network: 'test' }) network.simulate('click', { - preventDefault: () => {}, - stopPropagation: () => {}, + preventDefault: () => undefined, + stopPropagation: () => undefined, }) assert(props.hideNetworkDropdown.calledOnce) diff --git a/ui/app/components/app/asset-list-item/asset-list-item.js b/ui/app/components/app/asset-list-item/asset-list-item.js index bacae2d3a..1b7cbe672 100644 --- a/ui/app/components/app/asset-list-item/asset-list-item.js +++ b/ui/app/components/app/asset-list-item/asset-list-item.js @@ -60,7 +60,7 @@ const AssetListItem = ({ : null const sendTokenButton = useMemo(() => { - if (tokenAddress == null) { + if (tokenAddress === null || tokenAddress === undefined) { return null } return ( diff --git a/ui/app/components/app/asset-list/index.js b/ui/app/components/app/asset-list/index.js index 49abc01fd..47ee5ce9f 100644 --- a/ui/app/components/app/asset-list/index.js +++ b/ui/app/components/app/asset-list/index.js @@ -1 +1 @@ -export { default } from './asset-list.js' +export { default } from './asset-list' diff --git a/ui/app/components/app/confirm-page-container/confirm-detail-row/tests/confirm-detail-row.component.test.js b/ui/app/components/app/confirm-page-container/confirm-detail-row/tests/confirm-detail-row.component.test.js index 3c8c28612..32e7a2c1d 100644 --- a/ui/app/components/app/confirm-page-container/confirm-detail-row/tests/confirm-detail-row.component.test.js +++ b/ui/app/components/app/confirm-page-container/confirm-detail-row/tests/confirm-detail-row.component.test.js @@ -1,7 +1,7 @@ import React from 'react' import assert from 'assert' import { shallow } from 'enzyme' -import ConfirmDetailRow from '../confirm-detail-row.component.js' +import ConfirmDetailRow from '../confirm-detail-row.component' import sinon from 'sinon' const propsMethodSpies = { diff --git a/ui/app/components/app/confirm-page-container/confirm-page-container-header/confirm-page-container-header.component.js b/ui/app/components/app/confirm-page-container/confirm-page-container-header/confirm-page-container-header.component.js index f1f10a797..c72600274 100644 --- a/ui/app/components/app/confirm-page-container/confirm-page-container-header/confirm-page-container-header.component.js +++ b/ui/app/components/app/confirm-page-container/confirm-page-container-header/confirm-page-container-header.component.js @@ -30,8 +30,22 @@ export default function ConfirmPageContainerHeader ({ return (
- { !showAccountInHeader + { showAccountInHeader ? ( +
+
+ +
+
+ { shortenAddress(accountAddress) } +
+ +
+ ) + : (
) - : null - } - { showAccountInHeader - ? ( -
-
- -
-
- { shortenAddress(accountAddress) } -
- -
- ) - : null } { !isFullScreen && }
diff --git a/ui/app/components/app/connected-accounts-list/connected-accounts-list.component.js b/ui/app/components/app/connected-accounts-list/connected-accounts-list.component.js index 898af901e..5509e9cd4 100644 --- a/ui/app/components/app/connected-accounts-list/connected-accounts-list.component.js +++ b/ui/app/components/app/connected-accounts-list/connected-accounts-list.component.js @@ -37,6 +37,7 @@ export default class ConnectedAccountsList extends PureComponent { `Warning: Failed prop type: '${propName}' of component '${componentName}' requires prop 'removePermittedAccount'.`, ) } + return undefined }, } @@ -148,9 +149,9 @@ export default class ConnectedAccountsList extends PureComponent { : null } action={ - address !== selectedAddress - ? this.renderListItemAction(address) - : null + address === selectedAddress + ? null + : this.renderListItemAction(address) } /> ) diff --git a/ui/app/components/app/dropdowns/tests/dropdown.test.js b/ui/app/components/app/dropdowns/tests/dropdown.test.js index b32d1327f..3cb5c6005 100644 --- a/ui/app/components/app/dropdowns/tests/dropdown.test.js +++ b/ui/app/components/app/dropdowns/tests/dropdown.test.js @@ -2,7 +2,7 @@ import React from 'react' import assert from 'assert' import sinon from 'sinon' import { shallow } from 'enzyme' -import { DropdownMenuItem } from '../components/dropdown.js' +import { DropdownMenuItem } from '../components/dropdown' describe('Dropdown', function () { let wrapper diff --git a/ui/app/components/app/gas-customization/gas-modal-page-container/advanced-tab-content/advanced-tab-content.component.js b/ui/app/components/app/gas-customization/gas-modal-page-container/advanced-tab-content/advanced-tab-content.component.js index 19e3aa776..91c36f0a4 100644 --- a/ui/app/components/app/gas-customization/gas-modal-page-container/advanced-tab-content/advanced-tab-content.component.js +++ b/ui/app/components/app/gas-customization/gas-modal-page-container/advanced-tab-content/advanced-tab-content.component.js @@ -86,9 +86,9 @@ export default class AdvancedTabContent extends Component { ? (
{ t('liveGasPricePredictions') }
- {!gasEstimatesLoading - ? - : + {gasEstimatesLoading + ? + : }
{ t('slower') } diff --git a/ui/app/components/app/gas-customization/gas-modal-page-container/advanced-tab-content/tests/advanced-tab-content-component.test.js b/ui/app/components/app/gas-customization/gas-modal-page-container/advanced-tab-content/tests/advanced-tab-content-component.test.js index 303224d5e..caa4d1abc 100644 --- a/ui/app/components/app/gas-customization/gas-modal-page-container/advanced-tab-content/tests/advanced-tab-content-component.test.js +++ b/ui/app/components/app/gas-customization/gas-modal-page-container/advanced-tab-content/tests/advanced-tab-content-component.test.js @@ -2,7 +2,7 @@ import React from 'react' import assert from 'assert' import shallow from '../../../../../../../lib/shallow-with-context' import sinon from 'sinon' -import AdvancedTabContent from '../advanced-tab-content.component.js' +import AdvancedTabContent from '../advanced-tab-content.component' import GasPriceChart from '../../../gas-price-chart' import Loading from '../../../../../ui/loading-screen' diff --git a/ui/app/components/app/gas-customization/gas-modal-page-container/basic-tab-content/basic-tab-content.component.js b/ui/app/components/app/gas-customization/gas-modal-page-container/basic-tab-content/basic-tab-content.component.js index 94d22ee4a..5a80e4c98 100644 --- a/ui/app/components/app/gas-customization/gas-modal-page-container/basic-tab-content/basic-tab-content.component.js +++ b/ui/app/components/app/gas-customization/gas-modal-page-container/basic-tab-content/basic-tab-content.component.js @@ -20,15 +20,15 @@ export default class BasicTabContent extends Component {
{ t('estimatedProcessingTimes') }
{ t('selectAHigherGasFee') }
- {!gasPriceButtonGroupProps.loading - ? ( + {gasPriceButtonGroupProps.loading + ? + : ( ) - : }
{ t('acceleratingATransaction') }
diff --git a/ui/app/components/app/gas-customization/gas-modal-page-container/tests/gas-modal-page-container-component.test.js b/ui/app/components/app/gas-customization/gas-modal-page-container/tests/gas-modal-page-container-component.test.js index 473a651ce..8557fb2ec 100644 --- a/ui/app/components/app/gas-customization/gas-modal-page-container/tests/gas-modal-page-container-component.test.js +++ b/ui/app/components/app/gas-customization/gas-modal-page-container/tests/gas-modal-page-container-component.test.js @@ -2,7 +2,7 @@ import React from 'react' import assert from 'assert' import shallow from '../../../../../../lib/shallow-with-context' import sinon from 'sinon' -import GasModalPageContainer from '../gas-modal-page-container.component.js' +import GasModalPageContainer from '../gas-modal-page-container.component' import timeout from '../../../../../../lib/test-timeout' import PageContainer from '../../../../ui/page-container' diff --git a/ui/app/components/app/gas-customization/gas-price-button-group/gas-price-button-group.component.js b/ui/app/components/app/gas-customization/gas-price-button-group/gas-price-button-group.component.js index b578ff1ed..8916c7e8e 100644 --- a/ui/app/components/app/gas-customization/gas-price-button-group/gas-price-button-group.component.js +++ b/ui/app/components/app/gas-customization/gas-price-button-group/gas-price-button-group.component.js @@ -89,18 +89,18 @@ export default class GasPriceButtonGroup extends Component { } = this.props return ( - !buttonDataLoading - ? ( + buttonDataLoading + ?
{this.context.t('loading')}
+ : ( - { gasButtonInfo.map((obj, index) => this.renderButton(obj, buttonPropsAndFlags, index)) } + {gasButtonInfo.map((obj, index) => this.renderButton(obj, buttonPropsAndFlags, index))} ) - :
{ this.context.t('loading') }
) } } diff --git a/ui/app/components/app/gas-customization/gas-price-chart/gas-price-chart.component.js b/ui/app/components/app/gas-customization/gas-price-chart/gas-price-chart.component.js index 03aa53a9d..ef5f9e074 100644 --- a/ui/app/components/app/gas-customization/gas-price-chart/gas-price-chart.component.js +++ b/ui/app/components/app/gas-customization/gas-price-chart/gas-price-chart.component.js @@ -8,7 +8,7 @@ import { hideDataUI, setTickPosition, handleMouseMove, -} from './gas-price-chart.utils.js' +} from './gas-price-chart.utils' export default class GasPriceChart extends Component { static contextTypes = { diff --git a/ui/app/components/app/gas-customization/gas-price-chart/gas-price-chart.utils.js b/ui/app/components/app/gas-customization/gas-price-chart/gas-price-chart.utils.js index ab948d941..f60e36be1 100644 --- a/ui/app/components/app/gas-customization/gas-price-chart/gas-price-chart.utils.js +++ b/ui/app/components/app/gas-customization/gas-price-chart/gas-price-chart.utils.js @@ -124,6 +124,7 @@ export function setTickPosition (axis, n, newPosition, secondNewPosition) { .style('visibility', 'visible') } +/* eslint-disable babel/no-invalid-this */ export function appendOrUpdateCircle ({ data, itemIndex, cx, cy, cssId, appendOnly }) { const circle = this.main .select('.c3-selected-circles' + this.getTargetSelectorSuffix(data.id)) @@ -144,6 +145,7 @@ export function appendOrUpdateCircle ({ data, itemIndex, cx, cy, cssId, appendOn .attr('cy', cy) } } +/* eslint-enable babel/no-invalid-this */ export function setSelectedCircle ({ chart, @@ -163,7 +165,7 @@ export function setSelectedCircle ({ while (lowerX === higherX) { higherX = getCoordinateData(`.c3-circle-${count}`).x higherY = getCoordinateData(`.c3-circle-${count}`).y - count++ + count += 1 } } @@ -263,10 +265,10 @@ export function generateChart (gasPrices, estimatedTimes, gasPricesMax, estimate let text d.forEach((el) => { if (el && (el.value || el.value === 0) && !text) { - text = "" + "' + text = `
" + titleFormat(el.x) + '
` } }) - return text + '
${titleFormat(el.x)}
' + "
" + return `${text}
` }, position: function () { if (d3.select('#overlayed-circle').empty()) { diff --git a/ui/app/components/app/gas-customization/gas-price-chart/index.scss b/ui/app/components/app/gas-customization/gas-price-chart/index.scss index a26b477a0..774760cff 100644 --- a/ui/app/components/app/gas-customization/gas-price-chart/index.scss +++ b/ui/app/components/app/gas-customization/gas-price-chart/index.scss @@ -17,7 +17,6 @@ .tick text, .c3-axis-x-label, .c3-axis-y-label { - font-family: Roboto; font-style: normal; font-weight: bold; line-height: normal; @@ -53,7 +52,6 @@ } .custom-tooltip th { - font-family: Roboto; font-style: normal; font-weight: 500; line-height: normal; diff --git a/ui/app/components/app/home-notification/index.scss b/ui/app/components/app/home-notification/index.scss index 1aedb90ec..56222b454 100644 --- a/ui/app/components/app/home-notification/index.scss +++ b/ui/app/components/app/home-notification/index.scss @@ -35,7 +35,6 @@ } &__text { - font-family: Roboto, 'sans-serif'; font-style: normal; font-weight: normal; font-size: 12px; @@ -112,7 +111,6 @@ } &__content { - font-family: Roboto, 'sans-serif'; font-style: normal; font-weight: normal; font-size: 12px; diff --git a/ui/app/components/app/index.scss b/ui/app/components/app/index.scss index 00724f3e2..d538aa21c 100644 --- a/ui/app/components/app/index.scss +++ b/ui/app/components/app/index.scss @@ -1,5 +1,7 @@ +@import 'account-list-item/index'; @import 'account-menu/index'; @import 'add-token-button/index'; +@import '../ui/alert/index'; @import 'alerts/alerts'; @import 'app-header/index'; @import 'asset-list-item/asset-list-item'; @@ -9,6 +11,7 @@ @import 'confirm-page-container/index'; @import '../ui/currency-input/index'; @import '../ui/currency-display/index'; +@import '../ui/editable-label/index'; @import '../ui/error-message/index'; @import '../ui/export-text-container/index'; @import '../ui/identicon/index'; @@ -21,10 +24,13 @@ @import '../ui/page-container/index'; @import '../../pages/index'; @import 'permission-page-container/index'; +@import '../ui/qr-code/index'; +@import '../ui/readonly-input/index'; @import 'selected-account/index'; @import '../ui/sender-to-recipient/index'; @import '../ui/tabs/index'; @import '../ui/token-balance/index'; +@import 'signature-request-original/index'; @import 'token-cell/token-cell'; @import 'transaction-activity-log/index'; @import 'transaction-breakdown/index'; @@ -54,6 +60,7 @@ @import '../ui/dropdown/dropdown'; @import 'permissions-connect-header/index'; @import 'permissions-connect-footer/index'; +@import 'tab-bar/index'; @import 'wallet-overview/index'; @import '../ui/account-mismatch-warning/index'; @import '../ui/icon-border/icon-border'; diff --git a/ui/app/components/app/info-box/info-box.component.js b/ui/app/components/app/info-box/info-box.component.js index 68aae5d11..163869ef5 100644 --- a/ui/app/components/app/info-box/info-box.component.js +++ b/ui/app/components/app/info-box/info-box.component.js @@ -29,17 +29,17 @@ export default class InfoBox extends Component { render () { const { title, description } = this.props - return !this.state.isShowing - ? null - : ( + return this.state.isShowing + ? (
this.handleClose()} /> -
{ title }
-
{ description }
+
{title}
+
{description}
) + : null } } diff --git a/ui/app/components/app/menu-bar/account-options-menu.js b/ui/app/components/app/menu-bar/account-options-menu.js index 9edf908d4..32c31b6c0 100644 --- a/ui/app/components/app/menu-bar/account-options-menu.js +++ b/ui/app/components/app/menu-bar/account-options-menu.js @@ -6,7 +6,7 @@ import { useDispatch, useSelector } from 'react-redux' import { showModal } from '../../../store/actions' import { CONNECTED_ROUTE } from '../../../helpers/constants/routes' import { Menu, MenuItem } from '../../ui/menu' -import genAccountLink from '../../../../lib/account-link' +import getAccountLink from '../../../../lib/account-link' import { getCurrentKeyring, getCurrentNetwork, getRpcPrefsForCurrentProvider, getSelectedIdentity } from '../../../selectors' import { useI18nContext } from '../../../hooks/useI18nContext' import { useMetricEvent } from '../../../hooks/useMetricEvent' @@ -90,14 +90,14 @@ export default function AccountOptionsMenu ({ anchorElement, onClose }) { { viewOnEtherscanEvent() - global.platform.openTab({ url: genAccountLink(address, network, rpcPrefs) }) + global.platform.openTab({ url: getAccountLink(address, network, rpcPrefs) }) onClose() }} subtitle={ rpcPrefs.blockExplorerUrl ? ( - { rpcPrefs.blockExplorerUrl.match(/^https?:\/\/(.+)/)[1] } + { rpcPrefs.blockExplorerUrl.match(/^https?:\/\/(.+)/u)[1] } ) : null diff --git a/ui/app/components/app/menu-droppo.js b/ui/app/components/app/menu-droppo.js index 7ea66927b..79c22d8d8 100644 --- a/ui/app/components/app/menu-droppo.js +++ b/ui/app/components/app/menu-droppo.js @@ -37,8 +37,6 @@ export default class MenuDroppoComponent extends Component { if (isOpen) { this.outsideClickHandler = onClickOutside - } else if (isOpen) { - this.outsideClickHandler = null } } diff --git a/ui/app/components/app/modal/modal.component.js b/ui/app/components/app/modal/modal.component.js index 6c45160fd..41e4ea694 100644 --- a/ui/app/components/app/modal/modal.component.js +++ b/ui/app/components/app/modal/modal.component.js @@ -63,31 +63,32 @@ export default class Modal extends PureComponent {
{ children }
- { !hideFooter - ? ( -
- { - onCancel && ( - - ) - } - -
- ) - : null + { + hideFooter + ? null + : ( +
+ { + onCancel && ( + + ) + } + +
+ ) }
) diff --git a/ui/app/components/app/modal/tests/modal.component.test.js b/ui/app/components/app/modal/tests/modal.component.test.js index 83d9a81e7..dbb615233 100644 --- a/ui/app/components/app/modal/tests/modal.component.test.js +++ b/ui/app/components/app/modal/tests/modal.component.test.js @@ -48,10 +48,10 @@ describe('Modal Component', function () { it('should render a modal with different button types', function () { const wrapper = shallow( {}} + onCancel={() => undefined} cancelText="Cancel" cancelType="secondary" - onSubmit={() => {}} + onSubmit={() => undefined} submitText="Submit" submitType="confirm" />, @@ -66,9 +66,9 @@ describe('Modal Component', function () { it('should render a modal with children', function () { const wrapper = shallow( {}} + onCancel={() => undefined} cancelText="Cancel" - onSubmit={() => {}} + onSubmit={() => undefined} submitText="Submit" >
diff --git a/ui/app/components/app/modals/account-details-modal/account-details-modal.component.js b/ui/app/components/app/modals/account-details-modal/account-details-modal.component.js index fafdd8444..858ae8296 100644 --- a/ui/app/components/app/modals/account-details-modal/account-details-modal.component.js +++ b/ui/app/components/app/modals/account-details-modal/account-details-modal.component.js @@ -1,7 +1,7 @@ import React, { Component } from 'react' import PropTypes from 'prop-types' import AccountModalContainer from '../account-modal-container' -import genAccountLink from '../../../../../lib/account-link.js' +import getAccountLink from '../../../../../lib/account-link' import QrView from '../../../ui/qr-code' import EditableLabel from '../../../ui/editable-label' import Button from '../../../ui/button' @@ -42,9 +42,9 @@ export default class AccountDetailsModal extends Component { } return ( - + setAccountLabel(address, label)} /> @@ -56,17 +56,17 @@ export default class AccountDetailsModal extends Component { }} /> -
+
@@ -75,7 +75,7 @@ export default class AccountDetailsModal extends Component { ? (
@@ -44,6 +46,7 @@ AccountModalContainer.defaultProps = { } AccountModalContainer.propTypes = { + className: PropTypes.string, selectedIdentity: PropTypes.object.isRequired, showBackButton: PropTypes.bool, backButtonAction: PropTypes.func, diff --git a/ui/app/components/app/modals/account-modal-container/index.scss b/ui/app/components/app/modals/account-modal-container/index.scss new file mode 100644 index 000000000..6e553249b --- /dev/null +++ b/ui/app/components/app/modals/account-modal-container/index.scss @@ -0,0 +1,52 @@ +// Account Modal Container +.account-modal { + &__container { + display: flex; + flex-direction: column; + justify-content: flex-start; + align-items: center; + position: relative; + padding: 5px 0 31px 0; + border: 1px solid $silver; + border-radius: 4px; + } + + &__back { + color: $dusty-gray; + position: absolute; + top: 13px; + left: 17px; + cursor: pointer; + display: flex; + align-items: center; + } + + &__back-text { + font-size: 14px; + line-height: 18px; + padding-left: 3px; + } + + &__close { + font-size: 40px; + background-color: transparent; + color: $dusty-gray; + position: absolute; + cursor: pointer; + top: 10px; + right: 12px; + + &::after { + content: '\00D7'; + } + } + + & .identicon { + position: relative; + left: 0; + right: 0; + margin: 0 auto; + top: -32px; + margin-bottom: -32px; + } +} diff --git a/ui/app/components/app/modals/add-to-addressbook-modal/index.scss b/ui/app/components/app/modals/add-to-addressbook-modal/index.scss index b5e3b9ae7..cb84f30a0 100644 --- a/ui/app/components/app/modals/add-to-addressbook-modal/index.scss +++ b/ui/app/components/app/modals/add-to-addressbook-modal/index.scss @@ -9,7 +9,7 @@ border-bottom: 1px solid $Grey-100; &__header { - @extend %h3; + @include H3; } } diff --git a/ui/app/components/app/modals/cancel-transaction/tests/cancel-transaction.component.test.js b/ui/app/components/app/modals/cancel-transaction/tests/cancel-transaction.component.test.js index 416b796bc..3ccf6bda0 100644 --- a/ui/app/components/app/modals/cancel-transaction/tests/cancel-transaction.component.test.js +++ b/ui/app/components/app/modals/cancel-transaction/tests/cancel-transaction.component.test.js @@ -34,7 +34,7 @@ describe('CancelTransaction Component', function () { defaultNewGasPrice="0x3b9aca00" createCancelTransaction={createCancelTransactionSpy} hideModal={hideModalSpy} - showTransactionConfirmedModal={() => {}} + showTransactionConfirmedModal={() => undefined} />, { context: { t } }, ) diff --git a/ui/app/components/app/modals/confirm-remove-account/confirm-remove-account.component.js b/ui/app/components/app/modals/confirm-remove-account/confirm-remove-account.component.js index 12d652514..4258d9462 100644 --- a/ui/app/components/app/modals/confirm-remove-account/confirm-remove-account.component.js +++ b/ui/app/components/app/modals/confirm-remove-account/confirm-remove-account.component.js @@ -3,7 +3,7 @@ import PropTypes from 'prop-types' import Modal from '../../modal' import { addressSummary } from '../../../../helpers/utils/util' import Identicon from '../../../ui/identicon' -import genAccountLink from '../../../../../lib/account-link' +import getAccountLink from '../../../../../lib/account-link' export default class ConfirmRemoveAccount extends Component { static propTypes = { @@ -47,7 +47,7 @@ export default class ConfirmRemoveAccount extends Component {
{ - setCustomAmount(!selectedOptionIsUnlimited ? customSpendLimit : '') + setCustomAmount(selectedOptionIsUnlimited ? '' : customSpendLimit) hideModal() }} submitText={t('save')} diff --git a/ui/app/components/app/modals/export-private-key-modal/export-private-key-modal.component.js b/ui/app/components/app/modals/export-private-key-modal/export-private-key-modal.component.js index 695762b73..965d5a703 100644 --- a/ui/app/components/app/modals/export-private-key-modal/export-private-key-modal.component.js +++ b/ui/app/components/app/modals/export-private-key-modal/export-private-key-modal.component.js @@ -25,6 +25,7 @@ export default class ExportPrivateKeyModal extends Component { warning: PropTypes.node, showAccountDetailModal: PropTypes.func.isRequired, hideModal: PropTypes.func.isRequired, + clearAccountDetails: PropTypes.func.isRequired, previousModalState: PropTypes.string, } @@ -34,6 +35,10 @@ export default class ExportPrivateKeyModal extends Component { showWarning: true, } + componentWillUnmount () { + this.props.clearAccountDetails() + } + exportAccountAndGetPrivateKey = (password, address) => { const { exportAccount } = this.props @@ -47,7 +52,7 @@ export default class ExportPrivateKeyModal extends Component { renderPasswordLabel (privateKey) { return ( - + { privateKey ? this.context.t('copyPrivateKey') @@ -64,7 +69,7 @@ export default class ExportPrivateKeyModal extends Component { return ( this.setState({ password: event.target.value })} /> ) @@ -72,8 +77,8 @@ export default class ExportPrivateKeyModal extends Component { return ( copyToClipboard(plainKey)} @@ -83,12 +88,12 @@ export default class ExportPrivateKeyModal extends Component { renderButtons (privateKey, address, hideModal) { return ( -
+
{!privateKey && ( @@ -111,7 +116,7 @@ export default class ExportPrivateKeyModal extends Component { onClick={() => this.exportAccountAndGetPrivateKey(this.state.password, address)} type="secondary" large - className="export-private-key__button" + className="export-private-key-modal__button" disabled={!this.state.password} > {this.context.t('confirm')} @@ -139,28 +144,28 @@ export default class ExportPrivateKeyModal extends Component { return ( showAccountDetailModal()} > - {name} + {name} -
- {this.context.t('showPrivateKeys')} -
+
+ {this.context.t('showPrivateKeys')} +
{this.renderPasswordLabel(privateKey)} {this.renderPasswordInput(privateKey)} { (showWarning && warning) - ? {warning} + ? {warning} : null }
-
{this.context.t('privateKeyWarning')}
+
{this.context.t('privateKeyWarning')}
{this.renderButtons(privateKey, address, hideModal)} ) diff --git a/ui/app/components/app/modals/export-private-key-modal/export-private-key-modal.container.js b/ui/app/components/app/modals/export-private-key-modal/export-private-key-modal.container.js index 313729217..e1676f8be 100644 --- a/ui/app/components/app/modals/export-private-key-modal/export-private-key-modal.container.js +++ b/ui/app/components/app/modals/export-private-key-modal/export-private-key-modal.container.js @@ -1,5 +1,5 @@ import { connect } from 'react-redux' -import { exportAccount, hideWarning, showModal, hideModal } from '../../../../store/actions' +import { exportAccount, hideWarning, showModal, hideModal, clearAccountDetails } from '../../../../store/actions' import { getSelectedIdentity } from '../../../../selectors' import ExportPrivateKeyModal from './export-private-key-modal.component' @@ -32,6 +32,7 @@ function mapDispatchToProps (dispatch) { }, showAccountDetailModal: () => dispatch(showModal({ name: 'ACCOUNT_DETAILS' })), hideModal: () => dispatch(hideModal()), + clearAccountDetails: () => dispatch(clearAccountDetails()), } } diff --git a/ui/app/components/app/modals/export-private-key-modal/index.scss b/ui/app/components/app/modals/export-private-key-modal/index.scss new file mode 100644 index 000000000..8fd3c3133 --- /dev/null +++ b/ui/app/components/app/modals/export-private-key-modal/index.scss @@ -0,0 +1,106 @@ +.export-private-key-modal { + &__body-title { + margin-top: 16px; + margin-bottom: 16px; + font-size: 18px; + } + + &__divider { + width: 100%; + height: 1px; + margin: 19px 0 8px 0; + background-color: $alto; + } + + &__account-name { + margin-top: 9px; + font-size: 20px; + } + + &__password { + display: flex; + flex-direction: column; + } + + &__password-label, + &__password--error { + color: $scorpion; + font-size: 14px; + line-height: 18px; + margin-bottom: 10px; + } + + &__password--error { + color: $crimson; + margin-bottom: 0; + } + + &__password-input { + padding: 10px 0 13px 17px; + font-size: 16px; + line-height: 21px; + width: 291px; + height: 44px; + } + + &__password::-webkit-input-placeholder { + color: $dusty-gray; + } + + &__password--warning { + border-radius: 8px; + background-color: #fff6f6; + font-size: 12px; + font-weight: 500; + line-height: 15px; + color: $crimson; + width: 292px; + padding: 9px 15px; + margin-top: 18px; + } + + &__password-display-wrapper { + height: 80px; + width: 291px; + border: 1px solid $silver; + border-radius: 2px; + } + + &__password-display-textarea { + color: $crimson; + font-size: 16px; + line-height: 21px; + border: none; + height: 75px; + width: 100%; + overflow: hidden; + resize: none; + padding: 9px 13px 8px; + } + + &__buttons { + display: flex; + flex-direction: row; + justify-content: center; + } + + &__button { + margin-top: 17px; + width: 141px; + min-width: initial; + } + + &__button--cancel { + margin-right: 15px; + } + + & .ellip-address-wrapper { + display: flex; + justify-content: center; + border: 1px solid $alto; + padding: 5px 10px; + margin-top: 7px; + width: 286px; + } +} + diff --git a/ui/app/components/app/modals/fade-modal.js b/ui/app/components/app/modals/fade-modal.js index a59c8995b..3d12414d4 100644 --- a/ui/app/components/app/modals/fade-modal.js +++ b/ui/app/components/app/modals/fade-modal.js @@ -22,8 +22,9 @@ const insertRule = (css) => { const insertKeyframesRule = (keyframes) => { // random name + // eslint-disable-next-line no-plusplus const name = 'anim_' + (++index) + (+new Date()) - let css = '@' + 'keyframes ' + name + ' {' + let css = `@keyframes ${name} {` Object.keys(keyframes).forEach((key) => { css += key + ' {' @@ -133,8 +134,8 @@ class FadeModal extends Component { } static defaultProps = { - onShow: function () {}, - onHide: function () {}, + onShow: () => undefined, + onHide: () => undefined, keyboard: true, backdrop: true, closeOnClick: true, @@ -192,7 +193,7 @@ class FadeModal extends Component { const backdrop = this.props.backdrop ? (
(this.content = el)} tabIndex="-1" style={contentStyle} diff --git a/ui/app/components/app/modals/hide-token-confirmation-modal.js b/ui/app/components/app/modals/hide-token-confirmation-modal/hide-token-confirmation-modal.js similarity index 96% rename from ui/app/components/app/modals/hide-token-confirmation-modal.js rename to ui/app/components/app/modals/hide-token-confirmation-modal/hide-token-confirmation-modal.js index 5f8e6001a..58fd01170 100644 --- a/ui/app/components/app/modals/hide-token-confirmation-modal.js +++ b/ui/app/components/app/modals/hide-token-confirmation-modal/hide-token-confirmation-modal.js @@ -1,8 +1,8 @@ import PropTypes from 'prop-types' import React, { Component } from 'react' import { connect } from 'react-redux' -import * as actions from '../../../store/actions' -import Identicon from '../../ui/identicon' +import * as actions from '../../../../store/actions' +import Identicon from '../../../ui/identicon' function mapStateToProps (state) { return { diff --git a/ui/app/components/app/modals/hide-token-confirmation-modal/index.js b/ui/app/components/app/modals/hide-token-confirmation-modal/index.js new file mode 100644 index 000000000..31e866398 --- /dev/null +++ b/ui/app/components/app/modals/hide-token-confirmation-modal/index.js @@ -0,0 +1 @@ +export { default } from './hide-token-confirmation-modal' diff --git a/ui/app/components/app/modals/hide-token-confirmation-modal/index.scss b/ui/app/components/app/modals/hide-token-confirmation-modal/index.scss new file mode 100644 index 000000000..d640b6c5c --- /dev/null +++ b/ui/app/components/app/modals/hide-token-confirmation-modal/index.scss @@ -0,0 +1,61 @@ +.hide-token-confirmation { + min-height: 250.72px; + border-radius: 4px; + background-color: $white; + box-shadow: 0 1px 7px 0 rgba(0, 0, 0, 0.5); + + &__container { + padding: 24px 27px 21px; + display: flex; + flex-direction: column; + align-items: center; + } + + &__identicon { + margin-bottom: 10px; + } + + &__symbol { + color: $tundora; + font-size: 16px; + line-height: 24px; + text-align: center; + margin-bottom: 7.5px; + } + + &__title { + height: 30px; + width: 271.28px; + color: $tundora; + font-size: 22px; + line-height: 30px; + text-align: center; + margin-bottom: 10.5px; + } + + &__copy { + height: 41px; + width: 318px; + color: $scorpion; + font-size: 14px; + line-height: 18px; + text-align: center; + } + + &__buttons { + display: flex; + flex-direction: row; + justify-content: center; + margin-top: 15px; + width: 100%; + } + + &__button { + @include Paragraph; + + @extend %button; + + width: 141px; + margin: 0 5px; + } +} diff --git a/ui/app/components/app/modals/index.scss b/ui/app/components/app/modals/index.scss index ebb662b96..b6232aa16 100644 --- a/ui/app/components/app/modals/index.scss +++ b/ui/app/components/app/modals/index.scss @@ -1,8 +1,46 @@ +@import 'account-details-modal/index'; +@import 'account-modal-container/index'; +@import 'add-to-addressbook-modal/index'; @import 'cancel-transaction/index'; @import 'confirm-remove-account/index'; +@import 'deposit-ether-modal/index'; +@import 'edit-approval-permission/index'; +@import 'export-private-key-modal/index'; +@import 'hide-token-confirmation-modal/index'; +@import 'metametrics-opt-in-modal/index'; +@import 'new-account-modal/index'; +@import 'notification-modal/index'; @import 'qr-scanner/index'; @import 'transaction-confirmed/index'; -@import 'metametrics-opt-in-modal/index'; -@import './add-to-addressbook-modal/index'; -@import './edit-approval-permission/index'; -@import './new-account-modal/index'; + +.modal { + z-index: 1050; + position: fixed; + width: 500px; + transform: translate3d(-50%, -50%, 0); + top: 50%; + left: 50%; + + &__content { + margin: 0; + background-color: white; + animation-fill-mode: forwards; + } + + &__backdrop { + position: fixed; + top: 0; + right: 0; + bottom: 0; + left: 0; + z-index: 1040; + background-color: #373a47; + animation-fill-mode: forwards; + animation-duration: 0.3s; + } + + & > div:focus { + outline: none !important; + } +} + diff --git a/ui/app/components/app/modals/metametrics-opt-in-modal/tests/metametrics-opt-in-modal.test.js b/ui/app/components/app/modals/metametrics-opt-in-modal/tests/metametrics-opt-in-modal.test.js index 70e7d9924..0d2787ebc 100644 --- a/ui/app/components/app/modals/metametrics-opt-in-modal/tests/metametrics-opt-in-modal.test.js +++ b/ui/app/components/app/modals/metametrics-opt-in-modal/tests/metametrics-opt-in-modal.test.js @@ -17,7 +17,7 @@ describe('MetaMetrics Opt In', function () { wrapper = mount( , { context: { - metricsEvent: () => {}, + metricsEvent: () => undefined, }, }, ) diff --git a/ui/app/components/app/modals/new-account-modal/index.scss b/ui/app/components/app/modals/new-account-modal/index.scss index 31dfff92d..bbe440041 100644 --- a/ui/app/components/app/modals/new-account-modal/index.scss +++ b/ui/app/components/app/modals/new-account-modal/index.scss @@ -9,7 +9,7 @@ border-bottom: 1px solid $Grey-100; &__header { - @extend %header--18; + @include H4; font-weight: bold; display: flex; diff --git a/ui/app/components/app/modals/notification-modal/index.js b/ui/app/components/app/modals/notification-modal/index.js new file mode 100644 index 000000000..a2aab7c1d --- /dev/null +++ b/ui/app/components/app/modals/notification-modal/index.js @@ -0,0 +1 @@ +export { default } from './notification-modal' diff --git a/ui/app/components/app/modals/notification-modal/index.scss b/ui/app/components/app/modals/notification-modal/index.scss new file mode 100644 index 000000000..93e085496 --- /dev/null +++ b/ui/app/components/app/modals/notification-modal/index.scss @@ -0,0 +1,56 @@ +.notification-modal { + &__wrapper { + display: flex; + flex-direction: column; + justify-content: flex-start; + align-items: center; + position: relative; + border: 1px solid $alto; + box-shadow: 0 0 2px 2px $alto; + } + + &__header { + background: $wild-sand; + width: 100%; + display: flex; + justify-content: center; + padding: 30px; + font-size: 22px; + color: $nile-blue; + } + + &__message { + padding: 20px; + width: 100%; + display: flex; + justify-content: center; + font-size: 17px; + color: $nile-blue; + } + + &__buttons { + display: flex; + justify-content: space-evenly; + width: 100%; + margin-bottom: 24px; + padding: 0 42px; + + &__btn { + cursor: pointer; + } + } + + &__link { + color: $primary-blue; + } + + .modal-close-x::after { + content: '\00D7'; + font-size: 2em; + color: $dusty-gray; + position: absolute; + top: 25px; + right: 17.5px; + cursor: pointer; + } +} diff --git a/ui/app/components/app/modals/notification-modal.js b/ui/app/components/app/modals/notification-modal/notification-modal.js similarity index 97% rename from ui/app/components/app/modals/notification-modal.js rename to ui/app/components/app/modals/notification-modal/notification-modal.js index 7fe776934..71f826747 100644 --- a/ui/app/components/app/modals/notification-modal.js +++ b/ui/app/components/app/modals/notification-modal/notification-modal.js @@ -1,7 +1,7 @@ import PropTypes from 'prop-types' import React, { Component } from 'react' import { connect } from 'react-redux' -import { hideModal } from '../../../store/actions' +import { hideModal } from '../../../../store/actions' class NotificationModal extends Component { static contextProps = { diff --git a/ui/app/components/app/modals/qr-scanner/qr-scanner.component.js b/ui/app/components/app/modals/qr-scanner/qr-scanner.component.js index 63ca45b88..fd79c9e41 100644 --- a/ui/app/components/app/modals/qr-scanner/qr-scanner.component.js +++ b/ui/app/components/app/modals/qr-scanner/qr-scanner.component.js @@ -117,11 +117,11 @@ export default class QrScanner extends Component { const result = this.parseContent(content.text) if (!this.mounted) { return - } else if (result.type !== 'unknown') { + } else if (result.type === 'unknown') { + this.setState({ error: new Error(this.context.t('unknownQrCode')) }) + } else { this.props.qrCodeDetected(result) this.stopAndClose() - } else { - this.setState({ error: new Error(this.context.t('unknownQrCode')) }) } } catch (error) { if (!this.mounted) { @@ -248,7 +248,7 @@ export default class QrScanner extends Component { display: ready === READY_STATE.READY ? 'block' : 'none', }} /> - { ready !== READY_STATE.READY ? : null} + {ready === READY_STATE.READY ? null : }
diff --git a/ui/app/components/app/modals/tests/account-details-modal.test.js b/ui/app/components/app/modals/tests/account-details-modal.test.js index 3c0dd8f25..505b823cd 100644 --- a/ui/app/components/app/modals/tests/account-details-modal.test.js +++ b/ui/app/components/app/modals/tests/account-details-modal.test.js @@ -46,7 +46,7 @@ describe('Account Details Modal', function () { }) it('sets account label when changing default account label', function () { - const accountLabel = wrapper.find('.account-modal__name').first() + const accountLabel = wrapper.find('.account-details-modal__name').first() accountLabel.simulate('submit', 'New Label') assert(props.setAccountLabel.calledOnce) @@ -54,7 +54,7 @@ describe('Account Details Modal', function () { }) it('opens new tab when view block explorer is clicked', function () { - const modalButton = wrapper.find('.account-modal__button') + const modalButton = wrapper.find('.account-details-modal__button') const etherscanLink = modalButton.first() etherscanLink.simulate('click') @@ -62,7 +62,7 @@ describe('Account Details Modal', function () { }) it('shows export private key modal when clicked', function () { - const modalButton = wrapper.find('.account-modal__button') + const modalButton = wrapper.find('.account-details-modal__button') const etherscanLink = modalButton.last() etherscanLink.simulate('click') @@ -73,9 +73,9 @@ describe('Account Details Modal', function () { const blockExplorerUrl = 'https://block.explorer' wrapper.setProps({ rpcPrefs: { blockExplorerUrl } }) - const modalButton = wrapper.find('.account-modal__button') + const modalButton = wrapper.find('.account-details-modal__button') const blockExplorerLink = modalButton.first() - assert.equal(blockExplorerLink.html(), '') + assert.equal(blockExplorerLink.html(), '') }) }) diff --git a/ui/app/components/app/permission-page-container/index.scss b/ui/app/components/app/permission-page-container/index.scss index c26189e0c..2e3f10aa8 100644 --- a/ui/app/components/app/permission-page-container/index.scss +++ b/ui/app/components/app/permission-page-container/index.scss @@ -31,7 +31,7 @@ } &__title { - @extend %header--18; + @include H4; line-height: 25px; text-align: center; @@ -84,7 +84,7 @@ } &__permissions-header { - @extend %content-text; + @include H6; line-height: 20px; color: #6a737d; diff --git a/ui/app/components/app/permissions-connect-footer/index.scss b/ui/app/components/app/permissions-connect-footer/index.scss index ac6508417..51ee8a09f 100644 --- a/ui/app/components/app/permissions-connect-footer/index.scss +++ b/ui/app/components/app/permissions-connect-footer/index.scss @@ -5,9 +5,8 @@ align-items: center; &__text { - @extend %content-text; + @include H7; - font-size: 12px; line-height: 17px; color: #6a737d; display: flex; diff --git a/ui/app/components/app/permissions-connect-header/index.scss b/ui/app/components/app/permissions-connect-header/index.scss index 1b29ec3e0..1ec0628e0 100644 --- a/ui/app/components/app/permissions-connect-header/index.scss +++ b/ui/app/components/app/permissions-connect-header/index.scss @@ -26,7 +26,7 @@ } &__title { - @extend %header--24; + @include H3; text-align: center; color: $Black-100; @@ -35,7 +35,7 @@ &__text, &__subtitle { - @extend %content-text; + @include H6; text-align: center; color: $Grey-500; diff --git a/ui/app/components/app/selected-account/selected-account.component.js b/ui/app/components/app/selected-account/selected-account.component.js index c9561f820..ab5b56b24 100644 --- a/ui/app/components/app/selected-account/selected-account.component.js +++ b/ui/app/components/app/selected-account/selected-account.component.js @@ -3,7 +3,7 @@ import PropTypes from 'prop-types' import copyToClipboard from 'copy-to-clipboard' import { shortenAddress, checksumAddress } from '../../../helpers/utils/util' -import Tooltip from '../../ui/tooltip-v2.js' +import Tooltip from '../../ui/tooltip-v2' class SelectedAccount extends Component { state = { diff --git a/ui/app/components/app/selected-account/tests/selected-account-component.test.js b/ui/app/components/app/selected-account/tests/selected-account-component.test.js index 73b659e10..323ead37b 100644 --- a/ui/app/components/app/selected-account/tests/selected-account-component.test.js +++ b/ui/app/components/app/selected-account/tests/selected-account-component.test.js @@ -9,7 +9,7 @@ describe('SelectedAccount Component', function () { - ), { context: { t: () => {} } }) + ), { context: { t: () => undefined } }) // Checksummed version of address is displayed assert.equal(wrapper.find('.selected-account__address').text(), '0x1B82...5C9D') assert.equal(wrapper.find('.selected-account__name').text(), 'testName') diff --git a/ui/app/components/app/sidebars/tests/sidebars-component.test.js b/ui/app/components/app/sidebars/tests/sidebars-component.test.js index 8a203204e..ba92c72a5 100644 --- a/ui/app/components/app/sidebars/tests/sidebars-component.test.js +++ b/ui/app/components/app/sidebars/tests/sidebars-component.test.js @@ -3,7 +3,7 @@ import assert from 'assert' import { shallow } from 'enzyme' import sinon from 'sinon' import ReactCSSTransitionGroup from 'react-transition-group/CSSTransitionGroup' -import Sidebar from '../sidebar.component.js' +import Sidebar from '../sidebar.component' import CustomizeGas from '../../gas-customization/gas-modal-page-container' diff --git a/ui/app/css/itcss/components/request-signature.scss b/ui/app/components/app/signature-request-original/index.scss similarity index 95% rename from ui/app/css/itcss/components/request-signature.scss rename to ui/app/components/app/signature-request-original/index.scss index 03623e187..6af476fd6 100644 --- a/ui/app/css/itcss/components/request-signature.scss +++ b/ui/app/components/app/signature-request-original/index.scss @@ -8,7 +8,6 @@ flex-flow: column nowrap; z-index: 25; align-items: center; - font-family: Roboto; position: relative; height: 100%; @@ -63,7 +62,6 @@ &__header__text { color: #5b5d67; - font-family: Roboto; font-size: 22px; line-height: 29px; z-index: 3; @@ -104,7 +102,6 @@ &__account-item { height: 22px; background-color: $white; - font-family: Roboto; line-height: 16px; font-size: 12px; width: 124px; @@ -163,7 +160,6 @@ height: 48px; width: 240px; color: $tundora; - font-family: Roboto; font-size: 18px; line-height: 24px; text-align: center; @@ -172,7 +168,6 @@ &__notice, &__warning { - font-family: "Avenir Next"; font-size: 14px; line-height: 19px; text-align: center; @@ -207,7 +202,6 @@ &__row-title { width: 80px; color: $dusty-gray; - font-family: Roboto; font-size: 16px; line-height: 22px; margin-top: 12px; @@ -217,7 +211,6 @@ &__row-value { color: $scorpion; - font-family: Roboto; font-size: 14px; line-height: 19px; width: 100%; diff --git a/ui/app/components/app/signature-request-original/signature-request-original.component.js b/ui/app/components/app/signature-request-original/signature-request-original.component.js index 8587f024e..29e06bab6 100644 --- a/ui/app/components/app/signature-request-original/signature-request-original.component.js +++ b/ui/app/components/app/signature-request-original/signature-request-original.component.js @@ -7,7 +7,7 @@ import { ObjectInspector } from 'react-inspector' import { ENVIRONMENT_TYPE_NOTIFICATION, MESSAGE_TYPE } from '../../../../../app/scripts/lib/enums' import { getEnvironmentType } from '../../../../../app/scripts/lib/util' import Identicon from '../../ui/identicon' -import AccountListItem from '../../../pages/send/account-list-item/account-list-item.component' +import AccountListItem from '../account-list-item' import { conversionUtil } from '../../../helpers/utils/conversion-util' import Button from '../../ui/button' @@ -95,7 +95,6 @@ export default class SignatureRequestOriginal extends Component {
diff --git a/ui/app/components/app/signature-request/index.scss b/ui/app/components/app/signature-request/index.scss index 27e7fcfbc..4de4f249b 100644 --- a/ui/app/components/app/signature-request/index.scss +++ b/ui/app/components/app/signature-request/index.scss @@ -38,7 +38,6 @@ min-height: min-content; &__title { - font-family: Roboto; font-style: normal; font-weight: 500; font-size: 18px; @@ -65,7 +64,6 @@ &__identicon-initial { position: absolute; - font-family: Roboto; font-style: normal; font-weight: 500; font-size: 60px; diff --git a/ui/app/components/app/signature-request/signature-request-header/signature-request-header.component.js b/ui/app/components/app/signature-request/signature-request-header/signature-request-header.component.js index 89440acdc..2ec74748c 100644 --- a/ui/app/components/app/signature-request/signature-request-header/signature-request-header.component.js +++ b/ui/app/components/app/signature-request/signature-request-header/signature-request-header.component.js @@ -1,6 +1,6 @@ import React, { PureComponent } from 'react' import PropTypes from 'prop-types' -import AccountListItem from '../../../../pages/send/account-list-item/account-list-item.component' +import AccountListItem from '../../account-list-item' import NetworkDisplay from '../../network-display' export default class SignatureRequestHeader extends PureComponent { @@ -16,7 +16,6 @@ export default class SignatureRequestHeader extends PureComponent {
{fromAccount && ( )} diff --git a/ui/app/components/app/signature-request/signature-request-message/index.scss b/ui/app/components/app/signature-request/signature-request-message/index.scss index 7eef17560..37c0fba72 100644 --- a/ui/app/components/app/signature-request/signature-request-message/index.scss +++ b/ui/app/components/app/signature-request/signature-request-message/index.scss @@ -28,7 +28,6 @@ padding-left: 12px; padding-right: 12px; width: 360px; - font-family: monospace; @media screen and (min-width: 576px) { width: auto; @@ -36,7 +35,6 @@ } &__type-title { - font-family: monospace; font-style: normal; font-weight: normal; font-size: 14px; diff --git a/ui/app/components/app/signature-request/tests/signature-request.test.js b/ui/app/components/app/signature-request/tests/signature-request.test.js index f3b717ec4..8956a957d 100644 --- a/ui/app/components/app/signature-request/tests/signature-request.test.js +++ b/ui/app/components/app/signature-request/tests/signature-request.test.js @@ -10,9 +10,9 @@ describe('Signature Request Component', function () { it('should render a div with one child', function () { const wrapper = shallow(( {}} - cancel={() => {}} - sign={() => {}} + clearConfirmTransaction={() => undefined} + cancel={() => undefined} + sign={() => undefined} txData={{ msgParams: { data: '{"message": {"from": {"name": "hello"}}}', diff --git a/ui/app/components/app/tab-bar/index.js b/ui/app/components/app/tab-bar/index.js new file mode 100644 index 000000000..74f9a7529 --- /dev/null +++ b/ui/app/components/app/tab-bar/index.js @@ -0,0 +1 @@ +export { default } from './tab-bar' diff --git a/ui/app/components/app/tab-bar/index.scss b/ui/app/components/app/tab-bar/index.scss new file mode 100644 index 000000000..0b9d0605d --- /dev/null +++ b/ui/app/components/app/tab-bar/index.scss @@ -0,0 +1,80 @@ +.tab-bar { + display: flex; + flex-direction: column; + justify-content: flex-start; + + + &__tab { + display: flex; + flex-flow: row nowrap; + align-items: flex-start; + min-width: 0; + flex: 0 0 auto; + box-sizing: border-box; + font-size: 16px; + padding: 16px 24px; + opacity: 0.5; + transition: opacity 200ms ease-in-out; + + @media screen and (min-width: 576px) { + &:hover { + opacity: 0.4; + } + + &:active { + opacity: 0.6; + } + } + + @media screen and (max-width: 575px) { + font-size: 18px; + padding: 24px; + border-bottom: 1px solid $alto; + opacity: 1; + } + + &__content { + flex: 1 1 auto; + width: 0; + + &__description { + display: none; + + @media screen and (max-width: 575px) { + display: block; + font-size: 14px; + font-weight: 300; + margin-top: 8px; + min-height: 14px; + } + } + } + + &__caret { + display: none; + + @media screen and (max-width: 575px) { + display: block; + background-image: url('/images/caret-right.svg'); + width: 36px; + height: 36px; + opacity: 0.5; + background-size: contain; + background-repeat: no-repeat; + background-position: center; + + [dir='rtl'] & { + transform: rotate(180deg); + } + } + } + + &--active { + opacity: 1 !important; + } + } + + &__grow-tab { + flex-grow: 1; + } +} diff --git a/ui/app/components/app/tab-bar.js b/ui/app/components/app/tab-bar/tab-bar.js similarity index 100% rename from ui/app/components/app/tab-bar.js rename to ui/app/components/app/tab-bar/tab-bar.js diff --git a/ui/app/components/app/transaction-activity-log/tests/transaction-activity-log.component.test.js b/ui/app/components/app/transaction-activity-log/tests/transaction-activity-log.component.test.js index c3422e58e..99947104c 100644 --- a/ui/app/components/app/transaction-activity-log/tests/transaction-activity-log.component.test.js +++ b/ui/app/components/app/transaction-activity-log/tests/transaction-activity-log.component.test.js @@ -40,8 +40,8 @@ describe('TransactionActivityLog Component', function () { inlineRetryIndex={-1} inlineCancelIndex={-1} nativeCurrency="ETH" - onCancel={() => {}} - onRetry={() => {}} + onCancel={() => undefined} + onRetry={() => undefined} primaryTransactionStatus="confirmed" />, { context: { t: (str1, str2) => (str2 ? str1 + str2 : str1) } }, @@ -87,8 +87,8 @@ describe('TransactionActivityLog Component', function () { inlineRetryIndex={2} inlineCancelIndex={3} nativeCurrency="ETH" - onCancel={() => {}} - onRetry={() => {}} + onCancel={() => undefined} + onRetry={() => undefined} primaryTransactionStatus="pending" isEarliestNonce />, @@ -136,8 +136,8 @@ describe('TransactionActivityLog Component', function () { inlineRetryIndex={2} inlineCancelIndex={3} nativeCurrency="ETH" - onCancel={() => {}} - onRetry={() => {}} + onCancel={() => undefined} + onRetry={() => undefined} primaryTransactionStatus="pending" isEarliestNonce={false} />, diff --git a/ui/app/components/app/transaction-breakdown/transaction-breakdown-row/tests/transaction-breakdown-row.component.test.js b/ui/app/components/app/transaction-breakdown/transaction-breakdown-row/tests/transaction-breakdown-row.component.test.js index f9e144a42..752d8b6af 100644 --- a/ui/app/components/app/transaction-breakdown/transaction-breakdown-row/tests/transaction-breakdown-row.component.test.js +++ b/ui/app/components/app/transaction-breakdown/transaction-breakdown-row/tests/transaction-breakdown-row.component.test.js @@ -27,7 +27,7 @@ describe('TransactionBreakdownRow Component', function () { title="test" className="test-class" > - + , { context: { t: (str1, str2) => (str2 ? str1 + str2 : str1) } }, ) diff --git a/ui/app/components/app/transaction-breakdown/transaction-breakdown.component.js b/ui/app/components/app/transaction-breakdown/transaction-breakdown.component.js index 85c24a3e3..a534ae1a6 100644 --- a/ui/app/components/app/transaction-breakdown/transaction-breakdown.component.js +++ b/ui/app/components/app/transaction-breakdown/transaction-breakdown.component.js @@ -37,13 +37,14 @@ export default class TransactionBreakdown extends PureComponent { { t('transaction') }
- {typeof nonce !== 'undefined' - ? ( + {typeof nonce === 'undefined' + ? null + : ( - ) : null + ) } @@ -57,14 +58,14 @@ export default class TransactionBreakdown extends PureComponent { title={`${t('gasLimit')} (${t('units')})`} className="transaction-breakdown__row-title" > - {typeof gas !== 'undefined' - ? ( + {typeof gas === 'undefined' + ? '?' + : ( ) - : '?' } { @@ -81,8 +82,9 @@ export default class TransactionBreakdown extends PureComponent { ) } - {typeof gasPrice !== 'undefined' - ? ( + {typeof gasPrice === 'undefined' + ? '?' + : ( ) - : '?' } diff --git a/ui/app/components/app/transaction-list-item-details/tests/transaction-list-item-details.component.test.js b/ui/app/components/app/transaction-list-item-details/tests/transaction-list-item-details.component.test.js index 0c9726aef..f0e3edf4d 100644 --- a/ui/app/components/app/transaction-list-item-details/tests/transaction-list-item-details.component.test.js +++ b/ui/app/components/app/transaction-list-item-details/tests/transaction-list-item-details.component.test.js @@ -34,7 +34,7 @@ describe('TransactionListItemDetails Component', function () { title="Test Transaction Details" recipientAddress="0x1" senderAddress="0x2" - tryReverseResolveAddress={() => {}} + tryReverseResolveAddress={() => undefined} transactionGroup={transactionGroup} senderNickname="sender-nickname" recipientNickname="recipient-nickname" @@ -77,7 +77,7 @@ describe('TransactionListItemDetails Component', function () { {}} + tryReverseResolveAddress={() => undefined} transactionGroup={transactionGroup} showSpeedUp senderNickname="sender-nickname" @@ -117,7 +117,7 @@ describe('TransactionListItemDetails Component', function () { {}} + tryReverseResolveAddress={() => undefined} transactionGroup={transactionGroup} senderNickname="sender-nickname" recipientNickname="recipient-nickname" @@ -159,7 +159,7 @@ describe('TransactionListItemDetails Component', function () { {}} + tryReverseResolveAddress={() => undefined} transactionGroup={transactionGroup} senderNickname="sender-nickname" recipientNickname="recipient-nickname" diff --git a/ui/app/components/app/transaction-list-item/transaction-list-item.component.js b/ui/app/components/app/transaction-list-item/transaction-list-item.component.js index bd6a61c91..c2c1279eb 100644 --- a/ui/app/components/app/transaction-list-item/transaction-list-item.component.js +++ b/ui/app/components/app/transaction-list-item/transaction-list-item.component.js @@ -86,13 +86,15 @@ export default function TransactionListItem ({ transactionGroup, isEarliestNonce return null } - return !cancelEnabled ? ( - -
- {cancelButton} -
-
- ) : cancelButton + return cancelEnabled + ? cancelButton + : ( + +
+ {cancelButton} +
+
+ ) }, [isPending, t, isUnapproved, cancelEnabled, cancelTransaction, hasCancelled]) diff --git a/ui/app/css/itcss/components/alert.scss b/ui/app/components/ui/alert/index.scss similarity index 100% rename from ui/app/css/itcss/components/alert.scss rename to ui/app/components/ui/alert/index.scss diff --git a/ui/app/components/ui/button-group/index.scss b/ui/app/components/ui/button-group/index.scss index aea6d826f..4ba758c30 100644 --- a/ui/app/components/ui/button-group/index.scss +++ b/ui/app/components/ui/button-group/index.scss @@ -4,7 +4,6 @@ align-items: center; &__button { - font-family: Roboto; font-size: 1rem; color: $tundora; border-style: solid; diff --git a/ui/app/components/ui/button-group/tests/button-group-component.test.js b/ui/app/components/ui/button-group/tests/button-group-component.test.js index 755b0789d..f963c8696 100644 --- a/ui/app/components/ui/button-group/tests/button-group-component.test.js +++ b/ui/app/components/ui/button-group/tests/button-group-component.test.js @@ -2,7 +2,7 @@ import React from 'react' import assert from 'assert' import { shallow } from 'enzyme' import sinon from 'sinon' -import ButtonGroup from '../button-group.component.js' +import ButtonGroup from '../button-group.component' describe('ButtonGroup Component', function () { let wrapper diff --git a/ui/app/components/ui/button/buttons.scss b/ui/app/components/ui/button/buttons.scss index 2fdc1da01..0e38c049c 100644 --- a/ui/app/components/ui/button/buttons.scss +++ b/ui/app/components/ui/button/buttons.scss @@ -11,10 +11,9 @@ $hover-orange: #ffd3b5; $warning-light-orange: #f8b588; %button { - @include h6; + @include H6; font-weight: 500; - font-family: Roboto, Arial; line-height: 1.25rem; padding: 0.75rem 1rem; display: flex; @@ -34,7 +33,7 @@ $warning-light-orange: #f8b588; } %link { - @include h4; + @include H4; color: $Blue-500; line-height: 1.25rem; @@ -61,7 +60,7 @@ $warning-light-orange: #f8b588; %small-link { @extend %link; - @include h6; + @include H6; } .button { @@ -249,7 +248,6 @@ button.primary { box-shadow: 0 3px 6px rgba(247, 134, 28, 0.36); color: $white; font-size: 1.1em; - font-family: Roboto; text-transform: uppercase; } diff --git a/ui/app/components/ui/dropdown/dropdown.scss b/ui/app/components/ui/dropdown/dropdown.scss index 296ea95c0..49a684bb7 100644 --- a/ui/app/components/ui/dropdown/dropdown.scss +++ b/ui/app/components/ui/dropdown/dropdown.scss @@ -11,7 +11,6 @@ background-position: right 18px top 50%; background-color: white; padding: 8px 32px 8px 16px; - font-family: Roboto, 'sans-serif'; font-size: 14px; [dir='rtl'] & { diff --git a/ui/app/components/ui/editable-label.js b/ui/app/components/ui/editable-label/editable-label.js similarity index 100% rename from ui/app/components/ui/editable-label.js rename to ui/app/components/ui/editable-label/editable-label.js diff --git a/ui/app/components/ui/editable-label/index.js b/ui/app/components/ui/editable-label/index.js new file mode 100644 index 000000000..43078e7f7 --- /dev/null +++ b/ui/app/components/ui/editable-label/index.js @@ -0,0 +1 @@ +export { default } from './editable-label' diff --git a/ui/app/css/itcss/components/editable-label.scss b/ui/app/components/ui/editable-label/index.scss similarity index 100% rename from ui/app/css/itcss/components/editable-label.scss rename to ui/app/components/ui/editable-label/index.scss diff --git a/ui/app/components/ui/list-item/index.scss b/ui/app/components/ui/list-item/index.scss index a26efcb4c..2117dfc4d 100644 --- a/ui/app/components/ui/list-item/index.scss +++ b/ui/app/components/ui/list-item/index.scss @@ -5,7 +5,7 @@ background: #fff; padding: 24px 16px; - @extend %font; + @include Paragraph; border-top: 1px solid $mercury; border-bottom: 1px solid $mercury; diff --git a/ui/app/components/ui/menu/menu.scss b/ui/app/components/ui/menu/menu.scss index de3935539..a34deda53 100644 --- a/ui/app/components/ui/menu/menu.scss +++ b/ui/app/components/ui/menu/menu.scss @@ -9,7 +9,6 @@ flex-direction: column; align-items: center; padding: 0 16px; - font-family: Roboto, 'sans-serif'; font-size: 14px; font-weight: normal; line-height: 20px; @@ -28,7 +27,6 @@ .menu-item { background: none; - font-family: inherit; font-size: inherit; display: grid; grid-template-columns: min-content auto; diff --git a/ui/app/components/ui/page-container/page-container.component.js b/ui/app/components/ui/page-container/page-container.component.js index a35524121..b4af4e719 100644 --- a/ui/app/components/ui/page-container/page-container.component.js +++ b/ui/app/components/ui/page-container/page-container.component.js @@ -41,7 +41,7 @@ export default class PageContainer extends PureComponent { const { tabsComponent } = this.props if (!tabsComponent) { - return + return null } const numberOfTabs = React.Children.count(tabsComponent.props.children) diff --git a/ui/app/components/ui/page-container/tests/page-container.component.test.js b/ui/app/components/ui/page-container/tests/page-container.component.test.js deleted file mode 100644 index e69de29bb..000000000 diff --git a/ui/app/components/ui/popover/index.scss b/ui/app/components/ui/popover/index.scss index 1c3d8744c..a1ef85b06 100644 --- a/ui/app/components/ui/popover/index.scss +++ b/ui/app/components/ui/popover/index.scss @@ -33,10 +33,9 @@ align-items: center; justify-content: space-between; - @extend %font; + @include H4; font-weight: bold; - font-size: 18px; line-height: 25px; padding-bottom: 8px; @@ -52,10 +51,8 @@ } &__subtitle { - @extend %font; + @include H6; - font-weight: normal; - font-size: 14px; line-height: 20px; } diff --git a/ui/app/components/ui/qr-code/index.js b/ui/app/components/ui/qr-code/index.js new file mode 100644 index 000000000..f638ae4fb --- /dev/null +++ b/ui/app/components/ui/qr-code/index.js @@ -0,0 +1 @@ +export { default } from './qr-code' diff --git a/ui/app/components/ui/qr-code/index.scss b/ui/app/components/ui/qr-code/index.scss new file mode 100644 index 000000000..86bd5af43 --- /dev/null +++ b/ui/app/components/ui/qr-code/index.scss @@ -0,0 +1,25 @@ +.qr-code { + display: flex; + flex-direction: column; + justify-content: center; + align-items: center; + + &__message-container > div:first-child { + margin-top: 18px; + font-size: 15px; + color: #4d4d4d; + } + + &__message { + font-size: 12px; + color: #f7861c; + } + + &__error { + display: flex; + justify-content: center; + align-items: center; + color: #f7861c; + margin-bottom: 9px; + } +} diff --git a/ui/app/components/ui/qr-code.js b/ui/app/components/ui/qr-code/qr-code.js similarity index 79% rename from ui/app/components/ui/qr-code.js rename to ui/app/components/ui/qr-code/qr-code.js index 267277c01..0ddf6caa6 100644 --- a/ui/app/components/ui/qr-code.js +++ b/ui/app/components/ui/qr-code/qr-code.js @@ -3,8 +3,8 @@ import React from 'react' import qrCode from 'qrcode-generator' import { connect } from 'react-redux' import { isHexPrefixed } from 'ethereumjs-util' -import ReadOnlyInput from './readonly-input' -import { checksumAddress } from '../../helpers/utils/util' +import ReadOnlyInput from '../readonly-input/readonly-input' +import { checksumAddress } from '../../../helpers/utils/util' export default connect(mapStateToProps)(QrCodeView) @@ -24,20 +24,20 @@ function QrCodeView (props) { qrImage.make() return ( -
+
{ Array.isArray(message) ? ( -
+
{props.Qr.message.map((message, index) => ( -
+
{message}
))}
) : message && ( -
+
{message}
) @@ -45,21 +45,20 @@ function QrCodeView (props) { { props.warning ? (props.warning && ( - + {props.warning} )) : null }
diff --git a/ui/app/components/ui/readonly-input/index.js b/ui/app/components/ui/readonly-input/index.js new file mode 100644 index 000000000..151a02ee8 --- /dev/null +++ b/ui/app/components/ui/readonly-input/index.js @@ -0,0 +1 @@ +export { default } from './readonly-input' diff --git a/ui/app/components/ui/readonly-input/index.scss b/ui/app/components/ui/readonly-input/index.scss new file mode 100644 index 000000000..9eff60bbb --- /dev/null +++ b/ui/app/components/ui/readonly-input/index.scss @@ -0,0 +1,8 @@ +.readonly-input { + &__input { + direction: ltr; + overflow: hidden; + text-overflow: ellipsis; + width: 100%; + } +} diff --git a/ui/app/components/ui/readonly-input.js b/ui/app/components/ui/readonly-input/readonly-input.js similarity index 78% rename from ui/app/components/ui/readonly-input.js rename to ui/app/components/ui/readonly-input/readonly-input.js index b884da1bc..eba6fd6c2 100644 --- a/ui/app/components/ui/readonly-input.js +++ b/ui/app/components/ui/readonly-input/readonly-input.js @@ -1,5 +1,6 @@ import PropTypes from 'prop-types' import React from 'react' +import classnames from 'classnames' export default function ReadOnlyInput (props) { const { @@ -13,9 +14,9 @@ export default function ReadOnlyInput (props) { const InputType = textarea ? 'textarea' : 'input' return ( -
+
event.target.select()} diff --git a/ui/app/components/ui/toggle-button/index.scss b/ui/app/components/ui/toggle-button/index.scss index cdd99f7f7..09827888c 100644 --- a/ui/app/components/ui/toggle-button/index.scss +++ b/ui/app/components/ui/toggle-button/index.scss @@ -3,7 +3,6 @@ $self: &; &__status { - font-family: Roboto; font-style: normal; font-weight: normal; font-size: 16px; diff --git a/ui/app/components/ui/unit-input/index.scss b/ui/app/components/ui/unit-input/index.scss index ed80f26ac..c86f487b5 100644 --- a/ui/app/components/ui/unit-input/index.scss +++ b/ui/app/components/ui/unit-input/index.scss @@ -36,7 +36,6 @@ &__input { color: #4d4d4d; font-size: 1rem; - font-family: Roboto; border: none; max-width: 22ch; height: 16px; diff --git a/ui/app/components/ui/unit-input/unit-input.component.js b/ui/app/components/ui/unit-input/unit-input.component.js index d2368291f..6c43aaf26 100644 --- a/ui/app/components/ui/unit-input/unit-input.component.js +++ b/ui/app/components/ui/unit-input/unit-input.component.js @@ -58,7 +58,7 @@ export default class UnitInput extends PureComponent { getInputWidth (value) { const valueString = String(value) const valueLength = valueString.length || 1 - const decimalPointDeficit = valueString.match(/\./) ? -0.5 : 0 + const decimalPointDeficit = valueString.match(/\./u) ? -0.5 : 0 return (valueLength + decimalPointDeficit + 0.5) + 'ch' } diff --git a/ui/app/contexts/metametrics.js b/ui/app/contexts/metametrics.js index b1440429e..19349bb5d 100644 --- a/ui/app/contexts/metametrics.js +++ b/ui/app/contexts/metametrics.js @@ -60,7 +60,7 @@ export function MetaMetricsProvider ({ children }) { const { eventOpts = {} } = config const { name = '' } = eventOpts const { currentPath: overrideCurrentPath = '' } = overrides - const isSendFlow = Boolean(name.match(/^send|^confirm/) || overrideCurrentPath.match(/send|confirm/)) + const isSendFlow = Boolean(name.match(/^send|^confirm/u) || overrideCurrentPath.match(/send|confirm/u)) if (participateInMetaMetrics || config.isOptIn) { return sendMetaMetricsEvent({ @@ -80,6 +80,8 @@ export function MetaMetricsProvider ({ children }) { ...overrides, }) } + + return undefined }, [ network, environmentType, diff --git a/ui/app/css/itcss/generic/index.scss b/ui/app/css/base-styles.scss similarity index 65% rename from ui/app/css/itcss/generic/index.scss rename to ui/app/css/base-styles.scss index 64c9688f6..8b2220f9c 100644 --- a/ui/app/css/itcss/generic/index.scss +++ b/ui/app/css/base-styles.scss @@ -1,8 +1,4 @@ -/* - Generic - */ -@import './reset'; * { box-sizing: border-box; @@ -10,9 +6,7 @@ html, body { - font-family: Roboto, Arial; color: #4d4d4d; - font-weight: 400; width: 100%; height: 100%; margin: 0; @@ -25,27 +19,38 @@ html { min-height: 500px; } -.app-root { - overflow: hidden; - position: relative; -} - -.app-primary { - display: flex; -} - .mouse-user-styles { button:focus, input:focus, textarea:focus, .unit-input__input, - .account-list-item__account-primary-balance, - .account-list-item__input, .currency-display__input { outline: none; } } +/* + This error class is used in the following files still: + /ui/app/pages/create-account/connect-hardware/index.js + /ui/app/pages/create-account/import-account/json.js + /ui/app/pages/create-account/import-account/private-key.js + /ui/app/pages/first-time-flow/create-password/import-with-seed-phrase/import-with-seed-phrase.component.js + /ui/app/pages/keychains/restore-vault.js +*/ +.error { + color: #f7861c; + margin-bottom: 9px; +} + +/* + This warning class is used in the following files still: + /ui/app/pages/create-account/import-account/json.js + /ui/app/pages/confirm-add-suggested-token/confirm-add-suggested-token.component.js +*/ +.warning { + color: #ffae00; +} + /* stylelint-disable */ #app-content { overflow-x: hidden; @@ -121,19 +126,8 @@ input.form-control { } } -.hide-text-overflow { - white-space: nowrap; - overflow: hidden; - text-overflow: ellipsis; +/** Default Typography on base elements **/ +* { + font-family: $font-family; } -.pinned-to-bottom { - position: absolute; - bottom: 0; -} - -.pinned-to-bottom-right { - position: absolute; - bottom: 0; - right: 0; -} diff --git a/ui/app/css/design-system/breakpoints.scss b/ui/app/css/design-system/breakpoints.scss new file mode 100644 index 000000000..80a4176b0 --- /dev/null +++ b/ui/app/css/design-system/breakpoints.scss @@ -0,0 +1,6 @@ +/* +Responsive Breakpoints +*/ +$break-small: 575px; +$break-midpoint: 780px; +$break-large: 576px; diff --git a/ui/app/css/variables/colors.scss b/ui/app/css/design-system/colors.scss similarity index 100% rename from ui/app/css/variables/colors.scss rename to ui/app/css/design-system/colors.scss diff --git a/ui/app/css/design-system/deprecated-colors.scss b/ui/app/css/design-system/deprecated-colors.scss new file mode 100644 index 000000000..c65f0bfa0 --- /dev/null +++ b/ui/app/css/design-system/deprecated-colors.scss @@ -0,0 +1,48 @@ +/** + These colors are either deprecated or will move into colors.scss + when approved for the design system +**/ + +// Base Colors +$white: #fff; +$black: #000; +$orange: #ffa500; +$red: #f00; +$gray: #808080; + +/* + Colors + http://chir.ag/projects/name-that-color + */ +$gallery: #efefef; +$wild-sand: #f6f6f6; +$dusty-gray: #9b9b9b; +$alto: #dedede; +$alabaster: #fafafa; +$silver-chalice: #aeaeae; +$tundora: #4d4d4d; +$nile-blue: #1b344d; +$scorpion: #5d5d5d; +$silver: #cdcdcd; +$caribbean-green: #02c9b1; +$monzo: #d0021b; +$crimson: #e91550; +$blue-lagoon: #038789; +$purple: #690496; +$tulip-tree: #ebb33f; +$malibu-blue: #7ac9fd; +$athens-grey: #e9edf0; +$geyser: #d2d8dd; +$manatee: #93949d; +$spindle: #c7ddec; +$mid-gray: #5b5d67; +$cape-cod: #38393a; +$dodger-blue: #3099f2; +$ecstasy: #f7861c; +$linen: #fdf4f4; +$oslo-gray: #8c8e94; +$polar: #fafcfe; +$blizzard-blue: #bfdef3; +$mischka: #dddee9; +$web-orange: #f2a202; +$mercury: #e5e5e5; diff --git a/ui/app/css/design-system/index.scss b/ui/app/css/design-system/index.scss new file mode 100644 index 000000000..08b0c8b25 --- /dev/null +++ b/ui/app/css/design-system/index.scss @@ -0,0 +1,4 @@ +@import './colors.scss'; +@import './deprecated-colors.scss'; +@import './typography.scss'; +@import './breakpoints.scss'; diff --git a/ui/app/css/design-system/typography.scss b/ui/app/css/design-system/typography.scss new file mode 100644 index 000000000..70cc4bef4 --- /dev/null +++ b/ui/app/css/design-system/typography.scss @@ -0,0 +1,151 @@ +$fa-font-path: 'fonts/fontawesome'; + +@import '../../../../node_modules/@fortawesome/fontawesome-free/scss/fontawesome'; +@import '../../../../node_modules/@fortawesome/fontawesome-free/scss/solid'; +@import '../../../../node_modules/@fortawesome/fontawesome-free/scss/regular'; + +@font-face { + font-family: 'Roboto'; + font-style: normal; + font-weight: 100; + src: local('Roboto Thin'), local('Roboto-Thin'), url('fonts/Roboto/Roboto-Thin.ttf') format('truetype'); +} + +@font-face { + font-family: 'Roboto'; + font-style: normal; + font-weight: 300; + src: local('Roboto Light'), local('Roboto-Light'), url('fonts/Roboto/Roboto-Light.ttf') format('truetype'); +} + +@font-face { + font-family: 'Roboto'; + font-style: normal; + font-weight: 400; + src: local('Roboto'), local('Roboto-Regular'), url('fonts/Roboto/Roboto-Regular.ttf') format('truetype'); +} + +@font-face { + font-family: 'Roboto'; + font-style: normal; + font-weight: 500; + src: local('Roboto Medium'), local('Roboto-Medium'), url('fonts/Roboto/Roboto-Medium.ttf') format('truetype'); +} + +@font-face { + font-family: 'Roboto'; + font-style: normal; + font-weight: 700; + src: local('Roboto Bold'), local('Roboto-Bold'), url('fonts/Roboto/Roboto-Bold.ttf') format('truetype'); +} + +@font-face { + font-family: 'Roboto'; + font-style: normal; + font-weight: 900; + src: local('Roboto Black'), local('Roboto-Black'), url('fonts/Roboto/Roboto-Black.ttf') format('truetype'); +} + +@font-face { + font-family: 'Euclid'; + font-style: normal; + font-weight: 400; + src: url('fonts/Euclid/EuclidCircularB-Regular-WebXL.ttf') format('truetype'); +} + +@font-face { + font-family: 'Euclid'; + font-style: italic; + font-weight: 400; + src: url('fonts/Euclid/EuclidCircularB-RegularItalic-WebXL.ttf') format('truetype'); +} + +@font-face { + font-family: 'Euclid'; + font-style: normal; + font-weight: 700; + src: url('fonts/Euclid/EuclidCircularB-Bold-WebXL.ttf') format('truetype'); +} + +$font-family: Euclid, Roboto, Helvetica, Arial, sans-serif; + +// Typography +@mixin H1 { + font-style: normal; + font-weight: normal; + font-size: 2.5rem; + font-family: $font-family; + line-height: 140%; +} + + +@mixin H2 { + font-style: normal; + font-weight: normal; + font-size: 2rem; + font-family: $font-family; + line-height: 140%; +} + +@mixin H3 { + font-style: normal; + font-weight: normal; + font-size: 1.5rem; + font-family: $font-family; + line-height: 140%; +} + +@mixin H4 { + font-style: normal; + font-weight: normal; + font-size: 1.125rem; + font-family: $font-family; + line-height: 140%; +} + +@mixin H5 { + font-style: normal; + font-weight: normal; + font-size: 1rem; + font-family: $font-family; + line-height: 140%; +} + +@mixin H6 { + font-style: normal; + font-weight: normal; + font-size: 0.875rem; // 14px @default + line-height: 140%; +} + +@mixin Paragraph { + font-style: normal; + font-weight: normal; + font-size: 1rem; + font-family: $font-family; + line-height: 140%; +} + +@mixin H7 { + font-style: normal; + font-weight: normal; + font-size: 0.75rem; + font-family: $font-family; + line-height: 140%; +} + +@mixin H8 { + font-style: normal; + font-weight: normal; + font-size: 0.625rem; + font-family: $font-family; + line-height: 140%; +} + +@mixin H9 { + font-style: normal; + font-weight: normal; + font-size: 0.5rem; + font-family: $font-family; + line-height: 140%; +} diff --git a/ui/app/css/index.scss b/ui/app/css/index.scss index d757a2374..9b994f19a 100644 --- a/ui/app/css/index.scss +++ b/ui/app/css/index.scss @@ -4,7 +4,9 @@ They are included first because they will be used to replace bad variable names in itcss prior to it being fully removed from the system. */ -@import './variables/index'; +@import './reset.scss'; +@import './design-system/index'; +@import './base-styles.scss'; /* ITCSS @@ -17,7 +19,6 @@ */ @import './itcss/settings/index'; @import './itcss/tools/index'; -@import './itcss/generic/index'; @import './itcss/objects/index'; @import './itcss/components/index'; @import './itcss/trumps/index'; diff --git a/ui/app/css/itcss/components/account-dropdown.scss b/ui/app/css/itcss/components/account-dropdown.scss deleted file mode 100644 index 1d7baf7b6..000000000 --- a/ui/app/css/itcss/components/account-dropdown.scss +++ /dev/null @@ -1,110 +0,0 @@ -.account-dropdown-name { - font-family: Roboto; -} - -.account-dropdown-balance { - color: $dusty-gray; - line-height: 19px; -} - -.account-dropdown-edit-button { - color: $dusty-gray; - font-family: Roboto; - - &:hover { - color: $white; - } -} - -.account-list-item { - &__top-row { - display: flex; - margin-top: 10px; - margin-left: 8px; - position: relative; - } - - &__tooltip-wrapper { - left: -10px; - } - - &__account-balances { - height: auto; - border: none; - background-color: transparent; - color: #9b9b9b; - margin-left: 34px; - margin-top: 4px; - position: relative; - } - - &__primary-cached-container { - display: flex; - } - - &__cached-star { - margin-left: 4px; - } - - &__cached-balances { - div:first-of-type { - color: $web-orange; - } - - div:last-of-type { - color: rgba(220, 153, 18, 0.6901960784313725); - } - } - - &__account-name { - font-size: 16px; - margin-left: 8px; - } - - &__icon { - position: absolute; - right: 12px; - top: 1px; - } - - &__account-primary-balance, - &__account-secondary-balance { - font-family: Roboto; - line-height: 16px; - font-size: 12px; - } - - &__balance-flag { - position: absolute; - top: 3px; - left: -8px; - color: $primary-blue; - } - - &__account-primary-balance { - color: $scorpion; - border: none; - } - - &__account-secondary-balance { - color: $dusty-gray; - } - - &__account-address { - margin-left: 35px; - width: 80%; - overflow: hidden; - text-overflow: ellipsis; - } - - &__dropdown { - &:hover { - background: rgba($alto, 0.2); - cursor: pointer; - - input { - background: rgba($alto, 0.1); - } - } - } -} diff --git a/ui/app/css/itcss/components/confirm.scss b/ui/app/css/itcss/components/confirm.scss deleted file mode 100644 index 7a034e4e9..000000000 --- a/ui/app/css/itcss/components/confirm.scss +++ /dev/null @@ -1,350 +0,0 @@ -.confirm-screen-container { - position: relative; - align-items: center; - font-family: Roboto; - flex: 1 0 auto; - flex-flow: column nowrap; - box-shadow: 0 2px 4px 0 rgba($black, 0.08); - border-radius: 8px; - display: flex; - - @media screen and (max-width: 575px) { - width: 100%; - box-shadow: initial; - } -} - -.notification { - .confirm-screen-wrapper { - @media screen and (max-width: $break-small) { - height: calc(100vh - 85px); - } - } -} - -.confirm-screen-wrapper { - height: 100%; - width: 380px; - background-color: $white; - display: flex; - flex-flow: column nowrap; - z-index: 25; - align-items: center; - font-family: Roboto; - position: relative; - overflow-y: auto; - overflow-x: hidden; - border-top-left-radius: 8px; - border-top-right-radius: 8px; - - @media screen and (max-width: $break-small) { - width: 100%; - overflow-x: hidden; - overflow-y: auto; - top: 0; - box-shadow: none; - height: calc(100vh - 58px - 85px); - border-top-left-radius: 0; - border-top-right-radius: 0; - } -} - -.confirm-screen-wrapper > .confirm-screen-total-box { - margin-left: 10px; - margin-right: 10px; -} - -.confirm-screen-wrapper > .confirm-memo-wrapper { - margin: 0; -} - -.confirm-screen-header { - height: 88px; - background-color: $athens-grey; - position: relative; - display: flex; - justify-content: center; - align-items: center; - font-size: 22px; - line-height: 29px; - width: 100%; - padding: 25px 0; - flex: 0 0 auto; - - @media screen and (max-width: $break-small) { - font-size: 20px; - } -} - -.confirm-screen-header-tip { - height: 25px; - width: 25px; - background: $athens-grey; - position: absolute; - transform: rotate(45deg); - top: 71px; - left: 0; - right: 0; - margin: 0 auto; -} - -.confirm-screen-title { - line-height: 27px; - - @media screen and (max-width: $break-small) { - margin-left: 22px; - margin-right: 8px; - } -} - -.confirm-screen-back-button { - color: $primary-blue; - font-family: Roboto; - font-size: 1rem; - position: absolute; - top: 38px; - right: 38px; - background: none; -} - -.confirm-screen-account-wrapper { - display: flex; - flex-direction: column; - align-items: center; -} - -.confirm-screen-account-name { - margin-top: 12px; - font-size: 14px; - line-height: 19px; - color: $scorpion; - text-align: center; -} - -.confirm-screen-row-info { - font-size: 16px; - line-height: 21px; -} - -.confirm-screen-account-number { - font-size: 10px; - line-height: 16px; - color: $dusty-gray; - text-align: center; - height: 16px; -} - -.confirm-send-ether, -.confirm-send-token { - i.fa-arrow-right { - align-self: start; - margin: 24px 14px 0 !important; - } -} - -.confirm-screen-identicons { - margin-top: 24px; - flex: 0 0 auto; - - i.fa-arrow-right { - align-self: start; - margin: 42px 14px 0; - } - - i.fa-file-text-o { - font-size: 60px; - margin: 16px 8px 0 8px; - text-align: center; - } -} - -.confirm-screen-sending-to-message { - text-align: center; - font-size: 16px; - margin-top: 30px; - font-family: Roboto; - font-weight: 300; -} - -.confirm-screen-send-amount { - color: $scorpion; - margin-top: 12px; - text-align: center; - font-size: 40px; - line-height: 53px; - flex: 0 0 auto; -} - -.confirm-screen-send-amount-currency { - font-size: 20px; - line-height: 20px; - text-align: center; - flex: 0 0 auto; -} - -.confirm-memo-wrapper { - min-height: 24px; - width: 100%; - border-bottom: 1px solid $alto; - flex: 0 0 auto; -} - -.confirm-screen-send-memo { - color: $scorpion; - font-size: 16px; - line-height: 19px; - font-weight: 400; -} - -.confirm-screen-label { - font-size: 16px; - line-height: 40px; - color: $scorpion; - text-align: left; -} - -section .confirm-screen-account-name, -section .confirm-screen-account-number, -.confirm-screen-row-info, -.confirm-screen-row-detail { - text-align: left; -} - -.confirm-screen-rows { - display: flex; - flex-flow: column nowrap; - width: 100%; - flex: 0 0 auto; -} - -.confirm-screen-section-column { - flex: 0.5; -} - -.confirm-screen-row { - display: flex; - flex-flow: row nowrap; - width: 100%; - align-items: center; - padding: 12px; - padding-left: 35px; - font-size: 16px; - line-height: 22px; - - &:not(:last-of-type) { - border-bottom: 1px solid $alto; - } -} - -@media screen and (max-width: 379px) { - .confirm-screen-row { - span.confirm-screen-section-column { - flex: 0.4; - } - - div.confirm-screen-section-column { - flex: 0.6; - } - - .currency-display__input { - font-size: 14px; - } - } -} - -.confirm-screen-row-detail { - font-size: 12px; - line-height: 16px; - color: $dusty-gray; -} - -.confirm-screen-total-box { - background-color: $wild-sand; - position: relative; - - .confirm-screen-label { - line-height: 21px; - } - - .confirm-screen-row-detail { - color: $scorpion; - } - - &__subtitle { - font-size: 12px; - line-height: 16px; - } - - .confirm-screen-row-info { - font-size: 16px; - font-weight: 500; - line-height: 21px; - } -} - -.confirm-screen-error { - font-size: 12px; - line-height: 12px; - color: #f00; - position: absolute; - right: 12px; - width: 80px; - text-align: right; -} - -.confirm-screen-row.confirm-screen-total-box { - .confirm-screen-section-column--with-error { - flex: 0.6; - } -} - -@media screen and (max-width: 379px) { - .confirm-screen-row.confirm-screen-total-box { - .confirm-screen-section-column--with-error { - flex: 0.4; - } - } -} - -.confirm-screen-form { - position: relative; - - .confirm-screen-error { - right: 0; - width: 100%; - margin-top: 7px; - text-align: center; - } -} - -.confirm-screen-confirm-button { - height: 50px; - border-radius: 4px; - background-color: #02c9b1; - font-size: 16px; - color: $white; - text-align: center; - font-family: Roboto; - padding-top: 15px; - padding-bottom: 15px; - border-width: 0; - box-shadow: none; - flex: 1 0 auto; - margin: 0 5px; -} - -.btn-light.confirm-screen-cancel-button { - height: 50px; - background: none; - border: none; - opacity: 1; - font-family: Roboto; - border-width: 0; - padding-top: 15px; - padding-bottom: 15px; - font-size: 16px; - box-shadow: none; - cursor: pointer; - flex: 1 0 auto; - margin: 0 5px; -} diff --git a/ui/app/css/itcss/components/currency-display.scss b/ui/app/css/itcss/components/currency-display.scss deleted file mode 100644 index 9ece7a672..000000000 --- a/ui/app/css/itcss/components/currency-display.scss +++ /dev/null @@ -1,86 +0,0 @@ -.currency-display { - height: 54px; - border: 1px solid $alto; - border-radius: 4px; - background-color: $white; - color: $scorpion; - font-family: Roboto; - font-size: 16px; - padding: 8px 10px; - position: relative; - - &__primary-row { - display: flex; - } - - &__input { - color: $scorpion; - font-family: Roboto; - font-size: 16px; - line-height: 22px; - border: none; - max-width: 22ch; - } - - &__primary-currency { - color: $scorpion; - font-weight: 400; - font-family: Roboto; - font-size: 16px; - line-height: 22px; - } - - &__converted-row { - display: flex; - } - - &__converted-value, - &__converted-currency { - color: $dusty-gray; - font-family: Roboto; - font-size: 12px; - line-height: 12px; - } - - &__input-wrapper { - position: relative; - display: flex; - flex: 1; - max-width: 100%; - - input[type="number"] { - -moz-appearance: textfield; - } - - input[type="number"]::-webkit-inner-spin-button { - -webkit-appearance: none; - -moz-appearance: none; - display: none; - } - - input[type="number"]:hover::-webkit-inner-spin-button { - -webkit-appearance: none; - -moz-appearance: none; - display: none; - } - } - - &__currency-symbol { - margin-top: 1px; - color: $scorpion; - } - - .react-numeric-input { - input[type="number"]::-webkit-inner-spin-button { - -webkit-appearance: none; - -moz-appearance: none; - display: none; - } - - input[type="number"]:hover::-webkit-inner-spin-button { - -webkit-appearance: none; - -moz-appearance: none; - display: none; - } - } -} diff --git a/ui/app/css/itcss/components/index.scss b/ui/app/css/itcss/components/index.scss index b9a698503..4693a30ed 100644 --- a/ui/app/css/itcss/components/index.scss +++ b/ui/app/css/itcss/components/index.scss @@ -6,26 +6,16 @@ @import '../../../components/ui/icon/preloader/index'; @import './footer'; @import './network'; -@import './modal'; -@import './alert'; @import './newui-sections'; -@import './account-dropdown'; @import './send'; -@import './confirm'; @import './loading-overlay'; // Tx List and Sections -@import './transaction-list'; -@import './sections'; -@import './currency-display'; @import './menu'; @import './gas-slider'; -@import './tab-bar'; @import './simple-dropdown'; -@import './request-signature'; @import './request-encryption-public-key'; @import './request-decrypt-message'; -@import './editable-label'; @import './pages/index'; @import './new-account'; @import './tooltip'; diff --git a/ui/app/css/itcss/components/modal.scss b/ui/app/css/itcss/components/modal.scss index 567e7a418..e69de29bb 100644 --- a/ui/app/css/itcss/components/modal.scss +++ b/ui/app/css/itcss/components/modal.scss @@ -1,549 +0,0 @@ -.modal { - z-index: 1050; - position: fixed; - width: 500px; - transform: translate3d(-50%, -50%, 0); - top: 50%; - left: 50%; - - .content { - margin: 0; - background-color: white; - animation-fill-mode: forwards; - } -} - -.backdrop { - position: fixed; - top: 0; - right: 0; - bottom: 0; - left: 0; - z-index: 1040; - background-color: #373a47; - animation-fill-mode: forwards; - animation-duration: 0.3s; -} - -.modal > div:focus { - outline: none !important; -} - -// Account Modal Container -.account-modal-container { - display: flex; - flex-direction: column; - justify-content: flex-start; - align-items: center; - position: relative; - padding: 5px 0 31px 0; - border: 1px solid $silver; - border-radius: 4px; - font-family: Roboto; - - button { - cursor: pointer; - } -} - -.account-modal-back { - color: $dusty-gray; - position: absolute; - top: 13px; - left: 17px; - cursor: pointer; - - &__text { - margin-top: 2px; - font-family: Roboto; - font-size: 14px; - line-height: 18px; - } -} - -.account-modal-close { - font-size: 40px; - background-color: transparent; - color: $dusty-gray; - position: absolute; - top: 10px; - right: 12px; -} - -.account-modal-close::after { - content: '\00D7'; -} - -.account-modal-container .identicon { - position: relative; - left: 0; - right: 0; - margin: 0 auto; - top: -32px; - margin-bottom: -32px; -} - - -// Account Details Modal - -.account-modal-container { - .qr-header { - margin-top: 9px; - font-size: 20px; - } - - .qr-wrapper { - margin-top: 5px; - } - - .ellip-address-wrapper { - display: flex; - justify-content: center; - border: 1px solid $alto; - padding: 5px 10px; - font-family: Roboto; - margin-top: 7px; - width: 286px; - } - - .account-modal__button { - margin-top: 17px; - padding: 10px 22px; - width: 286px; - } -} - -.account-modal-divider { - width: 100%; - height: 1px; - margin: 19px 0 8px 0; - background-color: $alto; -} - -// Export Private Key Modal - -.account-modal-container .account-name { - margin-top: 9px; - font-size: 20px; -} - -.account-modal-container .modal-body-title { - margin-top: 16px; - margin-bottom: 16px; - font-size: 18px; -} - -.account-modal__name { - margin-top: 9px; - font-size: 20px; -} - -.private-key-password { - display: flex; - flex-direction: column; -} - -.private-key-password-label, -.private-key-password-error { - color: $scorpion; - font-size: 14px; - line-height: 18px; - margin-bottom: 10px; -} - -.private-key-password-error { - color: $crimson; - margin-bottom: 0; -} - -.private-key-password-input { - padding: 10px 0 13px 17px; - font-size: 16px; - line-height: 21px; - width: 291px; - height: 44px; -} - -.private-key-password::-webkit-input-placeholder { - color: $dusty-gray; - font-family: Roboto; -} - -.private-key-password-warning { - border-radius: 8px; - background-color: #fff6f6; - font-size: 12px; - font-weight: 500; - line-height: 15px; - color: $crimson; - width: 292px; - padding: 9px 15px; - margin-top: 18px; - font-family: Roboto; -} - -.export-private-key-buttons { - display: flex; - flex-direction: row; - justify-content: center; -} - -.export-private-key__button { - margin-top: 17px; - width: 141px; - min-width: initial; -} - -.export-private-key__button--cancel { - margin-right: 15px; -} - -.private-key-password-display-wrapper { - height: 80px; - width: 291px; - border: 1px solid $silver; - border-radius: 2px; -} - -.private-key-password-display-textarea { - color: $crimson; - font-family: Roboto; - font-size: 16px; - line-height: 21px; - border: none; - height: 75px; - width: 100%; - overflow: hidden; - resize: none; - padding: 9px 13px 8px; -} - -.modal-close-x::after { - content: '\00D7'; - font-size: 2em; - color: $dusty-gray; - position: absolute; - top: 25px; - right: 17.5px; - font-family: sans-serif; - cursor: pointer; -} - -// Hide token confirmation - -.hide-token-confirmation { - min-height: 250.72px; - border-radius: 4px; - background-color: $white; - box-shadow: 0 1px 7px 0 rgba(0, 0, 0, 0.5); - - &__container { - padding: 24px 27px 21px; - display: flex; - flex-direction: column; - align-items: center; - } - - &__identicon { - margin-bottom: 10px; - } - - &__symbol { - color: $tundora; - font-family: Roboto; - font-size: 16px; - line-height: 24px; - text-align: center; - margin-bottom: 7.5px; - } - - &__title { - height: 30px; - width: 271.28px; - color: $tundora; - font-family: Roboto; - font-size: 22px; - line-height: 30px; - text-align: center; - margin-bottom: 10.5px; - } - - &__copy { - height: 41px; - width: 318px; - color: $scorpion; - font-family: Roboto; - font-size: 14px; - line-height: 18px; - text-align: center; - } - - &__buttons { - display: flex; - flex-direction: row; - justify-content: center; - margin-top: 15px; - width: 100%; - } - - &__button { - @include paragraph; - - @extend %button; - - width: 141px; - margin: 0 5px; - } -} - -//Notification Modal - -.notification-modal { - &__wrapper { - display: flex; - flex-direction: column; - justify-content: flex-start; - align-items: center; - position: relative; - border: 1px solid $alto; - box-shadow: 0 0 2px 2px $alto; - font-family: Roboto; - } - - &__header { - background: $wild-sand; - width: 100%; - display: flex; - justify-content: center; - padding: 30px; - font-size: 22px; - color: $nile-blue; - } - - &__message { - padding: 20px; - width: 100%; - display: flex; - justify-content: center; - font-size: 17px; - color: $nile-blue; - } - - &__buttons { - display: flex; - justify-content: space-evenly; - width: 100%; - margin-bottom: 24px; - padding: 0 42px; - - &__btn { - cursor: pointer; - } - } - - &__link { - color: $primary-blue; - } -} - -// Deposit Ether Modal -.deposit-ether-modal { - border-radius: 8px; - font-family: Roboto; - display: flex; - flex-flow: column; - height: 100%; - - &__header { - width: 100%; - border-radius: 8px 8px 0 0; - background-color: $mid-gray; - display: flex; - position: relative; - padding: 25px; - flex-flow: column; - align-items: flex-start; - - &__title { - color: $white; - font-size: 24px; - line-height: 32px; - } - - &__description { - color: $white; - font-size: 16px; - line-height: 22px; - margin-top: 10px; - } - - &__close::after { - content: '\00D7'; - font-size: 2em; - color: $white; - position: absolute; - top: 20.8px; - right: 28px; - cursor: pointer; - } - } - - &__buy-rows { - width: 100%; - padding: 0 30px; - display: flex; - flex-flow: column nowrap; - flex: 1; - align-items: center; - - @media screen and (max-width: 575px) { - height: 0; - } - } - - &__logo { - height: 60px; - background-repeat: no-repeat; - background-size: contain; - background-position: center; - width: 100%; - display: flex; - justify-content: center; - align-items: center; - } - - &__buy-row { - border-bottom: 1px solid $alto; - display: flex; - justify-content: space-between; - align-items: center; - flex: 1 0 auto; - padding: 30px 0 20px; - min-height: 170px; - - @media screen and (max-width: 575px) { - min-height: 270px; - flex-flow: column; - justify-content: flex-start; - } - - &__back { - position: absolute; - top: 10px; - left: 0; - } - - &__logo-container { - display: flex; - justify-content: center; - flex: 0 0 auto; - padding: 0 20px; - - @media screen and (min-width: 576px) { - width: 12rem; - } - - @media screen and (max-width: 575px) { - width: 100%; - max-height: 6rem; - padding-bottom: 20px; - } - } - - &__right { - display: flex; - } - - &__description { - color: $cape-cod; - padding-bottom: 20px; - align-self: flex-start; - - @media screen and (min-width: 575px) { - width: 15rem; - } - - &__title { - font-size: 20px; - line-height: 30px; - } - - &__text { - font-size: 14px; - line-height: 22px; - margin-top: 7px; - } - } - - &__button { - display: flex; - justify-content: flex-end; - - @media screen and (min-width: 575px) { - min-width: 300px; - } - } - } - - &__buy-row:last-of-type { - border-bottom: 0; - } - - &__deposit-button { - width: 257px; - } - - .simple-dropdown { - color: #5b5d67; - font-size: 16px; - line-height: 21px; - border: 1px solid #d8d8d8; - background-color: #fff; - text-align: center; - width: 100%; - height: 45px; - line-height: 44px; - font-family: Roboto; - font-weight: 300; - } - - .simple-dropdown__selected { - text-align: center; - } -} - -//Notification Modal - -.notification-modal-wrapper { - display: flex; - flex-direction: column; - justify-content: flex-start; - align-items: center; - position: relative; - border: 1px solid $alto; - box-shadow: 0 0 2px 2px $alto; - font-family: Roboto; -} - -.notification-modal-header { - background: $wild-sand; - width: 100%; - display: flex; - justify-content: center; - align-items: center; - padding: 30px; - font-size: 22px; - color: $nile-blue; -} - -.notification-modal-message { - padding: 20px; -} - -.notification-modal-message { - width: 100%; - display: flex; - justify-content: center; - font-size: 17px; - color: $nile-blue; -} diff --git a/ui/app/css/itcss/components/network.scss b/ui/app/css/itcss/components/network.scss index b00fa5ec1..31ca8c201 100644 --- a/ui/app/css/itcss/components/network.scss +++ b/ui/app/css/itcss/components/network.scss @@ -66,7 +66,6 @@ .network-name { padding: 0 4px; - font-family: Roboto; font-size: 12px; line-height: 14px; flex: 1 1 auto; @@ -167,7 +166,6 @@ height: 25px; width: 120px; color: $white; - font-family: Roboto; font-size: 18px; line-height: 25px; text-align: center; @@ -177,7 +175,6 @@ min-height: 36px; width: 265px; color: $dusty-gray; - font-family: Roboto; font-size: 14px; line-height: 18px; } diff --git a/ui/app/css/itcss/components/new-account.scss b/ui/app/css/itcss/components/new-account.scss index 77fd07afa..c7aa38e03 100644 --- a/ui/app/css/itcss/components/new-account.scss +++ b/ui/app/css/itcss/components/new-account.scss @@ -23,7 +23,6 @@ &__title { color: $tundora; - font-family: Roboto; font-size: 32px; font-weight: 500; line-height: 43px; @@ -40,7 +39,6 @@ height: 54px; padding: 15px 10px; color: $dusty-gray; - font-family: Roboto; font-size: 18px; line-height: 24px; text-align: center; @@ -87,7 +85,6 @@ &__select-label { color: $scorpion; - font-family: Roboto; font-size: 16px; line-height: 21px; } @@ -123,7 +120,6 @@ &__instruction { color: $scorpion; - font-family: Roboto; font-size: 16px; line-height: 21px; align-self: flex-start; @@ -144,7 +140,6 @@ background-color: $white; margin-top: 16px; color: $scorpion; - font-family: Roboto; font-size: 16px; padding: 0 20px; } @@ -364,7 +359,6 @@ margin-bottom: 23px; align-self: flex-start; color: $scorpion; - font-family: Roboto; font-size: 16px; line-height: 21px; font-weight: bold; @@ -376,7 +370,6 @@ margin-bottom: 23px; align-self: flex-end; color: $scorpion; - font-family: Roboto; font-size: 16px; line-height: 21px; font-weight: normal; @@ -461,7 +454,6 @@ margin-left: 16px; padding: 0; text-transform: uppercase; - font-family: Roboto; } } @@ -520,7 +512,6 @@ &__input-label { color: $scorpion; - font-family: Roboto; font-size: 16px; line-height: 21px; align-self: flex-start; @@ -533,7 +524,6 @@ border-radius: 4px; background-color: $white; color: $scorpion; - font-family: Roboto; font-size: 16px; line-height: 21px; margin-top: 15px; diff --git a/ui/app/css/itcss/components/newui-sections.scss b/ui/app/css/itcss/components/newui-sections.scss index 2572c5fa4..57c1f6d77 100644 --- a/ui/app/css/itcss/components/newui-sections.scss +++ b/ui/app/css/itcss/components/newui-sections.scss @@ -17,7 +17,6 @@ $sub-mid-size-breakpoint-range: "screen and (min-width: #{$break-large}) and (ma // Main container .main-container { z-index: $main-container-z-index; - font-family: Roboto; } .main-container::-webkit-scrollbar { @@ -120,7 +119,6 @@ $sub-mid-size-breakpoint-range: "screen and (min-width: #{$break-large}) and (ma .unlock-screen-container { z-index: $main-container-z-index; - font-family: Roboto; display: flex; justify-content: center; align-items: center; diff --git a/ui/app/css/itcss/components/request-decrypt-message.scss b/ui/app/css/itcss/components/request-decrypt-message.scss index 7387e944a..fd2ee53a8 100644 --- a/ui/app/css/itcss/components/request-decrypt-message.scss +++ b/ui/app/css/itcss/components/request-decrypt-message.scss @@ -8,7 +8,6 @@ flex-flow: column nowrap; z-index: 25; align-items: center; - font-family: Roboto; position: relative; height: 100%; @@ -63,7 +62,6 @@ &__header__text { color: #5b5d67; - font-family: Roboto; font-size: 22px; line-height: 29px; z-index: 3; @@ -105,7 +103,6 @@ &__account-item { height: 22px; background-color: $white; - font-family: Roboto; line-height: 16px; font-size: 12px; width: 124px; @@ -156,7 +153,6 @@ } &__notice { - font-family: "Avenir Next"; font-size: 14px; line-height: 19px; text-align: center; diff --git a/ui/app/css/itcss/components/request-encryption-public-key.scss b/ui/app/css/itcss/components/request-encryption-public-key.scss index a4d601267..8860ca5d8 100644 --- a/ui/app/css/itcss/components/request-encryption-public-key.scss +++ b/ui/app/css/itcss/components/request-encryption-public-key.scss @@ -8,7 +8,6 @@ flex-flow: column nowrap; z-index: 25; align-items: center; - font-family: Roboto; position: relative; height: 100%; @@ -63,7 +62,6 @@ &__header__text { color: #5b5d67; - font-family: Roboto; font-size: 22px; line-height: 29px; z-index: 3; @@ -105,7 +103,6 @@ &__account-item { height: 22px; background-color: $white; - font-family: Roboto; line-height: 16px; font-size: 12px; width: 124px; @@ -156,7 +153,6 @@ } &__notice { - font-family: "Avenir Next"; font-size: 14px; line-height: 19px; text-align: center; diff --git a/ui/app/css/itcss/components/sections.scss b/ui/app/css/itcss/components/sections.scss deleted file mode 100644 index f9bba2827..000000000 --- a/ui/app/css/itcss/components/sections.scss +++ /dev/null @@ -1,435 +0,0 @@ -// Old scss, do not lint - clean up later -/* stylelint-disable */ - - -/* -App Sections - TODO: Move into separate files. -*/ - -/* initialize */ -textarea.twelve-word-phrase { - padding: 12px; - width: 300px; - height: 140px; - font-size: 16px; - background: $white; - resize: none; -} - -.initialize-screen { - width: 100%; - z-index: $main-container-z-index; - background: #f7f7f7; -} - -.initialize-screen hr { - width: 60px; - margin: 12px; - border-color: #f7861c; - border-style: solid; -} - -.initialize-screen label { - margin-top: 20px; -} - -.initialize-screen button.create-vault { - margin-top: 40px; -} - -.initialize-screen .warning { - font-size: 14px; - margin: 0 16px; -} - -/* unlock */ -.error { - color: #f7861c; - margin-bottom: 9px; -} - -.warning { - color: #ffae00; -} - -.lock { - width: 50px; - height: 50px; -} - -.lock.locked { - transform: scale(1.5); - opacity: 0; - transition: opacity 400ms ease-in, transform 400ms ease-in; -} - -.lock.unlocked { - transform: scale(1); - opacity: 1; - transition: opacity 500ms ease-out, transform 500ms ease-out, background 200ms ease-in; -} - -.lock.locked .lock-top { - transform: scaleX(1) translateX(0); - transition: transform 250ms ease-in; -} - -.lock.unlocked .lock-top { - transform: scaleX(-1) translateX(-12px); - transition: transform 250ms ease-in; -} - -.lock.unlocked:hover { - border-radius: 4px; - background: #e5e5e5; - border: 1px solid #b1b1b1; -} - -.lock.unlocked:active { - background: #c3c3c3; -} - -.section-title .fa-arrow-left { - margin: -2px 8px 0 -8px; -} - -.sizing-input { - font-size: 14px; - height: 30px; - padding-left: 5px; -} - -.editable-label { - display: flex; -} - -/* accounts */ - -.accounts-section { - margin: 0 0; -} - -.accounts-section .horizontal-line { - margin: 0 18px; -} - -.accounts-list-option { - height: 120px; -} - -.accounts-list-option .identicon-wrapper { - width: 100px; -} - -.unconftx-link { - margin-top: 24px; - cursor: pointer; -} - -.unconftx-link .fa-arrow-right { - margin: 0 -8px 0 8px; -} - -/* identity panel */ - -.identity-panel { - font-weight: 500; -} - -.identity-panel .identicon-wrapper { - margin: 4px; - margin-top: 8px; - display: flex; - align-items: center; -} - -.identity-panel .identicon-wrapper span { - margin: 0 auto; -} - -.identity-panel .identity-data { - margin: 8px 8px 8px 18px; -} - -.identity-panel i { - margin-top: 32px; - margin-right: 6px; - color: #b9b9b9; -} - -.identity-panel .arrow-right { - padding-left: 18px; - width: 42px; - min-width: 18px; - height: 100%; -} - -.identity-copy.flex-column { - flex: 0.25 0 auto; - justify-content: center; -} - -/* accounts screen */ - -.identity-section { -} - -.identity-section .identity-panel { - background: #e9e9e9; - border-bottom: 1px solid #b1b1b1; - cursor: pointer; -} - -.identity-section .identity-panel.selected { - background: $white; - color: #f3c83e; -} - -.identity-section .identity-panel.selected .identicon { - border-color: $orange; -} - -.identity-section .accounts-list-option:hover, -.identity-section .accounts-list-option.selected { - background: $white; -} - -/* account detail screen */ - -.account-detail-section { - display: flex; - flex-wrap: wrap; - overflow-y: auto; - flex-direction: inherit; -} - -.grow-tenx { - flex-grow: 10; -} - -.name-label { -} - -.unapproved-tx-icon { - height: 16px; - width: 16px; - background: rgb(47, 174, 244); - border-color: $silver-chalice; - border-radius: 13px; -} - -.edit-text { - height: 100%; - visibility: hidden; -} - -.editing-label { - display: flex; - justify-content: flex-start; - margin-left: 50px; - margin-bottom: 2px; - font-size: 11px; - text-rendering: geometricPrecision; - color: #f7861c; -} - -.name-label:hover .edit-text { - visibility: visible; -} - -/* tx confirm */ - -.unconftx-section input[type=password] { - height: 22px; - padding: 2px; - margin: 12px; - margin-bottom: 24px; - border-radius: 4px; - border: 2px solid #f3c83e; - background: #faf6f0; -} - -/* Info screen */ -.info-gray { - font-family: Roboto; - text-transform: uppercase; - color: $silver-chalice; -} - -.icon-size { - width: 20px; -} - -.info { - font-family: Roboto, Arial; - padding-bottom: 10px; - display: inline-block; - padding-left: 5px; -} - -/* buy eth warning screen */ -.custom-radios { - justify-content: space-around; - align-items: center; -} - -.custom-radio-selected { - width: 17px; - height: 17px; - border: solid; - border-style: double; - border-radius: 15px; - border-width: 5px; - background: rgba(247, 134, 28, 1); - border-color: #f7f7f7; -} - -.custom-radio-inactive { - width: 14px; - height: 14px; - border: solid; - border-width: 1px; - border-radius: 24px; - border-color: $silver-chalice; -} - -.radio-titles { - color: rgba(247, 134, 28, 1); -} - -.eth-warning { - transition: opacity 400ms ease-in, transform 400ms ease-in; -} - -.buy-subview { - transition: opacity 400ms ease-in, transform 400ms ease-in; -} - -.input-container:hover .edit-text { - visibility: visible; -} - -.buy-inputs { - font-family: Roboto; - font-size: 13px; - height: 20px; - background: transparent; - box-sizing: border-box; - border: solid; - border-color: transparent; - border-width: 0.5px; - border-radius: 2px; -} - -.input-container:hover .buy-inputs { - box-sizing: inherit; - border: solid; - border-color: #f7861c; - border-width: 0.5px; - border-radius: 2px; -} - -.buy-inputs:focus { - border: solid; - border-color: #f7861c; - border-width: 0.5px; - border-radius: 2px; -} - -.activeForm { - background: #f7f7f7; - border: none; - border-radius: 8px 8px 0 0; - width: 50%; - text-align: center; - padding-bottom: 4px; -} - -.inactiveForm { - border: none; - border-radius: 8px 8px 0 0; - width: 50%; - text-align: center; - padding-bottom: 4px; -} - -.ex-coins { - font-family: Roboto; - text-transform: uppercase; - text-align: center; - font-size: 33px; - width: 118px; - height: 42px; - padding: 1px; - color: #4d4d4d; -} - -.marketinfo { - font-family: Roboto; - color: $silver-chalice; - font-size: 15px; - line-height: 17px; -} - -#fromCoin::-webkit-calendar-picker-indicator { - display: none; -} - -#coinList { - width: 400px; - height: 500px; - overflow: scroll; -} - -.icon-control .fa-sync { - visibility: hidden; -} - -.icon-control:hover .fa-sync { - visibility: visible; -} - -.icon-control:hover .fa-chevron-right { - visibility: hidden; -} - -.inactive { - color: $silver-chalice; -} - -.inactive button { - background: $silver-chalice; - color: $white; -} - -.qr-ellip-address, -.ellip-address { - /*rtl:ignore*/ - direction: ltr; - overflow: hidden; - text-overflow: ellipsis; - width: 100%; -} - -.qr-header { - font-size: 25px; - margin-top: 40px; -} - -.qr-message { - font-size: 12px; - color: #f7861c; -} - -div.message-container > div:first-child { - margin-top: 18px; - font-size: 15px; - color: #4d4d4d; -} - -.pop-hover:hover { - transform: scale(1.1); -} - -/* stylelint-enable */ diff --git a/ui/app/css/itcss/components/send.scss b/ui/app/css/itcss/components/send.scss index e82d938d6..df18572cd 100644 --- a/ui/app/css/itcss/components/send.scss +++ b/ui/app/css/itcss/components/send.scss @@ -2,7 +2,6 @@ display: flex; flex-flow: column nowrap; z-index: 25; - font-family: Roboto; @media screen and (max-width: $break-small) { width: 100%; @@ -76,7 +75,6 @@ margin: 4px 0 20px; font-size: 16px; line-height: 22.4px; - font-family: Roboto; } .send-screen-gas-input { @@ -186,7 +184,6 @@ padding: 13px 19px; font-size: 16px; border-radius: 4px; - font-family: Roboto; font-weight: 500; } @@ -316,7 +313,6 @@ display: flex; flex-flow: column nowrap; z-index: 25; - font-family: Roboto; &__content { width: 498px; @@ -407,7 +403,6 @@ flex-flow: column nowrap; z-index: 25; align-items: center; - font-family: Roboto; position: relative; @media screen and (max-width: $break-small) { @@ -588,7 +583,6 @@ &__form-label { color: $scorpion; - font-family: Roboto; font-size: 16px; line-height: 22px; width: 95px; @@ -602,7 +596,6 @@ border: 1px solid $alto; border-radius: 4px; background-color: $white; - font-family: Roboto; line-height: 16px; font-size: 12px; color: $tundora; @@ -745,7 +738,6 @@ background-color: $white; color: $tundora; padding: 10px; - font-family: Roboto; font-size: 16px; line-height: 21px; } @@ -763,14 +755,12 @@ background-color: $white; color: $tundora; padding: 10px; - font-family: Roboto; font-size: 16px; line-height: 21px; } } &__amount-max { - font-family: Roboto; font-size: 12px; position: relative; display: inline-block; @@ -873,7 +863,6 @@ border-radius: 4px; background-color: #fff; box-shadow: 0 2px 4px 0 rgba(0, 0, 0, 0.14); - font-family: Roboto; display: flex; flex-flow: column; @@ -903,7 +892,6 @@ content: '\00D7'; font-size: 1.8em; color: $dusty-gray; - font-family: sans-serif; cursor: pointer; margin-right: 19.25px; } @@ -1000,7 +988,6 @@ &__title { height: 26px; color: $tundora; - font-family: Roboto; font-size: 20px; line-height: 26px; margin-top: 17px; @@ -1010,7 +997,6 @@ height: 38px; width: 314px; color: $tundora; - font-family: Roboto; font-size: 14px; line-height: 19px; margin-top: 17px; @@ -1101,7 +1087,6 @@ font-size: 1em; font-size: 14px; color: #2f9ae0; - font-family: Roboto; } .sliders-icon { diff --git a/ui/app/css/itcss/components/tab-bar.scss b/ui/app/css/itcss/components/tab-bar.scss deleted file mode 100644 index 2579b279f..000000000 --- a/ui/app/css/itcss/components/tab-bar.scss +++ /dev/null @@ -1,79 +0,0 @@ -.tab-bar { - display: flex; - flex-direction: column; - justify-content: flex-start; -} - -.tab-bar__tab { - display: flex; - flex-flow: row nowrap; - align-items: flex-start; - min-width: 0; - flex: 0 0 auto; - box-sizing: border-box; - font-size: 16px; - padding: 16px 24px; - opacity: 0.5; - transition: opacity 200ms ease-in-out; - - @media screen and (min-width: 576px) { - &:hover { - opacity: 0.4; - } - - &:active { - opacity: 0.6; - } - } - - @media screen and (max-width: 575px) { - font-size: 18px; - padding: 24px; - border-bottom: 1px solid $alto; - opacity: 1; - } - - &__content { - flex: 1 1 auto; - width: 0; - - &__description { - display: none; - - @media screen and (max-width: 575px) { - display: block; - font-size: 14px; - font-weight: 300; - margin-top: 8px; - min-height: 14px; - } - } - } - - &__caret { - display: none; - - @media screen and (max-width: 575px) { - display: block; - background-image: url('/images/caret-right.svg'); - width: 36px; - height: 36px; - opacity: 0.5; - background-size: contain; - background-repeat: no-repeat; - background-position: center; - - [dir='rtl'] & { - transform: rotate(180deg); - } - } - } - - &--active { - opacity: 1 !important; - } -} - -.tab-bar__grow-tab { - flex-grow: 1; -} diff --git a/ui/app/css/itcss/components/tooltip.scss b/ui/app/css/itcss/components/tooltip.scss index 97840ca1a..68728538a 100644 --- a/ui/app/css/itcss/components/tooltip.scss +++ b/ui/app/css/itcss/components/tooltip.scss @@ -8,7 +8,6 @@ position: absolute; z-index: 1070; display: block; - font-family: "Helvetica Neue", Helvetica, Arial, sans-serif; font-style: normal; font-weight: normal; letter-spacing: normal; diff --git a/ui/app/css/itcss/components/transaction-list.scss b/ui/app/css/itcss/components/transaction-list.scss deleted file mode 100644 index 486c48694..000000000 --- a/ui/app/css/itcss/components/transaction-list.scss +++ /dev/null @@ -1,299 +0,0 @@ -.tx-list-container { - height: 87.5%; - - @media screen and (min-width: $break-large) { - overflow-y: scroll; - } -} - -.tx-list-header-wrapper { - flex: 0 0 auto; -} - -.tx-list-header { - text-transform: capitalize; -} - -@media screen and (max-width: $break-small) { - .tx-list-header-wrapper { - margin-top: 0.2em; - margin-bottom: 0.6em; - justify-content: center; - flex: 0 0 auto; - } - - .tx-list-header { - align-self: center; - font-size: 12px; - color: $dusty-gray; - font-family: Roboto; - text-transform: uppercase; - } -} - -@media screen and (min-width: $break-large) { - .tx-list-header { - font-size: 16px; - margin: 1.1em 2.37em 0.8em; - } - - .tx-list-container::-webkit-scrollbar { - display: none; - } -} - -.tx-list-content-divider { - height: 1px; - background: rgb(231, 231, 231); - flex: 0 0 1px; - - @media screen and (max-width: $break-small) { - margin: 0.1em 0; - } - - @media screen and (min-width: $break-large) { - margin: 0.1em 2.37em; - } -} - -.tx-list-item-wrapper { - flex: 1 1 auto; - width: 0; - align-items: stretch; - justify-content: flex-start; - display: flex; - flex-flow: column nowrap; - - @media screen and (max-width: $break-small) { - padding: 0 1.3em 0.8em; - } - - @media screen and (min-width: $break-large) { - padding-bottom: 8px; - } -} - -.tx-list-pending-item-container { - cursor: pointer; - opacity: 0.5; -} - -.tx-list-date-wrapper { - margin-top: 6px; - flex: 1 1 auto; -} - -.tx-list-content-wrapper { - align-items: stretch; - margin: 4px 0; - flex: 1 0 auto; - width: 100%; - display: flex; - flex-flow: row nowrap; - - @media screen and (max-width: $break-small) { - font-size: 12px; - - .tx-list-status { - font-size: 12px !important; - } - - .tx-list-account { - font-size: 14px !important; - } - - .tx-list-value { - font-size: 14px; - line-height: 18px; - } - - .tx-list-fiat-value { - font-size: 12px; - line-height: 22px; - } - } -} - -.tx-list-item-retry-container { - background: #d1edff; - width: 100%; - border-radius: 12px; - font-size: 0.75rem; - display: flex; - justify-content: center; - margin-left: 44px; - width: calc(100% - 44px); - padding: 4px; - cursor: pointer; - - @media screen and (min-width: 576px) and (max-width: 679px) { - flex-flow: column; - align-items: center; - } - - @media screen and (min-width: 380px) and (max-width: 575px) { - flex-flow: row; - } - - @media screen and (max-width: 379px) { - flex-flow: column; - align-items: center; - } -} - -.tx-list-item-retry-link { - text-decoration: underline; - margin-left: 6px; - cursor: pointer; - - @media screen and (min-width: 576px) and (max-width: 679px) { - margin-left: 0; - } - - @media screen and (min-width: 380px) and (max-width: 575px) { - margin-left: 6px; - } - - @media screen and (max-width: 379px) { - margin-left: 0; - text-align: center; - } -} - -.tx-list-date { - color: $dusty-gray; - font-size: 12px; - font-family: Roboto; -} - -.tx-list-identicon-wrapper { - align-self: center; - flex: 0 0 auto; - margin-right: 16px; - display: flex; -} - -.tx-list-account-and-status-wrapper { - display: flex; - flex: 1 1 auto; - flex-flow: row wrap; - width: 0; - - @media screen and (max-width: $break-small) { - flex-direction: column; - justify-content: flex-start; - align-items: flex-start; - align-self: center; - - .tx-list-account-wrapper { - height: 18px; - - .tx-list-account { - line-height: 14px; - } - } - } - - @media screen and (min-width: $break-large) { - flex-direction: row; - justify-content: flex-start; - align-items: center; - - .tx-list-account-wrapper { - flex: 1.3 2 auto; - min-width: 153px; - } - - .tx-list-status-wrapper { - flex: 6 6 auto; - } - } - - .tx-list-account { - font-size: 16px; - color: $scorpion; - } - - .tx-list-status { - color: $dusty-gray; - font-size: 16px; - text-transform: capitalize; - } - - .tx-list-status--rejected, - .tx-list-status--failed { - color: $monzo; - } - - .tx-list-status--dropped { - opacity: 0.5; - } -} - -.tx-list-item { - border-bottom: 1px solid $geyser; - flex: 0 0 auto; - display: flex; - flex-flow: row nowrap; - - @media screen and (min-width: $break-large) { - padding: 0 2.37em; - } - - &:last-of-type { - border-bottom: 1px solid rgb(231, 231, 231); - margin-bottom: 32px; - } - - &__wrapper { - align-self: center; - flex: 2 2 auto; - color: $dusty-gray; - - .tx-list-value { - font-size: 16px; - text-align: right; - } - - .tx-list-value--confirmed { - color: $caribbean-green; - } - - .tx-list-fiat-value { - font-size: 12px; - text-align: right; - } - } - - &--empty { - text-align: center; - border-bottom: none !important; - padding: 16px; - } -} - -.tx-list-details-wrapper { - overflow: hidden; - flex: 0 0 35%; -} - -.tx-list-value { - font-size: 16px; - text-align: right; - text-overflow: ellipsis; - white-space: nowrap; - overflow: hidden; -} - -.tx-list-fiat-value { - font-size: 12px; - line-height: initial; - text-align: right; - text-overflow: ellipsis; - white-space: nowrap; - overflow: hidden; -} - -.tx-list-value--confirmed { - color: $caribbean-green; -} diff --git a/ui/app/css/itcss/settings/index.scss b/ui/app/css/itcss/settings/index.scss index bbf79c80f..a7152a435 100644 --- a/ui/app/css/itcss/settings/index.scss +++ b/ui/app/css/itcss/settings/index.scss @@ -1,2 +1 @@ @import './variables'; -@import './typography'; diff --git a/ui/app/css/itcss/settings/typography.scss b/ui/app/css/itcss/settings/typography.scss deleted file mode 100644 index 27390b6ee..000000000 --- a/ui/app/css/itcss/settings/typography.scss +++ /dev/null @@ -1,84 +0,0 @@ -$fa-font-path: 'fonts/fontawesome'; - -@import '../../../../../node_modules/@fortawesome/fontawesome-free/scss/fontawesome'; -@import '../../../../../node_modules/@fortawesome/fontawesome-free/scss/solid'; -@import '../../../../../node_modules/@fortawesome/fontawesome-free/scss/regular'; - -@font-face { - font-family: 'Roboto'; - font-style: normal; - font-weight: 100; - src: local('Roboto Thin'), local('Roboto-Thin'), url('fonts/Roboto/Roboto-Thin.ttf') format('truetype'); -} - -@font-face { - font-family: 'Roboto'; - font-style: normal; - font-weight: 300; - src: local('Roboto Light'), local('Roboto-Light'), url('fonts/Roboto/Roboto-Light.ttf') format('truetype'); -} - -@font-face { - font-family: 'Roboto'; - font-style: normal; - font-weight: 400; - src: local('Roboto'), local('Roboto-Regular'), url('fonts/Roboto/Roboto-Regular.ttf') format('truetype'); -} - -@font-face { - font-family: 'Roboto'; - font-style: normal; - font-weight: 500; - src: local('Roboto Medium'), local('Roboto-Medium'), url('fonts/Roboto/Roboto-Medium.ttf') format('truetype'); -} - -@font-face { - font-family: 'Roboto'; - font-style: normal; - font-weight: 700; - src: local('Roboto Bold'), local('Roboto-Bold'), url('fonts/Roboto/Roboto-Bold.ttf') format('truetype'); -} - -@font-face { - font-family: 'Roboto'; - font-style: normal; - font-weight: 900; - src: local('Roboto Black'), local('Roboto-Black'), url('fonts/Roboto/Roboto-Black.ttf') format('truetype'); -} - -@mixin fontScale($weight: 400, $size: 1rem) { - font-weight: $weight; - font-size: $size; -} - -@mixin h1($weight: 400, $size: 2.5rem) { - @include fontScale($weight, $size); -} - -@mixin h2($weight: 400, $size: 2rem) { - @include fontScale($weight, $size); -} - -@mixin h3($weight: 400, $size: 1.5rem) { - @include fontScale($weight, $size); -} - -@mixin h4($weight: 400, $size: 1.125rem) { - @include fontScale($weight, $size); -} - -@mixin h5($weight: 400, $size: 1rem) { - @include fontScale($weight, $size); -} - -@mixin h6($weight: 400, $size: 0.875rem) { - @include fontScale($weight, $size); -} - -@mixin h7($weight: 400, $size: 0.75rem) { - @include fontScale($weight, $size); -} - -@mixin paragraph($weight: 400, $size: 1rem) { - @include fontScale($weight, $size); -} diff --git a/ui/app/css/itcss/settings/variables.scss b/ui/app/css/itcss/settings/variables.scss index 9a40ec9ff..dec398884 100644 --- a/ui/app/css/itcss/settings/variables.scss +++ b/ui/app/css/itcss/settings/variables.scss @@ -1,51 +1,3 @@ -/* - Variables - */ - -// Base Colors -$white: #fff; -$black: #000; -$orange: #ffa500; -$red: #f00; -$gray: #808080; - -/* - Colors - http://chir.ag/projects/name-that-color - */ -$gallery: #efefef; -$wild-sand: #f6f6f6; -$dusty-gray: #9b9b9b; -$alto: #dedede; -$alabaster: #fafafa; -$silver-chalice: #aeaeae; -$tundora: #4d4d4d; -$nile-blue: #1b344d; -$scorpion: #5d5d5d; -$silver: #cdcdcd; -$caribbean-green: #02c9b1; -$monzo: #d0021b; -$crimson: #e91550; -$blue-lagoon: #038789; -$purple: #690496; -$tulip-tree: #ebb33f; -$malibu-blue: #7ac9fd; -$athens-grey: #e9edf0; -$geyser: #d2d8dd; -$manatee: #93949d; -$spindle: #c7ddec; -$mid-gray: #5b5d67; -$cape-cod: #38393a; -$dodger-blue: #3099f2; -$ecstasy: #f7861c; -$linen: #fdf4f4; -$oslo-gray: #8c8e94; -$polar: #fafcfe; -$blizzard-blue: #bfdef3; -$mischka: #dddee9; -$web-orange: #f2a202; -$mercury: #e5e5e5; - /* Z-Indicies */ @@ -98,48 +50,6 @@ $sidebar-overlay-z-index: 25; mascot - 0 - remove? */ -/* - Responsive Breakpoints - */ -$break-small: 575px; -$break-midpoint: 780px; -$break-large: 576px; - - -$primary-font-type: Roboto; - - -// Font Sizes -%h3 { - font-size: 1.5rem; - line-height: 2.125rem; - font-weight: 400; -} - -%h4 { - font-size: 1.125rem; - line-height: 1.3125rem; - font-weight: 400; -} - -%h5 { - font-size: 1rem; - line-height: 1.25rem; - font-weight: 400; -} - -%h6 { - font-size: 0.875rem; - line-height: 1.25rem; - font-weight: 400; -} - -%h8 { - font-size: 0.75rem; - line-height: 1.0625rem; - font-weight: 400; -} - /* Spacing Variables @@ -176,36 +86,3 @@ $xxlarge-spacing: 64px; border-color: $Blue-500; } } - -// Font mixin - -%font { - font-family: Roboto; - font-style: normal; - font-weight: normal; - color: $Grey-800; -} - -%font--bold { - @extend %font; - - font-weight: bold; -} - -%header--18 { - @extend %font; - - font-size: 18px; -} - -%header--24 { - @extend %font; - - font-size: 24px; -} - -%content-text { - @extend %font; - - font-size: 14px; -} diff --git a/ui/app/css/itcss/tools/utilities.scss b/ui/app/css/itcss/tools/utilities.scss index 1d0d1c463..aa80ab867 100644 --- a/ui/app/css/itcss/tools/utilities.scss +++ b/ui/app/css/itcss/tools/utilities.scss @@ -112,14 +112,6 @@ z-index: 1; } -.select-none { - cursor: inherit; - -moz-user-select: none; - -webkit-user-select: none; - -ms-user-select: none; - user-select: none; -} - .pointer { cursor: pointer; } diff --git a/ui/app/css/itcss/generic/reset.scss b/ui/app/css/reset.scss similarity index 91% rename from ui/app/css/itcss/generic/reset.scss rename to ui/app/css/reset.scss index b60fcd068..9ee5607cf 100644 --- a/ui/app/css/itcss/generic/reset.scss +++ b/ui/app/css/reset.scss @@ -88,9 +88,11 @@ video { padding: 0; border: 0; font-size: 100%; - /* stylelint-disable */ - font: inherit; - /* stylelint-enable */ + font-weight: inherit; + font-style: inherit; + font-variant: inherit; + font-size: inherit; + line-height: inherit; vertical-align: baseline; } diff --git a/ui/app/css/variables/index.scss b/ui/app/css/variables/index.scss deleted file mode 100644 index 7aa2d674f..000000000 --- a/ui/app/css/variables/index.scss +++ /dev/null @@ -1 +0,0 @@ -@import './colors.scss'; diff --git a/ui/app/ducks/app/app.js b/ui/app/ducks/app/app.js index 177ed812c..e7672dd37 100644 --- a/ui/app/ducks/app/app.js +++ b/ui/app/ducks/app/app.js @@ -110,7 +110,7 @@ export default function reduceApp (state = {}, action) { // modal methods: - case actionConstants.MODAL_OPEN: + case actionConstants.MODAL_OPEN: { const { name, ...modalProps } = action.payload return { @@ -124,6 +124,7 @@ export default function reduceApp (state = {}, action) { previousModalState: { ...appState.modal.modalState }, }, } + } case actionConstants.MODAL_CLOSE: return { @@ -136,6 +137,12 @@ export default function reduceApp (state = {}, action) { ), } + case actionConstants.CLEAR_ACCOUNT_DETAILS: + return { + ...appState, + accountDetail: {}, + } + case actionConstants.FORGOT_PASSWORD: return { ...appState, @@ -232,7 +239,7 @@ export default function reduceApp (state = {}, action) { warning: '', } - case actionConstants.SET_HARDWARE_WALLET_DEFAULT_HD_PATH: + case actionConstants.SET_HARDWARE_WALLET_DEFAULT_HD_PATH: { const { device, path } = action.value const newDefaults = { ...appState.defaultHdPaths } newDefaults[device] = path @@ -241,6 +248,7 @@ export default function reduceApp (state = {}, action) { ...appState, defaultHdPaths: newDefaults, } + } case actionConstants.SHOW_LOADING: return { diff --git a/ui/app/ducks/confirm-transaction/confirm-transaction.duck.js b/ui/app/ducks/confirm-transaction/confirm-transaction.duck.js index 416407d5d..536307ac7 100644 --- a/ui/app/ducks/confirm-transaction/confirm-transaction.duck.js +++ b/ui/app/ducks/confirm-transaction/confirm-transaction.duck.js @@ -104,7 +104,7 @@ export default function reducer (state = initState, action = {}) { ...state, methodData: {}, } - case UPDATE_TRANSACTION_AMOUNTS: + case UPDATE_TRANSACTION_AMOUNTS: { const { fiatTransactionAmount, ethTransactionAmount, hexTransactionAmount } = action.payload return { ...state, @@ -112,7 +112,8 @@ export default function reducer (state = initState, action = {}) { ethTransactionAmount: ethTransactionAmount || state.ethTransactionAmount, hexTransactionAmount: hexTransactionAmount || state.hexTransactionAmount, } - case UPDATE_TRANSACTION_FEES: + } + case UPDATE_TRANSACTION_FEES: { const { fiatTransactionFee, ethTransactionFee, hexTransactionFee } = action.payload return { ...state, @@ -120,7 +121,8 @@ export default function reducer (state = initState, action = {}) { ethTransactionFee: ethTransactionFee || state.ethTransactionFee, hexTransactionFee: hexTransactionFee || state.hexTransactionFee, } - case UPDATE_TRANSACTION_TOTALS: + } + case UPDATE_TRANSACTION_TOTALS: { const { fiatTransactionTotal, ethTransactionTotal, hexTransactionTotal } = action.payload return { ...state, @@ -128,7 +130,8 @@ export default function reducer (state = initState, action = {}) { ethTransactionTotal: ethTransactionTotal || state.ethTransactionTotal, hexTransactionTotal: hexTransactionTotal || state.hexTransactionTotal, } - case UPDATE_TOKEN_PROPS: + } + case UPDATE_TOKEN_PROPS: { const { tokenSymbol = '', tokenDecimals = '' } = action.payload return { ...state, @@ -138,6 +141,7 @@ export default function reducer (state = initState, action = {}) { tokenDecimals, }, } + } case UPDATE_NONCE: return { ...state, diff --git a/ui/app/ducks/confirm-transaction/confirm-transaction.duck.test.js b/ui/app/ducks/confirm-transaction/confirm-transaction.duck.test.js index 720d0307b..60ada9797 100644 --- a/ui/app/ducks/confirm-transaction/confirm-transaction.duck.test.js +++ b/ui/app/ducks/confirm-transaction/confirm-transaction.duck.test.js @@ -3,7 +3,7 @@ import configureMockStore from 'redux-mock-store' import thunk from 'redux-thunk' import sinon from 'sinon' -import ConfirmTransactionReducer, * as actions from './confirm-transaction.duck.js' +import ConfirmTransactionReducer, * as actions from './confirm-transaction.duck' const initialState = { txData: {}, @@ -482,7 +482,7 @@ describe('Confirm Transaction Duck', function () { beforeEach(function () { global.eth = { getCode: sinon.stub().callsFake( - (address) => Promise.resolve(address && address.match(/isContract/) ? 'not-0x' : '0x'), + (address) => Promise.resolve(address && address.match(/isContract/u) ? 'not-0x' : '0x'), ), } }) diff --git a/ui/app/ducks/gas/gas-duck.test.js b/ui/app/ducks/gas/gas-duck.test.js index c46875693..a152bff16 100644 --- a/ui/app/ducks/gas/gas-duck.test.js +++ b/ui/app/ducks/gas/gas-duck.test.js @@ -67,7 +67,7 @@ describe('Gas Duck', function () { { expectedTime: 1, expectedWait: 0.5, gasprice: 20, somethingElse: 'foobar' }, ] const fakeFetch = (url) => new Promise((resolve) => { - const dataToResolve = url.match(/ethgasAPI/) + const dataToResolve = url.match(/ethgasAPI/u) ? mockEthGasApiResponse : mockPredictTableResponse resolve({ diff --git a/ui/app/ducks/gas/gas.duck.js b/ui/app/ducks/gas/gas.duck.js index c1d7336e3..78b9ef8ba 100644 --- a/ui/app/ducks/gas/gas.duck.js +++ b/ui/app/ducks/gas/gas.duck.js @@ -399,29 +399,28 @@ export function fetchGasEstimates (blockTime) { const next = arr[i + 1] if (!next) { return [{ expectedWait, gasprice }] - } else { - const supplementalPrice = getRandomArbitrary(gasprice, next.gasprice) - const supplementalTime = extrapolateY({ - higherY: next.expectedWait, - lowerY: expectedWait, - higherX: next.gasprice, - lowerX: gasprice, - xForExtrapolation: supplementalPrice, - }) - const supplementalPrice2 = getRandomArbitrary(supplementalPrice, next.gasprice) - const supplementalTime2 = extrapolateY({ - higherY: next.expectedWait, - lowerY: supplementalTime, - higherX: next.gasprice, - lowerX: supplementalPrice, - xForExtrapolation: supplementalPrice2, - }) - return [ - { expectedWait, gasprice }, - { expectedWait: supplementalTime, gasprice: supplementalPrice }, - { expectedWait: supplementalTime2, gasprice: supplementalPrice2 }, - ] } + const supplementalPrice = getRandomArbitrary(gasprice, next.gasprice) + const supplementalTime = extrapolateY({ + higherY: next.expectedWait, + lowerY: expectedWait, + higherX: next.gasprice, + lowerX: gasprice, + xForExtrapolation: supplementalPrice, + }) + const supplementalPrice2 = getRandomArbitrary(supplementalPrice, next.gasprice) + const supplementalTime2 = extrapolateY({ + higherY: next.expectedWait, + lowerY: supplementalTime, + higherX: next.gasprice, + lowerX: supplementalPrice, + xForExtrapolation: supplementalPrice2, + }) + return [ + { expectedWait, gasprice }, + { expectedWait: supplementalTime, gasprice: supplementalPrice }, + { expectedWait: supplementalTime2, gasprice: supplementalPrice2 }, + ] })) const withOutliersRemoved = inliersByIQR(withSupplementalTimeEstimates.slice(0).reverse(), 'expectedWait').reverse() const timeMappedToSeconds = withOutliersRemoved.map(({ expectedWait, gasprice }) => { @@ -453,11 +452,11 @@ export function fetchGasEstimates (blockTime) { export function setCustomGasPriceForRetry (newPrice) { return (dispatch) => { - if (newPrice !== '0x0') { - dispatch(setCustomGasPrice(newPrice)) - } else { + if (newPrice === '0x0') { const { fast } = loadLocalStorageData('BASIC_PRICE_ESTIMATES') dispatch(setCustomGasPrice(decGWEIToHexWEI(fast))) + } else { + dispatch(setCustomGasPrice(newPrice)) } } } diff --git a/ui/app/ducks/metamask/metamask.js b/ui/app/ducks/metamask/metamask.js index e3f35bf38..e6449a622 100644 --- a/ui/app/ducks/metamask/metamask.js +++ b/ui/app/ducks/metamask/metamask.js @@ -84,13 +84,14 @@ export default function reduceMetamask (state = {}, action) { selectedAddress: action.value, } - case actionConstants.SET_ACCOUNT_LABEL: + case actionConstants.SET_ACCOUNT_LABEL: { const account = action.value.account const name = action.value.label const id = {} id[account] = Object.assign({}, metamaskState.identities[account], { name }) const identities = Object.assign({}, metamaskState.identities, id) return Object.assign(metamaskState, { identities }) + } case actionConstants.SET_CURRENT_FIAT: return Object.assign(metamaskState, { @@ -197,7 +198,7 @@ export default function reduceMetamask (state = {}, action) { }, }) - case actionConstants.UPDATE_SEND_TOKEN: + case actionConstants.UPDATE_SEND_TOKEN: { const newSend = { ...metamaskState.send, token: action.value, @@ -225,6 +226,7 @@ export default function reduceMetamask (state = {}, action) { return Object.assign(metamaskState, { send: newSend, }) + } case actionConstants.UPDATE_SEND_ENS_RESOLUTION: return { @@ -265,7 +267,7 @@ export default function reduceMetamask (state = {}, action) { }, } - case actionConstants.UPDATE_TRANSACTION_PARAMS: + case actionConstants.UPDATE_TRANSACTION_PARAMS: { const { id: txId, value } = action let { currentNetworkTxList } = metamaskState currentNetworkTxList = currentNetworkTxList.map((tx) => { @@ -281,6 +283,7 @@ export default function reduceMetamask (state = {}, action) { ...metamaskState, currentNetworkTxList, } + } case actionConstants.SET_PARTICIPATE_IN_METAMETRICS: return { diff --git a/ui/app/ducks/send/send-duck.test.js b/ui/app/ducks/send/send-duck.test.js index 3dda8728b..9731d5b2c 100644 --- a/ui/app/ducks/send/send-duck.test.js +++ b/ui/app/ducks/send/send-duck.test.js @@ -6,7 +6,7 @@ import SendReducer, { updateSendErrors, showGasButtonGroup, hideGasButtonGroup, -} from './send.duck.js' +} from './send.duck' describe('Send Duck', function () { const mockState = { diff --git a/ui/app/helpers/higher-order-components/initialized/index.js b/ui/app/helpers/higher-order-components/initialized/index.js index 863fcb389..5aa9f0809 100644 --- a/ui/app/helpers/higher-order-components/initialized/index.js +++ b/ui/app/helpers/higher-order-components/initialized/index.js @@ -1 +1 @@ -export { default } from './initialized.container.js' +export { default } from './initialized.container' diff --git a/ui/app/helpers/utils/common.util.js b/ui/app/helpers/utils/common.util.js index a45fdc407..365ff4376 100644 --- a/ui/app/helpers/utils/common.util.js +++ b/ui/app/helpers/utils/common.util.js @@ -1,5 +1,5 @@ export function camelCaseToCapitalize (str = '') { return str - .replace(/([A-Z])/g, ' $1') - .replace(/^./, (str) => str.toUpperCase()) + .replace(/([A-Z])/ug, ' $1') + .replace(/^./u, (str) => str.toUpperCase()) } diff --git a/ui/app/helpers/utils/conversion-util.js b/ui/app/helpers/utils/conversion-util.js index adc9b65e2..784fd4e12 100644 --- a/ui/app/helpers/utils/conversion-util.js +++ b/ui/app/helpers/utils/conversion-util.js @@ -99,7 +99,7 @@ const converter = ({ } if (fromCurrency !== toCurrency) { - if (conversionRate == null) { + if (conversionRate === null || conversionRate === undefined) { throw new Error(`Converting from ${fromCurrency} to ${toCurrency} requires a conversionRate, but one was not provided`) } let rate = toBigNumber.dec(conversionRate) diff --git a/ui/app/helpers/utils/conversions.util.js b/ui/app/helpers/utils/conversions.util.js index 5e1c21ff7..0cde0d0ac 100644 --- a/ui/app/helpers/utils/conversions.util.js +++ b/ui/app/helpers/utils/conversions.util.js @@ -129,3 +129,12 @@ export function hexWEIToDecGWEI (decGWEI) { toDenomination: 'GWEI', }) } + +export function decETHToDecWEI (decEth) { + return conversionUtil(decEth, { + fromNumericBase: 'dec', + toNumericBase: 'dec', + fromDenomination: 'ETH', + toDenomination: 'WEI', + }) +} diff --git a/ui/app/helpers/utils/conversions.util.test.js b/ui/app/helpers/utils/conversions.util.test.js new file mode 100644 index 000000000..553fd1fd6 --- /dev/null +++ b/ui/app/helpers/utils/conversions.util.test.js @@ -0,0 +1,29 @@ +import * as utils from './conversions.util' +import assert from 'assert' + +describe('decETHToDecWEI', function () { + it('should correctly convert 1 ETH to WEI', function () { + const weiValue = utils.decETHToDecWEI('1') + assert.equal(weiValue, '1000000000000000000') + }) + + it('should correctly convert 0.000000000000000001 ETH to WEI', function () { + const weiValue = utils.decETHToDecWEI('0.000000000000000001') + assert.equal(weiValue, '1') + }) + + it('should correctly convert 1000000.000000000000000001 ETH to WEI', function () { + const weiValue = utils.decETHToDecWEI('1000000.000000000000000001') + assert.equal(weiValue, '1000000000000000000000001') + }) + + it('should correctly convert 9876.543210 ETH to WEI', function () { + const weiValue = utils.decETHToDecWEI('9876.543210') + assert.equal(weiValue, '9876543210000000000000') + }) + + it('should correctly convert 1.0000000000000000 ETH to WEI', function () { + const weiValue = utils.decETHToDecWEI('1.0000000000000000') + assert.equal(weiValue, '1000000000000000000') + }) +}) diff --git a/ui/app/helpers/utils/i18n-helper.js b/ui/app/helpers/utils/i18n-helper.js index 7fccc92cb..198e025d5 100644 --- a/ui/app/helpers/utils/i18n-helper.js +++ b/ui/app/helpers/utils/i18n-helper.js @@ -48,15 +48,18 @@ export const getMessage = (localeCode, localeMessages, key, substitutions) => { // perform substitutions if (hasSubstitutions) { - const parts = phrase.split(/(\$\d)/g) + const parts = phrase.split(/(\$\d)/ug) const substitutedParts = parts.map((part) => { - const subMatch = part.match(/\$(\d)/) + const subMatch = part.match(/\$(\d)/u) if (!subMatch) { return part } const substituteIndex = Number(subMatch[1]) - 1 - if (substitutions[substituteIndex] == null && !missingSubstitutionErrors[localeCode]?.[key]) { + if ( + (substitutions[substituteIndex] === null || substitutions[substituteIndex] === undefined) && + !missingSubstitutionErrors[localeCode]?.[key] + ) { if (!missingSubstitutionErrors[localeCode]) { missingSubstitutionErrors[localeCode] = {} } diff --git a/ui/app/helpers/utils/metametrics.util.js b/ui/app/helpers/utils/metametrics.util.js index 0ffe856bf..ce76b8385 100644 --- a/ui/app/helpers/utils/metametrics.util.js +++ b/ui/app/helpers/utils/metametrics.util.js @@ -157,24 +157,30 @@ function composeUrl (config) { const urlref = previousPath && composeUrlRefParamAddition(previousPath, confirmTransactionOrigin) - const dimensions = !pageOpts.hideDimensions ? composeCustomDimensionParamAddition({ - network, - environmentType, - activeCurrency, - accountType, - version, - numberOfTokens: (customVariables && customVariables.numberOfTokens) || numberOfTokens, - numberOfAccounts: (customVariables && customVariables.numberOfAccounts) || numberOfAccounts, - }) : '' + const dimensions = pageOpts.hideDimensions + ? '' + : ( + composeCustomDimensionParamAddition({ + network, + environmentType, + activeCurrency, + accountType, + version, + numberOfTokens: (customVariables && customVariables.numberOfTokens) || numberOfTokens, + numberOfAccounts: (customVariables && customVariables.numberOfAccounts) || numberOfAccounts, + }) + ) const url = currentPath ? `&url=${encodeURIComponent(`${METAMETRICS_TRACKING_URL}${currentPath}`)}` : '' const _id = metaMetricsId && !excludeMetaMetricsId ? `&_id=${metaMetricsId.slice(2, 18)}` : '' const rand = `&rand=${String(Math.random()).slice(2)}` const pv_id = currentPath ? `&pv_id=${ethUtil.bufferToHex(ethUtil.sha3(currentPath)).slice(2, 8)}` : '' - const uid = metaMetricsId && !excludeMetaMetricsId - ? `&uid=${metaMetricsId.slice(2, 18)}` - : excludeMetaMetricsId - ? '&uid=0000000000000000' - : '' + + let uid = '' + if (excludeMetaMetricsId) { + uid = '&uid=0000000000000000' + } else if (metaMetricsId) { + uid = `&uid=${metaMetricsId.slice(2, 18)}` + } return [ base, e_c, e_a, e_n, cvar, action_name, urlref, dimensions, url, _id, rand, pv_id, uid, new_visit ].join('') } diff --git a/ui/app/helpers/utils/switch-direction.js b/ui/app/helpers/utils/switch-direction.js index 2ccbfbaf0..f0ed42bf1 100644 --- a/ui/app/helpers/utils/switch-direction.js +++ b/ui/app/helpers/utils/switch-direction.js @@ -1,6 +1,7 @@ /** * Switch the CSS stylesheet used between 'rtl' and 'ltr' * @param {('ltr' | 'rtl')} direction - Text direction, either left-to-right (ltr) or right-to-left (rtl) + * @return {Promise} */ const switchDirection = async (direction) => { if (direction === 'auto') { @@ -25,6 +26,8 @@ const switchDirection = async (direction) => { updatedLink.onerror = () => reject(new Error(`Failed to load '${direction}' stylesheet`)) }) } + + return undefined } export default switchDirection diff --git a/ui/app/helpers/utils/token-util.js b/ui/app/helpers/utils/token-util.js index eb427fe0b..bc091292a 100644 --- a/ui/app/helpers/utils/token-util.js +++ b/ui/app/helpers/utils/token-util.js @@ -23,6 +23,7 @@ async function getSymbolFromContract (tokenAddress) { return result[0] } catch (error) { log.warn(`symbol() call for token at address ${tokenAddress} resulted in error:`, error) + return undefined } } @@ -35,6 +36,7 @@ async function getDecimalsFromContract (tokenAddress) { return decimalsBN && decimalsBN.toString() } catch (error) { log.warn(`decimals() call for token at address ${tokenAddress} resulted in error:`, error) + return undefined } } diff --git a/ui/app/helpers/utils/transactions.util.js b/ui/app/helpers/utils/transactions.util.js index 5ea8daeab..3d14c0336 100644 --- a/ui/app/helpers/utils/transactions.util.js +++ b/ui/app/helpers/utils/transactions.util.js @@ -181,9 +181,10 @@ export function getLatestSubmittedTxWithNonce (transactions = [], nonce = '0x0') const { submittedTime, txParams: { nonce: currentNonce } = {} } = current if (currentNonce === nonce) { - return acc.submittedTime - ? submittedTime > acc.submittedTime ? current : acc - : current + if (!acc.submittedTime) { + return current + } + return submittedTime > acc.submittedTime ? current : acc } else { return acc } @@ -237,7 +238,7 @@ export function getStatusKey (transaction) { */ export function getBlockExplorerUrlForTx (networkId, hash, rpcPrefs = {}) { if (rpcPrefs.blockExplorerUrl) { - return `${rpcPrefs.blockExplorerUrl.replace(/\/+$/, '')}/tx/${hash}` + return `${rpcPrefs.blockExplorerUrl.replace(/\/+$/u, '')}/tx/${hash}` } const prefix = getEtherscanNetworkPrefix(networkId) return `https://${prefix}etherscan.io/tx/${hash}` diff --git a/ui/app/helpers/utils/util.js b/ui/app/helpers/utils/util.js index a6726cdba..28f3dd6f4 100644 --- a/ui/app/helpers/utils/util.js +++ b/ui/app/helpers/utils/util.js @@ -75,7 +75,7 @@ export function isValidDomainName (address) { // Checks that the domain consists of at least one valid domain pieces separated by periods, followed by a tld // Each piece of domain name has only the characters a-z, 0-9, and a hyphen (but not at the start or end of chunk) // A chunk has minimum length of 1, but minimum tld is set to 2 for now (no 1-character tlds exist yet) - .match(/^(?:[a-z0-9](?:[-a-z0-9]*[a-z0-9])?\.)+[a-z0-9][-a-z0-9]*[a-z0-9]$/) + .match(/^(?:[a-z0-9](?:[-a-z0-9]*[a-z0-9])?\.)+[a-z0-9][-a-z0-9]*[a-z0-9]$/u) return match !== null } @@ -102,7 +102,7 @@ export function parseBalance (balance) { let afterDecimal const wei = numericBalance(balance) const weiString = wei.toString() - const trailingZeros = /0+$/ + const trailingZeros = /0+$/u const beforeDecimal = weiString.length > 18 ? weiString.slice(0, weiString.length - 18) : '0' afterDecimal = ('000000000000000000' + wei).slice(-18).replace(trailingZeros, '') @@ -122,7 +122,7 @@ export function formatBalance (balance, decimalsToKeep, needsParse = true, ticke if (decimalsToKeep === undefined) { if (beforeDecimal === '0') { if (afterDecimal !== '0') { - const sigFigs = afterDecimal.match(/^0*(.{2})/) // default: grabs 2 most significant digits + const sigFigs = afterDecimal.match(/^0*(.{2})/u) // default: grabs 2 most significant digits if (sigFigs) { afterDecimal = sigFigs[0] } @@ -189,8 +189,9 @@ export function shortenBalance (balance, decimalsToKeep = 1) { export function normalizeToWei (amount, currency) { try { return amount.mul(bnTable.wei).div(bnTable[currency]) - } catch (e) {} - return amount + } catch (e) { + return amount + } } export function normalizeEthStringToWei (str) { @@ -218,7 +219,7 @@ export function normalizeNumberToWei (n, currency) { } export function isHex (str) { - return Boolean(str.match(/^(0x)?[0-9a-fA-F]+$/)) + return Boolean(str.match(/^(0x)?[0-9a-fA-F]+$/u)) } export function getContractAtAddress (tokenAddress) { diff --git a/ui/app/helpers/utils/util.test.js b/ui/app/helpers/utils/util.test.js index ef1f5f153..cbeb624d1 100644 --- a/ui/app/helpers/utils/util.test.js +++ b/ui/app/helpers/utils/util.test.js @@ -307,7 +307,7 @@ describe('util', function () { describe('#getRandomFileName', function () { it('should only return a string containing alphanumeric characters', function () { const result = util.getRandomFileName() - assert(result.match(/^[a-zA-Z0-9]*$/g)) + assert(result.match(/^[a-zA-Z0-9]*$/ug)) }) // 50 samples diff --git a/ui/app/hooks/tests/useCancelTransaction.test.js b/ui/app/hooks/tests/useCancelTransaction.test.js index 7e887486e..920b9e223 100644 --- a/ui/app/hooks/tests/useCancelTransaction.test.js +++ b/ui/app/hooks/tests/useCancelTransaction.test.js @@ -32,6 +32,7 @@ describe('useCancelTransaction', function () { balance: '0x3', } } + return undefined }) }) transactions.forEach((transactionGroup) => { @@ -45,7 +46,7 @@ describe('useCancelTransaction', function () { it(`should return a function that kicks off cancellation for id ${transactionId}`, function () { const { result } = renderHook(() => useCancelTransaction(transactionGroup)) assert.equal(typeof result.current[1], 'function') - result.current[1]({ preventDefault: () => {}, stopPropagation: () => {} }) + result.current[1]({ preventDefault: () => undefined, stopPropagation: () => undefined }) assert.equal( dispatch.calledWith( showModal({ @@ -75,6 +76,7 @@ describe('useCancelTransaction', function () { balance: '0x9C2007651B2500000', } } + return undefined }) }) transactions.forEach((transactionGroup) => { @@ -88,7 +90,7 @@ describe('useCancelTransaction', function () { it(`should return a function that kicks off cancellation for id ${transactionId}`, function () { const { result } = renderHook(() => useCancelTransaction(transactionGroup)) assert.equal(typeof result.current[1], 'function') - result.current[1]({ preventDefault: () => {}, stopPropagation: () => {} }) + result.current[1]({ preventDefault: () => undefined, stopPropagation: () => undefined }) assert.equal( dispatch.calledWith( showModal({ diff --git a/ui/app/hooks/tests/useCurrencyDisplay.test.js b/ui/app/hooks/tests/useCurrencyDisplay.test.js index 793af907f..850a08960 100644 --- a/ui/app/hooks/tests/useCurrencyDisplay.test.js +++ b/ui/app/hooks/tests/useCurrencyDisplay.test.js @@ -108,6 +108,7 @@ describe('useCurrencyDisplay', function () { } else if (selector === getConversionRate) { return 280.45 } + return undefined }) const hookReturn = renderHook(() => useCurrencyDisplay(value, restProps)) const [ displayValue, parts ] = hookReturn.result.current diff --git a/ui/app/hooks/tests/useRetryTransaction.test.js b/ui/app/hooks/tests/useRetryTransaction.test.js index d6c55d0f8..e4e8160a8 100644 --- a/ui/app/hooks/tests/useRetryTransaction.test.js +++ b/ui/app/hooks/tests/useRetryTransaction.test.js @@ -12,7 +12,7 @@ describe('useRetryTransaction', function () { describe('when transaction meets retry enabled criteria', function () { const dispatch = sinon.spy(() => Promise.resolve({ blockTime: 0 })) const trackEvent = sinon.spy() - const event = { preventDefault: () => {}, stopPropagation: () => {} } + const event = { preventDefault: () => undefined, stopPropagation: () => undefined } before(function () { sinon.stub(reactRedux, 'useDispatch').returns(dispatch) diff --git a/ui/app/hooks/tests/useTokenData.test.js b/ui/app/hooks/tests/useTokenData.test.js index 9bc507de4..7154581c6 100644 --- a/ui/app/hooks/tests/useTokenData.test.js +++ b/ui/app/hooks/tests/useTokenData.test.js @@ -65,9 +65,9 @@ const tests = [ describe('useTokenData', function () { tests.forEach((test) => { - const testTitle = test.tokenData !== null - ? `should return properly decoded data with _value ${test.tokenData.params[1].value}` - : `should return null when no data provided` + const testTitle = test.tokenData === null + ? `should return null when no data provided` + : `should return properly decoded data with _value ${test.tokenData.params[1].value}` it(testTitle, function () { const { result } = renderHook(() => useTokenData(test.data)) assert.deepEqual(result.current, test.tokenData) diff --git a/ui/app/hooks/useTimeout.js b/ui/app/hooks/useTimeout.js index 534c68216..244e9a34c 100644 --- a/ui/app/hooks/useTimeout.js +++ b/ui/app/hooks/useTimeout.js @@ -7,7 +7,7 @@ import { useState, useEffect, useRef, useCallback } from 'react' * @param {number} delay - delay in ms * @param {boolean} [immediate] - determines whether the timeout is invoked immediately * - * @return {Function} + * @return {Function|undefined} */ export function useTimeout (cb, delay, immediate = true) { const saveCb = useRef() @@ -19,7 +19,7 @@ export function useTimeout (cb, delay, immediate = true) { useEffect(() => { if (timeoutId !== 'start') { - return + return undefined } const id = setTimeout(() => { diff --git a/ui/app/hooks/useTransactionDisplayData.js b/ui/app/hooks/useTransactionDisplayData.js index 52d161e7d..c146d142d 100644 --- a/ui/app/hooks/useTransactionDisplayData.js +++ b/ui/app/hooks/useTransactionDisplayData.js @@ -99,7 +99,7 @@ export function useTransactionDisplayData (transactionGroup) { // 3. Deposit // 4. Site interaction // 5. Approval - if (transactionCategory == null) { + if (transactionCategory === null || transactionCategory === undefined) { category = TRANSACTION_CATEGORY_SIGNATURE_REQUEST title = t('signatureRequest') subtitle = origin diff --git a/ui/app/hooks/useTransactionTimeRemaining.js b/ui/app/hooks/useTransactionTimeRemaining.js index a37a29ae6..f7834ead1 100644 --- a/ui/app/hooks/useTransactionTimeRemaining.js +++ b/ui/app/hooks/useTransactionTimeRemaining.js @@ -85,6 +85,7 @@ export function useTransactionTimeRemaining ( }, 10000) return () => clearInterval(interval.current) } + return undefined }, [ isMainNet, transactionTimeFeatureActive, diff --git a/ui/app/pages/add-token/tests/add-token.test.js b/ui/app/pages/add-token/tests/add-token.test.js index fa9e4bd19..da4a42f20 100644 --- a/ui/app/pages/add-token/tests/add-token.test.js +++ b/ui/app/pages/add-token/tests/add-token.test.js @@ -19,7 +19,7 @@ describe('Add Token', function () { const props = { history: { - push: sinon.stub().callsFake(() => {}), + push: sinon.stub().callsFake(() => undefined), }, setPendingTokens: sinon.spy(), clearPendingTokens: sinon.spy(), diff --git a/ui/app/pages/confirm-approve/confirm-approve-content/index.scss b/ui/app/pages/confirm-approve/confirm-approve-content/index.scss index 70771fcaf..d6a5d71c9 100644 --- a/ui/app/pages/confirm-approve/confirm-approve-content/index.scss +++ b/ui/app/pages/confirm-approve/confirm-approve-content/index.scss @@ -4,7 +4,6 @@ align-items: center; width: 100%; height: 100%; - font-family: Roboto; font-style: normal; &__identicon-wrapper { @@ -21,7 +20,6 @@ flex-flow: column; align-items: center; width: 390px; - font-family: Roboto; font-style: normal; padding-left: 24px; padding-right: 24px; diff --git a/ui/app/pages/confirm-approve/confirm-approve.util.js b/ui/app/pages/confirm-approve/confirm-approve.util.js index 0318c6bed..02ae4fe1e 100644 --- a/ui/app/pages/confirm-approve/confirm-approve.util.js +++ b/ui/app/pages/confirm-approve/confirm-approve.util.js @@ -1,5 +1,5 @@ import { decimalToHex } from '../../helpers/utils/conversions.util' -import { calcTokenValue } from '../../helpers/utils/token-util.js' +import { calcTokenValue } from '../../helpers/utils/token-util' import { getTokenData } from '../../helpers/utils/transactions.util' export function getCustomTxParamsData (data, { customPermissionAmount, decimals }) { diff --git a/ui/app/pages/confirm-decrypt-message/confirm-decrypt-message.component.js b/ui/app/pages/confirm-decrypt-message/confirm-decrypt-message.component.js index a95e6d4cd..6b3c0adae 100644 --- a/ui/app/pages/confirm-decrypt-message/confirm-decrypt-message.component.js +++ b/ui/app/pages/confirm-decrypt-message/confirm-decrypt-message.component.js @@ -3,7 +3,7 @@ import PropTypes from 'prop-types' import copyToClipboard from 'copy-to-clipboard' import classnames from 'classnames' -import AccountListItem from '../send/account-list-item/account-list-item.component' +import AccountListItem from '../../components/app/account-list-item' import Button from '../../components/ui/button' import Identicon from '../../components/ui/identicon' import Tooltip from '../../components/ui/tooltip-v2' @@ -119,7 +119,6 @@ export default class ConfirmDecryptMessage extends Component {
@@ -221,7 +220,7 @@ export default class ConfirmDecryptMessage extends Component { className="request-decrypt-message__message-text" > { !hasDecrypted && !hasError ? txData.msgParams.data : rawMessage } - { !hasError ? '' : errorMessage } + { hasError ? errorMessage : '' }
{ decryptMessageInline(txData, event).then((result) => { - if (!result.error) { - this.setState({ hasDecrypted: true, rawMessage: result.rawData }) - } else { + if (result.error) { this.setState({ hasError: true, errorMessage: this.context.t('decryptInlineError', [result.error]) }) + } else { + this.setState({ hasDecrypted: true, rawMessage: result.rawData }) } }) }} diff --git a/ui/app/pages/confirm-encryption-public-key/confirm-encryption-public-key.component.js b/ui/app/pages/confirm-encryption-public-key/confirm-encryption-public-key.component.js index 5ef485c72..3dbba9b8f 100644 --- a/ui/app/pages/confirm-encryption-public-key/confirm-encryption-public-key.component.js +++ b/ui/app/pages/confirm-encryption-public-key/confirm-encryption-public-key.component.js @@ -1,7 +1,7 @@ import React, { Component } from 'react' import PropTypes from 'prop-types' -import AccountListItem from '../send/account-list-item/account-list-item.component' +import AccountListItem from '../../components/app/account-list-item' import Button from '../../components/ui/button' import Identicon from '../../components/ui/identicon' @@ -99,7 +99,6 @@ export default class ConfirmEncryptionPublicKey extends Component {
diff --git a/ui/app/pages/confirm-transaction-base/confirm-transaction-base.component.js b/ui/app/pages/confirm-transaction-base/confirm-transaction-base.component.js index 7f8df4168..1b44c4376 100644 --- a/ui/app/pages/confirm-transaction-base/confirm-transaction-base.component.js +++ b/ui/app/pages/confirm-transaction-base/confirm-transaction-base.component.js @@ -727,7 +727,7 @@ export function getMethodName (camelCase) { } return camelCase - .replace(/([a-z])([A-Z])/g, '$1 $2') - .replace(/([A-Z])([a-z])/g, ' $1$2') - .replace(/ +/g, ' ') + .replace(/([a-z])([A-Z])/ug, '$1 $2') + .replace(/([A-Z])([a-z])/ug, ' $1$2') + .replace(/ +/ug, ' ') } diff --git a/ui/app/pages/confirm-transaction-base/confirm-transaction-base.container.js b/ui/app/pages/confirm-transaction-base/confirm-transaction-base.container.js index 11fb474fc..1759e967d 100644 --- a/ui/app/pages/confirm-transaction-base/confirm-transaction-base.container.js +++ b/ui/app/pages/confirm-transaction-base/confirm-transaction-base.container.js @@ -93,13 +93,10 @@ const mapStateToProps = (state, ownProps) => { const { balance } = accounts[fromAddress] const { name: fromName } = identities[fromAddress] const toAddress = propsToAddress || txParamsToAddress - const toName = identities[toAddress] - ? identities[toAddress].name - : ( - casedContractMap[toAddress] - ? casedContractMap[toAddress].name - : shortenAddress(checksumAddress(toAddress)) - ) + + const toName = identities[toAddress]?.name || + casedContractMap[toAddress]?.name || + shortenAddress(checksumAddress(toAddress)) const checksummedAddress = checksumAddress(toAddress) const addressBookObject = addressBook[checksummedAddress] diff --git a/ui/app/pages/confirm-transaction-switch/confirm-transaction-switch.container.js b/ui/app/pages/confirm-transaction-switch/confirm-transaction-switch.container.js index 11daa6cc6..b0d0a8924 100644 --- a/ui/app/pages/confirm-transaction-switch/confirm-transaction-switch.container.js +++ b/ui/app/pages/confirm-transaction-switch/confirm-transaction-switch.container.js @@ -5,7 +5,7 @@ import { unconfirmedTransactionsListSelector } from '../../selectors' const mapStateToProps = (state, ownProps) => { const { metamask: { unapprovedTxs } } = state const { match: { params = {}, url } } = ownProps - const urlId = url && url.match(/\d+/) && url.match(/\d+/)[0] + const urlId = url && url.match(/\d+/u) && url.match(/\d+/u)[0] const { id: paramsId } = params const transactionId = paramsId || urlId diff --git a/ui/app/pages/create-account/connect-hardware/account-list.js b/ui/app/pages/create-account/connect-hardware/account-list.js index 933a26b5d..cac29cdf0 100644 --- a/ui/app/pages/create-account/connect-hardware/account-list.js +++ b/ui/app/pages/create-account/connect-hardware/account-list.js @@ -1,7 +1,7 @@ import PropTypes from 'prop-types' import React, { Component } from 'react' import Select from 'react-select' -import genAccountLink from '../../../../lib/account-link.js' +import getAccountLink from '../../../../lib/account-link' import Button from '../../../components/ui/button' class AccountList extends Component { @@ -101,7 +101,7 @@ class AccountList extends Component {
{ + for (const device of ['trezor', 'ledger']) { const unlocked = await this.props.checkHardwareStatus(device, this.props.defaultHdPaths[device]) if (unlocked) { this.setState({ unlocked: true }) this.getPage(device, 0, this.props.defaultHdPaths[device]) } - }) + } } connectToHardwareWallet = (device) => { if (this.state.accounts.length) { - return null + return } // Default values diff --git a/ui/app/pages/create-account/import-account/index.js b/ui/app/pages/create-account/import-account/index.js index 13d26f8f0..5cd5c25ff 100644 --- a/ui/app/pages/create-account/import-account/index.js +++ b/ui/app/pages/create-account/import-account/index.js @@ -3,9 +3,8 @@ import PropTypes from 'prop-types' import Select from 'react-select' // Subviews -import JsonImportView from './json.js' - -import PrivateKeyImportView from './private-key.js' +import JsonImportView from './json' +import PrivateKeyImportView from './private-key' export default class AccountImportSubview extends Component { static contextTypes = { diff --git a/ui/app/pages/create-account/import-account/json.js b/ui/app/pages/create-account/import-account/json.js index 304e52c50..55a77cb4e 100644 --- a/ui/app/pages/create-account/import-account/json.js +++ b/ui/app/pages/create-account/import-account/json.js @@ -101,7 +101,8 @@ class JsonImportSubview extends Component { if (!fileContents) { const message = this.context.t('needImportFile') - return displayWarning(message) + displayWarning(message) + return } const password = this.inputRef.current.value diff --git a/ui/app/pages/error/index.scss b/ui/app/pages/error/index.scss index cf0c2aeb4..14ec9da84 100644 --- a/ui/app/pages/error/index.scss +++ b/ui/app/pages/error/index.scss @@ -2,7 +2,6 @@ display: flex; flex-flow: column nowrap; align-items: center; - font-family: Roboto; font-style: normal; font-weight: normal; padding: 35px 10px 10px 10px; diff --git a/ui/app/pages/first-time-flow/end-of-flow/index.scss b/ui/app/pages/first-time-flow/end-of-flow/index.scss index f085ea99e..34d04d1c2 100644 --- a/ui/app/pages/first-time-flow/end-of-flow/index.scss +++ b/ui/app/pages/first-time-flow/end-of-flow/index.scss @@ -1,6 +1,5 @@ .end-of-flow { color: black; - font-family: Roboto; font-style: normal; .app-header__logo-container { diff --git a/ui/app/pages/first-time-flow/index.scss b/ui/app/pages/first-time-flow/index.scss index 3b7498b2b..19e769e10 100644 --- a/ui/app/pages/first-time-flow/index.scss +++ b/ui/app/pages/first-time-flow/index.scss @@ -72,7 +72,6 @@ /*rtl:ignore*/ direction: ltr; font-size: 1rem; - font-family: Roboto; border: 1px solid #cdcdcd; border-radius: 6px; background-color: #fff; @@ -149,7 +148,6 @@ } &__checkbox-label { - font-family: Roboto; font-style: normal; font-weight: normal; line-height: normal; diff --git a/ui/app/pages/first-time-flow/metametrics-opt-in/index.scss b/ui/app/pages/first-time-flow/metametrics-opt-in/index.scss index a5cb6e1da..18df92891 100644 --- a/ui/app/pages/first-time-flow/metametrics-opt-in/index.scss +++ b/ui/app/pages/first-time-flow/metametrics-opt-in/index.scss @@ -27,7 +27,6 @@ &__title { position: relative; margin-top: 20px; - font-family: Roboto; font-style: normal; font-weight: normal; line-height: normal; @@ -43,7 +42,6 @@ } &__description { - font-family: Roboto; font-style: normal; font-weight: normal; line-height: 21px; diff --git a/ui/app/pages/first-time-flow/metametrics-opt-in/metametrics-opt-in.component.js b/ui/app/pages/first-time-flow/metametrics-opt-in/metametrics-opt-in.component.js index e5d622ef2..789de5372 100644 --- a/ui/app/pages/first-time-flow/metametrics-opt-in/metametrics-opt-in.component.js +++ b/ui/app/pages/first-time-flow/metametrics-opt-in/metametrics-opt-in.component.js @@ -88,7 +88,7 @@ export default class MetaMetricsOptIn extends Component { onCancel={() => { setParticipateInMetaMetrics(false) .then(() => { - const promise = participateInMetaMetrics !== false + const promise = participateInMetaMetrics === true ? metricsEvent({ eventOpts: { category: 'Onboarding', @@ -110,7 +110,7 @@ export default class MetaMetricsOptIn extends Component { onSubmit={() => { setParticipateInMetaMetrics(true) .then(([_, metaMetricsId]) => { - const promise = participateInMetaMetrics !== true + const promise = participateInMetaMetrics === false ? metricsEvent({ eventOpts: { category: 'Onboarding', diff --git a/ui/app/pages/first-time-flow/onboarding-initiator-util.js b/ui/app/pages/first-time-flow/onboarding-initiator-util.js index 7653f7852..a7848bdbe 100644 --- a/ui/app/pages/first-time-flow/onboarding-initiator-util.js +++ b/ui/app/pages/first-time-flow/onboarding-initiator-util.js @@ -16,12 +16,12 @@ const returnToOnboardingInitiatorTab = async (onboardingInitiator) => { }) })) - if (!tab) { + if (tab) { + window.close() + } else { // this case can happen if the tab was closed since being checked with `extension.tabs.get` log.warn(`Setting current tab to onboarding initiator has failed; falling back to redirect`) window.location.assign(onboardingInitiator.location) - } else { - window.close() } } diff --git a/ui/app/pages/first-time-flow/seed-phrase/confirm-seed-phrase/confirm-seed-phrase.component.js b/ui/app/pages/first-time-flow/seed-phrase/confirm-seed-phrase/confirm-seed-phrase.component.js index 8847a0d01..8cc34e2af 100644 --- a/ui/app/pages/first-time-flow/seed-phrase/confirm-seed-phrase/confirm-seed-phrase.component.js +++ b/ui/app/pages/first-time-flow/seed-phrase/confirm-seed-phrase/confirm-seed-phrase.component.js @@ -173,10 +173,10 @@ export default class ConfirmSeedPhrase extends PureComponent { className="confirm-seed-phrase__seed-word--sorted" selected={isSelected} onClick={() => { - if (!isSelected) { - this.handleSelectSeedWord(index) - } else { + if (isSelected) { this.handleDeselectSeedWord(index) + } else { + this.handleSelectSeedWord(index) } }} word={word} diff --git a/ui/app/pages/first-time-flow/seed-phrase/reveal-seed-phrase/tests/reveal-seed-phrase.test.js b/ui/app/pages/first-time-flow/seed-phrase/reveal-seed-phrase/tests/reveal-seed-phrase.test.js index a9ac7b66c..dfc045778 100644 --- a/ui/app/pages/first-time-flow/seed-phrase/reveal-seed-phrase/tests/reveal-seed-phrase.test.js +++ b/ui/app/pages/first-time-flow/seed-phrase/reveal-seed-phrase/tests/reveal-seed-phrase.test.js @@ -23,7 +23,7 @@ describe('Reveal Seed Phrase', function () { , { context: { t: (str) => str, - metricsEvent: () => {}, + metricsEvent: () => undefined, }, }, ) diff --git a/ui/app/pages/first-time-flow/seed-phrase/seed-phrase.component.js b/ui/app/pages/first-time-flow/seed-phrase/seed-phrase.component.js index 67eccb34c..ade1904c4 100644 --- a/ui/app/pages/first-time-flow/seed-phrase/seed-phrase.component.js +++ b/ui/app/pages/first-time-flow/seed-phrase/seed-phrase.component.js @@ -30,10 +30,10 @@ export default class SeedPhrase extends PureComponent { if (!seedPhrase) { verifySeedPhrase() .then((verifiedSeedPhrase) => { - if (!verifiedSeedPhrase) { - history.push(DEFAULT_ROUTE) - } else { + if (verifiedSeedPhrase) { this.setState({ verifiedSeedPhrase }) + } else { + history.push(DEFAULT_ROUTE) } }) } diff --git a/ui/app/pages/first-time-flow/select-action/index.scss b/ui/app/pages/first-time-flow/select-action/index.scss index 34a72a10c..1b398a73e 100644 --- a/ui/app/pages/first-time-flow/select-action/index.scss +++ b/ui/app/pages/first-time-flow/select-action/index.scss @@ -11,7 +11,6 @@ } &__body-header { - font-family: Roboto; font-style: normal; font-weight: normal; line-height: 39px; @@ -59,7 +58,6 @@ } &__button-text-big { - font-family: Roboto; font-style: normal; font-weight: normal; line-height: 28px; @@ -70,7 +68,6 @@ } &__button-text-small { - font-family: Roboto; font-style: normal; font-weight: normal; line-height: 20px; diff --git a/ui/app/pages/home/index.scss b/ui/app/pages/home/index.scss index 814223bf3..4d4926e86 100644 --- a/ui/app/pages/home/index.scss +++ b/ui/app/pages/home/index.scss @@ -43,10 +43,11 @@ display: flex; flex-direction: column; - @extend %content-text; + @include H6; padding-left: 24px; padding-right: 24px; + color: $Grey-800; div { margin-bottom: 20px; diff --git a/ui/app/pages/index.scss b/ui/app/pages/index.scss index 95bdc7489..8154fc77d 100644 --- a/ui/app/pages/index.scss +++ b/ui/app/pages/index.scss @@ -12,3 +12,4 @@ @import 'confirm-approve/index'; @import 'permissions-connect/index'; @import 'asset/asset'; +@import 'token/index'; diff --git a/ui/app/pages/keychains/index.scss b/ui/app/pages/keychains/index.scss index a70255d0d..54b52981f 100644 --- a/ui/app/pages/keychains/index.scss +++ b/ui/app/pages/keychains/index.scss @@ -95,7 +95,6 @@ .import-account__faq-link { font-size: 18px; line-height: 23px; - font-family: Roboto; } .import-account__selector-label { @@ -110,7 +109,6 @@ background-color: #fff; margin-top: 14px; color: #5b5d67; - font-family: Roboto; font-size: 18px; line-height: 23px; padding: 14px 21px; @@ -125,7 +123,6 @@ font-size: 18px; line-height: 23px; margin-top: 21px; - font-family: Roboto; } .import-account__input-wrapper { @@ -173,7 +170,6 @@ border: 1px solid #1b344d; border-radius: 4px; color: #1b344d; - font-family: Roboto; font-size: 18px; display: flex; flex-flow: column nowrap; @@ -190,7 +186,6 @@ .import-account__file-name { color: #000; - font-family: Roboto; font-size: 18px; line-height: 23px; margin-left: 22px; diff --git a/ui/app/pages/mobile-sync/mobile-sync.component.js b/ui/app/pages/mobile-sync/mobile-sync.component.js index d93e64c0d..51ad3e6b7 100644 --- a/ui/app/pages/mobile-sync/mobile-sync.component.js +++ b/ui/app/pages/mobile-sync/mobile-sync.component.js @@ -131,7 +131,7 @@ export default class MobileSyncPage extends Component { const { channel, message } = data // handle message if (channel !== this.channelName || !message) { - return false + return } if (message.event === 'start-sync') { @@ -173,8 +173,10 @@ export default class MobileSyncPage extends Component { chunkString (str, size) { const numChunks = Math.ceil(str.length / size) const chunks = new Array(numChunks) - for (let i = 0, o = 0; i < numChunks; ++i, o += size) { + for (let i = 0, o = 0; i < numChunks;) { chunks[i] = str.substr(o, size) + i += 1 + o += size } return chunks } @@ -192,10 +194,10 @@ export default class MobileSyncPage extends Component { storeInHistory: false, }, (status, response) => { - if (!status.error) { - resolve() - } else { + if (status.error) { reject(response) + } else { + resolve() } }) }) @@ -203,7 +205,7 @@ export default class MobileSyncPage extends Component { async startSyncing () { if (this.syncing) { - return false + return } this.syncing = true this.setState({ syncing: true }) @@ -251,10 +253,10 @@ export default class MobileSyncPage extends Component { storeInHistory: false, }, (status, response) => { - if (!status.error) { - resolve() - } else { + if (status.error) { reject(response) + } else { + resolve() } }, ) @@ -369,7 +371,6 @@ export default class MobileSyncPage extends Component { {t('syncWithMobileScanThisCode')}
- { page === '2' + return redirecting + ? null + : ( +
+ {page === '2' ? (
this.goBack()}> - { t('back') } + {t('back')}
) : null }
- { t('xOfY', [ page, '2' ]) } + {t('xOfY', [page, '2'])}
) - : null } render () { diff --git a/ui/app/pages/permissions-connect/redirect/index.scss b/ui/app/pages/permissions-connect/redirect/index.scss index b2cc68554..fa90ca0c1 100644 --- a/ui/app/pages/permissions-connect/redirect/index.scss +++ b/ui/app/pages/permissions-connect/redirect/index.scss @@ -4,7 +4,7 @@ justify-content: center; &__result { - @extend %header--24; + @include H3; position: absolute; top: 30%; diff --git a/ui/app/pages/routes/routes.component.js b/ui/app/pages/routes/routes.component.js index 578483425..88b8321e9 100644 --- a/ui/app/pages/routes/routes.component.js +++ b/ui/app/pages/routes/routes.component.js @@ -265,16 +265,16 @@ export default class Routes extends Component { } toggleMetamaskActive () { - if (!this.props.isUnlocked) { + if (this.props.isUnlocked) { + // currently active: deactivate + this.props.lockMetaMask() + } else { // currently inactive: redirect to password box const passwordBox = document.querySelector('input[type=password]') if (!passwordBox) { return } passwordBox.focus() - } else { - // currently active: deactivate - this.props.lockMetaMask() } } diff --git a/ui/app/pages/send/account-list-item/account-list-item.component.js b/ui/app/pages/send/account-list-item/account-list-item.component.js deleted file mode 100644 index 58df336e5..000000000 --- a/ui/app/pages/send/account-list-item/account-list-item.component.js +++ /dev/null @@ -1,101 +0,0 @@ -import React from 'react' -import PropTypes from 'prop-types' -import classnames from 'classnames' -import { checksumAddress } from '../../../helpers/utils/util' -import Identicon from '../../../components/ui/identicon' -import UserPreferencedCurrencyDisplay from '../../../components/app/user-preferenced-currency-display' -import { PRIMARY, SECONDARY } from '../../../helpers/constants/common' -import Tooltip from '../../../components/ui/tooltip-v2' -import AccountMismatchWarning from '../../../components/ui/account-mismatch-warning/account-mismatch-warning.component' -import { useI18nContext } from '../../../hooks/useI18nContext' - -export default function AccountListItem ({ - account, - className, - displayAddress = false, - displayBalance = true, - handleClick, - icon = null, - balanceIsCached, - showFiat = true, -}) { - const t = useI18nContext() - const { name, address, balance } = account || {} - - return ( -
handleClick && handleClick({ name, address, balance })} - > - -
- - -
{ name || address }
- - {icon &&
{ icon }
} - - -
- - {displayAddress && name && ( -
- { checksumAddress(address) } -
- )} - - {displayBalance && ( - -
-
- - { - balanceIsCached - ? * - : null - } -
- {showFiat && ( - - )} -
-
- )} - -
- ) -} - -AccountListItem.propTypes = { - account: PropTypes.object, - className: PropTypes.string, - displayAddress: PropTypes.bool, - displayBalance: PropTypes.bool, - handleClick: PropTypes.func, - icon: PropTypes.node, - balanceIsCached: PropTypes.bool, - showFiat: PropTypes.bool, -} diff --git a/ui/app/pages/send/account-list-item/account-list-item.container.js b/ui/app/pages/send/account-list-item/account-list-item.container.js deleted file mode 100644 index 40888d3ba..000000000 --- a/ui/app/pages/send/account-list-item/account-list-item.container.js +++ /dev/null @@ -1,21 +0,0 @@ -import { connect } from 'react-redux' -import { - getNativeCurrency, - getIsMainnet, - isBalanceCached, - getPreferences, -} from '../../../selectors' -import AccountListItem from './account-list-item.component' - -export default connect(mapStateToProps)(AccountListItem) - -function mapStateToProps (state) { - const { showFiatInTestnets } = getPreferences(state) - const isMainnet = getIsMainnet(state) - - return { - nativeCurrency: getNativeCurrency(state), - balanceIsCached: isBalanceCached(state), - showFiat: (isMainnet || !!showFiatInTestnets), - } -} diff --git a/ui/app/pages/send/account-list-item/index.js b/ui/app/pages/send/account-list-item/index.js deleted file mode 100644 index 907485cf7..000000000 --- a/ui/app/pages/send/account-list-item/index.js +++ /dev/null @@ -1 +0,0 @@ -export { default } from './account-list-item.container' diff --git a/ui/app/pages/send/account-list-item/tests/account-list-item-container.test.js b/ui/app/pages/send/account-list-item/tests/account-list-item-container.test.js deleted file mode 100644 index 611830d78..000000000 --- a/ui/app/pages/send/account-list-item/tests/account-list-item-container.test.js +++ /dev/null @@ -1,63 +0,0 @@ -import assert from 'assert' -import proxyquire from 'proxyquire' - -let mapStateToProps - -proxyquire('../account-list-item.container.js', { - 'react-redux': { - connect: (ms) => { - mapStateToProps = ms - return () => ({}) - }, - }, - '../../../selectors': { - getConversionRate: () => `mockConversionRate`, - getCurrentCurrency: () => `mockCurrentCurrency`, - getNativeCurrency: () => `mockNativeCurrency`, - isBalanceCached: () => `mockBalanceIsCached`, - getPreferences: ({ showFiatInTestnets }) => ({ - showFiatInTestnets, - }), - getIsMainnet: ({ isMainnet }) => isMainnet, - }, -}) - -describe('account-list-item container', function () { - - describe('mapStateToProps()', function () { - - it('should map the correct properties to props', function () { - assert.deepEqual(mapStateToProps({ isMainnet: true, showFiatInTestnets: false }), { - nativeCurrency: 'mockNativeCurrency', - balanceIsCached: 'mockBalanceIsCached', - showFiat: true, - }) - }) - - it('should map the correct properties to props when in mainnet and showFiatInTestnet is true', function () { - assert.deepEqual(mapStateToProps({ isMainnet: true, showFiatInTestnets: true }), { - nativeCurrency: 'mockNativeCurrency', - balanceIsCached: 'mockBalanceIsCached', - showFiat: true, - }) - }) - - it('should map the correct properties to props when not in mainnet and showFiatInTestnet is true', function () { - assert.deepEqual(mapStateToProps({ isMainnet: false, showFiatInTestnets: true }), { - nativeCurrency: 'mockNativeCurrency', - balanceIsCached: 'mockBalanceIsCached', - showFiat: true, - }) - }) - - it('should map the correct properties to props when not in mainnet and showFiatInTestnet is false', function () { - assert.deepEqual(mapStateToProps({ isMainnet: false, showFiatInTestnets: false }), { - nativeCurrency: 'mockNativeCurrency', - balanceIsCached: 'mockBalanceIsCached', - showFiat: false, - }) - }) - - }) - -}) diff --git a/ui/app/pages/send/send-content/add-recipient/add-recipient.component.js b/ui/app/pages/send/send-content/add-recipient/add-recipient.component.js index de4e3a89e..76b6a5570 100644 --- a/ui/app/pages/send/send-content/add-recipient/add-recipient.component.js +++ b/ui/app/pages/send/send-content/add-recipient/add-recipient.component.js @@ -233,6 +233,8 @@ export default class AddRecipient extends Component { ) } + + return null } } diff --git a/ui/app/pages/send/send-content/add-recipient/ens-input.component.js b/ui/app/pages/send/send-content/add-recipient/ens-input.component.js index 8e9d10425..df8bf87a2 100644 --- a/ui/app/pages/send/send-content/add-recipient/ens-input.component.js +++ b/ui/app/pages/send/send-content/add-recipient/ens-input.component.js @@ -122,7 +122,7 @@ export default class EnsInput extends Component { if (!networkHasEnsSupport && !isValidAddress(input) && !isValidAddressHead(input)) { updateEnsResolution('') - updateEnsResolutionError(!networkHasEnsSupport ? 'Network does not support ENS' : '') + updateEnsResolutionError(networkHasEnsSupport ? '' : 'Network does not support ENS') return } @@ -236,7 +236,7 @@ export default class EnsInput extends Component { const { loadingEns, ensFailure, ensResolution, toError } = this.state if (toError) { - return + return null } if (loadingEns) { @@ -269,6 +269,8 @@ export default class EnsInput extends Component { /> ) } + + return null } } diff --git a/ui/app/pages/send/send-content/add-recipient/tests/add-recipient-utils.test.js b/ui/app/pages/send/send-content/add-recipient/tests/add-recipient-utils.test.js index a35ba5b9f..628420688 100644 --- a/ui/app/pages/send/send-content/add-recipient/tests/add-recipient-utils.test.js +++ b/ui/app/pages/send/send-content/add-recipient/tests/add-recipient-utils.test.js @@ -9,7 +9,7 @@ import { } from '../../../send.constants' const stubs = { - isValidAddress: sinon.stub().callsFake((to) => Boolean(to.match(/^[0xabcdef123456798]+$/))), + isValidAddress: sinon.stub().callsFake((to) => Boolean(to.match(/^[0xabcdef123456798]+$/u))), } const toRowUtils = proxyquire('../add-recipient.js', { diff --git a/ui/app/pages/send/send-content/send-amount-row/amount-max-button/amount-max-button.component.js b/ui/app/pages/send/send-content/send-amount-row/amount-max-button/amount-max-button.component.js index 59fcea367..adab9856e 100644 --- a/ui/app/pages/send/send-content/send-amount-row/amount-max-button/amount-max-button.component.js +++ b/ui/app/pages/send/send-content/send-amount-row/amount-max-button/amount-max-button.component.js @@ -51,12 +51,12 @@ export default class AmountMaxButton extends Component { name: 'Clicked "Amount Max"', }, }) - if (!maxModeOn) { - setMaxModeTo(true) - this.setMaxAmount() - } else { + if (maxModeOn) { setMaxModeTo(false) clearMaxAmount() + } else { + setMaxModeTo(true) + this.setMaxAmount() } } diff --git a/ui/app/pages/send/send-content/send-amount-row/amount-max-button/amount-max-button.container.js b/ui/app/pages/send/send-content/send-amount-row/amount-max-button/amount-max-button.container.js index 4060b3eee..e187a1592 100644 --- a/ui/app/pages/send/send-content/send-amount-row/amount-max-button/amount-max-button.container.js +++ b/ui/app/pages/send/send-content/send-amount-row/amount-max-button/amount-max-button.container.js @@ -7,7 +7,7 @@ import { getSendMaxModeState, getBasicGasEstimateLoadingStatus, } from '../../../../../selectors' -import { calcMaxAmount } from './amount-max-button.utils.js' +import { calcMaxAmount } from './amount-max-button.utils' import { updateSendAmount, setMaxModeTo, diff --git a/ui/app/pages/send/send-content/send-amount-row/amount-max-button/tests/amount-max-button-component.test.js b/ui/app/pages/send/send-content/send-amount-row/amount-max-button/tests/amount-max-button-component.test.js index 322d21288..008bcec30 100644 --- a/ui/app/pages/send/send-content/send-amount-row/amount-max-button/tests/amount-max-button-component.test.js +++ b/ui/app/pages/send/send-content/send-amount-row/amount-max-button/tests/amount-max-button-component.test.js @@ -2,7 +2,7 @@ import React from 'react' import assert from 'assert' import { shallow } from 'enzyme' import sinon from 'sinon' -import AmountMaxButton from '../amount-max-button.component.js' +import AmountMaxButton from '../amount-max-button.component' describe('AmountMaxButton Component', function () { let wrapper @@ -13,7 +13,7 @@ describe('AmountMaxButton Component', function () { setMaxModeTo: sinon.spy(), } - const MOCK_EVENT = { preventDefault: () => {} } + const MOCK_EVENT = { preventDefault: () => undefined } before(function () { sinon.spy(AmountMaxButton.prototype, 'setMaxAmount') @@ -33,7 +33,7 @@ describe('AmountMaxButton Component', function () { ), { context: { t: (str) => str + '_t', - metricsEvent: () => {}, + metricsEvent: () => undefined, }, }) instance = wrapper.instance() diff --git a/ui/app/pages/send/send-content/send-amount-row/amount-max-button/tests/amount-max-button-utils.test.js b/ui/app/pages/send/send-content/send-amount-row/amount-max-button/tests/amount-max-button-utils.test.js index 08fc28b73..caafcfb51 100644 --- a/ui/app/pages/send/send-content/send-amount-row/amount-max-button/tests/amount-max-button-utils.test.js +++ b/ui/app/pages/send/send-content/send-amount-row/amount-max-button/tests/amount-max-button-utils.test.js @@ -1,7 +1,7 @@ import assert from 'assert' import { calcMaxAmount, -} from '../amount-max-button.utils.js' +} from '../amount-max-button.utils' describe('amount-max-button utils', function () { diff --git a/ui/app/pages/send/send-content/send-amount-row/tests/send-amount-row-component.test.js b/ui/app/pages/send/send-content/send-amount-row/tests/send-amount-row-component.test.js index 6264c137c..b22819f25 100644 --- a/ui/app/pages/send/send-content/send-amount-row/tests/send-amount-row-component.test.js +++ b/ui/app/pages/send/send-content/send-amount-row/tests/send-amount-row-component.test.js @@ -2,7 +2,7 @@ import React from 'react' import assert from 'assert' import { shallow } from 'enzyme' import sinon from 'sinon' -import SendAmountRow from '../send-amount-row.component.js' +import SendAmountRow from '../send-amount-row.component' import SendRowWrapper from '../../send-row-wrapper/send-row-wrapper.component' import AmountMaxButton from '../amount-max-button/amount-max-button.container' @@ -158,7 +158,7 @@ function shallowRenderSendAmountRow () { updateGasFeeError={updateGasFeeError} updateSendAmount={updateSendAmount} updateSendAmountError={updateSendAmountError} - updateGas={() => {}} + updateGas={() => undefined} /> ), { context: { t: (str) => str + '_t' } }) const instance = wrapper.instance() diff --git a/ui/app/pages/send/send-content/send-content.component.js b/ui/app/pages/send/send-content/send-content.component.js index 6ae20f19e..9188140f9 100644 --- a/ui/app/pages/send/send-content/send-content.component.js +++ b/ui/app/pages/send/send-content/send-content.component.js @@ -48,7 +48,7 @@ export default class SendContent extends Component { const { isOwnedAccount, showAddToAddressBookModal, contact = {} } = this.props if (isOwnedAccount || contact.name) { - return + return null } return ( diff --git a/ui/app/pages/send/send-content/send-gas-row/gas-fee-display/gas-fee-display.component.js b/ui/app/pages/send/send-content/send-gas-row/gas-fee-display/gas-fee-display.component.js index ddbee30bb..601cf0c5f 100644 --- a/ui/app/pages/send/send-content/send-gas-row/gas-fee-display/gas-fee-display.component.js +++ b/ui/app/pages/send/send-content/send-gas-row/gas-fee-display/gas-fee-display.component.js @@ -20,6 +20,7 @@ export default class GasFeeDisplay extends Component { return (
+ {/* eslint-disable-next-line no-nested-ternary */} {gasTotal ? (
diff --git a/ui/app/pages/send/send-content/send-gas-row/send-gas-row.container.js b/ui/app/pages/send/send-content/send-gas-row/send-gas-row.container.js index e38a53227..82e6b4a7d 100644 --- a/ui/app/pages/send/send-content/send-gas-row/send-gas-row.container.js +++ b/ui/app/pages/send/send-content/send-gas-row/send-gas-row.container.js @@ -21,7 +21,7 @@ import { import { isBalanceSufficient, calcGasTotal, -} from '../../send.utils.js' +} from '../../send.utils' import { calcMaxAmount } from '../send-amount-row/amount-max-button/amount-max-button.utils' import { showGasButtonGroup, diff --git a/ui/app/pages/send/send-content/send-gas-row/send-gas-row.scss b/ui/app/pages/send/send-content/send-gas-row/send-gas-row.scss index e69de29bb..b8a23d06b 100644 --- a/ui/app/pages/send/send-content/send-gas-row/send-gas-row.scss +++ b/ui/app/pages/send/send-content/send-gas-row/send-gas-row.scss @@ -0,0 +1,82 @@ +.currency-display { + height: 54px; + border: 1px solid $alto; + border-radius: 4px; + background-color: $white; + color: $scorpion; + font-size: 16px; + padding: 8px 10px; + position: relative; + + &__primary-row { + display: flex; + } + + &__input { + color: $scorpion; + font-size: 16px; + line-height: 22px; + border: none; + max-width: 22ch; + } + + &__primary-currency { + color: $scorpion; + font-weight: 400; + font-size: 16px; + line-height: 22px; + } + + &__converted-row { + display: flex; + } + + &__converted-value, + &__converted-currency { + color: $dusty-gray; + font-size: 12px; + line-height: 12px; + } + + &__input-wrapper { + position: relative; + display: flex; + flex: 1; + max-width: 100%; + + input[type="number"] { + -moz-appearance: textfield; + } + + input[type="number"]::-webkit-inner-spin-button { + -webkit-appearance: none; + -moz-appearance: none; + display: none; + } + + input[type="number"]:hover::-webkit-inner-spin-button { + -webkit-appearance: none; + -moz-appearance: none; + display: none; + } + } + + &__currency-symbol { + margin-top: 1px; + color: $scorpion; + } + + .react-numeric-input { + input[type="number"]::-webkit-inner-spin-button { + -webkit-appearance: none; + -moz-appearance: none; + display: none; + } + + input[type="number"]:hover::-webkit-inner-spin-button { + -webkit-appearance: none; + -moz-appearance: none; + display: none; + } + } +} diff --git a/ui/app/pages/send/send-content/send-gas-row/tests/send-gas-row-component.test.js b/ui/app/pages/send/send-content/send-gas-row/tests/send-gas-row-component.test.js index b5b1b7f53..45c5683b6 100644 --- a/ui/app/pages/send/send-content/send-gas-row/tests/send-gas-row-component.test.js +++ b/ui/app/pages/send/send-content/send-gas-row/tests/send-gas-row-component.test.js @@ -2,7 +2,7 @@ import React from 'react' import assert from 'assert' import { shallow } from 'enzyme' import sinon from 'sinon' -import SendGasRow from '../send-gas-row.component.js' +import SendGasRow from '../send-gas-row.component' import SendRowWrapper from '../../send-row-wrapper/send-row-wrapper.component' import GasFeeDisplay from '../gas-fee-display/gas-fee-display.component' diff --git a/ui/app/pages/send/send-content/send-hex-data-row/send-hex-data-row.component.js b/ui/app/pages/send/send-content/send-hex-data-row/send-hex-data-row.component.js index eeff87b84..cf774ae0c 100644 --- a/ui/app/pages/send/send-content/send-hex-data-row/send-hex-data-row.component.js +++ b/ui/app/pages/send/send-content/send-hex-data-row/send-hex-data-row.component.js @@ -15,7 +15,7 @@ export default class SendHexDataRow extends Component { onInput = (event) => { const { updateSendHexData, updateGas } = this.props - const data = event.target.value.replace(/\n/g, '') || null + const data = event.target.value.replace(/\n/ug, '') || null updateSendHexData(data) updateGas({ data }) } diff --git a/ui/app/pages/send/send-content/send-row-wrapper/send-row-error-message/tests/send-row-error-message-component.test.js b/ui/app/pages/send/send-content/send-row-wrapper/send-row-error-message/tests/send-row-error-message-component.test.js index 47d624598..6213173c2 100644 --- a/ui/app/pages/send/send-content/send-row-wrapper/send-row-error-message/tests/send-row-error-message-component.test.js +++ b/ui/app/pages/send/send-content/send-row-wrapper/send-row-error-message/tests/send-row-error-message-component.test.js @@ -1,7 +1,7 @@ import React from 'react' import assert from 'assert' import { shallow } from 'enzyme' -import SendRowErrorMessage from '../send-row-error-message.component.js' +import SendRowErrorMessage from '../send-row-error-message.component' describe('SendRowErrorMessage Component', function () { let wrapper diff --git a/ui/app/pages/send/send-content/send-row-wrapper/tests/send-row-wrapper-component.test.js b/ui/app/pages/send/send-content/send-row-wrapper/tests/send-row-wrapper-component.test.js index 6d793c1bd..424014441 100644 --- a/ui/app/pages/send/send-content/send-row-wrapper/tests/send-row-wrapper-component.test.js +++ b/ui/app/pages/send/send-content/send-row-wrapper/tests/send-row-wrapper-component.test.js @@ -1,7 +1,7 @@ import React from 'react' import assert from 'assert' import { shallow } from 'enzyme' -import SendRowWrapper from '../send-row-wrapper.component.js' +import SendRowWrapper from '../send-row-wrapper.component' import SendRowErrorMessage from '../send-row-error-message/send-row-error-message.container' diff --git a/ui/app/pages/send/send-content/tests/send-content-component.test.js b/ui/app/pages/send/send-content/tests/send-content-component.test.js index 01dc83277..6fdb76312 100644 --- a/ui/app/pages/send/send-content/tests/send-content-component.test.js +++ b/ui/app/pages/send/send-content/tests/send-content-component.test.js @@ -1,7 +1,7 @@ import React from 'react' import assert from 'assert' import { shallow } from 'enzyme' -import SendContent from '../send-content.component.js' +import SendContent from '../send-content.component' import PageContainerContent from '../../../../components/ui/page-container/page-container-content.component' import SendAmountRow from '../send-amount-row/send-amount-row.container' diff --git a/ui/app/pages/send/send-footer/tests/send-footer-component.test.js b/ui/app/pages/send/send-footer/tests/send-footer-component.test.js index 12317cf09..ba2c8c1e5 100644 --- a/ui/app/pages/send/send-footer/tests/send-footer-component.test.js +++ b/ui/app/pages/send/send-footer/tests/send-footer-component.test.js @@ -3,7 +3,7 @@ import assert from 'assert' import { shallow } from 'enzyme' import sinon from 'sinon' import { CONFIRM_TRANSACTION_ROUTE } from '../../../../helpers/constants/routes' -import SendFooter from '../send-footer.component.js' +import SendFooter from '../send-footer.component' import PageContainerFooter from '../../../../components/ui/page-container/page-container-footer' describe('SendFooter Component', function () { @@ -18,7 +18,7 @@ describe('SendFooter Component', function () { const historySpies = { push: sinon.spy(), } - const MOCK_EVENT = { preventDefault: () => {} } + const MOCK_EVENT = { preventDefault: () => undefined } before(function () { sinon.spy(SendFooter.prototype, 'onCancel') diff --git a/ui/app/pages/send/send-header/tests/send-header-component.test.js b/ui/app/pages/send/send-header/tests/send-header-component.test.js index 8e9c75f8f..3667a2504 100644 --- a/ui/app/pages/send/send-header/tests/send-header-component.test.js +++ b/ui/app/pages/send/send-header/tests/send-header-component.test.js @@ -2,7 +2,7 @@ import React from 'react' import assert from 'assert' import { shallow } from 'enzyme' import sinon from 'sinon' -import SendHeader from '../send-header.component.js' +import SendHeader from '../send-header.component' import PageContainerHeader from '../../../../components/ui/page-container/page-container-header' describe('SendHeader Component', function () { diff --git a/ui/app/pages/send/send.component.js b/ui/app/pages/send/send.component.js index e73aa8bf7..0c7f7804a 100644 --- a/ui/app/pages/send/send.component.js +++ b/ui/app/pages/send/send.component.js @@ -225,7 +225,8 @@ export default class SendTransactionScreen extends Component { } = this.props if (!query) { - return this.setState({ toError: '', toWarning: '' }) + this.setState({ toError: '', toWarning: '' }) + return } const toErrorObject = getToErrorObject(query, hasHexData, network) diff --git a/ui/app/pages/send/send.container.js b/ui/app/pages/send/send.container.js index e4a1c8194..ca58a3e7d 100644 --- a/ui/app/pages/send/send.container.js +++ b/ui/app/pages/send/send.container.js @@ -45,7 +45,7 @@ import { import { getTokens } from '../../ducks/metamask/metamask' import { calcGasTotal, -} from './send.utils.js' +} from './send.utils' import { isValidDomainName, } from '../../helpers/utils/util' @@ -90,9 +90,9 @@ function mapDispatchToProps (dispatch) { value, data, }) => { - !editingTransactionId - ? dispatch(updateGasData({ gasPrice, selectedAddress, sendToken, blockGasLimit, to, value, data })) - : dispatch(setGasTotal(calcGasTotal(gasLimit, gasPrice))) + editingTransactionId + ? dispatch(setGasTotal(calcGasTotal(gasLimit, gasPrice))) + : dispatch(updateGasData({ gasPrice, selectedAddress, sendToken, blockGasLimit, to, value, data })) }, updateSendTokenBalance: ({ sendToken, tokenContract, address }) => { dispatch(updateSendTokenBalance({ diff --git a/ui/app/pages/send/send.scss b/ui/app/pages/send/send.scss index e9b8cd265..61b1fe805 100644 --- a/ui/app/pages/send/send.scss +++ b/ui/app/pages/send/send.scss @@ -1,3 +1,5 @@ +@import './send-content/send-gas-row/send-gas-row'; + .send { &__header { position: relative; @@ -6,7 +8,7 @@ padding: 14px 0 3px 0; .page-container__title { - @extend %h4; + @include H4; text-align: center; } @@ -91,7 +93,7 @@ } &__group-label { - @extend %h8; + @include H8; background-color: $Grey-000; color: $Grey-600; @@ -136,7 +138,7 @@ } &__subtitle { - @extend %h8; + @include H8; color: $Grey-500; } @@ -186,7 +188,7 @@ } &__input { - @extend %h6; + @include H6; flex: 1 1 auto; width: 0; diff --git a/ui/app/pages/send/send.utils.js b/ui/app/pages/send/send.utils.js index 7ffc5dcdb..ca0fdf044 100644 --- a/ui/app/pages/send/send.utils.js +++ b/ui/app/pages/send/send.utils.js @@ -301,7 +301,7 @@ function addGasBuffer (initialGasLimitHex, blockGasLimitHex, bufferMultiplier = function generateTokenTransferData ({ toAddress = '0x0', amount = '0x0', sendToken }) { if (!sendToken) { - return + return undefined } return TOKEN_TRANSFER_FUNCTION_SIGNATURE + Array.prototype.map.call( abi.rawEncode(['address', 'uint256'], [toAddress, ethUtil.addHexPrefix(amount)]), @@ -314,7 +314,7 @@ function getToAddressForGasUpdate (...addresses) { } function removeLeadingZeroes (str) { - return str.replace(/^0*(?=\d)/, '') + return str.replace(/^0*(?=\d)/u, '') } function ellipsify (text, first = 6, last = 4) { diff --git a/ui/app/pages/send/tests/send-component.test.js b/ui/app/pages/send/tests/send-component.test.js index 757b8fa63..43c296009 100644 --- a/ui/app/pages/send/tests/send-component.test.js +++ b/ui/app/pages/send/tests/send-component.test.js @@ -63,12 +63,12 @@ describe('Send Component', function () { tokenBalance="mockTokenBalance" tokenContract={{ method: 'mockTokenMethod' }} updateAndSetGasLimit={propsMethodSpies.updateAndSetGasLimit} - qrCodeDetected={() => {}} - scanQrCode={() => {}} - updateSendEnsResolution={() => {}} - updateSendEnsResolutionError={() => {}} + qrCodeDetected={() => undefined} + scanQrCode={() => undefined} + updateSendEnsResolution={() => undefined} + updateSendEnsResolutionError={() => undefined} updateSendErrors={propsMethodSpies.updateSendErrors} - updateSendTo={() => {}} + updateSendTo={() => undefined} updateSendTokenBalance={propsMethodSpies.updateSendTokenBalance} resetSendState={propsMethodSpies.resetSendState} updateToNicknameIfNecessary={propsMethodSpies.updateToNicknameIfNecessary} diff --git a/ui/app/pages/send/tests/send-container.test.js b/ui/app/pages/send/tests/send-container.test.js index 84a138d92..ae9cfd2d4 100644 --- a/ui/app/pages/send/tests/send-container.test.js +++ b/ui/app/pages/send/tests/send-container.test.js @@ -21,7 +21,7 @@ proxyquire('../send.container.js', { return () => ({}) }, }, - 'react-router-dom': { withRouter: () => {} }, + 'react-router-dom': { withRouter: () => undefined }, 'redux': { compose: (_, arg2) => () => arg2() }, '../../store/actions': actionSpies, '../../ducks/send/send.duck': duckActionSpies, diff --git a/ui/app/pages/send/tests/send-utils.test.js b/ui/app/pages/send/tests/send-utils.test.js index 08bc30289..b1f57e49a 100644 --- a/ui/app/pages/send/tests/send-utils.test.js +++ b/ui/app/pages/send/tests/send-utils.test.js @@ -10,10 +10,10 @@ import { const stubs = { addCurrencies: sinon.stub().callsFake((a, b) => { - if (String(a).match(/^0x.+/)) { + if (String(a).match(/^0x.+/u)) { a = Number(String(a).slice(2)) } - if (String(b).match(/^0x.+/)) { + if (String(b).match(/^0x.+/u)) { b = Number(String(b).slice(2)) } return a + b @@ -294,8 +294,8 @@ describe('send utils', function () { to: '0xisContract', estimateGasMethod: sinon.stub().callsFake( ({ to }) => { - if (typeof to === 'string' && to.match(/willFailBecauseOf:/)) { - throw new Error(to.match(/:(.+)$/)[1]) + if (typeof to === 'string' && to.match(/willFailBecauseOf:/u)) { + throw new Error(to.match(/:(.+)$/u)[1]) } return { toString: (n) => `0xabc${n}` } }, @@ -311,7 +311,7 @@ describe('send utils', function () { beforeEach(function () { global.eth = { getCode: sinon.stub().callsFake( - (address) => Promise.resolve(address.match(/isContract/) ? 'not-0x' : '0x'), + (address) => Promise.resolve(address.match(/isContract/u) ? 'not-0x' : '0x'), ), } }) diff --git a/ui/app/pages/settings/advanced-tab/advanced-tab.component.js b/ui/app/pages/settings/advanced-tab/advanced-tab.component.js index df952eff6..ec8cbbbda 100644 --- a/ui/app/pages/settings/advanced-tab/advanced-tab.component.js +++ b/ui/app/pages/settings/advanced-tab/advanced-tab.component.js @@ -489,7 +489,7 @@ export default class AdvancedTab extends PureComponent { function addUrlProtocolPrefix (urlString) { if (!urlString.match( - /(^http:\/\/)|(^https:\/\/)/, + /(^http:\/\/)|(^https:\/\/)/u, )) { return 'https://' + urlString } diff --git a/ui/app/pages/settings/advanced-tab/tests/advanced-tab-component.test.js b/ui/app/pages/settings/advanced-tab/tests/advanced-tab-component.test.js index 69fe064c8..cd8e9a200 100644 --- a/ui/app/pages/settings/advanced-tab/tests/advanced-tab-component.test.js +++ b/ui/app/pages/settings/advanced-tab/tests/advanced-tab-component.test.js @@ -10,10 +10,10 @@ describe('AdvancedTab Component', function () { const root = shallow( {}} - setIpfsGateway={() => {}} - setShowFiatConversionOnTestnetsPreference={() => {}} - setThreeBoxSyncingPermission={() => {}} + setAutoLockTimeLimit={() => undefined} + setIpfsGateway={() => undefined} + setShowFiatConversionOnTestnetsPreference={() => undefined} + setThreeBoxSyncingPermission={() => undefined} threeBoxDisabled threeBoxSyncingAllowed={false} />, @@ -33,9 +33,9 @@ describe('AdvancedTab Component', function () { {}} - setShowFiatConversionOnTestnetsPreference={() => {}} - setThreeBoxSyncingPermission={() => {}} + setIpfsGateway={() => undefined} + setShowFiatConversionOnTestnetsPreference={() => undefined} + setThreeBoxSyncingPermission={() => undefined} threeBoxDisabled threeBoxSyncingAllowed={false} />, diff --git a/ui/app/pages/settings/contact-list-tab/contact-list-tab.component.js b/ui/app/pages/settings/contact-list-tab/contact-list-tab.component.js index 835963a83..dfcb35c19 100644 --- a/ui/app/pages/settings/contact-list-tab/contact-list-tab.component.js +++ b/ui/app/pages/settings/contact-list-tab/contact-list-tab.component.js @@ -121,6 +121,7 @@ export default class ContactListTab extends Component { } else if (!hideAddressBook && showingMyAccounts) { return () } + return null } render () { diff --git a/ui/app/pages/settings/contact-list-tab/contact-list-tab.container.js b/ui/app/pages/settings/contact-list-tab/contact-list-tab.container.js index d3bb1799a..63a7db52d 100644 --- a/ui/app/pages/settings/contact-list-tab/contact-list-tab.container.js +++ b/ui/app/pages/settings/contact-list-tab/contact-list-tab.container.js @@ -20,7 +20,7 @@ const mapStateToProps = (state, ownProps) => { const { location } = ownProps const { pathname } = location - const pathNameTail = pathname.match(/[^/]+$/)[0] + const pathNameTail = pathname.match(/[^/]+$/u)[0] const pathNameTailIsAddress = pathNameTail.includes('0x') const viewingContact = Boolean(pathname.match(CONTACT_VIEW_ROUTE) || pathname.match(CONTACT_MY_ACCOUNTS_VIEW_ROUTE)) diff --git a/ui/app/pages/settings/contact-list-tab/edit-contact/edit-contact.container.js b/ui/app/pages/settings/contact-list-tab/edit-contact/edit-contact.container.js index 3766f1ac8..4cd7bd59e 100644 --- a/ui/app/pages/settings/contact-list-tab/edit-contact/edit-contact.container.js +++ b/ui/app/pages/settings/contact-list-tab/edit-contact/edit-contact.container.js @@ -15,7 +15,7 @@ import { addToAddressBook, removeFromAddressBook, setAccountLabel } from '../../ const mapStateToProps = (state, ownProps) => { const { location } = ownProps const { pathname } = location - const pathNameTail = pathname.match(/[^/]+$/)[0] + const pathNameTail = pathname.match(/[^/]+$/u)[0] const pathNameTailIsAddress = pathNameTail.includes('0x') const address = pathNameTailIsAddress ? pathNameTail.toLowerCase() : ownProps.match.params.id diff --git a/ui/app/pages/settings/contact-list-tab/index.scss b/ui/app/pages/settings/contact-list-tab/index.scss index 02273a66f..9c33c3701 100644 --- a/ui/app/pages/settings/contact-list-tab/index.scss +++ b/ui/app/pages/settings/contact-list-tab/index.scss @@ -33,7 +33,6 @@ &__header, &__header--edit { &__name { - font-family: Roboto; font-style: normal; font-weight: normal; font-size: 24px; @@ -179,7 +178,6 @@ } &__header { - font-family: Roboto; font-style: normal; font-weight: normal; font-size: 18px; @@ -193,7 +191,6 @@ } &__text { - font-family: Roboto; font-style: normal; font-weight: normal; font-size: 14px; diff --git a/ui/app/pages/settings/contact-list-tab/view-contact/view-contact.component.js b/ui/app/pages/settings/contact-list-tab/view-contact/view-contact.component.js index ce9312c87..9b3e9a17c 100644 --- a/ui/app/pages/settings/contact-list-tab/view-contact/view-contact.component.js +++ b/ui/app/pages/settings/contact-list-tab/view-contact/view-contact.component.js @@ -15,7 +15,7 @@ function quadSplit (address) { '0x ' + address .slice(2) - .match(/.{1,4}/g) + .match(/.{1,4}/ug) .join(' ') ) } diff --git a/ui/app/pages/settings/contact-list-tab/view-contact/view-contact.container.js b/ui/app/pages/settings/contact-list-tab/view-contact/view-contact.container.js index 7f7c5d8c1..33579d154 100644 --- a/ui/app/pages/settings/contact-list-tab/view-contact/view-contact.container.js +++ b/ui/app/pages/settings/contact-list-tab/view-contact/view-contact.container.js @@ -15,7 +15,7 @@ import { const mapStateToProps = (state, ownProps) => { const { location } = ownProps const { pathname } = location - const pathNameTail = pathname.match(/[^/]+$/)[0] + const pathNameTail = pathname.match(/[^/]+$/u)[0] const pathNameTailIsAddress = pathNameTail.includes('0x') const address = pathNameTailIsAddress ? pathNameTail.toLowerCase() : ownProps.match.params.id diff --git a/ui/app/pages/settings/index.scss b/ui/app/pages/settings/index.scss index 0c4371cf4..b72deb39e 100644 --- a/ui/app/pages/settings/index.scss +++ b/ui/app/pages/settings/index.scss @@ -70,7 +70,6 @@ } &__sub-header-text { - font-family: Roboto; font-style: normal; font-weight: normal; font-size: 20px; diff --git a/ui/app/pages/settings/networks-tab/index.scss b/ui/app/pages/settings/networks-tab/index.scss index 92504f641..e539ece40 100644 --- a/ui/app/pages/settings/networks-tab/index.scss +++ b/ui/app/pages/settings/networks-tab/index.scss @@ -96,7 +96,6 @@ } &__network-form-label { - font-family: Roboto; font-style: normal; font-weight: normal; font-size: 14px; @@ -177,7 +176,6 @@ &__networks-list-name { margin-left: 11px; - font-family: Roboto; font-style: normal; font-weight: normal; font-size: 16px; diff --git a/ui/app/pages/settings/networks-tab/network-form/network-form.component.js b/ui/app/pages/settings/networks-tab/network-form/network-form.component.js index 34209983a..8f029771f 100644 --- a/ui/app/pages/settings/networks-tab/network-form/network-form.component.js +++ b/ui/app/pages/settings/networks-tab/network-form/network-form.component.js @@ -214,7 +214,7 @@ export default class NetworkForm extends PureComponent { isValidWhenAppended = (url) => { const appendedRpc = `http://${url}` - return validUrl.isWebUri(appendedRpc) && !url.match(/^https?:\/\/$/) + return validUrl.isWebUri(appendedRpc) && !url.match(/^https?:\/\/$/u) } validateBlockExplorerURL = (url, stateKey) => { diff --git a/ui/app/pages/settings/security-tab/tests/security-tab.test.js b/ui/app/pages/settings/security-tab/tests/security-tab.test.js index 1ac996d05..d5720aa6a 100644 --- a/ui/app/pages/settings/security-tab/tests/security-tab.test.js +++ b/ui/app/pages/settings/security-tab/tests/security-tab.test.js @@ -28,7 +28,7 @@ describe('Security Tab', function () { , { context: { t: (str) => str, - metricsEvent: () => {}, + metricsEvent: () => undefined, }, }, ) diff --git a/ui/app/pages/settings/settings-tab/settings-tab.component.js b/ui/app/pages/settings/settings-tab/settings-tab.component.js index 39d67b5f9..2e3c7f220 100644 --- a/ui/app/pages/settings/settings-tab/settings-tab.component.js +++ b/ui/app/pages/settings/settings-tab/settings-tab.component.js @@ -1,6 +1,6 @@ import React, { PureComponent } from 'react' import PropTypes from 'prop-types' -import availableCurrencies from '../../../helpers/constants/available-conversions' +import availableCurrencies from '../../../helpers/constants/available-conversions.json' import SimpleDropdown from '../../../components/app/dropdowns/simple-dropdown' import ToggleButton from '../../../components/ui/toggle-button' import locales from '../../../../../app/_locales/index.json' diff --git a/ui/app/pages/settings/settings.container.js b/ui/app/pages/settings/settings.container.js index ebeb2ae4b..e0b3cfbaf 100644 --- a/ui/app/pages/settings/settings.container.js +++ b/ui/app/pages/settings/settings.container.js @@ -42,7 +42,7 @@ const ROUTES_TO_I18N_KEYS = { const mapStateToProps = (state, ownProps) => { const { location } = ownProps const { pathname } = location - const pathNameTail = pathname.match(/[^/]+$/)[0] + const pathNameTail = pathname.match(/[^/]+$/u)[0] const isAddressEntryPage = pathNameTail.includes('0x') const isMyAccountsPage = pathname.match('my-accounts') diff --git a/ui/app/pages/token/fee-card/fee-card.js b/ui/app/pages/token/fee-card/fee-card.js new file mode 100644 index 000000000..42e751d77 --- /dev/null +++ b/ui/app/pages/token/fee-card/fee-card.js @@ -0,0 +1,69 @@ +import React from 'react' +import PropTypes from 'prop-types' + +export default function FeeCard ({ + onFeeRowClick = null, + feeRowText, + feeRowLinkText = '', + primaryFee, + secondaryFee = '', + onSecondRowClick = null, + secondRowText = '', + secondRowLinkText = '', + hideSecondRow = false, +}) { + return ( +
+
+
onFeeRowClick && onFeeRowClick()}> +
+
+ {feeRowText} +
+ {onFeeRowClick && ( +
+ {feeRowLinkText} +
+ )} +
+
+
+ {primaryFee} +
+ {secondaryFee && ( +
+ {secondaryFee} +
+ )} +
+
+ {!hideSecondRow && secondRowText && ( +
+
+
+ {secondRowText} +
+ {secondRowLinkText && ( +
onSecondRowClick && onSecondRowClick()}> + {secondRowLinkText} +
+ )} +
+
+ )} +
+
+ ) +} + +FeeCard.propTypes = { + onFeeRowClick: PropTypes.func, + feeRowText: PropTypes.string.isRequired, + feeRowLinkText: PropTypes.string, + primaryFee: PropTypes.string.isRequired, + secondaryFee: PropTypes.string, + onSecondRowClick: PropTypes.func, + secondRowText: PropTypes.string, + secondRowLinkText: PropTypes.string, + hideSecondRow: PropTypes.bool, +} diff --git a/ui/app/pages/token/fee-card/fee-card.stories.js b/ui/app/pages/token/fee-card/fee-card.stories.js new file mode 100644 index 000000000..3e5b854bc --- /dev/null +++ b/ui/app/pages/token/fee-card/fee-card.stories.js @@ -0,0 +1,47 @@ +import React from 'react' +import FeeCard from './fee-card' +import { action } from '@storybook/addon-actions' +import { text } from '@storybook/addon-knobs/react' + +const containerStyle = { + width: '300px', +} + +export default { + title: 'FeeCard', +} + +export const WithSecondRow = () => { + return ( +
+ +
+ ) +} + +export const WithoutSecondRow = () => { + return ( +
+ +
+ ) +} diff --git a/ui/app/pages/token/fee-card/index.js b/ui/app/pages/token/fee-card/index.js new file mode 100644 index 000000000..84bc1acbb --- /dev/null +++ b/ui/app/pages/token/fee-card/index.js @@ -0,0 +1 @@ +export { default } from './fee-card' diff --git a/ui/app/pages/token/fee-card/index.scss b/ui/app/pages/token/fee-card/index.scss new file mode 100644 index 000000000..d9acd2554 --- /dev/null +++ b/ui/app/pages/token/fee-card/index.scss @@ -0,0 +1,102 @@ +.fee-card { + border-radius: 8px; + border: 1px solid $Grey-100; + width: 100%; + margin-top: auto; + margin-bottom: 8px; + + @include H7; + + &__main { + padding: 16px 16px 12px 16px; + } + + &__row-header { + display: flex; + align-items: center; + margin-top: 8px; + justify-content: space-between; + + @media screen and (min-width: 576px) { + @include H6; + } + + &:first-of-type { + margin-top: 0; + } + + div { + display: flex; + align-items: center; + } + } + + &__row-header-text { + font-weight: bold; + margin-right: 8px; + cursor: pointer; + } + + &__row { + display: flex; + align-items: center; + justify-content: space-between; + margin-top: 8px; + } + + &__row-label { + display: flex; + align-items: center; + + img { + height: 10px; + width: 10px; + margin-left: 4px; + cursor: pointer; + } + } + + &__row-text { + margin-right: 8px; + } + + &__row-fee { + margin-right: 4px; + } + + &__link { + color: $Blue-500; + cursor: pointer; + } + + &__total-box { + border-top: 1px solid $Grey-100; + padding: 12px 16px 16px 16px; + } + + &__total-row { + display: flex; + justify-content: space-between; + align-items: center; + font-weight: bold; + } + + &__total-secondary { + width: 100%; + display: flex; + justify-content: flex-end; + font-weight: bold; + color: $Grey-500; + margin-top: 4px; + } + + &__row-header-secondary { + color: $Grey-500; + margin-right: 20px; + } + + &__row-header-primary { + font-weight: bold; + color: $Grey-500; + } +} diff --git a/ui/app/pages/token/index.scss b/ui/app/pages/token/index.scss new file mode 100644 index 000000000..013ff3928 --- /dev/null +++ b/ui/app/pages/token/index.scss @@ -0,0 +1 @@ +@import 'fee-card/index'; diff --git a/ui/app/selectors/permissions.js b/ui/app/selectors/permissions.js index d42081153..47d7857da 100644 --- a/ui/app/selectors/permissions.js +++ b/ui/app/selectors/permissions.js @@ -261,10 +261,10 @@ export function getPermissionsMetadataHostCounts (state) { const metadata = getPermissionDomainsMetadata(state) return Object.values(metadata).reduce((counts, { host }) => { if (host) { - if (!counts[host]) { - counts[host] = 1 - } else { + if (counts[host]) { counts[host] += 1 + } else { + counts[host] = 1 } } return counts diff --git a/ui/app/store/actionConstants.js b/ui/app/store/actionConstants.js index 4a11aa111..ac7cc11a0 100644 --- a/ui/app/store/actionConstants.js +++ b/ui/app/store/actionConstants.js @@ -36,6 +36,7 @@ export const SET_CURRENT_FIAT = 'SET_CURRENT_FIAT' export const SHOW_SEND_TOKEN_PAGE = 'SHOW_SEND_TOKEN_PAGE' export const SHOW_PRIVATE_KEY = 'SHOW_PRIVATE_KEY' export const SET_ACCOUNT_LABEL = 'SET_ACCOUNT_LABEL' +export const CLEAR_ACCOUNT_DETAILS = 'CLEAR_ACCOUNT_DETAILS' // tx conf screen export const COMPLETED_TX = 'COMPLETED_TX' export const TRANSACTION_ERROR = 'TRANSACTION_ERROR' diff --git a/ui/app/store/actions.js b/ui/app/store/actions.js index 49a43da24..c9c4a63dd 100644 --- a/ui/app/store/actions.js +++ b/ui/app/store/actions.js @@ -46,7 +46,8 @@ export function tryUnlockMetamask (password) { return new Promise((resolve, reject) => { background.submitPassword(password, (error) => { if (error) { - return reject(error) + reject(error) + return } resolve() @@ -61,7 +62,8 @@ export function tryUnlockMetamask (password) { background.verifySeedPhrase((err) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } resolve() @@ -87,7 +89,8 @@ export function createNewVaultAndRestore (password, seed) { return new Promise((resolve, reject) => { background.createNewVaultAndRestore(password, seed, (err, _vault) => { if (err) { - return reject(err) + reject(err) + return } vault = _vault resolve() @@ -146,7 +149,8 @@ export function submitPassword (password) { return new Promise((resolve, reject) => { background.submitPassword(password, (error) => { if (error) { - return reject(error) + reject(error) + return } resolve() @@ -158,7 +162,8 @@ export function createNewVault (password) { return new Promise((resolve, reject) => { background.createNewVaultAndKeychain(password, (error) => { if (error) { - return reject(error) + reject(error) + return } resolve(true) @@ -170,7 +175,8 @@ export function verifyPassword (password) { return new Promise((resolve, reject) => { background.verifyPassword(password, (error) => { if (error) { - return reject(error) + reject(error) + return } resolve(true) @@ -182,7 +188,8 @@ export function verifySeedPhrase () { return new Promise((resolve, reject) => { background.verifySeedPhrase((error, seedWords) => { if (error) { - return reject(error) + reject(error) + return } resolve(seedWords) @@ -228,7 +235,8 @@ export function fetchInfoToSync () { background.fetchInfoToSync((err, result) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } resolve(result) }) @@ -245,7 +253,8 @@ export function resetAccount () { dispatch(hideLoadingIndication()) if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } log.info('Transaction history reset for ' + account) @@ -264,9 +273,11 @@ export function removeAccount (address) { await new Promise((resolve, reject) => { background.removeAccount(address, (error, account) => { if (error) { - return reject(error) + reject(error) + return } - return resolve(account) + resolve(account) + return }) }) await forceUpdateMetamaskState(dispatch) @@ -395,11 +406,13 @@ export function unlockHardwareWalletAccount (index, deviceName, hdPath) { if (err) { log.error(err) dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } dispatch(hideLoadingIndication()) - return resolve() + resolve() + return }) }) } @@ -576,7 +589,8 @@ export function signTx (txData) { return (dispatch) => { global.ethQuery.sendTransaction(txData, (err) => { if (err) { - return dispatch(displayWarning(err.message)) + dispatch(displayWarning(err.message)) + return } }) dispatch(showConfTxPage()) @@ -776,7 +790,8 @@ const updateMetamaskStateFromBackground = () => { return new Promise((resolve, reject) => { background.getState((error, newState) => { if (error) { - return reject(error) + reject(error) + return } resolve(newState) @@ -795,7 +810,8 @@ export function updateTransaction (txData) { dispatch(txError(err)) dispatch(goHome()) log.error(err.message) - return reject(err) + reject(err) + return } resolve(txData) @@ -823,7 +839,8 @@ export function updateAndApproveTx (txData) { dispatch(txError(err)) dispatch(goHome()) log.error(err.message) - return reject(err) + reject(err) + return } resolve(txData) @@ -975,7 +992,8 @@ export function cancelTx (txData) { return new Promise((resolve, reject) => { background.cancelTransaction(txData.id, (err) => { if (err) { - return reject(err) + reject(err) + return } resolve() @@ -1006,7 +1024,8 @@ export function cancelTxs (txDataList) { const cancellations = txIds.map((id) => new Promise((resolve, reject) => { background.cancelTransaction(id, (err) => { if (err) { - return reject(err) + reject(err) + return } resolve() @@ -1025,7 +1044,8 @@ export function cancelTxs (txDataList) { dispatch(hideLoadingIndication()) if (getEnvironmentType() === ENVIRONMENT_TYPE_NOTIFICATION) { - return global.platform.closeCurrentWindow() + global.platform.closeCurrentWindow() + return } } } @@ -1036,9 +1056,11 @@ export function markPasswordForgotten () { await new Promise((resolve, reject) => { return background.markPasswordForgotten((error) => { if (error) { - return reject(error) + reject(error) + return } - return resolve() + resolve() + return }) }) } finally { @@ -1130,7 +1152,8 @@ const backgroundSetLocked = () => { return new Promise((resolve, reject) => { background.setLocked((error) => { if (error) { - return reject(error) + reject(error) + return } resolve() }) @@ -1220,7 +1243,8 @@ export function addPermittedAccount (origin, address) { await new Promise((resolve, reject) => { background.addPermittedAccount(origin, address, (error) => { if (error) { - return reject(error) + reject(error) + return } resolve() }) @@ -1234,7 +1258,8 @@ export function removePermittedAccount (origin, address) { await new Promise((resolve, reject) => { background.removePermittedAccount(origin, address, (error) => { if (error) { - return reject(error) + reject(error) + return } resolve() }) @@ -1264,7 +1289,8 @@ export function addToken (address, symbol, decimals, image) { dispatch(hideLoadingIndication()) if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } dispatch(updateTokens(tokens)) resolve(tokens) @@ -1281,7 +1307,8 @@ export function removeToken (address) { dispatch(hideLoadingIndication()) if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } dispatch(updateTokens(tokens)) resolve(tokens) @@ -1319,7 +1346,8 @@ export function removeSuggestedTokens () { } dispatch(clearPendingTokens()) if (getEnvironmentType() === ENVIRONMENT_TYPE_NOTIFICATION) { - return global.platform.closeCurrentWindow() + global.platform.closeCurrentWindow() + return } resolve(suggestedTokens) }) @@ -1357,7 +1385,8 @@ export function createCancelTransaction (txId, customGasPrice) { background.createCancelTransaction(txId, customGasPrice, (err, newState) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } const { currentNetworkTxList } = newState @@ -1380,7 +1409,8 @@ export function createSpeedUpTransaction (txId, customGasPrice, customGasLimit) background.createSpeedUpTransaction(txId, customGasPrice, customGasLimit, (err, newState) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } const { currentNetworkTxList } = newState @@ -1402,7 +1432,8 @@ export function createRetryTransaction (txId, customGasPrice, customGasLimit) { background.createSpeedUpTransaction(txId, customGasPrice, customGasLimit, (err, newState) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } const { currentNetworkTxList } = newState @@ -1517,7 +1548,8 @@ export function delRpcTarget (oldRpc) { if (err) { log.error(err) dispatch(displayWarning('Had a problem removing network!')) - return reject(err) + reject(err) + return } resolve() }) @@ -1541,7 +1573,8 @@ export function addToAddressBook (recipient, nickname = '', memo = '') { throw error } if (!set) { - return dispatch(displayWarning('Address book failed to update')) + dispatch(displayWarning('Address book failed to update')) + return } } } @@ -1688,21 +1721,24 @@ export function exportAccount (password, address) { log.error('Error in submitting password.') dispatch(hideLoadingIndication()) dispatch(displayWarning('Incorrect Password.')) - return reject(err) + reject(err) + return } log.debug(`background.exportAccount`) - return background.exportAccount(address, function (err, result) { + background.exportAccount(address, function (err, result) { dispatch(hideLoadingIndication()) if (err) { log.error(err) dispatch(displayWarning('Had a problem exporting the account.')) - return reject(err) + reject(err) + return } dispatch(showPrivateKey(result)) - return resolve(result) + resolve(result) + return }) }) }) @@ -1716,22 +1752,24 @@ export function exportAccounts (password, addresses) { background.submitPassword(password, function (err) { if (err) { log.error('Error in submitting password.') - return reject(err) + reject(err) + return } log.debug(`background.exportAccounts`) - const accountPromises = addresses.map((address) => - new Promise( - (resolve, reject) => background.exportAccount(address, function (err, result) { - if (err) { - log.error(err) - dispatch(displayWarning('Had a problem exporting the account.')) - return reject(err) - } - return resolve(result) - }), - ), - ) - return resolve(Promise.all(accountPromises)) + const accountPromises = addresses.map((address) => new Promise( + (resolve, reject) => background.exportAccount(address, function (err, result) { + if (err) { + log.error(err) + dispatch(displayWarning('Had a problem exporting the account.')) + reject(err) + return + } + resolve(result) + return + }), + )) + resolve(Promise.all(accountPromises)) + return }) }) } @@ -1755,7 +1793,8 @@ export function setAccountLabel (account, label) { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } dispatch({ @@ -1769,6 +1808,12 @@ export function setAccountLabel (account, label) { } } +export function clearAccountDetails () { + return { + type: actionConstants.CLEAR_ACCOUNT_DETAILS, + } +} + export function showSendTokenPage () { return { type: actionConstants.SHOW_SEND_TOKEN_PAGE, @@ -1793,7 +1838,8 @@ export function setFeatureFlag (feature, activated, notificationType) { dispatch(hideLoadingIndication()) if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } dispatch(updateFeatureFlags(updatedFeatureFlags)) notificationType && dispatch(showModal({ name: notificationType })) @@ -1819,7 +1865,8 @@ export function setPreference (preference, value) { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } dispatch(updatePreferences(updatedPreferences)) @@ -1912,7 +1959,8 @@ export function setParticipateInMetaMetrics (val) { log.debug(err) if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } dispatch({ @@ -1933,7 +1981,8 @@ export function setMetaMetricsSendCount (val) { background.setMetaMetricsSendCount(val, (err) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } dispatch({ @@ -1954,7 +2003,8 @@ export function setUseBlockie (val) { background.setUseBlockie(val, (err) => { dispatch(hideLoadingIndication()) if (err) { - return dispatch(displayWarning(err.message)) + dispatch(displayWarning(err.message)) + return } }) dispatch({ @@ -1971,7 +2021,8 @@ export function setUseNonceField (val) { background.setUseNonceField(val, (err) => { dispatch(hideLoadingIndication()) if (err) { - return dispatch(displayWarning(err.message)) + dispatch(displayWarning(err.message)) + return } }) dispatch({ @@ -1988,7 +2039,8 @@ export function setUsePhishDetect (val) { background.setUsePhishDetect(val, (err) => { dispatch(hideLoadingIndication()) if (err) { - return dispatch(displayWarning(err.message)) + dispatch(displayWarning(err.message)) + return } }) } @@ -2001,7 +2053,8 @@ export function setIpfsGateway (val) { background.setIpfsGateway(val, (err) => { dispatch(hideLoadingIndication()) if (err) { - return dispatch(displayWarning(err.message)) + dispatch(displayWarning(err.message)) + return } else { dispatch({ type: actionConstants.SET_IPFS_GATEWAY, @@ -2022,7 +2075,8 @@ export function updateCurrentLocale (key) { background.setCurrentLocale(key, (err, textDirection) => { if (err) { dispatch(hideLoadingIndication()) - return dispatch(displayWarning(err.message)) + dispatch(displayWarning(err.message)) + return } switchDirection(textDirection) dispatch(setCurrentLocale(key, localeMessages)) @@ -2086,9 +2140,10 @@ export function rejectPermissionsRequest (requestId) { background.rejectPermissionsRequest(requestId, (err) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } - return forceUpdateMetamaskState(dispatch) + forceUpdateMetamaskState(dispatch) .then(resolve) .catch(reject) }) @@ -2119,7 +2174,8 @@ export function setFirstTimeFlowType (type) { log.debug(`background.setFirstTimeFlowType`) background.setFirstTimeFlowType(type, (err) => { if (err) { - return dispatch(displayWarning(err.message)) + dispatch(displayWarning(err.message)) + return } }) dispatch({ @@ -2147,7 +2203,8 @@ export function setLastActiveTime () { return (dispatch) => { background.setLastActiveTime((err) => { if (err) { - return dispatch(displayWarning(err.message)) + dispatch(displayWarning(err.message)) + return } }) } @@ -2252,9 +2309,10 @@ export function setSeedPhraseBackedUp (seedPhraseBackupState) { background.setSeedPhraseBackedUp(seedPhraseBackupState, (err) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } - return forceUpdateMetamaskState(dispatch) + forceUpdateMetamaskState(dispatch) .then(resolve) .catch(reject) }) @@ -2268,7 +2326,8 @@ export function initializeThreeBox () { background.initializeThreeBox((err) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } resolve() }) @@ -2282,7 +2341,8 @@ export function setShowRestorePromptToFalse () { background.setShowRestorePromptToFalse((err) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } resolve() }) @@ -2296,7 +2356,8 @@ export function turnThreeBoxSyncingOn () { background.turnThreeBoxSyncingOn((err) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } resolve() }) @@ -2310,7 +2371,8 @@ export function restoreFromThreeBox (accountAddress) { background.restoreFromThreeBox(accountAddress, (err) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } resolve() }) @@ -2324,7 +2386,8 @@ export function getThreeBoxLastUpdated () { background.getThreeBoxLastUpdated((err, lastUpdated) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } resolve(lastUpdated) }) @@ -2338,7 +2401,8 @@ export function setThreeBoxSyncingPermission (threeBoxSyncingAllowed) { background.setThreeBoxSyncingPermission(threeBoxSyncingAllowed, (err) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } resolve() }) @@ -2368,7 +2432,8 @@ export function getNextNonce () { background.getNextNonce(address, (err, nextNonce) => { if (err) { dispatch(displayWarning(err.message)) - return reject(err) + reject(err) + return } dispatch(setNextNonce(nextNonce)) resolve(nextNonce) diff --git a/ui/index.js b/ui/index.js index bc61913b2..e771624be 100644 --- a/ui/index.js +++ b/ui/index.js @@ -28,7 +28,8 @@ export default function launchMetamaskUi (opts, cb) { // check if we are unlocked first backgroundConnection.getState(function (err, metamaskState) { if (err) { - return cb(err) + cb(err) + return } startApp(metamaskState, backgroundConnection, opts) .then((store) => { @@ -188,7 +189,8 @@ window.logStateString = function (cb) { const state = window.getCleanAppState() global.platform.getPlatformInfo((err, platform) => { if (err) { - return cb(err) + cb(err) + return } state.platform = platform const stateString = JSON.stringify(state, null, 2) diff --git a/ui/lib/account-link.js b/ui/lib/account-link.js index 1f9ba293e..eadecdd3c 100644 --- a/ui/lib/account-link.js +++ b/ui/lib/account-link.js @@ -1,33 +1,23 @@ export default function getAccountLink (address, network, rpcPrefs) { if (rpcPrefs && rpcPrefs.blockExplorerUrl) { - return `${rpcPrefs.blockExplorerUrl.replace(/\/+$/, '')}/address/${address}` + return `${rpcPrefs.blockExplorerUrl.replace(/\/+$/u, '')}/address/${address}` } const net = parseInt(network) - let link switch (net) { case 1: // main net - link = `https://etherscan.io/address/${address}` - break + return `https://etherscan.io/address/${address}` case 2: // morden test net - link = `https://morden.etherscan.io/address/${address}` - break + return `https://morden.etherscan.io/address/${address}` case 3: // ropsten test net - link = `https://ropsten.etherscan.io/address/${address}` - break + return `https://ropsten.etherscan.io/address/${address}` case 4: // rinkeby test net - link = `https://rinkeby.etherscan.io/address/${address}` - break + return `https://rinkeby.etherscan.io/address/${address}` case 42: // kovan test net - link = `https://kovan.etherscan.io/address/${address}` - break + return `https://kovan.etherscan.io/address/${address}` case 5: // goerli test net - link = `https://goerli.etherscan.io/address/${address}` - break + return `https://goerli.etherscan.io/address/${address}` default: - link = '' - break + return '' } - - return link } diff --git a/yarn.lock b/yarn.lock index 9d4efe99f..8915372b2 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1851,6 +1851,13 @@ "@nodelib/fs.scandir" "2.1.3" fastq "^1.6.0" +"@npmcli/move-file@^1.0.1": + version "1.0.1" + resolved "https://registry.yarnpkg.com/@npmcli/move-file/-/move-file-1.0.1.tgz#de103070dac0f48ce49cf6693c23af59c0f70464" + integrity sha512-Uv6h1sT+0DrblvIrolFtbvM1FgWm+/sy4B3pvLp67Zys+thcukzS5ekn7HsZFGpWP4Q3fYJCljbWQE/XivMRLw== + dependencies: + mkdirp "^1.0.4" + "@popperjs/core@^2.4.0": version "2.4.0" resolved "https://registry.yarnpkg.com/@popperjs/core/-/core-2.4.0.tgz#0e1bdf8d021e7ea58affade33d9d607e11365915" @@ -2580,6 +2587,11 @@ resolved "https://registry.yarnpkg.com/@types/is-function/-/is-function-1.0.0.tgz#1b0b819b1636c7baf0d6785d030d12edf70c3e83" integrity sha512-iTs9HReBu7evG77Q4EC8hZnqRt57irBDkK9nvmHroiOIVwYMQc4IvYvdRgwKfYepunIY7Oh/dBuuld+Gj9uo6w== +"@types/json-schema@^7.0.4": + version "7.0.5" + resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.5.tgz#dcce4430e64b443ba8945f0290fb564ad5bac6dd" + integrity sha512-7+2BITlgjgDhH0vvwZU/HZJVyk+2XUlvxXe8dFMedNX/aMkaOq++rMAFXc0tM7ij15QaWlbdQASBR9dihi+bDQ== + "@types/json5@^0.0.29": version "0.0.29" resolved "https://registry.yarnpkg.com/@types/json5/-/json5-0.0.29.tgz#ee28707ae94e11d2b827bcbe5270bcea7f3e71ee" @@ -3351,22 +3363,12 @@ ajv@^5.1.0: fast-json-stable-stringify "^2.0.0" json-schema-traverse "^0.3.0" -ajv@^6.1.0: - version "6.10.0" - resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.10.0.tgz#90d0d54439da587cd7e843bfb7045f50bd22bdf1" - integrity sha512-nffhOpkymDECQyR0mnsUtoCE8RlX38G0rYP+wgLWFyZuUyuuojSSvi/+euOiQBIn63whYwYVIIH1TvE3tu4OEg== +ajv@^6.1.0, ajv@^6.10.0, ajv@^6.12.2, ajv@^6.9.1: + version "6.12.3" + resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.12.3.tgz#18c5af38a111ddeb4f2697bd78d68abc1cabd706" + integrity sha512-4K0cK3L1hsqk9xIb2z9vs/XU+PGJZ9PNpJRDS9YLzmNdX6jmVPfamLvTJr0aDAusnHyCHO6MjzlkAsgtqp9teA== dependencies: - fast-deep-equal "^2.0.1" - fast-json-stable-stringify "^2.0.0" - json-schema-traverse "^0.4.1" - uri-js "^4.2.2" - -ajv@^6.10.0, ajv@^6.9.1: - version "6.10.1" - resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.10.1.tgz#ebf8d3af22552df9dd049bfbe50cc2390e823593" - integrity sha512-w1YQaVGNC6t2UCPjEawK/vo/dG8OOrVtUmhBT1uJJYxbl5kU2Tj3v6LGqBcsysN1yhuCStJCCA3GqdvKY8sqXQ== - dependencies: - fast-deep-equal "^2.0.1" + fast-deep-equal "^3.1.1" fast-json-stable-stringify "^2.0.0" json-schema-traverse "^0.4.1" uri-js "^4.2.2" @@ -6084,27 +6086,6 @@ cacache@^12.0.2: unique-filename "^1.1.1" y18n "^4.0.0" -cacache@^12.0.3: - version "12.0.4" - resolved "https://registry.yarnpkg.com/cacache/-/cacache-12.0.4.tgz#668bcbd105aeb5f1d92fe25570ec9525c8faa40c" - integrity sha512-a0tMB40oefvuInr4Cwb3GerbL9xTj1D5yg0T5xrjGCGyfvbxseIXX7BAO/u/hIXdafzOI5JC3wDwHyf24buOAQ== - dependencies: - bluebird "^3.5.5" - chownr "^1.1.1" - figgy-pudding "^3.5.1" - glob "^7.1.4" - graceful-fs "^4.1.15" - infer-owner "^1.0.3" - lru-cache "^5.1.1" - mississippi "^3.0.0" - mkdirp "^0.5.1" - move-concurrently "^1.0.1" - promise-inflight "^1.0.1" - rimraf "^2.6.3" - ssri "^6.0.1" - unique-filename "^1.1.1" - y18n "^4.0.0" - cacache@^13.0.1: version "13.0.1" resolved "https://registry.yarnpkg.com/cacache/-/cacache-13.0.1.tgz#a8000c21697089082f85287a1aec6e382024a71c" @@ -6129,6 +6110,29 @@ cacache@^13.0.1: ssri "^7.0.0" unique-filename "^1.1.1" +cacache@^15.0.4: + version "15.0.5" + resolved "https://registry.yarnpkg.com/cacache/-/cacache-15.0.5.tgz#69162833da29170d6732334643c60e005f5f17d0" + integrity sha512-lloiL22n7sOjEEXdL8NAjTgv9a1u43xICE9/203qonkZUCj5X1UEWIdf2/Y0d6QcCtMzbKQyhrcDbdvlZTs/+A== + dependencies: + "@npmcli/move-file" "^1.0.1" + chownr "^2.0.0" + fs-minipass "^2.0.0" + glob "^7.1.4" + infer-owner "^1.0.4" + lru-cache "^6.0.0" + minipass "^3.1.1" + minipass-collect "^1.0.2" + minipass-flush "^1.0.5" + minipass-pipeline "^1.2.2" + mkdirp "^1.0.3" + p-map "^4.0.0" + promise-inflight "^1.0.1" + rimraf "^3.0.2" + ssri "^8.0.0" + tar "^6.0.2" + unique-filename "^1.1.1" + cache-base@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/cache-base/-/cache-base-1.0.1.tgz#0a7f46416831c8b662ee36fe4e7c59d76f666ab2" @@ -6571,6 +6575,11 @@ chownr@^1.1.2: resolved "https://registry.yarnpkg.com/chownr/-/chownr-1.1.3.tgz#42d837d5239688d55f303003a508230fa6727142" integrity sha512-i70fVHhmV3DtTl6nqvZOnIjbY0Pe4kAUjwHj8z0zAdgBtYrJyYwLKCCuRBQ5ppkyL0AkN7HKRnETdmdp1zqNXw== +chownr@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/chownr/-/chownr-2.0.0.tgz#15bfbe53d2eab4cf70f18a8cd68ebe5b3cb1dece" + integrity sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ== + chrome-trace-event@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/chrome-trace-event/-/chrome-trace-event-1.0.2.tgz#234090ee97c7d4ad1a2c4beae27505deffc608a4" @@ -7290,23 +7299,22 @@ copy-to-clipboard@^3.0.8: dependencies: toggle-selection "^1.0.3" -copy-webpack-plugin@^5.1.1: - version "5.1.1" - resolved "https://registry.yarnpkg.com/copy-webpack-plugin/-/copy-webpack-plugin-5.1.1.tgz#5481a03dea1123d88a988c6ff8b78247214f0b88" - integrity sha512-P15M5ZC8dyCjQHWwd4Ia/dm0SgVvZJMYeykVIVYXbGyqO4dWB5oyPHp9i7wjwo5LhtlhKbiBCdS2NvM07Wlybg== +copy-webpack-plugin@^6.0.3: + version "6.0.3" + resolved "https://registry.yarnpkg.com/copy-webpack-plugin/-/copy-webpack-plugin-6.0.3.tgz#2b3d2bfc6861b96432a65f0149720adbd902040b" + integrity sha512-q5m6Vz4elsuyVEIUXr7wJdIdePWTubsqVbEMvf1WQnHGv0Q+9yPRu7MtYFPt+GBOXRav9lvIINifTQ1vSCs+eA== dependencies: - cacache "^12.0.3" - find-cache-dir "^2.1.0" - glob-parent "^3.1.0" - globby "^7.1.1" - is-glob "^4.0.1" - loader-utils "^1.2.3" - minimatch "^3.0.4" + cacache "^15.0.4" + fast-glob "^3.2.4" + find-cache-dir "^3.3.1" + glob-parent "^5.1.1" + globby "^11.0.1" + loader-utils "^2.0.0" normalize-path "^3.0.0" - p-limit "^2.2.1" - schema-utils "^1.0.0" - serialize-javascript "^2.1.2" - webpack-log "^2.0.0" + p-limit "^3.0.1" + schema-utils "^2.7.0" + serialize-javascript "^4.0.0" + webpack-sources "^1.4.3" core-js-compat@^3.1.1: version "3.1.3" @@ -8681,13 +8689,6 @@ dir-glob@2.0.0: arrify "^1.0.1" path-type "^3.0.0" -dir-glob@^2.0.0: - version "2.2.2" - resolved "https://registry.yarnpkg.com/dir-glob/-/dir-glob-2.2.2.tgz#fa09f0694153c8918b18ba0deafae94769fc50c4" - integrity sha512-f9LBi5QWzIW3I6e//uxZoLBlUt9kcp66qo0sSCxL6YZKc75R1c4MFCoe/LaZiBGmgujvQdxc5Bn3QhfyvK5Hsw== - dependencies: - path-type "^3.0.0" - dir-glob@^3.0.1: version "3.0.1" resolved "https://registry.yarnpkg.com/dir-glob/-/dir-glob-3.0.1.tgz#56dbf73d992a4a93ba1584f4534063fd2e41717f" @@ -11182,6 +11183,11 @@ fast-deep-equal@^2.0.1: resolved "https://registry.yarnpkg.com/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz#7b05218ddf9667bf7f370bf7fdb2cb15fdd0aa49" integrity sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk= +fast-deep-equal@^3.1.1: + version "3.1.3" + resolved "https://registry.yarnpkg.com/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz#3a7d56b559d6cbc3eb512325244e619a65c6c525" + integrity sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q== + fast-future@~1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/fast-future/-/fast-future-1.0.2.tgz#8435a9aaa02d79248d17d704e76259301d99280a" @@ -11199,7 +11205,7 @@ fast-glob@^2.0.2: merge2 "^1.2.3" micromatch "^3.1.10" -fast-glob@^3.0.3, fast-glob@^3.1.1, fast-glob@^3.2.2: +fast-glob@^3.0.3, fast-glob@^3.1.1, fast-glob@^3.2.2, fast-glob@^3.2.4: version "3.2.4" resolved "https://registry.yarnpkg.com/fast-glob/-/fast-glob-3.2.4.tgz#d20aefbf99579383e7f3cc66529158c9b98554d3" integrity sha512-kr/Oo6PX51265qeuCYsyGypiO5uJFgBS0jksyG7FUeCyQzNwYnzrNIMR1NXfkZXsMYXYLRAHgISHBz8gQcxKHQ== @@ -11516,13 +11522,13 @@ find-cache-dir@^2.0.0, find-cache-dir@^2.1.0: make-dir "^2.0.0" pkg-dir "^3.0.0" -find-cache-dir@^3.0.0, find-cache-dir@^3.2.0: - version "3.2.0" - resolved "https://registry.yarnpkg.com/find-cache-dir/-/find-cache-dir-3.2.0.tgz#e7fe44c1abc1299f516146e563108fd1006c1874" - integrity sha512-1JKclkYYsf1q9WIJKLZa9S9muC+08RIjzAlLrK4QcYLJMS6mk9yombQ9qf+zJ7H9LS800k0s44L4sDq9VYzqyg== +find-cache-dir@^3.0.0, find-cache-dir@^3.2.0, find-cache-dir@^3.3.1: + version "3.3.1" + resolved "https://registry.yarnpkg.com/find-cache-dir/-/find-cache-dir-3.3.1.tgz#89b33fad4a4670daa94f855f7fbe31d6d84fe880" + integrity sha512-t2GDMt3oGC/v+BMwzmllWDuJF/xcDtE5j/fCGbqDD7OLuJkj0cfh1YSA5VKPvwMeLFLNDBkwOKZ2X85jGLVftQ== dependencies: commondir "^1.0.1" - make-dir "^3.0.0" + make-dir "^3.0.2" pkg-dir "^4.1.0" find-root@^1.1.0: @@ -12331,10 +12337,10 @@ glob-parent@^3.0.1, glob-parent@^3.1.0: is-glob "^3.1.0" path-dirname "^1.0.0" -glob-parent@^5.0.0, glob-parent@^5.1.0, glob-parent@~5.1.0: - version "5.1.0" - resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-5.1.0.tgz#5f4c1d1e748d30cd73ad2944b3577a81b081e8c2" - integrity sha512-qjtRgnIVmOfnKUE3NJAQEdk+lKrxfw8t5ke7SXtfMTHcjsBfOfWXCQfdb30zfDoZQ2IRSIiidmjtbHZPZ++Ihw== +glob-parent@^5.0.0, glob-parent@^5.1.0, glob-parent@^5.1.1, glob-parent@~5.1.0: + version "5.1.1" + resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-5.1.1.tgz#b6c1ef417c4e5663ea498f1c45afac6916bbc229" + integrity sha512-FnI+VGOpnlGHWZxthPGR+QhR78fuiK0sNLkHQv+bL9fQi57lNNdquIbna/WrfROrolq8GK5Ek6BiMwqL/voRYQ== dependencies: is-glob "^4.0.1" @@ -12595,18 +12601,6 @@ globby@^6.1.0: pify "^2.0.0" pinkie-promise "^2.0.0" -globby@^7.1.1: - version "7.1.1" - resolved "https://registry.yarnpkg.com/globby/-/globby-7.1.1.tgz#fb2ccff9401f8600945dfada97440cca972b8680" - integrity sha1-+yzP+UAfhgCUXfral0QMypcrhoA= - dependencies: - array-union "^1.0.1" - dir-glob "^2.0.0" - glob "^7.1.2" - ignore "^3.3.5" - pify "^3.0.0" - slash "^1.0.0" - globjoin@^0.1.4: version "0.1.4" resolved "https://registry.yarnpkg.com/globjoin/-/globjoin-0.1.4.tgz#2f4494ac8919e3767c5cbb691e9f463324285d43" @@ -15551,13 +15545,13 @@ jed@1.1.1: resolved "https://registry.yarnpkg.com/jed/-/jed-1.1.1.tgz#7a549bbd9ffe1585b0cd0a191e203055bee574b4" integrity sha1-elSbvZ/+FYWwzQoZHiAwVb7ldLQ= -jest-worker@^24.9.0: - version "24.9.0" - resolved "https://registry.yarnpkg.com/jest-worker/-/jest-worker-24.9.0.tgz#5dbfdb5b2d322e98567898238a9697bcce67b3e5" - integrity sha512-51PE4haMSXcHohnSMdM42anbvZANYTqMrr52tVKPqqsPJMzoP6FYYDVqahX/HrAoKEKz3uUPzSvKs9A3qR4iVw== +jest-worker@^25.4.0: + version "25.5.0" + resolved "https://registry.yarnpkg.com/jest-worker/-/jest-worker-25.5.0.tgz#2611d071b79cea0f43ee57a3d118593ac1547db1" + integrity sha512-/dsSmUkIy5EBGfv/IjjqmFxrNAUpBERfGs1oHROyD7yxjG/w+t0GOJDX8O1k32ySmd7+a5IhnJU2qQFcJ4n1vw== dependencies: merge-stream "^2.0.0" - supports-color "^6.1.0" + supports-color "^7.0.0" jmespath@^0.15.0: version "0.15.0" @@ -17123,6 +17117,15 @@ loader-utils@^1.0.1, loader-utils@^1.0.2, loader-utils@^1.1.0: emojis-list "^2.0.0" json5 "^0.5.0" +loader-utils@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/loader-utils/-/loader-utils-2.0.0.tgz#e4cace5b816d425a166b5f097e10cd12b36064b0" + integrity sha512-rP4F0h2RaWSvPEkD7BLDFQnvSf+nK+wr3ESUjNTyAGobqrijmW92zc+SO6d4p4B1wh7+B/Jg1mkQe5NYUEHtHQ== + dependencies: + big.js "^5.2.2" + emojis-list "^3.0.0" + json5 "^2.1.2" + locale-currency@0.0.1: version "0.0.1" resolved "https://registry.yarnpkg.com/locale-currency/-/locale-currency-0.0.1.tgz#c9e15a22ff575b4b4bb947a4bf92ac236bd1fe9b" @@ -17566,6 +17569,13 @@ lru-cache@^5.1.1: dependencies: yallist "^3.0.2" +lru-cache@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-6.0.0.tgz#6d6fe6570ebd96aaf90fcad1dafa3b2566db3a94" + integrity sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA== + dependencies: + yallist "^4.0.0" + lru-queue@0.1: version "0.1.0" resolved "https://registry.yarnpkg.com/lru-queue/-/lru-queue-0.1.0.tgz#2738bd9f0d3cf4f84490c5736c48699ac632cda3" @@ -17624,10 +17634,10 @@ make-dir@^2.0.0: pify "^4.0.1" semver "^5.6.0" -make-dir@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/make-dir/-/make-dir-3.0.0.tgz#1b5f39f6b9270ed33f9f054c5c0f84304989f801" - integrity sha512-grNJDhb8b1Jm1qeqW5R/O63wUo4UXo2v2HMic6YT9i/HBlF93S8jkMgH7yugvY9ABDShH4VZMn8I+U8+fCNegw== +make-dir@^3.0.0, make-dir@^3.0.2: + version "3.1.0" + resolved "https://registry.yarnpkg.com/make-dir/-/make-dir-3.1.0.tgz#415e967046b3a7f1d185277d84aa58203726a13f" + integrity sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw== dependencies: semver "^6.0.0" @@ -18243,6 +18253,14 @@ minizlib@^1.2.1: dependencies: minipass "^2.2.1" +minizlib@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/minizlib/-/minizlib-2.1.0.tgz#fd52c645301ef09a63a2c209697c294c6ce02cf3" + integrity sha512-EzTZN/fjSvifSX0SlqUERCN39o6T40AMarPbv0MrarSFtIITCBh7bi+dU8nxGFHuqs9jdIAeoYoKuQAAASsPPA== + dependencies: + minipass "^3.0.0" + yallist "^4.0.0" + mississippi@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/mississippi/-/mississippi-3.0.0.tgz#ea0a3291f97e0b5e8776b363d5f0a12d94c67022" @@ -18294,6 +18312,11 @@ mkdirp@*, mkdirp@0.5.5, "mkdirp@>=0.5 0", mkdirp@^0.5.0, mkdirp@^0.5.1, mkdirp@^ dependencies: minimist "^1.2.5" +mkdirp@^1.0.3, mkdirp@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-1.0.4.tgz#3eb5ed62622756d79a5f0e2a221dfebad75c2f7e" + integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw== + mocha@^7.2.0: version "7.2.0" resolved "https://registry.yarnpkg.com/mocha/-/mocha-7.2.0.tgz#01cc227b00d875ab1eed03a75106689cfed5a604" @@ -19941,13 +19964,20 @@ p-limit@^2.0.0, p-limit@^2.2.0: dependencies: p-try "^2.0.0" -p-limit@^2.2.1: +p-limit@^2.3.0: version "2.3.0" resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-2.3.0.tgz#3dd33c647a214fdfffd835933eb086da0dc21db1" integrity sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w== dependencies: p-try "^2.0.0" +p-limit@^3.0.1: + version "3.0.2" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-3.0.2.tgz#1664e010af3cadc681baafd3e2a437be7b0fb5fe" + integrity sha512-iwqZSOoWIW+Ew4kAGUlN16J4M7OB3ysMLSZtnhmqx7njIHFPlxWBX8xo3lVTyFVq6mI/lL9qt2IsN1sHwaxJkg== + dependencies: + p-try "^2.0.0" + p-locate@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-2.0.0.tgz#20a0103b222a70c8fd39cc2e580680f3dde5ec43" @@ -19993,6 +20023,13 @@ p-map@^3.0.0: dependencies: aggregate-error "^3.0.0" +p-map@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/p-map/-/p-map-4.0.0.tgz#bb2f95a5eda2ec168ec9274e06a747c3e2904d2b" + integrity sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ== + dependencies: + aggregate-error "^3.0.0" + p-map@~1.1.1: version "1.1.1" resolved "https://registry.yarnpkg.com/p-map/-/p-map-1.1.1.tgz#05f5e4ae97a068371bc2a5cc86bfbdbc19c4ae7a" @@ -23319,10 +23356,10 @@ rimraf@^2.6.3, rimraf@^2.7.1: dependencies: glob "^7.1.3" -rimraf@^3.0.0: - version "3.0.1" - resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-3.0.1.tgz#48d3d4cb46c80d388ab26cd61b1b466ae9ae225a" - integrity sha512-IQ4ikL8SjBiEDZfk+DFVwqRK8md24RWMEJkdSlgNLkyyAImcjf8SWvU1qFMDOb4igBClbTQ/ugPqXcRwdFTxZw== +rimraf@^3.0.0, rimraf@^3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-3.0.2.tgz#f1a5402ba6220ad52cc1282bac1ae3aa49fd061a" + integrity sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA== dependencies: glob "^7.1.3" @@ -23655,12 +23692,13 @@ schema-utils@^1.0.0: ajv-errors "^1.0.0" ajv-keywords "^3.1.0" -schema-utils@^2.0.1, schema-utils@^2.5.0, schema-utils@^2.6.0, schema-utils@^2.6.1, schema-utils@^2.6.4: - version "2.6.4" - resolved "https://registry.yarnpkg.com/schema-utils/-/schema-utils-2.6.4.tgz#a27efbf6e4e78689d91872ee3ccfa57d7bdd0f53" - integrity sha512-VNjcaUxVnEeun6B2fiiUDjXXBtD4ZSH7pdbfIu1pOFwgptDPLMo/z9jr4sUfsjFVPqDCEin/F7IYlq7/E6yDbQ== +schema-utils@^2.0.1, schema-utils@^2.5.0, schema-utils@^2.6.0, schema-utils@^2.6.4, schema-utils@^2.6.6, schema-utils@^2.7.0: + version "2.7.0" + resolved "https://registry.yarnpkg.com/schema-utils/-/schema-utils-2.7.0.tgz#17151f76d8eae67fbbf77960c33c676ad9f4efc7" + integrity sha512-0ilKFI6QQF5nxDZLFn2dMjvc4hjg/Wkg7rHd3jK6/A4a1Hl9VFdQWvgB1UMGoU94pad1P/8N7fMcEnLnSiju8A== dependencies: - ajv "^6.10.2" + "@types/json-schema" "^7.0.4" + ajv "^6.12.2" ajv-keywords "^3.4.1" scope-analyzer@^2.0.1: @@ -23873,10 +23911,12 @@ serialize-error@^7.0.1: dependencies: type-fest "^0.13.1" -serialize-javascript@^2.1.2: - version "2.1.2" - resolved "https://registry.yarnpkg.com/serialize-javascript/-/serialize-javascript-2.1.2.tgz#ecec53b0e0317bdc95ef76ab7074b7384785fa61" - integrity sha512-rs9OggEUF0V4jUSecXazOYsLfu7OGK2qIn3c7IPBiffz32XniEp/TX9Xmc9LQfK2nQ2QKHvZ2oygKUGU0lG4jQ== +serialize-javascript@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/serialize-javascript/-/serialize-javascript-4.0.0.tgz#b525e1238489a5ecfc42afacc3fe99e666f4b1aa" + integrity sha512-GaNA54380uFefWghODBWEGisLZFj00nS5ACs6yHa9nLqlLpVLO8ChDGeKRjZnV4Nh4n0Qi7nhYZD/9fCPzEqkw== + dependencies: + randombytes "^2.1.0" serve-favicon@^2.5.0: version "2.5.0" @@ -24694,6 +24734,13 @@ ssri@^7.0.0: figgy-pudding "^3.5.1" minipass "^3.1.1" +ssri@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/ssri/-/ssri-8.0.0.tgz#79ca74e21f8ceaeddfcb4b90143c458b8d988808" + integrity sha512-aq/pz989nxVYwn16Tsbj1TqFpD5LLrQxHf5zaHuieFV+R0Bbr4y8qUsOA45hXT/N4/9UNXTarBjnjVmjSOVaAA== + dependencies: + minipass "^3.1.1" + stable@^0.1.8, stable@~0.1.8: version "0.1.8" resolved "https://registry.yarnpkg.com/stable/-/stable-0.1.8.tgz#836eb3c8382fe2936feaf544631017ce7d47a3cf" @@ -25390,7 +25437,7 @@ supports-color@^6.1.0: dependencies: has-flag "^3.0.0" -supports-color@^7.1.0: +supports-color@^7.0.0, supports-color@^7.1.0: version "7.1.0" resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-7.1.0.tgz#68e32591df73e25ad1c4b49108a2ec507962bfd1" integrity sha512-oRSIpR8pxT1Wr2FquTNnGet79b3BWljqOuoW/h4oBhxJ/HUbX5nX6JSruTkvXDCFMwDPvsaTTbvMLKZWSy0R5g== @@ -25648,6 +25695,18 @@ tar@^4.0.2: safe-buffer "^5.1.2" yallist "^3.0.3" +tar@^6.0.2: + version "6.0.2" + resolved "https://registry.yarnpkg.com/tar/-/tar-6.0.2.tgz#5df17813468a6264ff14f766886c622b84ae2f39" + integrity sha512-Glo3jkRtPcvpDlAs/0+hozav78yoXKFr+c4wgw62NNMO3oo4AaJdCo21Uu7lcwr55h39W2XD1LMERc64wtbItg== + dependencies: + chownr "^2.0.0" + fs-minipass "^2.0.0" + minipass "^3.0.0" + minizlib "^2.1.0" + mkdirp "^1.0.3" + yallist "^4.0.0" + tarn@^1.1.4: version "1.1.5" resolved "https://registry.yarnpkg.com/tarn/-/tarn-1.1.5.tgz#7be88622e951738b9fa3fb77477309242cdddc2d" @@ -25722,35 +25781,36 @@ term-size@^2.1.0: integrity sha512-UqvQSch04R+69g4RDhrslmGvGL3ucDRX/U+snYW0Mab4uCAyKSndUksaoqlJ81QKSpRnIsuOYQCbC2ZWx2896A== terser-webpack-plugin@^1.4.3: - version "1.4.3" - resolved "https://registry.yarnpkg.com/terser-webpack-plugin/-/terser-webpack-plugin-1.4.3.tgz#5ecaf2dbdc5fb99745fd06791f46fc9ddb1c9a7c" - integrity sha512-QMxecFz/gHQwteWwSo5nTc6UaICqN1bMedC5sMtUc7y3Ha3Q8y6ZO0iCR8pq4RJC8Hjf0FEPEHZqcMB/+DFCrA== + version "1.4.5" + resolved "https://registry.yarnpkg.com/terser-webpack-plugin/-/terser-webpack-plugin-1.4.5.tgz#a217aefaea330e734ffacb6120ec1fa312d6040b" + integrity sha512-04Rfe496lN8EYruwi6oPQkG0vo8C+HT49X687FZnpPF0qMAIHONI6HEXYPKDOE8e5HjXTyKfqRd/agHtH0kOtw== dependencies: cacache "^12.0.2" find-cache-dir "^2.1.0" is-wsl "^1.1.0" schema-utils "^1.0.0" - serialize-javascript "^2.1.2" + serialize-javascript "^4.0.0" source-map "^0.6.1" terser "^4.1.2" webpack-sources "^1.4.0" worker-farm "^1.7.0" terser-webpack-plugin@^2.1.2: - version "2.3.2" - resolved "https://registry.yarnpkg.com/terser-webpack-plugin/-/terser-webpack-plugin-2.3.2.tgz#6d3d1b0590c8f729bfbaeb7fb2528b8b62db4c74" - integrity sha512-SmvB/6gtEPv+CJ88MH5zDOsZdKXPS/Uzv2//e90+wM1IHFUhsguPKEILgzqrM1nQ4acRXN/SV4Obr55SXC+0oA== + version "2.3.8" + resolved "https://registry.yarnpkg.com/terser-webpack-plugin/-/terser-webpack-plugin-2.3.8.tgz#894764a19b0743f2f704e7c2a848c5283a696724" + integrity sha512-/fKw3R+hWyHfYx7Bv6oPqmk4HGQcrWLtV3X6ggvPuwPNHSnzvVV51z6OaaCOus4YLjutYGOz3pEpbhe6Up2s1w== dependencies: cacache "^13.0.1" - find-cache-dir "^3.2.0" - jest-worker "^24.9.0" - schema-utils "^2.6.1" - serialize-javascript "^2.1.2" + find-cache-dir "^3.3.1" + jest-worker "^25.4.0" + p-limit "^2.3.0" + schema-utils "^2.6.6" + serialize-javascript "^4.0.0" source-map "^0.6.1" - terser "^4.4.3" + terser "^4.6.12" webpack-sources "^1.4.3" -terser@^4.1.2, terser@^4.4.3: +terser@^4.1.2: version "4.6.3" resolved "https://registry.yarnpkg.com/terser/-/terser-4.6.3.tgz#e33aa42461ced5238d352d2df2a67f21921f8d87" integrity sha512-Lw+ieAXmY69d09IIc/yqeBqXpEQIpDGZqT34ui1QWXIUpR2RjbqEkT8X7Lgex19hslSqcWM5iMN2kM11eMsESQ==