From 15b70d1185bbdb9b20b20a8d3879f36c55fd50a6 Mon Sep 17 00:00:00 2001 From: James Mealy Date: Fri, 9 Aug 2024 14:15:25 +0200 Subject: [PATCH] Fix: correct filtering of history for txs marked trusted and imitation [SW-100] (#3907) * fix: filter imitation txs with trusted tokens * update gateway sdk * fix: create separate params for hiding trusted and imitation transactions * fix: separate untrusted and imitation filters in getTxHistory and getFilteredTxHistory * tests: update unit tests for fetchFilteredTxHistory * fix: remove unecessary default value --- src/components/transactions/TrustedToggle/index.tsx | 6 +++--- src/hooks/loadables/useLoadTxHistory.ts | 10 ++++++---- src/hooks/useTxHistory.ts | 11 ++++++----- src/services/transactions/index.ts | 12 ++++++++++-- src/store/settingsSlice.ts | 10 +++++----- src/utils/__tests__/tx-history-filter.test.ts | 10 +++++++--- src/utils/tx-history-filter.ts | 7 ++++--- 7 files changed, 41 insertions(+), 25 deletions(-) diff --git a/src/components/transactions/TrustedToggle/index.tsx b/src/components/transactions/TrustedToggle/index.tsx index 19dc0f9807..dfb513fb7e 100644 --- a/src/components/transactions/TrustedToggle/index.tsx +++ b/src/components/transactions/TrustedToggle/index.tsx @@ -1,13 +1,13 @@ import { useHasFeature } from '@/hooks/useChains' import { useAppDispatch, useAppSelector } from '@/store' -import { selectSettings, setshowOnlyTrustedTransactions } from '@/store/settingsSlice' +import { selectSettings, hideSuspiciousTransactions } from '@/store/settingsSlice' import { FEATURES } from '@/utils/chains' import madProps from '@/utils/mad-props' import _TrustedToggleButton from './TrustedToggleButton' const useOnlyTrusted = () => { const userSettings = useAppSelector(selectSettings) - return userSettings.showOnlyTrustedTransactions || false + return userSettings.hideSuspiciousTransactions || false } const useHasDefaultTokenList = () => { @@ -17,7 +17,7 @@ const useHasDefaultTokenList = () => { const useSetOnlyTrusted = () => { const dispatch = useAppDispatch() return (isOn: boolean) => { - dispatch(setshowOnlyTrustedTransactions(isOn)) + dispatch(hideSuspiciousTransactions(isOn)) } } diff --git a/src/hooks/loadables/useLoadTxHistory.ts b/src/hooks/loadables/useLoadTxHistory.ts index 284e139619..f656fad7a8 100644 --- a/src/hooks/loadables/useLoadTxHistory.ts +++ b/src/hooks/loadables/useLoadTxHistory.ts @@ -12,19 +12,21 @@ import { FEATURES } from '@/utils/chains' export const useLoadTxHistory = (): AsyncResult => { const { safe, safeAddress, safeLoaded } = useSafeInfo() const { chainId, txHistoryTag } = safe - const { showOnlyTrustedTransactions } = useAppSelector(selectSettings) + const { hideSuspiciousTransactions } = useAppSelector(selectSettings) const hasDefaultTokenlist = useHasFeature(FEATURES.DEFAULT_TOKENLIST) + const hideUntrustedTxs = (hasDefaultTokenlist && hideSuspiciousTransactions) || false + const hideImitationTxs = hideSuspiciousTransactions || false - // Re-fetch when chainId, address, showOnlyTrustedTransactions, or txHistoryTag changes + // Re-fetch when chainId, address, hideSuspiciousTransactions, or txHistoryTag changes const [data, error, loading] = useAsync( () => { if (!safeLoaded) return if (!safe.deployed) return Promise.resolve({ results: [] }) - return getTxHistory(chainId, safeAddress, hasDefaultTokenlist && showOnlyTrustedTransactions) + return getTxHistory(chainId, safeAddress, hideUntrustedTxs, hideImitationTxs) }, // eslint-disable-next-line react-hooks/exhaustive-deps - [safeLoaded, chainId, safeAddress, showOnlyTrustedTransactions, hasDefaultTokenlist, txHistoryTag, safe.deployed], + [safeLoaded, chainId, safeAddress, hideSuspiciousTransactions, hasDefaultTokenlist, txHistoryTag, safe.deployed], false, ) diff --git a/src/hooks/useTxHistory.ts b/src/hooks/useTxHistory.ts index 9fdefccd3b..ac260c1fb0 100644 --- a/src/hooks/useTxHistory.ts +++ b/src/hooks/useTxHistory.ts @@ -20,9 +20,10 @@ const useTxHistory = ( // The latest page of the history is always in the store const historyState = useAppSelector(selectTxHistory) const [filter] = useTxFilter() - const { showOnlyTrustedTransactions } = useAppSelector(selectSettings) + const { hideSuspiciousTransactions } = useAppSelector(selectSettings) const hasDefaultTokenlist = useHasFeature(FEATURES.DEFAULT_TOKENLIST) - const onlyTrusted = (hasDefaultTokenlist && showOnlyTrustedTransactions) || false + const hideUntrustedTxs = (hasDefaultTokenlist && hideSuspiciousTransactions) || false + const hideImitationTxs = hideSuspiciousTransactions || false const { safe: { chainId }, @@ -35,10 +36,10 @@ const useTxHistory = ( if (!(filter || pageUrl)) return return filter - ? fetchFilteredTxHistory(chainId, safeAddress, filter, onlyTrusted, pageUrl) - : getTxHistory(chainId, safeAddress, onlyTrusted, pageUrl) + ? fetchFilteredTxHistory(chainId, safeAddress, filter, hideUntrustedTxs, hideImitationTxs, pageUrl) + : getTxHistory(chainId, safeAddress, hideUntrustedTxs, hideImitationTxs, pageUrl) }, - [chainId, safeAddress, pageUrl, filter, onlyTrusted], + [filter, pageUrl, chainId, safeAddress, hideUntrustedTxs, hideImitationTxs], false, ) diff --git a/src/services/transactions/index.ts b/src/services/transactions/index.ts index ac1d248835..d9fb50fc40 100644 --- a/src/services/transactions/index.ts +++ b/src/services/transactions/index.ts @@ -21,13 +21,21 @@ export const getTxDetails = memoize( (id: string, chainId: string) => `${chainId}-${id}`, ) -export const getTxHistory = (chainId: string, safeAddress: string, trusted = false, pageUrl?: string) => { +export const getTxHistory = ( + chainId: string, + safeAddress: string, + hideUntrustedTxs: boolean, + hideImitationTxs: boolean, + pageUrl?: string, +) => { return getTransactionHistory( chainId, safeAddress, { timezone_offset: getTimezoneOffset(), // used for grouping txs by date - trusted, // if false, load all transactions, mark untrusted in the UI + // Untrusted and imitation txs are filtered together in the UI + trusted: hideUntrustedTxs, // if false, include transactions marked untrusted in the UI + imitation: !hideImitationTxs, // If true, include transactions marked imitation in the UI }, pageUrl, ) diff --git a/src/store/settingsSlice.ts b/src/store/settingsSlice.ts index f924958686..8f0422d0c2 100644 --- a/src/store/settingsSlice.ts +++ b/src/store/settingsSlice.ts @@ -29,7 +29,7 @@ export type SettingsState = { tokenList: TOKEN_LISTS - showOnlyTrustedTransactions?: boolean + hideSuspiciousTransactions?: boolean shortName: { copy: boolean @@ -53,7 +53,7 @@ export const initialState: SettingsState = { hiddenTokens: {}, - showOnlyTrustedTransactions: false, + hideSuspiciousTransactions: false, shortName: { copy: true, @@ -100,8 +100,8 @@ export const settingsSlice = createSlice({ setTokenList: (state, { payload }: PayloadAction) => { state.tokenList = payload }, - setshowOnlyTrustedTransactions: (state, { payload }: PayloadAction) => { - state.showOnlyTrustedTransactions = payload + hideSuspiciousTransactions: (state, { payload }: PayloadAction) => { + state.hideSuspiciousTransactions = payload }, setRpc: (state, { payload }: PayloadAction<{ chainId: string; rpc: string }>) => { const { chainId, rpc } = payload @@ -135,7 +135,7 @@ export const { setDarkMode, setHiddenTokensForChain, setTokenList, - setshowOnlyTrustedTransactions, + hideSuspiciousTransactions, setRpc, setTenderly, setOnChainSigning, diff --git a/src/utils/__tests__/tx-history-filter.test.ts b/src/utils/__tests__/tx-history-filter.test.ts index 956715118d..1c06e308f1 100644 --- a/src/utils/__tests__/tx-history-filter.test.ts +++ b/src/utils/__tests__/tx-history-filter.test.ts @@ -388,13 +388,14 @@ describe('tx-history-filter', () => { '0x123', { type: 'Incoming' as TxFilterType, filter: { value: '123' } }, false, + false, 'pageUrl1', ) expect(getIncomingTransfers).toHaveBeenCalledWith( '4', '0x123', - { value: '123', executed: undefined, timezone_offset: 3600000, trusted: false, imitation: false }, + { value: '123', executed: undefined, timezone_offset: 3600000, trusted: false, imitation: true }, 'pageUrl1', ) @@ -411,6 +412,7 @@ describe('tx-history-filter', () => { filter: { execution_date__gte: '1970-01-01T00:00:00.000Z', executed: 'true' }, }, false, + false, 'pageUrl2', ) @@ -422,7 +424,7 @@ describe('tx-history-filter', () => { executed: 'true', timezone_offset: 3600000, trusted: false, - imitation: false, + imitation: true, }, 'pageUrl2', ) @@ -437,13 +439,14 @@ describe('tx-history-filter', () => { '0x789', { type: 'Module-based' as TxFilterType, filter: { to: '0x123' } }, false, + false, 'pageUrl3', ) expect(getModuleTransactions).toHaveBeenCalledWith( '1', '0x789', - { to: '0x123', executed: undefined, timezone_offset: 3600000, trusted: false, imitation: false }, + { to: '0x123', executed: undefined, timezone_offset: 3600000, trusted: false, imitation: true }, 'pageUrl3', ) @@ -460,6 +463,7 @@ describe('tx-history-filter', () => { filter: { token_address: '0x123' }, }, false, + false, 'pageUrl3', ) diff --git a/src/utils/tx-history-filter.ts b/src/utils/tx-history-filter.ts index bcc4c5ba47..016d1cd0f7 100644 --- a/src/utils/tx-history-filter.ts +++ b/src/utils/tx-history-filter.ts @@ -119,15 +119,16 @@ export const fetchFilteredTxHistory = async ( chainId: string, safeAddress: string, filterData: TxFilter, - onlyTrusted: boolean, + hideUntrustedTxs: boolean, + hideImitationTxs: boolean, pageUrl?: string, ): Promise => { const fetchPage = () => { const query = { ...filterData.filter, timezone_offset: getTimezoneOffset(), - trusted: onlyTrusted ?? false, - imitation: onlyTrusted ?? false, + trusted: hideUntrustedTxs, + imitation: !hideImitationTxs, executed: filterData.type === TxFilterType.MULTISIG ? 'true' : undefined, }