diff --git a/ui/helpers/utils/multichain/blockExplorer.test.ts b/ui/helpers/utils/multichain/blockExplorer.test.ts index f37e9a17a2a4..6a86824c6b2b 100644 --- a/ui/helpers/utils/multichain/blockExplorer.test.ts +++ b/ui/helpers/utils/multichain/blockExplorer.test.ts @@ -14,6 +14,7 @@ import { MultichainNetwork } from '../../../selectors/multichain'; import { getMultichainBlockExplorerUrl, getMultichainAccountUrl, + getAssetDetailsAccountUrl, } from './blockExplorer'; const mockEvmNetwork: MultichainNetwork = { @@ -79,4 +80,44 @@ describe('Block Explorer Tests', () => { expect(result).toBe(expectedUrl); }); }); + + describe('getAssetDetailsAccountUrl', () => { + it('returns the correct account URL using configured block explorer for EVM networks', () => { + const address = '0x1234567890abcdef'; + // Uses the network's configured block explorer URL + const expectedUrl = `https://etherscan.io/address/${address}`; + + const result = getAssetDetailsAccountUrl(address, mockEvmNetwork); + + expect(result).toBe(expectedUrl); + }); + + it('falls back to Etherscan multichain when no block explorer is configured', () => { + const address = '0x1234567890abcdef'; + const networkWithoutExplorer: MultichainNetwork = { + ...mockEvmNetwork, + network: { + ...mockEvmNetwork.network, + rpcPrefs: { + imageUrl: ETH_TOKEN_IMAGE_URL, + // No blockExplorerUrl configured + }, + }, + }; + const expectedUrl = `https://etherscan.io/address/${address}#asset-multichain`; + + const result = getAssetDetailsAccountUrl(address, networkWithoutExplorer); + + expect(result).toBe(expectedUrl); + }); + + it('returns the correct account URL for non-EVM networks', () => { + const address = 'bc1qar0srrr7xfkvy5l643lydnw9re59gtzzwf5mdq'; + const expectedUrl = `https://mempool.space/address/${address}`; + + const result = getAssetDetailsAccountUrl(address, mockNonEvmNetwork); + + expect(result).toBe(expectedUrl); + }); + }); }); diff --git a/ui/helpers/utils/multichain/blockExplorer.ts b/ui/helpers/utils/multichain/blockExplorer.ts index fcb7063f09fc..97cb770966f6 100644 --- a/ui/helpers/utils/multichain/blockExplorer.ts +++ b/ui/helpers/utils/multichain/blockExplorer.ts @@ -1,4 +1,5 @@ import { KnownCaipNamespace, parseCaipChainId } from '@metamask/utils'; +import { getAccountLink } from '@metamask/etherscan-link'; import { MultichainNetwork } from '../../../selectors/multichain'; // TODO: Remove restricted import // eslint-disable-next-line import/no-restricted-paths @@ -31,3 +32,25 @@ export const getMultichainAccountUrl = ( return ''; }; + +export const getAssetDetailsAccountUrl = ( + address: string, + network: MultichainNetwork, +): string => { + const { namespace } = parseCaipChainId(network.chainId); + if (namespace === KnownCaipNamespace.Eip155) { + return getAccountLink( + normalizeSafeAddress(address), + network.network.chainId, + network.network?.rpcPrefs, + ); + } + + const { blockExplorerFormatUrls } = + network.network as MultichainProviderConfig; + if (blockExplorerFormatUrls) { + return formatBlockExplorerAddressUrl(blockExplorerFormatUrls, address); + } + + return ''; +}; diff --git a/ui/pages/asset/components/token-asset.tsx b/ui/pages/asset/components/token-asset.tsx index db071369cc5d..2ec7f36597f7 100644 --- a/ui/pages/asset/components/token-asset.tsx +++ b/ui/pages/asset/components/token-asset.tsx @@ -25,7 +25,7 @@ import { useTokenFiatAmount } from '../../../hooks/useTokenFiatAmount'; import { useTokenTracker } from '../../../hooks/useTokenTracker'; import { getTokenList, selectERC20TokensByChain } from '../../../selectors'; import { showModal } from '../../../store/actions'; -import { getMultichainAccountUrl } from '../../../helpers/utils/multichain/blockExplorer'; +import { getAssetDetailsAccountUrl } from '../../../helpers/utils/multichain/blockExplorer'; import { useMultichainSelector } from '../../../hooks/useMultichainSelector'; import { getMultichainNetwork } from '../../../selectors/multichain'; import { getInternalAccountBySelectedAccountGroupAndCaip } from '../../../selectors/multichain-accounts/account-tree'; @@ -112,7 +112,7 @@ const TokenAsset = ({ token, chainId }: { token: Token; chainId: Hex }) => { const blockExplorerLink = isEvm ? tokenTrackerLink - : getMultichainAccountUrl( + : getAssetDetailsAccountUrl( parseCaipAssetType(address as CaipAssetType).assetReference, multichainNetwork, );