From 4d5c247a2ca9cc3f7a100b77c6e243a80cf5ff0d Mon Sep 17 00:00:00 2001 From: Jakub Senko Date: Wed, 20 Nov 2024 10:42:47 +0100 Subject: [PATCH] refactor(suite): optimize how often fees are fetched in send form !!! WORK IN PROGRESS !!! do not merge yet This commit introduces a new approach to fetching fees. Previous state: Fees for every wallet account were fetched periodically after 10 blocks. This was problematic for various reasons: 1. The data weren't often needed. 2. Useless network requests. 3. Some fees were outdated, because fees aren't connected to blocks in any way - in fact, fee can update multiple times in between two blocks! New state: This solution mainly builds on the idea that fees aren't connected to blocks. This link is now removed. There is a dedicated `useFees` hook that is supposed to be called for every route that needs to display fees. The hook is responsible for decision on how often the fee should be fetched (decided manually in `networkToInterval` function). That way all logic behind fee fetching is located in one file. Consequence of this decision is that `updateFeeInfoThunk` is now "dumb" - it fetches new fees whenever it is called. While this solution is more verbose (`useFees` has to be called everywhere fees are needed), I think its explicit relationship improves readability of the code. What needs to be done before this commit is mergeable: 1. Set network refresh intervals in `networkToInterval` function. 2. Call `useFees` for every route that needs fees (swap, sell, etc.). 3. Move `useFees` hook to better location so that it can be used in `suite-native/module-send/src/screens/SendOutputsScreen.tsx:174`, too. Relates to #15087 --- packages/suite/src/hooks/wallet/useFees.ts | 33 +++++++++++++++++++ .../suite/src/views/wallet/send/index.tsx | 3 ++ .../src/blockchain/blockchainMiddleware.ts | 2 -- .../src/blockchain/blockchainThunks.ts | 9 ----- 4 files changed, 36 insertions(+), 11 deletions(-) create mode 100644 packages/suite/src/hooks/wallet/useFees.ts diff --git a/packages/suite/src/hooks/wallet/useFees.ts b/packages/suite/src/hooks/wallet/useFees.ts new file mode 100644 index 00000000000..46026a9c870 --- /dev/null +++ b/packages/suite/src/hooks/wallet/useFees.ts @@ -0,0 +1,33 @@ +import { useDispatch } from 'react-redux'; +import { useCallback, useEffect } from 'react'; + +import { NetworkSymbol } from "@suite-common/wallet-config"; +import { + updateFeeInfoThunk, +} from '@suite-common/wallet-core'; + +const networkToInterval = (symbol: NetworkSymbol): number => { + switch (symbol) { + case 'pol': + return 1000; + default: + return 10000; + } +} + +export const useFees = (symbol: NetworkSymbol) => { + const dispatch = useDispatch(); + + const refreshFees = useCallback(() => { + dispatch(updateFeeInfoThunk(symbol)) + }, [dispatch, symbol]) + + useEffect(() => { + refreshFees(); + const interval = setInterval(refreshFees, networkToInterval(symbol)); + + return () => { + clearInterval(interval) + } + }, [refreshFees, symbol]) +} diff --git a/packages/suite/src/views/wallet/send/index.tsx b/packages/suite/src/views/wallet/send/index.tsx index 59c02ea8be1..7361a8810d0 100644 --- a/packages/suite/src/views/wallet/send/index.tsx +++ b/packages/suite/src/views/wallet/send/index.tsx @@ -9,6 +9,7 @@ import { spacingsPx } from '@trezor/theme'; import { useSelector } from 'src/hooks/suite'; import { WalletLayout } from 'src/components/wallet'; import { useSendForm, SendContext, UseSendFormProps } from 'src/hooks/wallet/useSendForm'; +import { useFees } from 'src/hooks/wallet/useFees'; import { selectTargetAnonymityByAccountKey, selectRegisteredUtxosByAccountKey, @@ -78,6 +79,8 @@ const SendLoaded = ({ children, selectedAccount }: SendLoadedProps) => { const { symbol } = selectedAccount.account; + useFees(symbol); + if (props.sendRaw) { return ( diff --git a/suite-common/wallet-core/src/blockchain/blockchainMiddleware.ts b/suite-common/wallet-core/src/blockchain/blockchainMiddleware.ts index db493842a48..7e96df4f32a 100644 --- a/suite-common/wallet-core/src/blockchain/blockchainMiddleware.ts +++ b/suite-common/wallet-core/src/blockchain/blockchainMiddleware.ts @@ -7,7 +7,6 @@ import { onBlockchainConnectThunk, onBlockMinedThunk, onBlockchainNotificationThunk, - updateFeeInfoThunk, onBlockchainDisconnectThunk, } from './blockchainThunks'; @@ -31,7 +30,6 @@ export const prepareBlockchainMiddleware = createMiddlewareWithExtraDeps( } break; case TREZOR_CONNECT_BLOCKCHAIN_ACTIONS.BLOCK: - dispatch(updateFeeInfoThunk(action.payload.coin.shortcut)); dispatch(onBlockMinedThunk(action.payload)); // cardano stuff dispatch( diff --git a/suite-common/wallet-core/src/blockchain/blockchainThunks.ts b/suite-common/wallet-core/src/blockchain/blockchainThunks.ts index d71fad83345..bea9e8c9a45 100644 --- a/suite-common/wallet-core/src/blockchain/blockchainThunks.ts +++ b/suite-common/wallet-core/src/blockchain/blockchainThunks.ts @@ -33,7 +33,6 @@ import { selectAccounts } from '../accounts/accountsReducer'; import { fetchAndUpdateAccountThunk } from '../accounts/accountsThunks'; import { BLOCKCHAIN_MODULE_PREFIX, blockchainActions } from './blockchainActions'; import { selectBlockchainState, selectNetworkBlockchainInfo } from './blockchainReducer'; -import { selectNetworkFeeInfo } from '../fees/feesReducer'; const DEFAULT_ACCOUNT_SYNC_INTERVAL = 60 * 1000; @@ -108,14 +107,6 @@ export const updateFeeInfoThunk = createThunk( const network = getNetworkOptional(symbol.toLowerCase()); if (!network) return; const blockchainInfo = selectNetworkBlockchainInfo(getState(), network.symbol); - const feeInfo = selectNetworkFeeInfo(getState(), network.symbol); - - if ( - feeInfo && - feeInfo.blockHeight > 0 && - blockchainInfo.blockHeight - feeInfo.blockHeight < 10 - ) - return; let newFeeInfo;