TokenManager, fetch a fee quote from Iris, and initiate a
fast transfer of EURC from Ethereum Sepolia to Base Sepolia. This route uses the
sandbox EURC token ID that Iris lists on domains 0 and 6. The same pattern
applies to any registered token—swap in another tokenId and destination domain
as needed.
Prerequisites
Before you begin, ensure that you’ve:- Installed Node.js v22+
- Prepared an EVM testnet wallet with the private key available
- Added Base Sepolia to your wallet
- Funded your wallet with the following testnet tokens:
- Sepolia ETH (native token) from a public faucet
- Sepolia EURC from the Circle Faucet
- Base Sepolia ETH if you plan to submit the destination mint yourself
Step 1: Set up the project
1.1. Create the project and install dependencies
1.2. Configure TypeScript (optional)
Create atsconfig.json file:
tsconfig.json file:
1.3. Set environment variables
Open.env in your editor and add:
PRIVATE_KEYis the private key for the Ethereum Sepolia EOA that signs the source chain approval and transfer transactions. The direct-mint path also uses the same key to submit the destination mint on Base.
npm run start command loads variables from .env using Node.js native
env-file support.
Step 2: Configure clients and addresses
Createindex.ts and configure clients for Ethereum Sepolia and Base Sepolia.
TypeScript
basePublic is enough to confirm the destination balance.
Step 3: Fetch token metadata
Query the Iris API to retrieve the token’s decimal precision. Use the returneddecimals value to express the transfer amount in the token’s smallest unit.
EURC uses 6 decimals.
TypeScript
Step 4: Approve the source TokenManager
Approval goes to the per-token TokenManager, not to CrossChainTokenService.
Read the local TokenManager address from the service, then call approve on
the token.
TypeScript
Step 5: Check the fast transfer allowance
This quickstart uses a fast transfer (minFinalityThreshold = 1000), which consumes per-token fast burn allowance.
Confirm remaining capacity before you quote fees.
TypeScript
Step 6: Get a fee quote
Both paths call the same Iris fee-quote endpoint. Forwarding is selected in the quoterequests array—not by a different source chain function. Use Forwarded
mint to have Circle complete the destination mint, or Direct mint to
submit receiveMessage yourself.
- Forwarded mint
- Direct mint
Include a
FORWARD request so the quote covers destination mint gas. Pass the
Base recipient as destinationAddress in the forward params.TypeScript
Step 7: Initiate the transfer
CallcrossChainTransfer on the source service. The onchain call is the same
for both completion paths. The example uses bytes32(0) for destinationCaller
to allow permissionless relay, and 1000 for minFinalityThreshold to use a
fast transfer. For standard finality, use 2000 instead and omit PRE_FINALITY
from the quote—see
Transfer finality and fast burn allowance.
On EVM, destinationAddress must be the raw packed 20-byte address. Do not
ABI-encode it to 32 bytes.
TypeScript
Step 8: Complete the transfer on Base
Choose the completion path that matches the fee quote you requested in Step 6.- Forwarded mint
- Direct mint
When the quote includes
FORWARD, Circle submits the destination mint. Resolve
the token on Base and wait until the recipient balance increases.TypeScript
0x808456652fdb597867f38412077A9182bf77359F).