Skip to main content

Overview

The Assets API provides a list of all supported aggregated assets in the OneBalance system. Each aggregated asset represents a token type (like USDC or ETH) that exists across multiple chains, along with metadata about the individual chain-specific implementations.

API Methods

getAssets

Retrieve the complete list of supported aggregated assets.
assetsApi.getAssets(): Promise<Asset[]>

Parameters

This method takes no parameters.

Returns

Asset[]
array
Array of all supported aggregated assets

Example

import { assetsApi } from '@/lib/api/assets';

const assets = await assetsApi.getAssets();

console.log(`Found ${assets.length} supported assets`);

// Display each asset
assets.forEach(asset => {
  console.log(`${asset.symbol} (${asset.name})`);
  console.log(`  ID: ${asset.aggregatedAssetId}`);
  console.log(`  Decimals: ${asset.decimals}`);
  console.log(`  Available on ${asset.aggregatedEntities.length} chains`);
});

Example Response

[
  {
    "aggregatedAssetId": "ob:usdc",
    "symbol": "USDC",
    "name": "USD Coin",
    "decimals": 6,
    "aggregatedEntities": [
      {
        "assetType": "eip155:1/erc20:0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48",
        "decimals": 6,
        "name": "USD Coin",
        "symbol": "USDC"
      },
      {
        "assetType": "eip155:137/erc20:0x2791bca1f2de4661ed88a30c99a7a9449aa84174",
        "decimals": 6,
        "name": "USD Coin",
        "symbol": "USDC"
      },
      {
        "assetType": "eip155:42161/erc20:0xff970a61a04b1ca14834a43f5de4533ebddb5cc8",
        "decimals": 6,
        "name": "USD Coin",
        "symbol": "USDC"
      }
    ]
  },
  {
    "aggregatedAssetId": "ob:eth",
    "symbol": "ETH",
    "name": "Ethereum",
    "decimals": 18,
    "aggregatedEntities": [
      {
        "assetType": "eip155:1/slip44:60",
        "decimals": 18,
        "name": "Ethereum",
        "symbol": "ETH"
      },
      {
        "assetType": "eip155:10/slip44:60",
        "decimals": 18,
        "name": "Ethereum",
        "symbol": "ETH"
      },
      {
        "assetType": "eip155:8453/slip44:60",
        "decimals": 18,
        "name": "Ethereum",
        "symbol": "ETH"
      }
    ]
  }
]

Common Use Cases

Building Asset Selectors

import { assetsApi } from '@/lib/api/assets';
import { useState, useEffect } from 'react';

function AssetSelector({ onSelect }: { onSelect: (assetId: string) => void }) {
  const [assets, setAssets] = useState<Asset[]>([]);
  
  useEffect(() => {
    assetsApi.getAssets().then(setAssets);
  }, []);
  
  return (
    <select onChange={(e) => onSelect(e.target.value)}>
      <option value="">Select an asset...</option>
      {assets.map(asset => (
        <option key={asset.aggregatedAssetId} value={asset.aggregatedAssetId}>
          {asset.symbol} - {asset.name}
        </option>
      ))}
    </select>
  );
}

Finding Asset Details

function findAsset(assets: Asset[], assetId: string): Asset | undefined {
  return assets.find(asset => asset.aggregatedAssetId === assetId);
}

const assets = await assetsApi.getAssets();
const usdc = findAsset(assets, 'ob:usdc');

if (usdc) {
  console.log(`${usdc.name} is available on ${usdc.aggregatedEntities.length} chains`);
}

Checking Chain Support

import { extractChainIdFromAssetType } from '@/lib/types/chains';

function isAssetOnChain(
  asset: Asset,
  chainId: string | number
): boolean {
  const targetChainId = chainId.toString();
  
  return asset.aggregatedEntities.some(entity => {
    const entityChainId = extractChainIdFromAssetType(entity.assetType);
    return entityChainId === targetChainId;
  });
}

const assets = await assetsApi.getAssets();
const usdc = assets.find(a => a.aggregatedAssetId === 'ob:usdc');

if (usdc) {
  console.log('USDC on Ethereum?', isAssetOnChain(usdc, '1')); // true
  console.log('USDC on Polygon?', isAssetOnChain(usdc, '137')); // true
  console.log('USDC on Unknown?', isAssetOnChain(usdc, '99999')); // false
}

Formatting Asset Amounts

import { formatUnits, parseUnits } from 'viem';

function formatAssetAmount(
  amount: string,
  asset: Asset
): string {
  const formatted = formatUnits(BigInt(amount), asset.decimals);
  return `${parseFloat(formatted).toFixed(asset.decimals === 6 ? 2 : 4)} ${asset.symbol}`;
}

const assets = await assetsApi.getAssets();
const usdc = assets.find(a => a.aggregatedAssetId === 'ob:usdc');

if (usdc) {
  console.log(formatAssetAmount('1000000', usdc));
  // Output: "1.00 USDC"
}

Real-World Implementation

const fetchAssets = async () => {
  try {
    const data: Asset[] = await assetsApi.getAssets();
    setAssets(data);
  } catch (err) {
    setError(err instanceof Error ? err.message : 'Failed to fetch assets');
  } finally {
    setLoading(false);
  }
};

useEffect(() => {
  fetchAssets();
}, []);

Asset ID Format

OneBalance uses a consistent format for aggregated asset IDs:
ob:{symbol}
Where:
  • ob is the OneBalance prefix
  • {symbol} is the lowercase token symbol
ob:usdc   → USD Coin
ob:eth    → Ethereum
ob:usdt   → Tether USD
ob:dai    → Dai Stablecoin
ob:wbtc   → Wrapped Bitcoin

Caching Strategy

Asset lists change infrequently. Consider caching the response to improve performance.
let cachedAssets: Asset[] | null = null;
let cacheTime: number | null = null;
const CACHE_DURATION = 5 * 60 * 1000; // 5 minutes

async function getAssetsWithCache(): Promise<Asset[]> {
  const now = Date.now();
  
  if (cachedAssets && cacheTime && (now - cacheTime) < CACHE_DURATION) {
    return cachedAssets;
  }
  
  cachedAssets = await assetsApi.getAssets();
  cacheTime = now;
  
  return cachedAssets;
}

Filtering Assets

const stablecoins = assets.filter(asset => 
  ['USDC', 'USDT', 'DAI', 'BUSD'].includes(asset.symbol)
);

Error Handling

try {
  const assets = await assetsApi.getAssets();
  return assets;
} catch (error) {
  if (error instanceof Error) {
    console.error('Failed to fetch assets:', error.message);
    
    // Provide fallback or retry logic
    if (error.message.includes('network')) {
      // Retry after delay
      await new Promise(resolve => setTimeout(resolve, 2000));
      return assetsApi.getAssets();
    }
  }
  
  // Return empty array as fallback
  return [];
}

Best Practices

Cache Responses

Assets change rarely - cache for 5-10 minutes to reduce API calls

Load on Startup

Fetch assets early in app lifecycle for immediate availability

Validate Asset IDs

Always validate user-provided asset IDs against the supported list

Show Metadata

Display asset names and symbols for better UX

Build docs developers (and LLMs) love