Money & Markets

Circle API: A Developer's Guide to USDC & EURC Payments

A concise, end-to-end tutorial for on-ramping fiat, managing balances, and executing crypto and bank payouts using Circle's APIs.

Klaudia Chen

Author

3 min read
0 views

1. Initial Setup & Authentication

This tutorial provides a complete, copy-paste cURL workflow for moving USDC and EURC with Circle's APIs.

First, set up your shell environment for the sandbox:

export CIRCLE_API_KEY="YOUR_API_KEY"
export CIRCLE_API_BASE="https://api-sandbox.circle.com"
alias ccurl='curl -H "Authorization: Bearer $CIRCLE_API_KEY" -H "Content-Type: application/json"'

Next, verify authentication and retrieve your masterWalletId:

ccurl "$CIRCLE_API_BASE/v1/configuration"

All examples use the sandbox. For production, update the CIRCLE_API_BASE URL.

2. Fiat On-Ramp: Wire to USDC/EURC

Link a US bank account.

export BANK_ID=$(ccurl -X POST "$CIRCLE_API_BASE/v1/businessAccount/banks/wires" -d '{
  "idempotencyKey": "'$(uuidgen)'",
  "accountNumber": "123456789",
  "routingNumber": "021000021",
  "billingDetails": {
    "name": "John Smith",
    "city": "Boston",
    "country": "US",
    "line1": "1 Main Street",
    "district": "MA",
    "postalCode": "02201"
  }
}' | jq -r '.data.id')

echo "Bank ID: $BANK_ID"

Retrieve deposit instructions to get the trackingRef.

export TRACKING_REF=$(ccurl "$CIRCLE_API_BASE/v1/businessAccount/banks/wires/$BANK_ID/instructions" | jq -r '.data.trackingRef')

echo "Tracking Ref: $TRACKING_REF"

Simulate an incoming wire transfer using the sandbox-only mock API.

ccurl -X POST "$CIRCLE_API_BASE/v1/mocks/payments/wire" -d '{
  "trackingRef": "'$TRACKING_REF'",
  "amount": {
    "amount": "1000.00",
    "currency": "USD"
  }
}'

Verify the mock deposit is complete.

ccurl "$CIRCLE_API_BASE/v1/businessAccount/deposits?type=WIRE"

3. Crypto On-Ramp: Deposit from an External Wallet

Generate a deposit address to receive USDC or EURC from an external blockchain wallet. Specify the currency ('USD' for USDC, 'EUR' for EURC) and the chain (e.g., 'BASE', 'ETH').

ccurl -X POST "$CIRCLE_API_BASE/v1/businessAccount/wallets/addresses/deposit" -d '{
  "currency": "USD",
  "chain": "ETH"
}'

Note: Funds must be sent to this address using the correct Circle-issued token contract for the specified chain. Refer to the official list of Supported Tokens.

4. The Circle Money Flow: An Overview
4. The Circle Money Flow: An Overview

5. Checking Balances

Check your balances for USDC and EURC.

ccurl "$CIRCLE_API_BASE/v1/businessAccount/balances"

The response separates funds into available (ready for use) and unsettled (pending settlement, e.g., from a wire deposit). currency: "USD" represents your USDC balance, while "EUR" represents EURC.

6. Crypto Payout: Sending USDC/EURC

First, add the recipient address to your address book.

export RECIPIENT_ID=$(ccurl -X POST "$CIRCLE_API_BASE/v1/addressBook/recipients" -d '{
  "idempotencyKey": "'$(uuidgen)'",
  "address": "0x...",
  "chain": "ETH",
  "description": "My Payout Address"
}' | jq -r '.data.id')

echo "Recipient ID: $RECIPIENT_ID"

Poll the recipient's status until it becomes active; new addresses may require a brief review period.

Once active, create the payout using the recipient ID.

ccurl -X POST "$CIRCLE_API_BASE/v1/payouts" -d '{
  "idempotencyKey": "'$(uuidgen)'",
  "source": {
    "type": "wallet",
    "id": "'$masterWalletId'"
  },
  "destination": {
    "type": "address_book",
    "id": "'$RECIPIENT_ID'"
  },
  "amount": {
    "amount": "100.00",
    "currency": "USD"
  }
}'

Note: Payouts over $3,000 require additional Travel Rule information.

7. Fiat Payout: Withdrawing to a Bank

To off-ramp from USDC/EURC to a linked bank account, create a payout using the /v1/businessAccount/payouts endpoint. This is distinct from the endpoint used for crypto payouts.

Set the destination type to wire and use the $BANK_ID from the on-ramp step as the id.

export PAYOUT_ID=$(ccurl -X POST "$CIRCLE_API_BASE/v1/businessAccount/payouts" -d '{
  "idempotencyKey": "'$(uuidgen)'",
  "destination": {
    "type": "wire",
    "id": "'$BANK_ID'"
  },
  "amount": {
    "amount": "500.00",
    "currency": "USD"
  }
}' | jq -r '.data.id')

echo "Payout ID: $PAYOUT_ID"

Check the payout status using its ID.

ccurl "$CIRCLE_API_BASE/v1/businessAccount/payouts/$PAYOUT_ID"

8. Critical Guardrails & Next Steps

  • Asset Warning: Only send native Circle-issued USDC and EURC to your deposit addresses. Sending other assets will result in a permanent loss of funds.
  • Chain Support: Always verify the list of supported chains for USDC versus EURC before initiating a transfer, as they differ.
  • Testnet Funds: Obtain testnet USDC and EURC for sandbox development from the Circle Faucet.

To build on this foundation, explore Circle's Programmable Wallets for building web3 applications, or use the Cross-Chain Transfer Protocol (CCTP) for native, permissionless USDC transfers between chains.

Klaudia Chen

Written by

Klaudia Chen

Recommended

Stay Connected

Showcase Your Brand

Connect with our engaged tech audience. Explore impactful advertising opportunities tailored for you.

Inquire Now