Skip to content

Commit

Permalink
Move useBalances to kit package
Browse files Browse the repository at this point in the history
  • Loading branch information
corbanbrook committed Apr 30, 2024
1 parent 361ea82 commit ed7267a
Show file tree
Hide file tree
Showing 12 changed files with 147 additions and 187 deletions.
71 changes: 0 additions & 71 deletions packages/checkout/src/api/data.ts
Original file line number Diff line number Diff line change
@@ -1,78 +1,7 @@
import { getNetworkConfigAndClients } from '@0xsequence/kit'
import { TokenBalance, ContractType } from '@0xsequence/indexer'
import { ethers } from 'ethers'

import { getPaperNetworkName } from '../utils'

export interface GetTokenBalancesArgs {
accountAddress: string
chainId: number
verifiedOnly?: boolean
}

export const getNativeToken = async ({ accountAddress, chainId }: GetTokenBalancesArgs) => {
try {
const { indexerClient } = getNetworkConfigAndClients(chainId)

const res = await indexerClient.getEtherBalance({ accountAddress })

const tokenBalance: TokenBalance = {
chainId,
contractAddress: ethers.constants.AddressZero,
accountAddress,
balance: res?.balance.balanceWei || '0',
contractType: ContractType.UNKNOWN,
blockHash: '',
blockNumber: 0,
tokenID: ''
}
return [tokenBalance]
} catch (e) {
console.error(e)
return []
}
}

export const getTokenBalances = async ({ accountAddress, chainId, verifiedOnly }: GetTokenBalancesArgs) => {
try {
const { indexerClient } = getNetworkConfigAndClients(chainId)

const res = await indexerClient.getTokenBalances({
accountAddress,
includeMetadata: true,
metadataOptions: {
verifiedOnly: verifiedOnly ?? true
}
})

return res?.balances || []
} catch (e) {
console.error(e)
return []
}
}

export const fetchBalances = async ({ accountAddress, chainId }: GetTokenBalancesArgs) => {
try {
const tokenBalances = (
await Promise.all([
getNativeToken({
accountAddress,
chainId
}),
getTokenBalances({
accountAddress,
chainId
})
])
).flat()
return tokenBalances
} catch (e) {
console.error(e)
return []
}
}

export interface FetchPaperSecretArgs {
chainId: number
email: string
Expand Down
19 changes: 0 additions & 19 deletions packages/checkout/src/hooks/data.ts

This file was deleted.

1 change: 0 additions & 1 deletion packages/checkout/src/hooks/index.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
export * from './useCheckoutModal'
export * from './data'
export * from './useNavigation'
export * from './useModalTheme'
8 changes: 4 additions & 4 deletions packages/checkout/src/views/CheckoutSelection/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import React from 'react'
import { ethers } from 'ethers'
import { Box, Button, ChevronRightIcon, Divider, Text, PaymentsIcon, vars } from '@0xsequence/design-system'

import { getNativeTokenInfoByChainId, useContractInfo } from '@0xsequence/kit'
import { getNativeTokenInfoByChainId, useBalances, useContractInfo } from '@0xsequence/kit'

import { useAccount, useConfig } from 'wagmi'

Expand All @@ -11,7 +11,7 @@ import { OrderSummaryItem } from './component/OrderSummaryItem'
import { CoinIcon } from '../../shared/components/CoinIcon'
import { Skeleton } from '../../shared/components/Skeleton'
import { HEADER_HEIGHT } from '../../constants'
import { useNavigation, useCheckoutModal, useBalances } from '../../hooks'
import { useNavigation, useCheckoutModal } from '../../hooks'
import { compareAddress, formatDisplay } from '../../utils'
import * as styles from './styles.css'

Expand All @@ -32,8 +32,8 @@ export const CheckoutSelection = () => {
)

const { data: balancesData, isPending: isPendingBalances } = useBalances({
accountAddress: accountAddress || '',
chainId: cryptoCheckoutSettings?.chainId || 1
chainIds: [cryptoCheckoutSettings?.chainId || 1],
accountAddress: accountAddress || ''
})

const isPending = (isPendingContractInfo || isPendingBalances) && cryptoCheckoutSettings
Expand Down
17 changes: 7 additions & 10 deletions packages/kit/src/components/TxnDetails/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@ import React, { useEffect, useState } from 'react'
import { ethers } from 'ethers'
import { useConfig } from 'wagmi'

import { useTokenMetadata } from '@0xsequence/kit'
import { Skeleton, CollectibleTileImage, CoinIcon, formatDisplay, useBalances } from '@0xsequence/kit-wallet'
import { useTokenMetadata, useBalances } from '@0xsequence/kit'
import { Skeleton, CollectibleTileImage, CoinIcon, formatDisplay } from '@0xsequence/kit-wallet'
import { compareAddress, getNativeTokenInfoByChainId } from '../../utils'
import { commons } from '@0xsequence/core'
import { DecodingType, TransferProps, AwardItemProps, decodeTransactions } from '../../utils/txnDecoding'
Expand Down Expand Up @@ -96,14 +96,11 @@ const TransferItemInfo = ({ address, transferProps, chainId }: TransferItemInfoP
const isNFT = transferProps[0]?.contractType === ContractType.ERC1155 || transferProps[0]?.contractType === ContractType.ERC721
const nativeTokenInfo = getNativeTokenInfoByChainId(chainId, chains)

const { data: balances = [], isPending: isPendingBalances } = useBalances(
{
accountAddress: address,
chainIds: [chainId],
contractAddress
},
{ hideUnlistedTokens: false }
)
const { data: balances = [], isPending: isPendingBalances } = useBalances({
chainIds: [chainId],
accountAddress: address,
contractAddress
})

const { data: tokenMetadata, isPending: isPendingTokenMetadata } = useTokenMetadata(
chainId,
Expand Down
85 changes: 84 additions & 1 deletion packages/kit/src/hooks/data.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,97 @@ import { useQuery } from '@tanstack/react-query'

import { useMetadataClient } from './useMetadataClient'
import { useAPIClient } from './useAPIClient'
import { useIndexerClient } from './useIndexerClient'
import { useIndexerClient, useIndexerClients } from './useIndexerClient'
import { ContractType, SequenceIndexer, TokenBalance } from '@0xsequence/indexer'

import { zeroAddress } from 'viem'

export const time = {
oneSecond: 1 * 1000,
oneMinute: 60 * 1000,
oneHour: 60 * 60 * 1000
}

const getNativeTokenBalance = async (indexerClient: SequenceIndexer, chainId: number, accountAddress: string) => {
const res = await indexerClient.getEtherBalance({ accountAddress })

const tokenBalance: TokenBalance = {
chainId,
contractAddress: zeroAddress,
accountAddress,
balance: res?.balance.balanceWei || '0',
contractType: ContractType.UNKNOWN,
blockHash: '',
blockNumber: 0,
tokenID: ''
}

return [tokenBalance]
}

interface GetTokenBalancesArgs {
accountAddress: string
hideCollectibles?: boolean
includeMetadata?: boolean
verifiedOnly?: boolean
contractAddress?: string
}

const getTokenBalances = async (indexerClient: SequenceIndexer, args: GetTokenBalancesArgs) => {
const res = await indexerClient.getTokenBalances({
accountAddress: args.accountAddress,
includeMetadata: args.includeMetadata ?? true,
metadataOptions: {
verifiedOnly: args.verifiedOnly ?? true
},
...(args.contractAddress && { contractAddress: args.contractAddress })
})

return res?.balances || []
}

const getBalances = async (indexerClient: SequenceIndexer, chainId: number, args: GetTokenBalancesArgs) => {
if (!args.accountAddress) {
return []
}

const balances = (
await Promise.allSettled([
getNativeTokenBalance(indexerClient, chainId, args.accountAddress),
getTokenBalances(indexerClient, args)
])
)
.map(res => (res.status === 'fulfilled' ? res.value : []))
.flat()

return balances
}

interface UseBalancesArgs extends GetTokenBalancesArgs {
chainIds: number[]
}

// Gets native and token balances
export const useBalances = ({ chainIds, ...args }: UseBalancesArgs) => {
const indexerClients = useIndexerClients(chainIds)

return useQuery({
queryKey: ['balances', chainIds, args],
queryFn: async () => {
const res = (
await Promise.all(
Array.from(indexerClients.entries()).map(([chainId, indexerClient]) => getBalances(indexerClient, chainId, args))
)
).flat()

return res
},
retry: true,
staleTime: time.oneSecond * 30,
enabled: chainIds.length > 0 && !!args.accountAddress
})
}

interface UseCollectionBalanceArgs {
chainId: number
accountAddress: string
Expand Down
29 changes: 29 additions & 0 deletions packages/kit/src/hooks/useIndexerClient.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import { useMemo } from 'react'
import { useProjectAccessKey } from './useProjectAccessKey'
import { SequenceIndexer } from '@0xsequence/indexer'
import { ChainId, indexerURL, networks } from '@0xsequence/network'
import { useConfig } from 'wagmi'

export const useIndexerClient = (chainId: ChainId) => {
const projectAccessKey = useProjectAccessKey()
Expand All @@ -24,3 +25,31 @@ export const useIndexerClient = (chainId: ChainId) => {

return indexerClient
}

export const useIndexerClients = (chainIds: ChainId[]) => {
const projectAccessKey = useProjectAccessKey()

const indexerClients = useMemo(() => {
return new Map<ChainId, SequenceIndexer>()
}, [projectAccessKey])

const result = new Map<ChainId, SequenceIndexer>()

for (const chainId of chainIds) {
const network = networks[chainId]

if (!indexerClients.has(chainId)) {
indexerClients.set(chainId, new SequenceIndexer(indexerURL(network.name), projectAccessKey))
}

const indexerClient = indexerClients.get(chainId)

if (!indexerClient) {
throw new Error('Indexer client not found')
}

result.set(chainId, indexerClient)
}

return result
}
32 changes: 0 additions & 32 deletions packages/wallet/src/api/data.ts
Original file line number Diff line number Diff line change
Expand Up @@ -111,38 +111,6 @@ export const getTokenBalances = async (
}
}

export interface FetchBalancesOptions {
hideUnlistedTokens: boolean
hideCollectibles?: boolean
}

export const fetchBalances = async (
{ accountAddress, chainId }: GetTokenBalancesArgs,
{ hideUnlistedTokens, hideCollectibles }: FetchBalancesOptions
) => {
try {
const tokenBalances = (
await Promise.all([
getNativeToken({
accountAddress,
chainId
}),
getTokenBalances(
{
accountAddress,
chainId
},
{ hideUnlistedTokens, hideCollectibles }
)
])
).flat()
return tokenBalances
} catch (e) {
console.error(e)
return []
}
}

export interface GetCollectionBalanceArgs {
accountAddress: string
chainId: number
Expand Down
20 changes: 0 additions & 20 deletions packages/wallet/src/hooks/data.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,7 @@
import { ethers } from 'ethers'
import { useQuery, useInfiniteQuery } from '@tanstack/react-query'
import {
fetchBalances,
GetTokenBalancesArgs,
fetchCollectionBalance,
GetCollectionBalanceArgs,
fetchBalancesAssetsSummary,
getNativeToken,
getTokenBalances,
Expand All @@ -28,23 +25,6 @@ export const time = {
oneHour: 60 * 60 * 1000
}

export interface UseBalancesArgs extends Omit<GetTokenBalancesArgs, 'chainId'> {
chainIds: number[]
}

export const useBalances = (args: UseBalancesArgs, options: GetTokenBalancesOptions) =>
useQuery({
queryKey: ['balances', args, options],
queryFn: async () => {
const { chainIds, ...restArgs } = args
const balances = await Promise.all(chainIds.map(chainId => fetchBalances({ ...restArgs, chainId }, options)))
return balances.flat()
},
retry: true,
staleTime: time.oneSecond * 30,
enabled: args.chainIds.length > 0 && !!args.accountAddress
})

export const useBalancesAssetsSummary = (args: FetchBalancesAssetsArgs, options: GetTokenBalancesOptions) =>
useQuery({
queryKey: ['balancesAssetsSummary', args, options],
Expand Down
Loading

0 comments on commit ed7267a

Please sign in to comment.