diff --git a/apps/app/src/components/Address/Contract/ContractOverview.tsx b/apps/app/src/components/Address/Contract/ContractOverview.tsx index e6616ab5..f3129794 100644 --- a/apps/app/src/components/Address/Contract/ContractOverview.tsx +++ b/apps/app/src/components/Address/Contract/ContractOverview.tsx @@ -68,7 +68,12 @@ const ContractOverview = (props: Props) => { useEffect(() => { if (rpcError) { - switchRpc(); + try { + switchRpc(); + } catch (error) { + setRpcError(true); + console.error('Failed to switch RPC:', error); + } } }, [rpcError, switchRpc]); diff --git a/apps/app/src/components/NodeExplorer/Delegators.tsx b/apps/app/src/components/NodeExplorer/Delegators.tsx index d658c603..d3315e73 100644 --- a/apps/app/src/components/NodeExplorer/Delegators.tsx +++ b/apps/app/src/components/NodeExplorer/Delegators.tsx @@ -154,7 +154,12 @@ const Delegators = ({ accountId }: Props) => { useEffect(() => { if (error) { - switchRpc(); + try { + switchRpc(); + } catch (error) { + setError(true); + console.error('Failed to switch RPC:', error); + } } }, [error, switchRpc]); diff --git a/apps/app/src/pages/address/[id].tsx b/apps/app/src/pages/address/[id].tsx index fb3cbd66..eb85aa4e 100644 --- a/apps/app/src/pages/address/[id].tsx +++ b/apps/app/src/pages/address/[id].tsx @@ -250,7 +250,6 @@ const Address = ({ tab, }: InferGetServerSidePropsType) => { const router = useRouter(); - const [tabIndex, setTabIndex] = useState(0); const { id } = router.query; const { t } = useTranslation(); const { ftBalanceOf, contractCode, viewAccessKeys, viewAccount } = useRpc(); @@ -355,7 +354,12 @@ const Address = ({ useEffect(() => { if (rpcError) { - switchRpc(); + try { + switchRpc(); + } catch (error) { + setRpcError(true); + console.error('Failed to switch RPC:', error); + } } }, [rpcError, switchRpc]); @@ -445,22 +449,6 @@ const Address = ({ // eslint-disable-next-line react-hooks/exhaustive-deps }, [inventoryData?.fts, id, rpcUrl]); - useEffect(() => { - if (tab) { - const index = tabs.indexOf(tab as string); - if (index !== -1) { - const hasContractTab = - contractInfo && contractInfo?.methodNames?.length > 0; - let actualTabIndex = index; - if (!hasContractTab && index > 5) { - actualTabIndex = index - 1; - } - setTabIndex(actualTabIndex); - } - } - // eslint-disable-next-line react-hooks/exhaustive-deps - }, [tab]); - const onTab = (index: number) => { const { id } = router.query; @@ -474,8 +462,6 @@ const Address = ({ actualTabName = tabs[actualTabIndex + 1]; } - setTabIndex(actualTabIndex); - router.push({ pathname: router.pathname, query: { id, tab: actualTabName }, @@ -624,7 +610,7 @@ const Address = ({
<>
- + {[ { key: 0, label: t ? t('address:txns') : 'Transactions' }, @@ -668,7 +654,9 @@ const Address = ({ ].map(({ key, label }) => (

{label}

diff --git a/apps/app/src/pages/nft-token/[id]/index.tsx b/apps/app/src/pages/nft-token/[id]/index.tsx index ca9b4962..1aeb81ee 100644 --- a/apps/app/src/pages/nft-token/[id]/index.tsx +++ b/apps/app/src/pages/nft-token/[id]/index.tsx @@ -1,7 +1,7 @@ import Head from 'next/head'; import { appUrl } from '@/utils/config'; import { useRouter } from 'next/router'; -import { ReactElement, useEffect, useState } from 'react'; +import { ReactElement } from 'react'; import Layout from '@/components/Layouts'; import { env } from 'next-runtime-env'; import Overview from '@/components/Tokens/NFT/Overview'; @@ -181,7 +181,6 @@ const NFToken = ({ }: InferGetServerSidePropsType) => { const router = useRouter(); const { id } = router.query; - const [tabIndex, setTabIndex] = useState(0); const components = useBosComponents(); const token = tokenDetails?.contracts?.[0]; @@ -213,17 +212,7 @@ const NFToken = ({ : ''; const thumbnail = `${ogUrl}/thumbnail/nft-token?token=${token?.name}&network=${network}&brand=near`; - useEffect(() => { - if (tab) { - const index = tabs.indexOf(tab as string); - if (index !== -1) { - setTabIndex(index); - } - } - }, [tab]); - const onTab = (index: number) => { - setTabIndex(index); const { id } = router.query; const newQuery = { id, tab: tabs[index] }; router.push({ @@ -267,28 +256,31 @@ const NFToken = ({
- onTab(index)} selectedIndex={tabIndex}> + onTab(index)} + selectedIndex={tabs?.indexOf(tab)} + >

Transfers

Holders

Inventory

Comments

diff --git a/apps/app/src/pages/token/[id].tsx b/apps/app/src/pages/token/[id].tsx index 4423c63f..aa619673 100644 --- a/apps/app/src/pages/token/[id].tsx +++ b/apps/app/src/pages/token/[id].tsx @@ -2,7 +2,7 @@ import Head from 'next/head'; import { useRouter } from 'next/router'; import { appUrl } from '@/utils/config'; import Layout from '@/components/Layouts'; -import { ReactElement, useEffect, useState } from 'react'; +import { ReactElement } from 'react'; import { Tab, TabList, TabPanel, Tabs } from 'react-tabs'; import { env } from 'next-runtime-env'; import useTranslation from 'next-translate/useTranslation'; @@ -210,8 +210,6 @@ const TokenDetails = ({ const router = useRouter(); const { id, a }: any = router.query; const { t } = useTranslation(); - const [tabIndex, setTabIndex] = useState(0); - const hashes = ['Transfers', 'Holders', 'Info', 'FAQ', 'Comments']; const components = useBosComponents(); const token: Token = tokenDetails?.contracts?.[0]; @@ -244,17 +242,7 @@ const TokenDetails = ({ (store) => store.requestSignInWithWallet, ); - useEffect(() => { - if (tab) { - const index = tabs.indexOf(tab as string); - if (index !== -1) { - setTabIndex(index); - } - } - }, [tab]); - const onTab = (index: number) => { - setTabIndex(index); const { id } = router.query; const newQuery = { id, tab: tabs[index] }; router.push({ @@ -307,34 +295,47 @@ const TokenDetails = ({ )}
- onTab(index)} selectedIndex={tabIndex}> + onTab(index)} + selectedIndex={tabs.indexOf(tab)} + >

{t('token:fts.ft.transfers')}

{t('token:fts.ft.holders')}

Info

FAQ

Comments

diff --git a/apps/app/src/stores/rpc.ts b/apps/app/src/stores/rpc.ts index f13fa2b9..2a3fe0e3 100644 --- a/apps/app/src/stores/rpc.ts +++ b/apps/app/src/stores/rpc.ts @@ -21,23 +21,36 @@ const getClientCookie = (name: string) => { type RpcState = { rpc: string; + errorCount: number; setRpc: (rpc: string) => void; switchRpc: () => void; + resetErrorCount: () => void; }; export const useRpcStore = create((set, get) => ({ rpc: getClientCookie('rpcUrl') || RpcProviders?.[0]?.url || '', + errorCount: 0, setRpc: (rpc: string) => { setClientCookie('rpcUrl', rpc); - set(() => ({ rpc })); + set(() => ({ rpc, errorCount: 0 })); }, switchRpc: () => { + const { rpc, errorCount } = get(); + + if (errorCount >= RpcProviders?.length) { + throw new Error('All RPC providers have resulted in errors.'); + } + const currentIndex = RpcProviders.findIndex( - (provider) => provider.url === get().rpc, + (provider) => provider.url === rpc, ); - const nextIndex = (currentIndex + 1) % RpcProviders.length; + const nextIndex = (currentIndex + 1) % RpcProviders?.length; const nextRpc = RpcProviders[nextIndex].url; + setClientCookie('rpcUrl', nextRpc); - set({ rpc: nextRpc }); + set({ rpc: nextRpc, errorCount: errorCount + 1 }); + }, + resetErrorCount: () => { + set({ errorCount: 0 }); }, })); diff --git a/apps/app/src/utils/rpc.ts b/apps/app/src/utils/rpc.ts index a1a6bb78..4fad8cc8 100644 --- a/apps/app/src/utils/rpc.ts +++ b/apps/app/src/utils/rpc.ts @@ -23,10 +23,6 @@ export const RpcProviders = name: 'Lava Network', url: 'https://near.lava.build', }, - { - name: 'Lavender.Five', - url: 'https://near.lavenderfive.com/', - }, { name: 'dRPC', url: 'https://near.drpc.org',