Skip to main content

Fiat Payment

Volr Checkout API automatically converts fiat prices (KRW or USD) to stablecoin amounts.

How It Works

  1. Merchant creates Checkout with fiat price (e.g., 5,000 KRW)
  2. Volr API fetches current exchange rate (CoinGecko)
  3. Stablecoin amount calculated automatically (e.g., 3.70 USDC)
  4. Customer pays the calculated amount

Supported Currencies

Supported fiat currencies are managed dynamically. Get the current list via API:

GET /public/fiat-currencies
{
"ok": true,
"data": [
{ "code": "USD", "symbol": "$", "name": "US Dollar", "decimalPlaces": 2 },
{ "code": "KRW", "symbol": "₩", "name": "Korean Won", "decimalPlaces": 0 },
{ "code": "EUR", "symbol": "€", "name": "Euro", "decimalPlaces": 2 }
]
}
Fiat CurrencyDescription
USDUS Dollar
KRWSouth Korean Won
EUREuro
tip

Use GET /public/fiat-currencies to get the always up-to-date list of supported currencies.

Supported Tokens

Fiat conversion is only supported for stablecoins:

TokenWhy Supported
USDCUSD-pegged stablecoin
USDTUSD-pegged stablecoin
warning

Non-stablecoins like ETH or MATIC are not supported for fiat conversion due to price volatility.

Get Current Exchange Rates

You can check current exchange rates before creating a checkout. Two endpoints are available:

Public Endpoint (No Authentication)

GET /public/exchange-rates

Use this for displaying rates in your UI without authentication.

Dashboard Endpoint (Requires Authentication)

GET /dashboard/projects/{projectId}/checkouts/exchange-rate

Query Parameters

ParameterTypeRequiredDescription
fiatCurrencystringNoKRW or USD. Returns all rates if not specified

Response (Specific Currency)

GET /checkouts/exchange-rate?fiatCurrency=KRW
{
"ok": true,
"data": {
"fiatCurrency": "KRW",
"rates": {
"USDC": "1350.50",
"USDT": "1351.20"
},
"timestamp": "2026-01-30T10:30:00.000Z"
}
}

Response (All Rates)

GET /checkouts/exchange-rate
{
"ok": true,
"data": {
"rates": {
"USDC": {
"KRW": "1350.50",
"USD": "1.00"
},
"USDT": {
"KRW": "1351.20",
"USD": "1.001"
}
},
"timestamp": "2026-01-30T10:30:00.000Z",
"source": "cache"
}
}

Create Fiat Checkout

Request

curl -X POST https://api.volr.io/dashboard/projects/{projectId}/checkouts \
-H "x-api-key: volr_sk_xxx" \
-H "Content-Type: application/json" \
-d '{
"chainId": 8453,
"tokenAddress": "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913",
"fiatAmount": "5000",
"fiatCurrency": "KRW",
"itemName": "Americano"
}'

Response

{
"ok": true,
"data": {
"id": "cm5xyz123...",
"amount": "3703703",
"fiatAmount": "5000",
"fiatCurrency": "KRW",
"exchangeRateUsed": "1350.50",
"exchangeRateAt": "2026-01-30T10:30:00.000Z",
"expiresAt": "2026-01-30T11:00:00.000Z"
}
}

Exchange Rate Calculation

Formula:

tokenAmount = fiatAmount / exchangeRate

Example (5,000 KRW at rate 1,350.50):

5000 / 1350.50 = 3.7017 USDC
= 3701700 (6 decimals, rounded down)
Rounding

Token amounts are rounded down (floor) to prevent customers from overpaying.

Expiry Time Limit

To reduce exchange rate risk, fiat payments have a maximum expiry of 30 minutes.

  • Requesting expiryMinutes: 60 will be automatically adjusted to 30 minutes
  • Direct token payments (amount) can have up to 1440 minutes (24 hours) expiry

Error Handling

EXCHANGE_RATE_UNAVAILABLE

When exchange rate fetch fails:

{
"ok": false,
"error": {
"code": "EXCHANGE_RATE_UNAVAILABLE",
"message": "Unable to fetch exchange rate. Please try again later."
}
}

Solution: Retry after a moment, or specify amount directly.

UNSUPPORTED_TOKEN_FOR_FIAT

When attempting fiat payment with a non-stablecoin:

{
"ok": false,
"error": {
"code": "UNSUPPORTED_TOKEN_FOR_FIAT",
"message": "Token ETH is not supported for fiat conversion. Supported: USDC, USDT"
}
}

Best Practices

1. Pre-fetch Exchange Rates

Fetch rates beforehand to display estimated amounts on your payment UI.

const rates = await getExchangeRates('KRW');
const expectedUsdc = (priceKRW / parseFloat(rates.USDC)).toFixed(2);
console.log(`Approx. ${expectedUsdc} USDC`);

2. Inform About Rate Expiry

Let users know they need to create a new Checkout if payment isn't completed within 30 minutes.

3. Fallback Handling

Use a fallback rate or show an error message when rate fetch fails.

try {
const checkout = await createFiatCheckout(5000, 'KRW');
} catch (error) {
if (error.code === 'EXCHANGE_RATE_UNAVAILABLE') {
// Fallback: use fixed rate
const fallbackRate = 1350;
const amount = Math.floor(5000 / fallbackRate * 1e6);
const checkout = await createTokenCheckout(amount);
}
}