Skip to content

Commit

Permalink
Improve ux when wallet does not support chain, user rejects chain swi…
Browse files Browse the repository at this point in the history
…tch or double clicks
  • Loading branch information
pedromcunha committed Oct 30, 2024
1 parent 621ee82 commit 212d58a
Show file tree
Hide file tree
Showing 6 changed files with 82 additions and 75 deletions.
11 changes: 10 additions & 1 deletion packages/sdk/src/utils/viemWallet.ts
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,16 @@ export const adaptViemWallet = (wallet: WalletClient): AdaptedWallet => {
id: chainId
})
return
} catch (e) {
} catch (e: any) {
if (e && e?.message) {
if (e.message.includes('does not support the requested chain')) {
throw new Error('Wallet does not support chain')
} else if (e.message.includes('rejected')) {
throw e
} else if (e.message.includes('already pending')) {
return
}
}
const client = getClient()
const chain = client.chains.find((chain) => chain.id === chainId)
if (!chain) {
Expand Down
9 changes: 8 additions & 1 deletion packages/ui/src/components/common/ErrorWell.tsx
Original file line number Diff line number Diff line change
@@ -1,13 +1,15 @@
import * as React from 'react'
import { Text } from '../primitives/index.js'
import type { AxiosError } from 'axios'
import type { RelayChain } from '@reservoir0x/relay-sdk'

interface Props {
error?: Error | null | AxiosError
hasTxHashes?: boolean
fromChain?: RelayChain
}

const ErrorWell: React.FC<Props> = ({ error, hasTxHashes }) => {
const ErrorWell: React.FC<Props> = ({ error, hasTxHashes, fromChain }) => {
const renderedErrorMessage = React.useMemo((): React.ReactNode => {
if (error && ((error as AxiosError).response?.data as any)?.message) {
return (error as any).response?.data?.message
Expand All @@ -17,6 +19,11 @@ const ErrorWell: React.FC<Props> = ({ error, hasTxHashes }) => {
!error?.message
) {
return 'Oops! Something went wrong while processing your transaction.'
} else if (
error?.name &&
error?.message?.includes('does not support chain')
) {
return `Your wallet does not support ${fromChain?.displayName}`
}
if (!hasTxHashes) {
return 'Oops, something went wrong while initiating the bridge. Your request was not submitted. Please try again.'
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -190,7 +190,9 @@ const InnerSwapModal: FC<InnerSwapModalProps> = ({
quoteUpdatedAt,
linkedWallets,
multiWalletSupportEnabled,
useExternalLiquidity
useExternalLiquidity,
fromChain,
waitingForSteps
}) => {
useEffect(() => {
if (!open) {
Expand Down Expand Up @@ -273,6 +275,7 @@ const InnerSwapModal: FC<InnerSwapModalProps> = ({
linkedWallets={linkedWallets}
multiWalletSupportEnabled={multiWalletSupportEnabled}
useExternalLiquidity={useExternalLiquidity}
waitingForSteps={waitingForSteps}
/>
) : null}

Expand Down Expand Up @@ -313,6 +316,7 @@ const InnerSwapModal: FC<InnerSwapModalProps> = ({
address={address}
onOpenChange={onOpenChange}
transaction={transaction}
fromChain={fromChain}
/>
) : null}
</Flex>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -230,6 +230,52 @@ export const TransactionModalRenderer: FC<Props> = ({
)

const swap = useCallback(async () => {
const swapErrorHandler = (error: any) => {
if (
error &&
((typeof error.message === 'string' &&
error.message.includes('rejected')) ||
(typeof error === 'string' && error.includes('rejected')))
) {
onAnalyticEvent?.(EventNames.USER_REJECTED_WALLET)
setProgressStep(TransactionProgressStep.ReviewQuote)
return
}

const errorMessage = error?.response?.data?.message
? new Error(error?.response?.data?.message)
: error

onAnalyticEvent?.(EventNames.SWAP_ERROR, {
error_message: errorMessage,
wallet_connector: connector?.name,
quote_id: steps ? extractQuoteId(steps) : undefined,
amount_in: parseFloat(`${debouncedInputAmountValue}`),
currency_in: fromToken?.symbol,
chain_id_in: fromToken?.chainId,
amount_out: parseFloat(`${debouncedOutputAmountValue}`),
currency_out: toToken?.symbol,
chain_id_out: toToken?.chainId,
is_canonical: useExternalLiquidity,
txHashes: steps
?.map((step) => {
let txHashes: { chainId: number; txHash: string }[] = []
step.items?.forEach((item) => {
if (item.txHashes) {
txHashes = txHashes.concat([
...(item.txHashes ?? []),
...(item.internalTxHashes ?? [])
])
}
})
return txHashes
})
.flat()
})
setSwapError(errorMessage)
onSwapError?.(errorMessage, quote as Execute)
}

try {
onAnalyticEvent?.(EventNames.SWAP_CTA_CLICKED)
setWaitingForSteps(true)
Expand Down Expand Up @@ -258,83 +304,15 @@ export const TransactionModalRenderer: FC<Props> = ({
setSteps(currentSteps)
})
?.catch((error: any) => {
if (
error &&
((typeof error.message === 'string' &&
error.message.includes('rejected')) ||
(typeof error === 'string' && error.includes('rejected')))
) {
onAnalyticEvent?.(EventNames.USER_REJECTED_WALLET)
setProgressStep(TransactionProgressStep.ReviewQuote)
return
}

const errorMessage = error?.response?.data?.message
? new Error(error?.response?.data?.message)
: error

onAnalyticEvent?.(EventNames.SWAP_ERROR, {
error_message: errorMessage,
wallet_connector: connector?.name,
quote_id: steps ? extractQuoteId(steps) : undefined,
amount_in: parseFloat(`${debouncedInputAmountValue}`),
currency_in: fromToken?.symbol,
chain_id_in: fromToken?.chainId,
amount_out: parseFloat(`${debouncedOutputAmountValue}`),
currency_out: toToken?.symbol,
chain_id_out: toToken?.chainId,
is_canonical: useExternalLiquidity,
txHashes: steps
?.map((step) => {
let txHashes: { chainId: number; txHash: string }[] = []
step.items?.forEach((item) => {
if (item.txHashes) {
txHashes = txHashes.concat([
...(item.txHashes ?? []),
...(item.internalTxHashes ?? [])
])
}
})
return txHashes
})
.flat()
})
setSwapError(errorMessage)
onSwapError?.(errorMessage, quote as Execute)
swapErrorHandler(error)
})
.finally(() => {
setWaitingForSteps(false)
invalidateBalanceQueries()
})
} catch (e) {
} catch (error: any) {
swapErrorHandler(error)
setWaitingForSteps(false)
onAnalyticEvent?.(EventNames.SWAP_ERROR, {
error_message: e,
wallet_connector: connector?.name,
quote_id: steps ? extractQuoteId(steps) : undefined,
amount_in: parseFloat(`${debouncedInputAmountValue}`),
currency_in: fromToken?.symbol,
chain_id_in: fromToken?.chainId,
amount_out: parseFloat(`${debouncedOutputAmountValue}`),
currency_out: toToken?.symbol,
chain_id_out: toToken?.chainId,
is_canonical: useExternalLiquidity,
txHashes: steps
?.map((step) => {
let txHashes: { chainId: number; txHash: string }[] = []
step.items?.forEach((item) => {
if (item.txHashes) {
txHashes = txHashes.concat([
...(item.txHashes ?? []),
...(item.internalTxHashes ?? [])
])
}
})
return txHashes
})
.flat()
})
onSwapError?.(e as any, quote as Execute)
}
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [
Expand All @@ -351,6 +329,7 @@ export const TransactionModalRenderer: FC<Props> = ({
debouncedOutputAmountValue,
tradeType,
useExternalLiquidity,
waitingForSteps,
executeSwap,
setSteps,
invalidateBalanceQueries
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,12 +23,14 @@ import {
faRotateRight
} from '@fortawesome/free-solid-svg-icons/index.js'
import type { useRequests } from '@reservoir0x/relay-kit-hooks'
import type { RelayChain } from '@reservoir0x/relay-sdk'

type ErrorStepProps = {
error?: Error | null
address?: Address | string
allTxHashes: TxHashes
transaction?: ReturnType<typeof useRequests>['data']['0']
fromChain?: RelayChain
onOpenChange: (open: boolean) => void
}

Expand All @@ -37,6 +39,7 @@ export const ErrorStep: FC<ErrorStepProps> = ({
address,
allTxHashes,
transaction,
fromChain,
onOpenChange
}) => {
const errorMessage = transaction?.data?.failReason ?? error?.message
Expand Down Expand Up @@ -127,7 +130,11 @@ export const ErrorStep: FC<ErrorStepProps> = ({
: `It looks like an unknown issue occurred during the transaction. We apologize for the inconvenience, a refund has been sent to your wallet address.`}
</Text>
) : (
<ErrorWell error={mergedError} hasTxHashes={hasTxHashes} />
<ErrorWell
error={mergedError}
hasTxHashes={hasTxHashes}
fromChain={fromChain}
/>
)}
{depositTx || fillTx ? (
<>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ type ReviewQuoteProps = {
isFetchingQuote: boolean
isRefetchingQuote: boolean
waitingForSteps?: boolean
isExecuting?: boolean
swap?: () => void
quoteUpdatedAt: number
feeBreakdown: ChildrenProps['feeBreakdown']
Expand Down

0 comments on commit 212d58a

Please sign in to comment.