Skip to content

Commit

Permalink
feat: enable batch transfers for custom gas tokens (#1882)
Browse files Browse the repository at this point in the history
  • Loading branch information
brtkx authored Sep 12, 2024
1 parent 7c45194 commit 74245dd
Show file tree
Hide file tree
Showing 13 changed files with 178 additions and 69 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import {
PlusCircleIcon
} from '@heroicons/react/24/outline'
import dayjs from 'dayjs'
import { getProviderForChainId } from '@/token-bridge-sdk/utils'

import {
getStandardizedDate,
Expand All @@ -30,10 +31,20 @@ import { PendingDepositWarning } from './PendingDepositWarning'
import { TransactionsTableRow } from './TransactionsTableRow'
import { EmptyTransactionHistory } from './EmptyTransactionHistory'
import { Address } from '../../util/AddressUtils'
import { MergedTransaction } from '../../state/app/state'
import { useNativeCurrency } from '../../hooks/useNativeCurrency'

export const BatchTransferNativeTokenTooltip = ({
children,
tx
}: PropsWithChildren<{ tx: MergedTransaction }>) => {
const childProvider = getProviderForChainId(tx.childChainId)
const nativeCurrency = useNativeCurrency({ provider: childProvider })

export const BatchTransferEthTooltip = ({ children }: PropsWithChildren) => {
return (
<Tooltip content="This is any additional ETH you might have deposited along with your ERC-20, plus the refunded excess gas fee.">
<Tooltip
content={`This is any additional ${nativeCurrency.symbol} you might have deposited along with your ERC-20, plus the refunded excess gas fee.`}
>
{children}
</Tooltip>
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import dayjs from 'dayjs'
import CctpLogoColor from '@/images/CctpLogoColor.svg'
import ArbitrumLogo from '@/images/ArbitrumLogo.svg'
import EthereumLogoRoundLight from '@/images/EthereumLogoRoundLight.svg'
import { getProviderForChainId } from '@/token-bridge-sdk/utils'

import { useTxDetailsStore } from './TransactionHistory'
import { getExplorerUrl, getNetworkName, isNetwork } from '../../util/networks'
Expand All @@ -24,7 +25,8 @@ import { isTxCompleted } from './helpers'
import { Address } from '../../util/AddressUtils'
import { sanitizeTokenSymbol } from '../../util/TokenUtils'
import { isBatchTransfer } from '../../util/TokenDepositUtils'
import { BatchTransferEthTooltip } from './TransactionHistoryTable'
import { BatchTransferNativeTokenTooltip } from './TransactionHistoryTable'
import { useNativeCurrency } from '../../hooks/useNativeCurrency'

const DetailsBox = ({
children,
Expand Down Expand Up @@ -63,7 +65,10 @@ export const TransactionsTableDetails = ({
)
}, [transactions, txFromStore])

if (!tx || !address) {
const childProvider = getProviderForChainId(tx?.childChainId ?? 0)
const nativeCurrency = useNativeCurrency({ provider: childProvider })

if (!tx || !address || !nativeCurrency) {
return null
}

Expand Down Expand Up @@ -153,17 +158,19 @@ export const TransactionsTableDetails = ({
)}
</div>
{isBatchTransfer(tx) && (
<BatchTransferEthTooltip>
<BatchTransferNativeTokenTooltip tx={tx}>
<div className="flex items-center space-x-2">
<Image
height={20}
width={20}
alt="ETH logo"
src={EthereumLogoRoundLight}
alt={`${nativeCurrency.symbol} logo`}
src={
nativeCurrency.logoUrl ?? EthereumLogoRoundLight
}
/>
<span className="ml-2">
{formatAmount(Number(tx.value2), {
symbol: ether.symbol
symbol: nativeCurrency.symbol
})}
</span>
{isNetwork(tx.sourceChainId).isEthereumMainnet && (
Expand All @@ -172,7 +179,7 @@ export const TransactionsTableDetails = ({
</span>
)}
</div>
</BatchTransferEthTooltip>
</BatchTransferNativeTokenTooltip>
)}
</div>
</div>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import {
} from '@heroicons/react/24/outline'
import EthereumLogoRoundLight from '@/images/EthereumLogoRoundLight.svg'
import Image from 'next/image'
import { getProviderForChainId } from '@/token-bridge-sdk/utils'

import { DepositStatus, MergedTransaction } from '../../state/app/state'
import { formatAmount } from '../../util/NumberUtils'
Expand All @@ -30,9 +31,9 @@ import { TransactionsTableTokenImage } from './TransactionsTableTokenImage'
import { useTxDetailsStore } from './TransactionHistory'
import { TransactionsTableExternalLink } from './TransactionsTableExternalLink'
import { Address } from '../../util/AddressUtils'
import { ether } from '../../constants'
import { isBatchTransfer } from '../../util/TokenDepositUtils'
import { BatchTransferEthTooltip } from './TransactionHistoryTable'
import { BatchTransferNativeTokenTooltip } from './TransactionHistoryTable'
import { useNativeCurrency } from '../../hooks/useNativeCurrency'

const StatusLabel = ({ tx }: { tx: MergedTransaction }) => {
const { sourceChainId, destinationChainId } = tx
Expand Down Expand Up @@ -128,6 +129,8 @@ export function TransactionsTableRow({
className?: string
}) {
const { open: openTxDetails } = useTxDetailsStore()
const childProvider = getProviderForChainId(tx.childChainId)
const nativeCurrency = useNativeCurrency({ provider: childProvider })

const { sourceChainId, destinationChainId } = tx

Expand Down Expand Up @@ -190,21 +193,21 @@ export function TransactionsTableRow({
</TransactionsTableExternalLink>
</div>
{isBatchTransfer(tx) && (
<BatchTransferEthTooltip>
<BatchTransferNativeTokenTooltip tx={tx}>
<div className="flex items-center pr-3 align-middle">
<Image
height={20}
width={20}
alt="ETH logo"
src={EthereumLogoRoundLight}
alt={`${nativeCurrency.symbol} logo`}
src={nativeCurrency.logoUrl ?? EthereumLogoRoundLight}
/>
<span className="ml-2">
{formatAmount(Number(tx.value2), {
symbol: ether.symbol
symbol: nativeCurrency.symbol
})}
</span>
</div>
</BatchTransferEthTooltip>
</BatchTransferNativeTokenTooltip>
)}
</div>
<div className="flex items-center space-x-2">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@ import { useNetworksRelationship } from '../../hooks/useNetworksRelationship'
import { shortenAddress } from '../../util/CommonUtils'
import { NoteBox } from '../common/NoteBox'
import { BridgeTransferStarterFactory } from '@/token-bridge-sdk/BridgeTransferStarterFactory'
import { useIsBatchTransferSupported } from '../../hooks/TransferPanel/useIsBatchTransferSupported'
import { useArbQueryParams } from '../../hooks/useArbQueryParams'

export type CustomFeeTokenApprovalDialogProps = UseDialogProps & {
customFeeToken: NativeCurrencyErc20
Expand All @@ -34,6 +36,10 @@ export function CustomFeeTokenApprovalDialog(
const { sourceChain, destinationChain } = networks
const { parentChain, parentChainProvider } = useNetworksRelationship(networks)
const { isEthereumMainnet } = isNetwork(parentChain.id)
const isBatchTransferSupported = useIsBatchTransferSupported()
const [{ amount2 }] = useArbQueryParams()

const isBatchTransfer = isBatchTransferSupported && Number(amount2) > 0

const { data: l1Signer } = useSigner({ chainId: parentChain.id })
const l1GasPrice = useGasPrice({ provider: parentChainProvider })
Expand Down Expand Up @@ -141,6 +147,16 @@ export function CustomFeeTokenApprovalDialog(
as the fee token. Before continuing with your deposit, you must first
allow the bridge contract to access your{' '}
<span className="font-medium">{customFeeToken.symbol}</span>.
{isBatchTransfer && (
<span>
{' '}
This includes your deposit of{' '}
<span className="font-medium">
{amount2} {customFeeToken.symbol}
</span>{' '}
and gas fees.
</span>
)}
</span>

<Checkbox
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -757,10 +757,20 @@ export function TransferPanel() {
return
}

const isCustomNativeTokenAmount2 =
nativeCurrency.isCustom &&
isBatchTransferSupported &&
Number(amount2) > 0

const isNativeCurrencyApprovalRequired =
await bridgeTransferStarter.requiresNativeCurrencyApproval({
signer,
amount: amountBigNumber
amount: amountBigNumber,
options: {
approvalAmountIncrease: isCustomNativeTokenAmount2
? utils.parseUnits(amount2, nativeCurrency.decimals)
: undefined
}
})

if (isNativeCurrencyApprovalRequired) {
Expand All @@ -770,7 +780,12 @@ export function TransferPanel() {

const approvalTx = await bridgeTransferStarter.approveNativeCurrency({
signer,
amount: amountBigNumber
amount: amountBigNumber,
options: {
approvalAmountIncrease: isCustomNativeTokenAmount2
? utils.parseUnits(amount2, nativeCurrency.decimals)
: undefined
}
})

if (approvalTx) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,22 @@ import { useArbQueryParams } from '../../../hooks/useArbQueryParams'
function NativeCurrencyDestinationBalance({ prefix }: { prefix?: string }) {
const nativeCurrencyBalances = useNativeCurrencyBalances()
const [networks] = useNetworks()
const nativeCurrency = useNativeCurrency({
provider: networks.destinationChainProvider
})
const { isDepositMode } = useNetworksRelationship(networks)

if (nativeCurrency.isCustom) {
return (
<TokenBalance
forToken={nativeCurrency}
balance={nativeCurrencyBalances.destinationBalance}
on={isDepositMode ? NetworkType.childChain : NetworkType.parentChain}
prefix={prefix}
/>
)
}

return (
<ETHBalance
balance={nativeCurrencyBalances.destinationBalance}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -177,7 +177,8 @@ export function SourceNetworkBox({
decimals={nativeCurrency.decimals}
/>
<p className="mt-1 text-xs font-light text-white">
You can transfer ETH in the same transaction if you wish to.
You can transfer {nativeCurrency.symbol} in the same transaction
if you wish to.
</p>
</>
)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -105,12 +105,9 @@ export function useMaxAmount() {
if (!isDepositMode) {
return undefined
}
if (nativeCurrency.isCustom) {
return undefined
}

return nativeCurrencyMaxAmount
}, [isDepositMode, nativeCurrency.isCustom, nativeCurrencyMaxAmount])
}, [isDepositMode, nativeCurrencyMaxAmount])

return {
maxAmount,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -251,7 +251,10 @@ export function TransferPanelSummary({ token }: TransferPanelSummaryProps) {
<NativeCurrencyPrice amount={Number(amount)} showBrackets />
)}
{isBatchTransferSupported && Number(amount2) > 0 && (
<span> + {amount2} ETH</span>
<span>
{' '}
and {amount2} {childChainNativeCurrency.symbol}
</span>
)}
</span>
</div>
Expand Down
Loading

0 comments on commit 74245dd

Please sign in to comment.