From 2ced3a8bfa75b073a6357820ecfe21cd59858bc0 Mon Sep 17 00:00:00 2001 From: Dan J Miller Date: Mon, 15 Nov 2021 15:50:33 -0330 Subject: [PATCH] Add migration to set showTestNetworks to true if there is evidence of testnet use (#12675) * Add migration to set showTestNetworks to true if there is evidence the user has used a test network * Add migration to index file * Remove console.log * Clean up conditional structure in migration 67 --- app/scripts/migrations/067.js | 66 +++++++++ app/scripts/migrations/067.test.js | 217 +++++++++++++++++++++++++++++ app/scripts/migrations/index.js | 2 + 3 files changed, 285 insertions(+) create mode 100644 app/scripts/migrations/067.js create mode 100644 app/scripts/migrations/067.test.js diff --git a/app/scripts/migrations/067.js b/app/scripts/migrations/067.js new file mode 100644 index 000000000..98150edf7 --- /dev/null +++ b/app/scripts/migrations/067.js @@ -0,0 +1,66 @@ +import { cloneDeep } from 'lodash'; +import BigNumber from 'bignumber.js'; +import { TEST_CHAINS } from '../../../shared/constants/network'; + +const hexNumberIsGreaterThanZero = (hexNumber) => + new BigNumber(hexNumber || '0x0', 16).gt(0); + +const version = 67; + +/** + * Sets the showTestNetworks property to true if it was false or undefined, and there is evidence + * that the user has used a test net + */ +export default { + version, + async migrate(originalVersionedData) { + const versionedData = cloneDeep(originalVersionedData); + versionedData.meta.version = version; + const state = versionedData.data; + const newState = transformState(state); + versionedData.data = newState; + return versionedData; + }, +}; + +function transformState(state) { + const PreferencesController = state?.PreferencesController || {}; + const preferences = PreferencesController.preferences || {}; + + if (preferences.showTestNetworks) { + return state; + } + + const transactions = state?.TransactionController?.transactions || {}; + const provider = state.NetworkController?.provider || {}; + const cachedBalances = state.CachedBalancesController?.cachedBalances || {}; + + const userIsCurrentlyOnATestNet = TEST_CHAINS.includes(provider?.chainId); + const userHasMadeATestNetTransaction = Object.values( + transactions, + ).some(({ chainId }) => TEST_CHAINS.includes(chainId)); + const userHasACachedBalanceOnATestnet = TEST_CHAINS.some((chainId) => { + const cachedBalancesForChain = Object.values(cachedBalances[chainId] || {}); + const userHasABalanceGreaterThanZeroOnThisChain = cachedBalancesForChain.some( + hexNumberIsGreaterThanZero, + ); + return userHasABalanceGreaterThanZeroOnThisChain; + }); + const userHasUsedATestnet = + userIsCurrentlyOnATestNet || + userHasMadeATestNetTransaction || + userHasACachedBalanceOnATestnet; + + const newState = { + ...state, + PreferencesController: { + ...PreferencesController, + preferences: { + ...preferences, + showTestNetworks: userHasUsedATestnet, + }, + }, + }; + + return newState; +} diff --git a/app/scripts/migrations/067.test.js b/app/scripts/migrations/067.test.js new file mode 100644 index 000000000..85bfa76cf --- /dev/null +++ b/app/scripts/migrations/067.test.js @@ -0,0 +1,217 @@ +import { TEST_CHAINS } from '../../../shared/constants/network'; +import migration67 from './067'; + +describe('migration #67', () => { + it('should update the version metadata', async () => { + const oldStorage = { + meta: { + version: 66, + }, + data: {}, + }; + + const newStorage = await migration67.migrate(oldStorage); + expect(newStorage.meta).toStrictEqual({ + version: 67, + }); + }); + + it('should set showTestNetworks to true if the user is currently on a test network', async () => { + const oldStorage = { + meta: {}, + data: { + PreferencesController: { + preferences: { + showTestNetworks: false, + }, + }, + NetworkController: { + provider: { + chainId: TEST_CHAINS[0], + }, + }, + }, + }; + + const newStorage = await migration67.migrate(oldStorage); + expect( + newStorage.data.PreferencesController.preferences.showTestNetworks, + ).toBe(true); + }); + + it('should set showTestNetworks to true if there is a transaction on a test network in state', async () => { + const oldStorage = { + meta: {}, + data: { + PreferencesController: { + preferences: { + showTestNetworks: false, + }, + }, + NetworkController: { + provider: { + chainId: 'not a test net', + }, + }, + TransactionController: { + transactions: { + abc123: { + chainId: TEST_CHAINS[0], + }, + }, + }, + }, + }; + + const newStorage = await migration67.migrate(oldStorage); + expect( + newStorage.data.PreferencesController.preferences.showTestNetworks, + ).toBe(true); + }); + + it('should set showTestNetworks to true if the user has a cached balance on a test network', async () => { + const oldStorage = { + meta: {}, + data: { + PreferencesController: { + preferences: { + showTestNetworks: false, + }, + }, + NetworkController: { + provider: { + chainId: 'not a test net', + }, + }, + TransactionController: { + transactions: { + abc123: { + chainId: 'not a test net', + }, + }, + }, + CachedBalancesController: { + cachedBalances: { + '0x1': { + '0x027d4ae98b79d0c52918bab4c3170bea701fb8ab': '0x0', + '0x2f318c334780961fb129d2a6c30d0763d9a5c970': '0x0', + '0x7a46ce51fbbb29c34aea1fe9833c27b5d2781925': '0x0', + }, + [TEST_CHAINS[0]]: { + '0x027d4ae98b79d0c52918bab4c3170bea701fb8ab': '0x0', + '0x2f318c334780961fb129d2a6c30d0763d9a5c970': '0x1', + '0x7a46ce51fbbb29c34aea1fe9833c27b5d2781925': '0x0', + }, + [TEST_CHAINS[1]]: { + '0x027d4ae98b79d0c52918bab4c3170bea701fb8ab': '0x0', + '0x2f318c334780961fb129d2a6c30d0763d9a5c970': '0x0', + '0x7a46ce51fbbb29c34aea1fe9833c27b5d2781925': '0x0', + }, + }, + }, + }, + }; + + const newStorage = await migration67.migrate(oldStorage); + expect( + newStorage.data.PreferencesController.preferences.showTestNetworks, + ).toBe(true); + }); + + it('should leave showTestNetworks false if there is no evidence of test network usage', async () => { + const oldStorage = { + meta: {}, + data: { + PreferencesController: { + preferences: { + showTestNetworks: false, + }, + }, + NetworkController: { + provider: { + chainId: 'not a test net', + }, + }, + TransactionController: { + transactions: { + abc123: { + chainId: 'not a test net', + }, + }, + }, + CachedBalancesController: { + cachedBalances: { + '0x1': { + '0x027d4ae98b79d0c52918bab4c3170bea701fb8ab': '0x10', + '0x2f318c334780961fb129d2a6c30d0763d9a5c970': '0x20', + '0x7a46ce51fbbb29c34aea1fe9833c27b5d2781925': '0x30', + }, + [TEST_CHAINS[0]]: { + '0x027d4ae98b79d0c52918bab4c3170bea701fb8ab': '0x0', + '0x2f318c334780961fb129d2a6c30d0763d9a5c970': '0x0', + '0x7a46ce51fbbb29c34aea1fe9833c27b5d2781925': '0x0', + }, + [TEST_CHAINS[1]]: { + '0x027d4ae98b79d0c52918bab4c3170bea701fb8ab': '0x0', + '0x2f318c334780961fb129d2a6c30d0763d9a5c970': '0x0', + '0x7a46ce51fbbb29c34aea1fe9833c27b5d2781925': '0x0', + }, + }, + }, + }, + }; + const newStorage = await migration67.migrate(oldStorage); + expect( + newStorage.data.PreferencesController.preferences.showTestNetworks, + ).toBe(false); + }); + + it('should leave showTestNetworks true if it was true but there is no evidence of test network usage', async () => { + const oldStorage = { + meta: {}, + data: { + PreferencesController: { + preferences: { + showTestNetworks: true, + }, + }, + NetworkController: { + provider: { + chainId: 'not a test net', + }, + }, + TransactionController: { + transactions: { + abc123: { + chainId: 'not a test net', + }, + }, + }, + CachedBalancesController: { + cachedBalances: { + '0x1': { + '0x027d4ae98b79d0c52918bab4c3170bea701fb8ab': '0x10', + '0x2f318c334780961fb129d2a6c30d0763d9a5c970': '0x20', + '0x7a46ce51fbbb29c34aea1fe9833c27b5d2781925': '0x30', + }, + [TEST_CHAINS[0]]: { + '0x027d4ae98b79d0c52918bab4c3170bea701fb8ab': '0x0', + '0x2f318c334780961fb129d2a6c30d0763d9a5c970': '0x0', + '0x7a46ce51fbbb29c34aea1fe9833c27b5d2781925': '0x0', + }, + [TEST_CHAINS[1]]: { + '0x027d4ae98b79d0c52918bab4c3170bea701fb8ab': '0x0', + '0x2f318c334780961fb129d2a6c30d0763d9a5c970': '0x0', + '0x7a46ce51fbbb29c34aea1fe9833c27b5d2781925': '0x0', + }, + }, + }, + }, + }; + + const newStorage = await migration67.migrate(oldStorage); + expect( + newStorage.data.PreferencesController.preferences.showTestNetworks, + ).toBe(true); + }); +}); diff --git a/app/scripts/migrations/index.js b/app/scripts/migrations/index.js index 7baf840e3..2471381f5 100644 --- a/app/scripts/migrations/index.js +++ b/app/scripts/migrations/index.js @@ -70,6 +70,7 @@ import m063 from './063'; import m064 from './064'; import m065 from './065'; import m066 from './066'; +import m067 from './067'; const migrations = [ m002, @@ -137,6 +138,7 @@ const migrations = [ m064, m065, m066, + m067, ]; export default migrations;