Token Resolver
The token resolver maps token symbols and names to their on-chain addresses across all supported chains. It's the layer that lets you write "USDC" instead of "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913" when calling tools.
Tools: resolve_token, list_chain_tokens
How Resolution Works
The resolver has two layers:
-
Canonical registry — a curated list of well-known tokens (USDC, WETH, WBTC, DAI, etc.) with verified addresses for each supported chain. No network call required.
-
DexScreener fallback — if the symbol isn't in the registry, the resolver queries DexScreener to find the token by name or symbol. This covers long-tail assets that aren't in the canonical list.
resolve_token("USDC", chainId: 8453)
→ check canonical registry → found → return address
resolve_token("PEPE", chainId: 1)
→ check canonical registry → not found
→ query DexScreener → found → return address
Canonical Registry
The canonical registry contains tokens that are:
- Widely used across DeFi
- Verified to have the correct address on each chain
- Consistent across all web3agent tools
Canonical tokens include: USDC, USDT, DAI, WETH, WBTC, MATIC, BNB, AVAX, OP, ARB, LINK, UNI, AAVE, CRV, and others.
The registry is chain-aware. USDC on Base has a different address than USDC on Ethereum. The resolver returns the correct address for the requested chain.
Tools
resolve_token
Resolves a token symbol or name to its address on a specific chain. Uses the canonical registry first, then falls back to DexScreener.
// Via MCP tool
resolve_token({
symbol: "USDC",
chainId: 8453,
})
// Returns:
// {
// address: "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913",
// symbol: "USDC",
// name: "USD Coin",
// decimals: 6,
// chainId: 8453,
// source: "canonical" // or "dexscreener"
// }
// Long-tail token via DexScreener
resolve_token({
symbol: "PEPE",
chainId: 1,
})
// Returns:
// {
// address: "0x6982508145454Ce325dDbE47a25d4ec3d2311933",
// symbol: "PEPE",
// name: "Pepe",
// decimals: 18,
// chainId: 1,
// source: "dexscreener"
// }
list_chain_tokens
Returns all tokens in the canonical registry for a specific chain.
list_chain_tokens({
chainId: 8453,
})
// Returns array of token objects:
// [
// { address: "0x833589...", symbol: "USDC", name: "USD Coin", decimals: 6 },
// { address: "0x4200000000000000000000000000000000000006", symbol: "WETH", ... },
// ...
// ]
This is useful for building token pickers or validating that a token is supported before attempting a swap.
SDK Functions
import {
resolveToken,
resolveCanonicalToken,
resolveCanonicalTokenSync,
listChainTokens,
} from "web3agent";
resolveToken
Full resolution with DexScreener fallback. Makes a network call if the token isn't in the canonical registry.
import { resolveToken } from "web3agent";
const token = await resolveToken({
symbol: "USDC",
chainId: 8453,
});
console.log(token.address); // "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913"
console.log(token.decimals); // 6
resolveCanonicalToken
Registry-only lookup. Returns null if the token isn't in the canonical list. No network call.
import { resolveCanonicalToken } from "web3agent";
const token = await resolveCanonicalToken({
symbol: "WETH",
chainId: 8453,
});
if (!token) {
// Token not in canonical registry
}
resolveCanonicalTokenSync
Synchronous version of resolveCanonicalToken. Useful in contexts where async isn't available.
import { resolveCanonicalTokenSync } from "web3agent";
const token = resolveCanonicalTokenSync("WETH", 8453);
// Returns token object or null
listChainTokens
Returns all canonical tokens for a chain.
import { listChainTokens } from "web3agent";
const tokens = await listChainTokens({ chainId: 8453 });
for (const token of tokens) {
console.log(`${token.symbol}: ${token.address}`);
}
Canonical Token Addresses
Common tokens across the most-used chains:
USDC
| Chain | Chain ID | Address |
|---|---|---|
| Ethereum | 1 | 0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48 |
| Base | 8453 | 0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913 |
| Arbitrum | 42161 | 0xaf88d065e77c8cC2239327C5EDb3A432268e5831 |
| Optimism | 10 | 0x0b2C639c533813f4Aa9D7837CAf62653d097Ff85 |
| Polygon | 137 | 0x3c499c542cEF5E3811e1192ce70d8cC03d5c3359 |
WETH
| Chain | Chain ID | Address |
|---|---|---|
| Ethereum | 1 | 0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2 |
| Base | 8453 | 0x4200000000000000000000000000000000000006 |
| Arbitrum | 42161 | 0x82aF49447D8a07e3bd95BD0d56f35241523fBab1 |
| Optimism | 10 | 0x4200000000000000000000000000000000000006 |
| Polygon | 137 | 0x7ceB23fD6bC0adD59E62ac25578270cFf1b9f619 |
Naming Conventions
web3agent uses consistent parameter names across all tools and SDK functions. This matters when passing token addresses between tools:
| Correct | Incorrect |
|---|---|
fromToken | srcToken, tokenIn, inputToken |
toToken | dstToken, tokenOut, outputToken |
fromAmount | amountIn, inputAmount, srcAmount |
All tools and SDK functions follow this convention. If you're building on top of web3agent, use the same names to avoid confusion.
DexScreener Fallback Behavior
When a token isn't in the canonical registry, the resolver queries DexScreener and picks the result with the highest liquidity on the requested chain. This works well for established tokens but can return unexpected results for tokens with very low liquidity or multiple pools.
For production use cases where address accuracy is critical, prefer resolveCanonicalToken and handle the null case explicitly rather than relying on the DexScreener fallback.
Adding Tokens to the Registry
The canonical registry is part of the web3agent source code. To add a token, open a pull request to github.com/Apegurus/web3agent with the token address verified against the official contract deployment.