Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 20 additions & 11 deletions apps/web/src/hooks/useAddressBalance.ts
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,6 @@ export const useAddressBalance = (
chainId?: number,
options: UseAddressBalanceOptions = {},
) => {
// const { chainId } = useActiveChainId()
const { includeSpam = false, onlyWithPrice = false, filterByChainId, enabled = true } = options
const list = useCombinedActiveList()

Expand All @@ -88,10 +87,11 @@ export const useAddressBalance = (
const data = (await response.json()) || []

return data
}, [address])
}, [address, chainId])

const {
data: balances,
isPending,
isLoading,
error,
refetch,
Expand All @@ -107,13 +107,6 @@ export const useAddressBalance = (
const filteredBalances = useMemo(() => {
return balances
? balances
.map((b) => ({
...b,
token: {
...b.token,
logoURI: b.token.logoURI ?? list[b.chainId]?.[safeGetAddress(b.token.address)]?.token.logoURI,
},
}))
.filter((balance) => {
// Filter out spam tokens if includeSpam is false
if (!includeSpam && balance.token.isSpam) {
Expand All @@ -132,6 +125,13 @@ export const useAddressBalance = (

return true
})
.map((b) => ({
...b,
token: {
...b.token,
logoURI: b.token.logoURI ?? list[b.chainId]?.[safeGetAddress(b.token.address)]?.token.logoURI,
},
}))
.sort((a, b) => {
const aListed = isListedToken(a.chainId, a.token.address)
const bListed = isListedToken(b.chainId, b.token.address)
Expand Down Expand Up @@ -175,7 +175,7 @@ export const useAddressBalance = (
// Get the top balances by USD value
const getTopBalances = useCallback(
(limit: number = 5) => {
return [...filteredBalances]
return filteredBalances
.filter((balance) => balance.price?.totalUsd)
.sort((a, b) => {
const aValue = a.price?.totalUsd || 0
Expand Down Expand Up @@ -212,6 +212,7 @@ export const useAddressBalance = (

return {
balances: filteredBalances,
isPending,
isLoading,
error,
totalBalanceUsd: filteredTotalBalanceUsd,
Expand Down Expand Up @@ -261,7 +262,15 @@ export const useMultichainAddressBalance = () => {
isLoading: isEvmLoading || isSolanaLoading,
totalBalanceUsd: (evmTotalBalanceUsd ?? 0) + (solanaTotalBalanceUsd ?? 0),
}
}, [evmBalances, solanaBalances, isEvmLoading, isSolanaLoading, evmTotalBalanceUsd, solanaTotalBalanceUsd])
}, [
evmBalances,
solanaBalances,
isEvmLoading,
isSolanaLoading,
evmTotalBalanceUsd,
solanaTotalBalanceUsd,
isListedToken,
])
}

export default useAddressBalance
5 changes: 4 additions & 1 deletion apps/web/src/hooks/usePublicNodeWaitForTransaction.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import { CHAINS } from 'config/chains'
import { PUBLIC_NODES } from 'config/nodes'
import memoize from 'lodash/memoize'
import { useCallback } from 'react'
import { RetryableError, retry, retryExp } from 'state/multicall/retry'
import { RetryableError, retryExp } from 'state/multicall/retry'
import { fallbackWithRank } from 'utils/fallbackWithRank'
import {
BlockNotFoundError,
Expand All @@ -23,6 +23,7 @@ import {
} from 'viem'
import { usePublicClient } from 'wagmi'
import { useW3WConfig } from 'wallet/W3WConfigContext'
import { createWalletTransactionEvent } from 'state/wallet/updater'
import { useActiveChainId } from './useActiveChainId'

export const getViemClientsPublicNodes = memoize((w3WConfig = false) => {
Expand Down Expand Up @@ -70,6 +71,7 @@ export function usePublicNodeWaitForTransaction(chainId_?: number) {
})
if (receipt.status === 'success') {
refetchBlockData()
window.dispatchEvent(createWalletTransactionEvent(selectedChain, { type: 'other' }))
}
return receipt
}
Expand All @@ -79,6 +81,7 @@ export function usePublicNodeWaitForTransaction(chainId_?: number) {
const receipt = await provider.getTransactionReceipt({ hash: opts.hash })
if (receipt.status === 'success') {
refetchBlockData()
window.dispatchEvent(createWalletTransactionEvent(selectedChain, { type: 'other' }))
}
return receipt
} catch (error) {
Expand Down
2 changes: 2 additions & 0 deletions apps/web/src/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import { useQuery } from '@tanstack/react-query'
import { WALLET_API } from 'config/constants/endpoints'
import { UpdatePositionsReminder } from 'views/Farms/components/UpdatePositionsReminder'
import { useAccount } from 'wagmi'
import { WalletBalanceUpdater } from 'state/wallet/updater'
import ListsUpdater from './state/lists/updater'
import MulticallUpdater from './state/multicall/updater'
import TransactionUpdater, { SolanaTransactionUpdater } from './state/transactions/updater'
Expand All @@ -19,6 +20,7 @@ export function Updaters() {
))}
<SolanaTransactionUpdater />
<MulticallUpdater />
<WalletBalanceUpdater />
</>
)
}
Expand Down
2 changes: 2 additions & 0 deletions apps/web/src/state/transactions/actions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ export type TransactionType =
| 'bridge'
| 'claim-liquid-staking'
| 'place-limit-order'
| 'other'

export interface SerializableTransactionReceipt {
to: string
Expand Down Expand Up @@ -86,6 +87,7 @@ export const addTransaction = createAction<{
translatableSummary?: { text: string; data?: Record<string, string | number | undefined> }
type?: TransactionType
order?: Order
outputChainId?: number
crossChainFarm?: CrossChainFarmTransactionType
receipt?: SerializableTransactionReceipt
}>('transactions/addTransaction')
Expand Down
4 changes: 4 additions & 0 deletions apps/web/src/state/transactions/hooks.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ export function useTransactionAdder(overrideChainId?: number): (
claim?: { recipient: string }
type?: TransactionType
order?: Order
outputChainId?: number
crossChainFarm?: CrossChainFarmTransactionType
// add/remove pool
baseCurrencyId?: string
Expand Down Expand Up @@ -72,6 +73,7 @@ export function useTransactionAdder(overrideChainId?: number): (
claim,
type,
order,
outputChainId,
crossChainFarm,
receipt,
}: {
Expand All @@ -83,6 +85,7 @@ export function useTransactionAdder(overrideChainId?: number): (
order?: Order
crossChainFarm?: CrossChainFarmTransactionType
receipt?: SerializableTransactionReceipt
outputChainId?: number
} = {},
) => {
if (!from) return
Expand Down Expand Up @@ -118,6 +121,7 @@ export function useTransactionAdder(overrideChainId?: number): (
claim,
type,
order,
outputChainId,
crossChainFarm,
receipt,
}),
Expand Down
2 changes: 2 additions & 0 deletions apps/web/src/state/transactions/reducer.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ describe('transaction reducer', () => {
hash: '0x0',
approval: { tokenAddress: 'abc', spender: 'def' },
from: 'abc',
outputChainId: ChainId.ETHEREUM,
}),
)
const txs = store.getState()
Expand All @@ -38,6 +39,7 @@ describe('transaction reducer', () => {
expect(tx?.approval).toEqual({ tokenAddress: 'abc', spender: 'def' })
expect(tx?.from).toEqual('abc')
expect(tx?.addedTime).toBeGreaterThanOrEqual(beforeTime)
expect(tx?.outputChainId).toBeGreaterThanOrEqual(ChainId.ETHEREUM)
})
})

Expand Down
3 changes: 3 additions & 0 deletions apps/web/src/state/transactions/reducer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ export interface TransactionDetails {
confirmedTime?: number
from: string
crossChainFarm?: CrossChainFarmTransactionType
outputChainId?: number
}

export interface TransactionState {
Expand Down Expand Up @@ -59,6 +60,7 @@ export default createReducer(initialState, (builder) =>
claim,
type,
order,
outputChainId,
crossChainFarm,
receipt,
},
Expand All @@ -78,6 +80,7 @@ export default createReducer(initialState, (builder) =>
addedTime: now(),
type,
order,
outputChainId,
crossChainFarm,
receipt,
}
Expand Down
7 changes: 7 additions & 0 deletions apps/web/src/state/transactions/updater.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import useAccountActiveChain from 'hooks/useAccountActiveChain'
import { useSolanaConnectionWithRpcAtom } from 'hooks/solana/useSolanaConnectionWithRpcAtom'
import { TxVersion } from '@pancakeswap/solana-core-sdk'
import { useLatestTxReceipt } from 'state/farmsV4/state/accountPositions/hooks/useLatestTxReceipt'
import { createWalletTransactionEvent } from 'state/wallet/updater'
import {
FarmTransactionStatus,
MsgStatus,
Expand Down Expand Up @@ -88,6 +89,12 @@ export const Updater: React.FC<{ chainId: number }> = ({ chainId }) => {
const toast = receipt.status === 'success' ? toastSuccess : toastError
if (receipt.status === 'success') {
refetchBlockData()
window.dispatchEvent(
createWalletTransactionEvent(chainId, {
type: transaction?.type,
outputChainId: transaction?.outputChainId,
}),
)
}
toast(
t('Transaction receipt'),
Expand Down
115 changes: 115 additions & 0 deletions apps/web/src/state/wallet/updater.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,115 @@
import { ChainId, NonEVMChainId, UnifiedChainId } from '@pancakeswap/chains'
import useAccountActiveChain from 'hooks/useAccountActiveChain'
import useAddressBalance from 'hooks/useAddressBalance'
import { useEffect, useRef } from 'react'
import { TransactionDetails } from 'state/transactions/reducer'

const WALLET_TRX_EVENT_NAME = 'pcs:transaction-success'

interface WalletTransactionEvent
extends CustomEvent<{
chainId: UnifiedChainId
transaction: Partial<Pick<TransactionDetails, 'outputChainId' | 'type'>>
}> {}

export function createWalletTransactionEvent(
chainId: UnifiedChainId,
transaction: WalletTransactionEvent['detail']['transaction'],
): WalletTransactionEvent {
return new CustomEvent(WALLET_TRX_EVENT_NAME, {
detail: {
chainId,
transaction,
},
})
}

export const WalletBalanceUpdater: React.FC = () => {
const { account, solanaAccount } = useAccountActiveChain()

// Use BSC just to fetch EVM balances
const { isPending: isEvmPending, refresh: refreshEvmBalances } = useAddressBalance(account, ChainId.BSC, {
enabled: false,
})
const { isPending: isSolanaPending, refresh: refreshSolanaBalances } = useAddressBalance(
solanaAccount,
NonEVMChainId.SOLANA,
{ enabled: false },
)

const evmTimeoutRef = useRef<NodeJS.Timeout | null>(null)
const solanaTimeoutRef = useRef<NodeJS.Timeout | null>(null)

useEffect(() => {
const handleWalletTransaction = (event: WalletTransactionEvent) => {
const { transaction, chainId } = event.detail
if (!transaction?.type || !chainId) return

const delay = 15000

const refreshEvm = () => {
if (evmTimeoutRef.current) clearTimeout(evmTimeoutRef.current)
evmTimeoutRef.current = setTimeout(() => {
evmTimeoutRef.current = null
refreshEvmBalances()
}, delay)
}

const refreshSolana = () => {
if (solanaTimeoutRef.current) clearTimeout(solanaTimeoutRef.current)
solanaTimeoutRef.current = setTimeout(() => {
solanaTimeoutRef.current = null
refreshSolanaBalances()
}, delay)
}

switch (transaction.type) {
case 'bridge': {
const isToSolana = transaction.outputChainId === NonEVMChainId.SOLANA

if (isToSolana) {
if (!isSolanaPending) {
refreshSolana()
}
} else if (!isEvmPending) {
refreshEvm()
}
break
}

// List of transaction types that may introduce new tokens to the user's account
case 'swap':
case 'wrap':
case 'remove-liquidity-infinity-bin':
case 'remove-liquidity-infinity-cl':
case 'remove-liquidity-v3':
case 'collect-fee':
case 'remove-liquidity':
case 'limit-order-cancellation':
case 'claim-liquid-staking':
case 'other': {
if (chainId === NonEVMChainId.SOLANA) {
if (!isSolanaPending) {
refreshSolana()
}
} else if (!isEvmPending) {
refreshEvm()
}
break
}

default:
break
}
}

window.addEventListener(WALLET_TRX_EVENT_NAME, handleWalletTransaction as EventListener)
return () => {
window.removeEventListener(WALLET_TRX_EVENT_NAME, handleWalletTransaction as EventListener)
if (evmTimeoutRef.current) clearTimeout(evmTimeoutRef.current)
if (solanaTimeoutRef.current) clearTimeout(solanaTimeoutRef.current)
}
}, [refreshEvmBalances, refreshSolanaBalances, isEvmPending, isSolanaPending])

return null
}
Original file line number Diff line number Diff line change
Expand Up @@ -169,6 +169,7 @@ export const useBatchSwapTransaction = ({
addTransaction(
{ hash },
{
outputChainId: order?.trade?.outputAmount?.currency?.chainId,
summary: `Bridge ${order.trade.inputAmount.toSignificant(3)} ${
order.trade.inputAmount.currency.symbol
} to ${order.trade.outputAmount.currency.symbol}`,
Expand Down
Loading
Loading