mirror of
https://github.com/kremalicious/metamask-extension.git
synced 2024-11-22 01:47:00 +01:00
feat: implement swap event metric e2e test (#20129)
* implement swap event metric e2e test * fix lint error * clean up initial balance helpers * fix eslint warnings * Fix `token_to_amount` format to address firefox bug and refactor tests
This commit is contained in:
parent
280fd5f7ef
commit
537f1c7aee
@ -246,6 +246,7 @@ module.exports = {
|
|||||||
'shared/**/*.test.js',
|
'shared/**/*.test.js',
|
||||||
'ui/**/*.test.js',
|
'ui/**/*.test.js',
|
||||||
'ui/__mocks__/*.js',
|
'ui/__mocks__/*.js',
|
||||||
|
'test/e2e/helpers.test.js',
|
||||||
],
|
],
|
||||||
extends: ['@metamask/eslint-config-mocha'],
|
extends: ['@metamask/eslint-config-mocha'],
|
||||||
rules: {
|
rules: {
|
||||||
@ -271,10 +272,12 @@ module.exports = {
|
|||||||
'app/scripts/migrations/*.test.js',
|
'app/scripts/migrations/*.test.js',
|
||||||
'app/scripts/platforms/*.test.js',
|
'app/scripts/platforms/*.test.js',
|
||||||
'development/**/*.test.js',
|
'development/**/*.test.js',
|
||||||
|
'development/**/*.test.ts',
|
||||||
'shared/**/*.test.js',
|
'shared/**/*.test.js',
|
||||||
'shared/**/*.test.ts',
|
'shared/**/*.test.ts',
|
||||||
'test/helpers/*.js',
|
'test/helpers/*.js',
|
||||||
'test/jest/*.js',
|
'test/jest/*.js',
|
||||||
|
'test/e2e/helpers.test.js',
|
||||||
'ui/**/*.test.js',
|
'ui/**/*.test.js',
|
||||||
'ui/__mocks__/*.js',
|
'ui/__mocks__/*.js',
|
||||||
'shared/lib/error-utils.test.js',
|
'shared/lib/error-utils.test.js',
|
||||||
|
@ -9,6 +9,8 @@ module.exports = {
|
|||||||
'./app/scripts/controllers/permissions/**/*.test.js',
|
'./app/scripts/controllers/permissions/**/*.test.js',
|
||||||
'./app/scripts/controllers/mmi-controller.test.js',
|
'./app/scripts/controllers/mmi-controller.test.js',
|
||||||
'./app/scripts/constants/error-utils.test.js',
|
'./app/scripts/constants/error-utils.test.js',
|
||||||
|
'./development/fitness-functions/**/*.test.ts',
|
||||||
|
'./test/e2e/helpers.test.js',
|
||||||
],
|
],
|
||||||
recursive: true,
|
recursive: true,
|
||||||
require: ['test/env.js', 'test/setup.js'],
|
require: ['test/env.js', 'test/setup.js'],
|
||||||
|
@ -40,7 +40,10 @@ import {
|
|||||||
hexWEIToDecGWEI,
|
hexWEIToDecGWEI,
|
||||||
} from '../../../../shared/modules/conversion.utils';
|
} from '../../../../shared/modules/conversion.utils';
|
||||||
import { isSwapsDefaultTokenAddress } from '../../../../shared/modules/swaps.utils';
|
import { isSwapsDefaultTokenAddress } from '../../../../shared/modules/swaps.utils';
|
||||||
import { MetaMetricsEventCategory } from '../../../../shared/constants/metametrics';
|
import {
|
||||||
|
MetaMetricsEventCategory,
|
||||||
|
MetaMetricsEventName,
|
||||||
|
} from '../../../../shared/constants/metametrics';
|
||||||
import {
|
import {
|
||||||
CHAIN_ID_TO_GAS_LIMIT_BUFFER_MAP,
|
CHAIN_ID_TO_GAS_LIMIT_BUFFER_MAP,
|
||||||
NETWORK_TYPES,
|
NETWORK_TYPES,
|
||||||
@ -2128,7 +2131,7 @@ export default class TransactionController extends EventEmitter {
|
|||||||
);
|
);
|
||||||
|
|
||||||
this._trackMetaMetricsEvent({
|
this._trackMetaMetricsEvent({
|
||||||
event: 'Swap Completed',
|
event: MetaMetricsEventName.SwapCompleted,
|
||||||
category: MetaMetricsEventCategory.Swaps,
|
category: MetaMetricsEventCategory.Swaps,
|
||||||
sensitiveProperties: {
|
sensitiveProperties: {
|
||||||
...txMeta.swapMetaData,
|
...txMeta.swapMetaData,
|
||||||
@ -2139,6 +2142,12 @@ export default class TransactionController extends EventEmitter {
|
|||||||
trade_gas_cost_in_eth: transactionsCost.tradeGasCostInEth,
|
trade_gas_cost_in_eth: transactionsCost.tradeGasCostInEth,
|
||||||
trade_and_approval_gas_cost_in_eth:
|
trade_and_approval_gas_cost_in_eth:
|
||||||
transactionsCost.tradeAndApprovalGasCostInEth,
|
transactionsCost.tradeAndApprovalGasCostInEth,
|
||||||
|
// Firefox and Chrome have different implementations of the APIs
|
||||||
|
// that we rely on for communication accross the app. On Chrome big
|
||||||
|
// numbers are converted into number strings, on firefox they remain
|
||||||
|
// Big Number objects. As such, we convert them here for both
|
||||||
|
// browsers.
|
||||||
|
token_to_amount: txMeta.swapMetaData.token_to_amount.toString(10),
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -14,6 +14,7 @@ module.exports = {
|
|||||||
'<rootDir>/shared/**/*.(js|ts|tsx)',
|
'<rootDir>/shared/**/*.(js|ts|tsx)',
|
||||||
'<rootDir>/ui/**/*.(js|ts|tsx)',
|
'<rootDir>/ui/**/*.(js|ts|tsx)',
|
||||||
'<rootDir>/development/fitness-functions/**/*.test.(js|ts|tsx)',
|
'<rootDir>/development/fitness-functions/**/*.test.(js|ts|tsx)',
|
||||||
|
'<rootDir>/test/e2e/helpers.test.js',
|
||||||
],
|
],
|
||||||
coverageDirectory: './coverage',
|
coverageDirectory: './coverage',
|
||||||
coveragePathIgnorePatterns: ['.stories.*', '.snap'],
|
coveragePathIgnorePatterns: ['.stories.*', '.snap'],
|
||||||
@ -50,6 +51,7 @@ module.exports = {
|
|||||||
'<rootDir>/shared/**/*.test.(js|ts)',
|
'<rootDir>/shared/**/*.test.(js|ts)',
|
||||||
'<rootDir>/ui/**/*.test.(js|ts|tsx)',
|
'<rootDir>/ui/**/*.test.(js|ts|tsx)',
|
||||||
'<rootDir>/development/fitness-functions/**/*.test.(js|ts|tsx)',
|
'<rootDir>/development/fitness-functions/**/*.test.(js|ts|tsx)',
|
||||||
|
'<rootDir>/test/e2e/helpers.test.js',
|
||||||
],
|
],
|
||||||
testTimeout: 5500,
|
testTimeout: 5500,
|
||||||
// We have to specify the environment we are running in, which is jsdom. The
|
// We have to specify the environment we are running in, which is jsdom. The
|
||||||
|
@ -612,6 +612,18 @@ export enum MetaMetricsEventName {
|
|||||||
ActivityScreenOpened = 'Activity Screen Opened',
|
ActivityScreenOpened = 'Activity Screen Opened',
|
||||||
WhatsNewViewed = `What's New Viewed`,
|
WhatsNewViewed = `What's New Viewed`,
|
||||||
WhatsNewClicked = `What's New Link Clicked`,
|
WhatsNewClicked = `What's New Link Clicked`,
|
||||||
|
PrepareSwapPageLoaded = 'Prepare Swap Page Loaded',
|
||||||
|
QuotesRequested = 'Quotes Requested',
|
||||||
|
QuotesReceived = 'Quotes Received',
|
||||||
|
BestQuoteReviewed = 'Best Quote Reviewed',
|
||||||
|
AllAvailableQuotesOpened = 'All Available Quotes Opened',
|
||||||
|
SwapStarted = 'Swap Started',
|
||||||
|
TransactionAdded = 'Transaction Added',
|
||||||
|
TransactionSubmitted = 'Transaction Submitted',
|
||||||
|
TransactionApproved = 'Transaction Approved',
|
||||||
|
SwapCompleted = 'Swap Completed',
|
||||||
|
TransactionFinalized = 'Transaction Finalized',
|
||||||
|
ExitedSwaps = 'Exited Swaps',
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum MetaMetricsEventAccountType {
|
export enum MetaMetricsEventAccountType {
|
||||||
|
@ -589,9 +589,10 @@ function mockPhishingDetection(mockServer) {
|
|||||||
const PRIVATE_KEY =
|
const PRIVATE_KEY =
|
||||||
'0x7C9529A67102755B7E6102D6D950AC5D5863C98713805CEC576B945B15B71EAC';
|
'0x7C9529A67102755B7E6102D6D950AC5D5863C98713805CEC576B945B15B71EAC';
|
||||||
|
|
||||||
const generateETHBalance = (eth) => convertToHexValue(eth * 10 ** 18);
|
const convertETHToHexGwei = (eth) => convertToHexValue(eth * 10 ** 18);
|
||||||
|
|
||||||
const defaultGanacheOptions = {
|
const defaultGanacheOptions = {
|
||||||
accounts: [{ secretKey: PRIVATE_KEY, balance: generateETHBalance(25) }],
|
accounts: [{ secretKey: PRIVATE_KEY, balance: convertETHToHexGwei(25) }],
|
||||||
};
|
};
|
||||||
|
|
||||||
const SERVICE_WORKER_URL = 'chrome://inspect/#service-workers';
|
const SERVICE_WORKER_URL = 'chrome://inspect/#service-workers';
|
||||||
@ -654,7 +655,7 @@ const DEFAULT_GANACHE_OPTIONS = {
|
|||||||
accounts: [
|
accounts: [
|
||||||
{
|
{
|
||||||
secretKey: DEFAULT_PRIVATE_KEY,
|
secretKey: DEFAULT_PRIVATE_KEY,
|
||||||
balance: generateETHBalance(25),
|
balance: convertETHToHexGwei(25),
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
};
|
};
|
||||||
@ -687,6 +688,10 @@ const logInWithBalanceValidation = async (driver, ganacheServer) => {
|
|||||||
await assertAccountBalanceForDOM(driver, ganacheServer);
|
await assertAccountBalanceForDOM(driver, ganacheServer);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
async function sleepSeconds(sec) {
|
||||||
|
return new Promise((resolve) => setTimeout(resolve, sec * 1000));
|
||||||
|
}
|
||||||
|
|
||||||
function roundToXDecimalPlaces(number, decimalPlaces) {
|
function roundToXDecimalPlaces(number, decimalPlaces) {
|
||||||
return Math.round(number * 10 ** decimalPlaces) / 10 ** decimalPlaces;
|
return Math.round(number * 10 ** decimalPlaces) / 10 ** decimalPlaces;
|
||||||
}
|
}
|
||||||
@ -699,8 +704,15 @@ function generateRandNumBetween(x, y) {
|
|||||||
return randomNumber;
|
return randomNumber;
|
||||||
}
|
}
|
||||||
|
|
||||||
async function sleepSeconds(sec) {
|
function genRandInitBal(minETHBal = 10, maxETHBal = 100, decimalPlaces = 4) {
|
||||||
return new Promise((resolve) => setTimeout(resolve, sec * 1000));
|
const initialBalance = roundToXDecimalPlaces(
|
||||||
|
generateRandNumBetween(minETHBal, maxETHBal),
|
||||||
|
decimalPlaces,
|
||||||
|
);
|
||||||
|
|
||||||
|
const initialBalanceInHex = convertETHToHexGwei(initialBalance);
|
||||||
|
|
||||||
|
return { initialBalance, initialBalanceInHex };
|
||||||
}
|
}
|
||||||
|
|
||||||
async function terminateServiceWorker(driver) {
|
async function terminateServiceWorker(driver) {
|
||||||
@ -762,12 +774,44 @@ async function getEventPayloads(driver, mockedEndpoints, hasRequest = true) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
return isPending === !hasRequest;
|
return isPending === !hasRequest;
|
||||||
}, 10000);
|
}, driver.timeout);
|
||||||
const mockedRequests = [];
|
const mockedRequests = [];
|
||||||
for (const mockedEndpoint of mockedEndpoints) {
|
for (const mockedEndpoint of mockedEndpoints) {
|
||||||
mockedRequests.push(...(await mockedEndpoint.getSeenRequests()));
|
mockedRequests.push(...(await mockedEndpoint.getSeenRequests()));
|
||||||
}
|
}
|
||||||
return mockedRequests.map((req) => req.body.json.batch).flat();
|
|
||||||
|
return mockedRequests.map((req) => req.body.json?.batch).flat();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Asserts that each request passes all assertions in one group of assertions, and the order does not matter.
|
||||||
|
function assertInAnyOrder(requests, assertions) {
|
||||||
|
// Clone the array to avoid mutating the original
|
||||||
|
const assertionsClone = [...assertions];
|
||||||
|
|
||||||
|
return (
|
||||||
|
requests.every((request) => {
|
||||||
|
for (let a = 0; a < assertionsClone.length; a++) {
|
||||||
|
const assertionArray = assertionsClone[a];
|
||||||
|
|
||||||
|
const passed = assertionArray.reduce(
|
||||||
|
(acc, currAssertionFn) => currAssertionFn(request) && acc,
|
||||||
|
true,
|
||||||
|
);
|
||||||
|
|
||||||
|
if (passed) {
|
||||||
|
// Remove the used assertion array
|
||||||
|
assertionsClone.splice(a, 1);
|
||||||
|
// Exit the loop early since we found a matching assertion
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// No matching assertion found for this request
|
||||||
|
return false;
|
||||||
|
}) &&
|
||||||
|
// Ensure all assertions were used
|
||||||
|
assertionsClone.length === 0
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
@ -810,7 +854,7 @@ module.exports = {
|
|||||||
WALLET_PASSWORD,
|
WALLET_PASSWORD,
|
||||||
WINDOW_TITLES,
|
WINDOW_TITLES,
|
||||||
DEFAULT_GANACHE_OPTIONS,
|
DEFAULT_GANACHE_OPTIONS,
|
||||||
generateETHBalance,
|
convertETHToHexGwei,
|
||||||
roundToXDecimalPlaces,
|
roundToXDecimalPlaces,
|
||||||
generateRandNumBetween,
|
generateRandNumBetween,
|
||||||
sleepSeconds,
|
sleepSeconds,
|
||||||
@ -823,4 +867,6 @@ module.exports = {
|
|||||||
onboardingRevealAndConfirmSRP,
|
onboardingRevealAndConfirmSRP,
|
||||||
onboardingCompleteWalletCreation,
|
onboardingCompleteWalletCreation,
|
||||||
onboardingPinExtension,
|
onboardingPinExtension,
|
||||||
|
assertInAnyOrder,
|
||||||
|
genRandInitBal,
|
||||||
};
|
};
|
||||||
|
53
test/e2e/helpers.test.js
Normal file
53
test/e2e/helpers.test.js
Normal file
@ -0,0 +1,53 @@
|
|||||||
|
import { assertInAnyOrder } from './helpers';
|
||||||
|
|
||||||
|
describe('assertInAnyOrder()', () => {
|
||||||
|
it('returns true when all requests pass unique assertions', () => {
|
||||||
|
const requests = ['req1', 'req2', 'req3'];
|
||||||
|
const assertions = [
|
||||||
|
[(req) => req === 'req1'],
|
||||||
|
[(req) => req === 'req2'],
|
||||||
|
[(req) => req === 'req3'],
|
||||||
|
];
|
||||||
|
expect(assertInAnyOrder(requests, assertions)).toBe(true);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('returns true when all requests pass unique assertions independently of the order', () => {
|
||||||
|
const requests = ['req1', 'req2', 'req3'];
|
||||||
|
const assertions = [
|
||||||
|
[(req) => req === 'req3'],
|
||||||
|
[(req) => req === 'req2'],
|
||||||
|
[(req) => req === 'req1'],
|
||||||
|
];
|
||||||
|
expect(assertInAnyOrder(requests, assertions)).toBe(true);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('returns false when a request cannot pass any assertions', () => {
|
||||||
|
const requests = ['req1', 'req2', 'unknown'];
|
||||||
|
const assertions = [
|
||||||
|
[(req) => req === 'req1'],
|
||||||
|
[(req) => req === 'req2'],
|
||||||
|
[(req) => req === 'req3'],
|
||||||
|
];
|
||||||
|
expect(assertInAnyOrder(requests, assertions)).toBe(false);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('returns false when there are unused assertions', () => {
|
||||||
|
const requests = ['req1', 'req2'];
|
||||||
|
const assertions = [
|
||||||
|
[(req) => req === 'req1'],
|
||||||
|
[(req) => req === 'req2'],
|
||||||
|
[(req) => req === 'req3'],
|
||||||
|
];
|
||||||
|
expect(assertInAnyOrder(requests, assertions)).toBe(false);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('returns false when there are unused requests', () => {
|
||||||
|
const requests = ['req1', 'req2', 'req3', 'req4'];
|
||||||
|
const assertions = [
|
||||||
|
[(req) => req === 'req1'],
|
||||||
|
[(req) => req === 'req2'],
|
||||||
|
[(req) => req === 'req3'],
|
||||||
|
];
|
||||||
|
expect(assertInAnyOrder(requests, assertions)).toBe(false);
|
||||||
|
});
|
||||||
|
});
|
524
test/e2e/metrics/mock-data.js
Normal file
524
test/e2e/metrics/mock-data.js
Normal file
File diff suppressed because one or more lines are too long
572
test/e2e/metrics/swaps.spec.js
Normal file
572
test/e2e/metrics/swaps.spec.js
Normal file
@ -0,0 +1,572 @@
|
|||||||
|
const { strict: assert } = require('assert');
|
||||||
|
const { toHex } = require('@metamask/controller-utils');
|
||||||
|
const FixtureBuilder = require('../fixture-builder');
|
||||||
|
const {
|
||||||
|
withFixtures,
|
||||||
|
generateGanacheOptions,
|
||||||
|
DEFAULT_GANACHE_OPTIONS,
|
||||||
|
unlockWallet,
|
||||||
|
getEventPayloads,
|
||||||
|
assertInAnyOrder,
|
||||||
|
genRandInitBal,
|
||||||
|
} = require('../helpers');
|
||||||
|
const {
|
||||||
|
buildQuote,
|
||||||
|
reviewQuote,
|
||||||
|
waitForTransactionToComplete,
|
||||||
|
checkActivityTransaction,
|
||||||
|
changeExchangeRate,
|
||||||
|
} = require('../swaps/shared');
|
||||||
|
const {
|
||||||
|
MetaMetricsEventCategory,
|
||||||
|
MetaMetricsEventName,
|
||||||
|
} = require('../../../shared/constants/metametrics');
|
||||||
|
const {
|
||||||
|
TOKENS_API_MOCK_RESULT,
|
||||||
|
TOP_ASSETS_API_MOCK_RESULT,
|
||||||
|
AGGREGATOR_METADATA_API_MOCK_RESULT,
|
||||||
|
GAS_PRICE_API_MOCK_RESULT,
|
||||||
|
FEATURE_FLAGS_API_MOCK_RESULT,
|
||||||
|
NETWORKS_API_MOCK_RESULT,
|
||||||
|
TRADES_API_MOCK_RESULT,
|
||||||
|
NETWORKS_2_API_MOCK_RESULT,
|
||||||
|
} = require('./mock-data');
|
||||||
|
|
||||||
|
const numberOfSegmentRequests = 19;
|
||||||
|
|
||||||
|
async function mockSegmentAndMetaswapRequests(mockServer) {
|
||||||
|
return [
|
||||||
|
await mockServer
|
||||||
|
.forPost('https://api.segment.io/v1/batch')
|
||||||
|
.withJsonBodyIncluding({
|
||||||
|
batch: [{ properties: { category: MetaMetricsEventCategory.Swaps } }],
|
||||||
|
})
|
||||||
|
.times()
|
||||||
|
.thenCallback(() => ({ statusCode: 200 })),
|
||||||
|
await mockServer
|
||||||
|
.forGet('https://swap.metaswap.codefi.network/networks/1/tokens')
|
||||||
|
.thenCallback(() => ({ statusCode: 200, json: TOKENS_API_MOCK_RESULT })),
|
||||||
|
await mockServer
|
||||||
|
.forGet('https://swap.metaswap.codefi.network/networks/1/topAssets')
|
||||||
|
.thenCallback(() => ({
|
||||||
|
statusCode: 200,
|
||||||
|
json: TOP_ASSETS_API_MOCK_RESULT,
|
||||||
|
})),
|
||||||
|
await mockServer
|
||||||
|
.forGet(
|
||||||
|
'https://swap.metaswap.codefi.network/networks/1/aggregatorMetadata',
|
||||||
|
)
|
||||||
|
.thenCallback(() => ({
|
||||||
|
statusCode: 200,
|
||||||
|
json: AGGREGATOR_METADATA_API_MOCK_RESULT,
|
||||||
|
})),
|
||||||
|
await mockServer
|
||||||
|
.forGet('https://gas-api.metaswap.codefi.network/networks/1/gasPrices')
|
||||||
|
.thenCallback(() => ({
|
||||||
|
statusCode: 200,
|
||||||
|
json: GAS_PRICE_API_MOCK_RESULT,
|
||||||
|
})),
|
||||||
|
await mockServer
|
||||||
|
.forGet('https://swap.metaswap.codefi.network/featureFlags')
|
||||||
|
.thenCallback(() => ({
|
||||||
|
statusCode: 200,
|
||||||
|
json: FEATURE_FLAGS_API_MOCK_RESULT,
|
||||||
|
})),
|
||||||
|
await mockServer
|
||||||
|
.forGet('https://tx-insights.metaswap.codefi.network/networks')
|
||||||
|
.thenCallback(() => ({
|
||||||
|
statusCode: 200,
|
||||||
|
json: NETWORKS_API_MOCK_RESULT,
|
||||||
|
})),
|
||||||
|
await mockServer
|
||||||
|
.forGet('https://swap.metaswap.codefi.network/networks/1/trades')
|
||||||
|
.thenCallback(() => ({
|
||||||
|
statusCode: 200,
|
||||||
|
json: TRADES_API_MOCK_RESULT,
|
||||||
|
})),
|
||||||
|
await mockServer
|
||||||
|
.forGet('https://swap.metaswap.codefi.network/networks/1')
|
||||||
|
.thenCallback(() => ({
|
||||||
|
statusCode: 200,
|
||||||
|
json: NETWORKS_2_API_MOCK_RESULT,
|
||||||
|
})),
|
||||||
|
await mockServer
|
||||||
|
.forGet('https://token-api.metaswap.codefi.network/token/1337')
|
||||||
|
.thenCallback(() => ({
|
||||||
|
statusCode: 200,
|
||||||
|
json: {},
|
||||||
|
})),
|
||||||
|
];
|
||||||
|
}
|
||||||
|
|
||||||
|
describe('Swap Eth for another Token', function () {
|
||||||
|
it('Completes a Swap between ETH and DAI after changing initial rate', async function () {
|
||||||
|
const { initialBalanceInHex } = genRandInitBal();
|
||||||
|
|
||||||
|
await withFixtures(
|
||||||
|
{
|
||||||
|
fixtures: new FixtureBuilder()
|
||||||
|
.withMetaMetricsController({
|
||||||
|
metaMetricsId: 'fake-metrics-id',
|
||||||
|
participateInMetaMetrics: true,
|
||||||
|
})
|
||||||
|
.build(),
|
||||||
|
ganacheOptions: generateGanacheOptions({
|
||||||
|
accounts: [
|
||||||
|
{
|
||||||
|
secretKey: DEFAULT_GANACHE_OPTIONS.accounts[0].secretKey,
|
||||||
|
balance: initialBalanceInHex,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}),
|
||||||
|
title: this.test.title,
|
||||||
|
testSpecificMock: mockSegmentAndMetaswapRequests,
|
||||||
|
},
|
||||||
|
async ({ driver, mockedEndpoint: mockedEndpoints }) => {
|
||||||
|
await driver.navigate();
|
||||||
|
|
||||||
|
await unlockWallet(driver);
|
||||||
|
|
||||||
|
await getQuoteAndSwapTokens(driver);
|
||||||
|
|
||||||
|
const metricsReqs = await assertReqsNumAndFilterMetrics(
|
||||||
|
driver,
|
||||||
|
mockedEndpoints,
|
||||||
|
);
|
||||||
|
|
||||||
|
await assertNavSwapButtonClickedEvent(metricsReqs);
|
||||||
|
|
||||||
|
await assertPrepareSwapPageLoadedEvents(metricsReqs);
|
||||||
|
|
||||||
|
await assertQuotesRequestedEvents(metricsReqs);
|
||||||
|
|
||||||
|
await assertQuotesReceivedAndBestQuoteReviewedEvents(metricsReqs);
|
||||||
|
|
||||||
|
await assertAllAvailableQuotesOpenedEvents(metricsReqs);
|
||||||
|
|
||||||
|
await assertSwapStartedEvents(metricsReqs);
|
||||||
|
|
||||||
|
await assertSwapCompletedEvents(metricsReqs);
|
||||||
|
|
||||||
|
await assertExitedSwapsEvents(metricsReqs);
|
||||||
|
},
|
||||||
|
);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
async function getQuoteAndSwapTokens(driver) {
|
||||||
|
await buildQuote(driver, {
|
||||||
|
amount: 2,
|
||||||
|
swapTo: 'DAI',
|
||||||
|
});
|
||||||
|
await reviewQuote(driver, {
|
||||||
|
amount: 2,
|
||||||
|
swapFrom: 'TESTETH',
|
||||||
|
swapTo: 'DAI',
|
||||||
|
});
|
||||||
|
await changeExchangeRate(driver);
|
||||||
|
await reviewQuote(driver, {
|
||||||
|
amount: 2,
|
||||||
|
swapFrom: 'TESTETH',
|
||||||
|
swapTo: 'DAI',
|
||||||
|
skipCounter: true,
|
||||||
|
});
|
||||||
|
await driver.clickElement({ text: 'Swap', tag: 'button' });
|
||||||
|
await waitForTransactionToComplete(driver, { tokenName: 'DAI' });
|
||||||
|
await checkActivityTransaction(driver, {
|
||||||
|
index: 0,
|
||||||
|
amount: '2',
|
||||||
|
swapFrom: 'TESTETH',
|
||||||
|
swapTo: 'DAI',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
async function assertReqsNumAndFilterMetrics(driver, mockedEndpoints) {
|
||||||
|
const events = await getEventPayloads(driver, mockedEndpoints);
|
||||||
|
|
||||||
|
const numberOfMetaswapRequests = 9;
|
||||||
|
assert.equal(
|
||||||
|
events.length,
|
||||||
|
numberOfSegmentRequests + numberOfMetaswapRequests,
|
||||||
|
);
|
||||||
|
|
||||||
|
const reqs = events.slice(0, numberOfSegmentRequests);
|
||||||
|
|
||||||
|
return reqs;
|
||||||
|
}
|
||||||
|
|
||||||
|
async function assertNavSwapButtonClickedEvent(reqs) {
|
||||||
|
assert.equal(reqs[0].event, MetaMetricsEventName.NavSwapButtonClicked);
|
||||||
|
assert.deepStrictEqual(reqs[0].properties, {
|
||||||
|
category: MetaMetricsEventCategory.Swaps,
|
||||||
|
chain_id: toHex(1337),
|
||||||
|
environment_type: 'fullscreen',
|
||||||
|
locale: 'en',
|
||||||
|
location: 'Main View',
|
||||||
|
text: 'Swap',
|
||||||
|
token_symbol: 'ETH',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
async function assertPrepareSwapPageLoadedEvents(reqs) {
|
||||||
|
const assertionsReq1 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.PrepareSwapPageLoaded,
|
||||||
|
(req) => Object.keys(req.properties).length === 7,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
|
||||||
|
(req) => req.properties?.current_stx_enabled === false,
|
||||||
|
(req) => req.properties?.is_hardware_wallet === false,
|
||||||
|
(req) => req.properties?.stx_enabled === false,
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq2 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.PrepareSwapPageLoaded,
|
||||||
|
(req) => Object.keys(req.properties).length === 4,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
];
|
||||||
|
|
||||||
|
assert.ok(
|
||||||
|
assertInAnyOrder([reqs[1], reqs[2]], [assertionsReq1, assertionsReq2]),
|
||||||
|
'assertPrepareSwapPageLoadedEvents(): reqs[1] and reqs[2] did not match what was expected',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async function assertQuotesRequestedEvents(reqs) {
|
||||||
|
const assertionsReq3 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.QuotesRequested,
|
||||||
|
(req) => Object.keys(req.properties).length === 14,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
|
||||||
|
(req) => req.properties?.anonymizedData === true,
|
||||||
|
(req) => req.properties?.current_stx_enabled === false,
|
||||||
|
(req) => req.properties?.custom_slippage === false,
|
||||||
|
(req) => req.properties?.is_hardware_wallet === false,
|
||||||
|
(req) => req.properties?.request_type === 'Order',
|
||||||
|
(req) => req.properties?.slippage === 2,
|
||||||
|
(req) => req.properties?.stx_enabled === false,
|
||||||
|
(req) => req.properties?.token_from === 'TESTETH',
|
||||||
|
(req) => req.properties?.token_from_amount === '2',
|
||||||
|
(req) => req.properties?.token_to === 'DAI',
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq4 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.QuotesRequested,
|
||||||
|
(req) => Object.keys(req.properties).length === 4,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
];
|
||||||
|
|
||||||
|
assert.ok(
|
||||||
|
assertInAnyOrder([reqs[3], reqs[4]], [assertionsReq3, assertionsReq4]),
|
||||||
|
'assertQuotesRequestedEvents(): reqs[3] and reqs[4] did not match what was expected',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async function assertQuotesReceivedAndBestQuoteReviewedEvents(reqs) {
|
||||||
|
const assertionsReq5 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.QuotesReceived,
|
||||||
|
(req) => Object.keys(req.properties).length === 18,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
|
||||||
|
(req) => req.properties?.anonymizedData === true,
|
||||||
|
(req) => typeof req.properties?.available_quotes === 'number',
|
||||||
|
(req) => typeof req.properties?.best_quote_source === 'string',
|
||||||
|
(req) => req.properties?.current_stx_enabled === false,
|
||||||
|
(req) => req.properties?.custom_slippage === false,
|
||||||
|
(req) => req.properties?.is_hardware_wallet === false,
|
||||||
|
(req) => req.properties?.request_type === 'Order',
|
||||||
|
(req) => typeof req.properties?.response_time === 'number',
|
||||||
|
(req) => req.properties?.slippage === 2,
|
||||||
|
(req) => req.properties?.stx_enabled === false,
|
||||||
|
(req) => req.properties?.token_from === 'TESTETH',
|
||||||
|
(req) => req.properties?.token_from_amount === '2',
|
||||||
|
(req) => req.properties?.token_to === 'DAI',
|
||||||
|
(req) => typeof req.properties?.token_to_amount === 'string',
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq6 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.QuotesReceived,
|
||||||
|
(req) => Object.keys(req.properties).length === 4,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq7 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.BestQuoteReviewed,
|
||||||
|
(req) => Object.keys(req.properties).length === 17,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
|
||||||
|
(req) => typeof req.properties?.available_quotes === 'number',
|
||||||
|
(req) => typeof req.properties?.best_quote_source === 'string',
|
||||||
|
(req) => req.properties?.current_stx_enabled === false,
|
||||||
|
(req) => req.properties?.custom_slippage === false,
|
||||||
|
(req) => req.properties?.is_hardware_wallet === false,
|
||||||
|
(req) => req.properties?.request_type === false,
|
||||||
|
(req) => req.properties?.slippage === 2,
|
||||||
|
(req) => req.properties?.stx_enabled === false,
|
||||||
|
(req) => req.properties?.token_from === 'TESTETH',
|
||||||
|
(req) => req.properties?.token_from_amount === '2',
|
||||||
|
(req) => req.properties?.token_to === 'DAI',
|
||||||
|
(req) => typeof req.properties?.token_to_amount === 'string',
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq8 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.BestQuoteReviewed,
|
||||||
|
(req) => Object.keys(req.properties).length === 4,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
];
|
||||||
|
|
||||||
|
// When running this test on Chrome in particular, reqs[5], reqs[6], reqs[7]
|
||||||
|
// and reqs[8] sometimes switch order so we bundled them together for the
|
||||||
|
// assertion
|
||||||
|
|
||||||
|
assert.ok(
|
||||||
|
assertInAnyOrder(
|
||||||
|
[reqs[5], reqs[6], reqs[7], reqs[8]],
|
||||||
|
[assertionsReq5, assertionsReq6, assertionsReq7, assertionsReq8],
|
||||||
|
),
|
||||||
|
'assertQuotesReceivedAndBestQuoteReviewedEvents(): reqs[5], reqs[6], reqs[7] and reqs[8] did not match what was expected',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async function assertAllAvailableQuotesOpenedEvents(reqs) {
|
||||||
|
const assertionsReq9 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.AllAvailableQuotesOpened,
|
||||||
|
(req) => Object.keys(req.properties).length === 18,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
|
||||||
|
(req) => typeof req.properties?.available_quotes === 'number',
|
||||||
|
(req) => typeof req.properties?.best_quote_source === 'string',
|
||||||
|
(req) => req.properties?.current_stx_enabled === false,
|
||||||
|
(req) => req.properties?.custom_slippage === false,
|
||||||
|
(req) => req.properties?.is_hardware_wallet === false,
|
||||||
|
(req) => req.properties?.request_type === false,
|
||||||
|
(req) => req.properties?.slippage === 2,
|
||||||
|
(req) => req.properties?.stx_enabled === false,
|
||||||
|
(req) => req.properties?.token_from === 'TESTETH',
|
||||||
|
(req) => req.properties?.token_from_amount === '2',
|
||||||
|
(req) => req.properties?.token_to === 'DAI',
|
||||||
|
(req) => req.properties?.token_to === 'DAI',
|
||||||
|
(req) => req.properties?.other_quote_selected === false,
|
||||||
|
(req) => req.properties?.other_quote_selected_source === null,
|
||||||
|
(req) => typeof req.properties?.token_to_amount === 'string',
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq10 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.AllAvailableQuotesOpened,
|
||||||
|
(req) => Object.keys(req.properties).length === 4,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
];
|
||||||
|
|
||||||
|
assert.ok(
|
||||||
|
assertInAnyOrder([reqs[9], reqs[10]], [assertionsReq9, assertionsReq10]),
|
||||||
|
'assertAllAvailableQuotesOpenedEvents(): reqs[9] and reqs[10] did not match what was expected',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async function assertSwapStartedEvents(reqs) {
|
||||||
|
const assertionsReq11 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.SwapStarted,
|
||||||
|
(req) => Object.keys(req.properties).length === 24,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
|
||||||
|
(req) => req.properties?.token_from === 'TESTETH',
|
||||||
|
(req) => req.properties?.token_from_amount === '2',
|
||||||
|
(req) => req.properties?.token_to === 'DAI',
|
||||||
|
(req) => req.properties?.slippage === 2,
|
||||||
|
(req) => req.properties?.custom_slippage === false,
|
||||||
|
(req) => req.properties?.is_hardware_wallet === false,
|
||||||
|
(req) => req.properties?.stx_enabled === false,
|
||||||
|
(req) => req.properties?.current_stx_enabled === false,
|
||||||
|
(req) => typeof req.properties?.token_to_amount === 'string',
|
||||||
|
(req) => typeof req.properties?.best_quote_source === 'string',
|
||||||
|
(req) => typeof req.properties?.other_quote_selected === 'boolean',
|
||||||
|
(req) => typeof req.properties?.gas_fees === 'string',
|
||||||
|
(req) => typeof req.properties?.estimated_gas === 'string',
|
||||||
|
(req) => typeof req.properties?.suggested_gas_price === 'string',
|
||||||
|
(req) => typeof req.properties?.reg_tx_fee_in_usd === 'number',
|
||||||
|
(req) => typeof req.properties?.reg_tx_fee_in_eth === 'number',
|
||||||
|
(req) => typeof req.properties?.reg_tx_max_fee_in_usd === 'number',
|
||||||
|
(req) => typeof req.properties?.reg_tx_max_fee_in_eth === 'number',
|
||||||
|
(req) => typeof req.properties?.other_quote_selected_source === 'string',
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq12 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.SwapStarted,
|
||||||
|
(req) => Object.keys(req.properties).length === 4,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
];
|
||||||
|
|
||||||
|
assert.ok(
|
||||||
|
assertInAnyOrder([reqs[11], reqs[12]], [assertionsReq11, assertionsReq12]),
|
||||||
|
'assertSwapStartedEvents(): reqs[11] and reqs[12] did not match what was expected',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async function assertSwapCompletedEvents(reqs) {
|
||||||
|
const assertionsReq13 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.SwapCompleted,
|
||||||
|
(req) => Object.keys(req.properties).length === 30,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'background',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
|
||||||
|
(req) => req.properties?.token_from === 'TESTETH',
|
||||||
|
(req) => req.properties?.token_from_amount === '2',
|
||||||
|
(req) => req.properties?.token_to === 'DAI',
|
||||||
|
(req) => typeof req.properties?.token_to_amount === 'string',
|
||||||
|
(req) => req.properties?.slippage === 2,
|
||||||
|
(req) => req.properties?.custom_slippage === false,
|
||||||
|
(req) => req.properties?.best_quote_source === 'airswapV4',
|
||||||
|
(req) => typeof req.properties?.other_quote_selected === 'boolean',
|
||||||
|
(req) => typeof req.properties?.other_quote_selected_source === 'string',
|
||||||
|
(req) => typeof req.properties?.gas_fees === 'string',
|
||||||
|
(req) => typeof req.properties?.estimated_gas === 'string',
|
||||||
|
(req) => req.properties?.suggested_gas_price === '30',
|
||||||
|
(req) => req.properties?.used_gas_price === '30',
|
||||||
|
(req) => req.properties?.is_hardware_wallet === false,
|
||||||
|
(req) => req.properties?.stx_enabled === false,
|
||||||
|
(req) => req.properties?.current_stx_enabled === false,
|
||||||
|
(req) => typeof req.properties?.reg_tx_fee_in_usd === 'number',
|
||||||
|
(req) => typeof req.properties?.reg_tx_fee_in_eth === 'number',
|
||||||
|
(req) => typeof req.properties?.reg_tx_max_fee_in_usd === 'number',
|
||||||
|
(req) => typeof req.properties?.reg_tx_max_fee_in_eth === 'number',
|
||||||
|
(req) => req.properties?.token_to_amount_received === '',
|
||||||
|
(req) => req.properties?.quote_vs_executionRatio === null,
|
||||||
|
(req) => req.properties?.estimated_vs_used_gasRatio === '100%',
|
||||||
|
(req) => req.properties?.approval_gas_cost_in_eth === 0,
|
||||||
|
(req) => typeof req.properties?.trade_gas_cost_in_eth === 'number',
|
||||||
|
(req) =>
|
||||||
|
typeof req.properties?.trade_and_approval_gas_cost_in_eth === 'number',
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq14 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.SwapCompleted,
|
||||||
|
(req) => Object.keys(req.properties).length === 4,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'background',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
];
|
||||||
|
|
||||||
|
assert.ok(
|
||||||
|
assertInAnyOrder([reqs[13], reqs[14]], [assertionsReq13, assertionsReq14]),
|
||||||
|
'assertSwapCompletedEvents(): reqs[13] and reqs[14] did not match what was expected',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async function assertExitedSwapsEvents(reqs) {
|
||||||
|
const assertionsReq15 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.ExitedSwaps,
|
||||||
|
(req) => Object.keys(req.properties).length === 12,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
|
||||||
|
(req) => req.properties?.token_from_amount === '2',
|
||||||
|
(req) => req.properties?.request_type === false,
|
||||||
|
(req) => req.properties?.slippage === 2,
|
||||||
|
(req) => req.properties?.custom_slippage === false,
|
||||||
|
(req) => req.properties?.current_screen === 'awaiting-swap',
|
||||||
|
(req) => req.properties?.is_hardware_wallet === false,
|
||||||
|
(req) => req.properties?.stx_enabled === false,
|
||||||
|
(req) => req.properties?.current_stx_enabled === false,
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq16 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.ExitedSwaps,
|
||||||
|
(req) => Object.keys(req.properties).length === 4,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
];
|
||||||
|
|
||||||
|
assert.ok(
|
||||||
|
assertInAnyOrder([reqs[15], reqs[16]], [assertionsReq15, assertionsReq16]),
|
||||||
|
'assertExitedSwapsEvents(): reqs[15] and reqs[16] did not match what was expected',
|
||||||
|
);
|
||||||
|
|
||||||
|
const assertionsReq17 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.ExitedSwaps,
|
||||||
|
(req) => Object.keys(req.properties).length === 9,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
|
||||||
|
(req) => req.properties?.custom_slippage === true,
|
||||||
|
(req) => req.properties?.current_screen === 'awaiting-swap',
|
||||||
|
(req) => req.properties?.is_hardware_wallet === false,
|
||||||
|
(req) => req.properties?.stx_enabled === false,
|
||||||
|
(req) => req.properties?.current_stx_enabled === false,
|
||||||
|
];
|
||||||
|
|
||||||
|
const assertionsReq18 = [
|
||||||
|
(req) => req.event === MetaMetricsEventName.ExitedSwaps,
|
||||||
|
(req) => Object.keys(req.properties).length === 4,
|
||||||
|
|
||||||
|
(req) => req.properties?.category === MetaMetricsEventCategory.Swaps,
|
||||||
|
(req) => req.properties?.chain_id === toHex(1337),
|
||||||
|
(req) => req.properties?.environment_type === 'fullscreen',
|
||||||
|
(req) => req.properties?.locale === 'en',
|
||||||
|
];
|
||||||
|
|
||||||
|
assert.ok(
|
||||||
|
assertInAnyOrder([reqs[17], reqs[18]], [assertionsReq17, assertionsReq18]),
|
||||||
|
'assertExitedSwapsEvents(): reqs[17] and reqs[18] did not match what was expected',
|
||||||
|
);
|
||||||
|
}
|
@ -6,22 +6,19 @@ const {
|
|||||||
WALLET_PASSWORD,
|
WALLET_PASSWORD,
|
||||||
WINDOW_TITLES,
|
WINDOW_TITLES,
|
||||||
DEFAULT_GANACHE_OPTIONS,
|
DEFAULT_GANACHE_OPTIONS,
|
||||||
generateETHBalance,
|
|
||||||
roundToXDecimalPlaces,
|
|
||||||
generateRandNumBetween,
|
generateRandNumBetween,
|
||||||
sleepSeconds,
|
sleepSeconds,
|
||||||
terminateServiceWorker,
|
terminateServiceWorker,
|
||||||
unlockWallet,
|
unlockWallet,
|
||||||
largeDelayMs,
|
largeDelayMs,
|
||||||
|
genRandInitBal,
|
||||||
|
roundToXDecimalPlaces,
|
||||||
} = require('../helpers');
|
} = require('../helpers');
|
||||||
const FixtureBuilder = require('../fixture-builder');
|
const FixtureBuilder = require('../fixture-builder');
|
||||||
|
|
||||||
describe('MV3 - Restart service worker multiple times', function () {
|
describe('MV3 - Restart service worker multiple times', function () {
|
||||||
it('Simple simple send flow within full screen view should still be usable', async function () {
|
it('Simple simple send flow within full screen view should still be usable', async function () {
|
||||||
const initialBalance = roundToXDecimalPlaces(
|
const { initialBalance, initialBalanceInHex } = genRandInitBal();
|
||||||
generateRandNumBetween(10, 100),
|
|
||||||
4,
|
|
||||||
);
|
|
||||||
|
|
||||||
await withFixtures(
|
await withFixtures(
|
||||||
{
|
{
|
||||||
@ -30,7 +27,7 @@ describe('MV3 - Restart service worker multiple times', function () {
|
|||||||
accounts: [
|
accounts: [
|
||||||
{
|
{
|
||||||
secretKey: DEFAULT_GANACHE_OPTIONS.accounts[0].secretKey,
|
secretKey: DEFAULT_GANACHE_OPTIONS.accounts[0].secretKey,
|
||||||
balance: generateETHBalance(initialBalance),
|
balance: initialBalanceInHex,
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
}),
|
}),
|
||||||
|
@ -63,7 +63,10 @@ import {
|
|||||||
checkNetworkAndAccountSupports1559,
|
checkNetworkAndAccountSupports1559,
|
||||||
} from '../../selectors';
|
} from '../../selectors';
|
||||||
|
|
||||||
import { MetaMetricsEventCategory } from '../../../shared/constants/metametrics';
|
import {
|
||||||
|
MetaMetricsEventCategory,
|
||||||
|
MetaMetricsEventName,
|
||||||
|
} from '../../../shared/constants/metametrics';
|
||||||
import {
|
import {
|
||||||
ERROR_FETCHING_QUOTES,
|
ERROR_FETCHING_QUOTES,
|
||||||
QUOTES_NOT_AVAILABLE_ERROR,
|
QUOTES_NOT_AVAILABLE_ERROR,
|
||||||
@ -787,6 +790,18 @@ export const fetchQuotesAndSetQuoteState = (
|
|||||||
} else {
|
} else {
|
||||||
const newSelectedQuote = fetchedQuotes[selectedAggId];
|
const newSelectedQuote = fetchedQuotes[selectedAggId];
|
||||||
|
|
||||||
|
const tokenToAmountBN = calcTokenAmount(
|
||||||
|
newSelectedQuote.destinationAmount,
|
||||||
|
newSelectedQuote.decimals || 18,
|
||||||
|
);
|
||||||
|
|
||||||
|
// Firefox and Chrome have different implementations of the APIs
|
||||||
|
// that we rely on for communication accross the app. On Chrome big
|
||||||
|
// numbers are converted into number strings, on firefox they remain
|
||||||
|
// Big Number objects. As such, we convert them here for both
|
||||||
|
// browsers.
|
||||||
|
const tokenToAmountToString = tokenToAmountBN.toString(10);
|
||||||
|
|
||||||
trackEvent({
|
trackEvent({
|
||||||
event: 'Quotes Received',
|
event: 'Quotes Received',
|
||||||
category: MetaMetricsEventCategory.Swaps,
|
category: MetaMetricsEventCategory.Swaps,
|
||||||
@ -794,10 +809,7 @@ export const fetchQuotesAndSetQuoteState = (
|
|||||||
token_from: fromTokenSymbol,
|
token_from: fromTokenSymbol,
|
||||||
token_from_amount: String(inputValue),
|
token_from_amount: String(inputValue),
|
||||||
token_to: toTokenSymbol,
|
token_to: toTokenSymbol,
|
||||||
token_to_amount: calcTokenAmount(
|
token_to_amount: tokenToAmountToString,
|
||||||
newSelectedQuote.destinationAmount,
|
|
||||||
newSelectedQuote.decimals || 18,
|
|
||||||
),
|
|
||||||
request_type: balanceError ? 'Quote' : 'Order',
|
request_type: balanceError ? 'Quote' : 'Order',
|
||||||
slippage: maxSlippage,
|
slippage: maxSlippage,
|
||||||
custom_slippage: maxSlippage !== Slippage.default,
|
custom_slippage: maxSlippage !== Slippage.default,
|
||||||
@ -1177,7 +1189,7 @@ export const signAndSendTransactions = (
|
|||||||
}
|
}
|
||||||
|
|
||||||
trackEvent({
|
trackEvent({
|
||||||
event: 'Swap Started',
|
event: MetaMetricsEventName.SwapStarted,
|
||||||
category: MetaMetricsEventCategory.Swaps,
|
category: MetaMetricsEventCategory.Swaps,
|
||||||
sensitiveProperties: swapMetaData,
|
sensitiveProperties: swapMetaData,
|
||||||
});
|
});
|
||||||
|
Loading…
Reference in New Issue
Block a user